mirror of
https://github.com/Pax1601/DCSOlympus.git
synced 2025-10-29 16:56:34 +00:00
@@ -67,6 +67,7 @@ namespace DataIndex {
|
|||||||
targetingRange,
|
targetingRange,
|
||||||
aimMethodRange,
|
aimMethodRange,
|
||||||
acquisitionRange,
|
acquisitionRange,
|
||||||
|
airborne,
|
||||||
lastIndex,
|
lastIndex,
|
||||||
endOfData = 255
|
endOfData = 255
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -127,6 +127,7 @@ public:
|
|||||||
virtual void setAimMethodRange(double newValue) { updateValue(aimMethodRange, newValue, DataIndex::aimMethodRange); }
|
virtual void setAimMethodRange(double newValue) { updateValue(aimMethodRange, newValue, DataIndex::aimMethodRange); }
|
||||||
virtual void setAcquisitionRange(double newValue) { updateValue(acquisitionRange, newValue, DataIndex::acquisitionRange); }
|
virtual void setAcquisitionRange(double newValue) { updateValue(acquisitionRange, newValue, DataIndex::acquisitionRange); }
|
||||||
virtual void setRadarState(bool newValue) { updateValue(radarState, newValue, DataIndex::radarState); }
|
virtual void setRadarState(bool newValue) { updateValue(radarState, newValue, DataIndex::radarState); }
|
||||||
|
virtual void setAirborne(bool newValue) { updateValue(airborne, newValue, DataIndex::airborne); }
|
||||||
|
|
||||||
/********** Getters **********/
|
/********** Getters **********/
|
||||||
virtual string getCategory() { return category; };
|
virtual string getCategory() { return category; };
|
||||||
@@ -191,6 +192,7 @@ public:
|
|||||||
virtual double getAimMethodRange() { return aimMethodRange; }
|
virtual double getAimMethodRange() { return aimMethodRange; }
|
||||||
virtual double getAcquisitionRange() { return acquisitionRange; }
|
virtual double getAcquisitionRange() { return acquisitionRange; }
|
||||||
virtual bool getRadarState() { return radarState; }
|
virtual bool getRadarState() { return radarState; }
|
||||||
|
virtual bool getAirborne() { return airborne; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
unsigned int ID;
|
unsigned int ID;
|
||||||
@@ -258,6 +260,7 @@ protected:
|
|||||||
double targetingRange = 0;
|
double targetingRange = 0;
|
||||||
double aimMethodRange = 0;
|
double aimMethodRange = 0;
|
||||||
double acquisitionRange = 0;
|
double acquisitionRange = 0;
|
||||||
|
bool airborne = false;
|
||||||
|
|
||||||
/********** Other **********/
|
/********** Other **********/
|
||||||
unsigned int taskCheckCounter = 0;
|
unsigned int taskCheckCounter = 0;
|
||||||
|
|||||||
@@ -23,8 +23,8 @@ public:
|
|||||||
void deleteUnit(unsigned int ID, bool explosion, string explosionType, bool immediate);
|
void deleteUnit(unsigned int ID, bool explosion, string explosionType, bool immediate);
|
||||||
void acquireControl(unsigned int ID);
|
void acquireControl(unsigned int ID);
|
||||||
void loadDatabases();
|
void loadDatabases();
|
||||||
Unit* getClosestUnit(Unit* unit, unsigned char coalition, vector<string> categories, double &distance);
|
Unit* getClosestUnit(Unit* unit, unsigned char coalition, vector<string> categories, double &distance, bool airborneOnly = true);
|
||||||
map<Unit*, double> getUnitsInRange(Unit* unit, unsigned char coalition, vector<string> categories, double range);
|
map<Unit*, double> getUnitsInRange(Unit* unit, unsigned char coalition, vector<string> categories, double range, bool airborneOnly = true);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
map<unsigned int, Unit*> units;
|
map<unsigned int, Unit*> units;
|
||||||
|
|||||||
@@ -373,7 +373,7 @@ void GroundUnit::AIloop()
|
|||||||
lat = position.lat + RANDOM_MINUS_ONE_TO_ONE * (1 + (ShotsScatter::LOW - shotsScatter)) * 0.01;
|
lat = position.lat + RANDOM_MINUS_ONE_TO_ONE * (1 + (ShotsScatter::LOW - shotsScatter)) * 0.01;
|
||||||
lng = position.lng + RANDOM_MINUS_ONE_TO_ONE * (1 + (ShotsScatter::LOW - shotsScatter)) * 0.01;
|
lng = position.lng + RANDOM_MINUS_ONE_TO_ONE * (1 + (ShotsScatter::LOW - shotsScatter)) * 0.01;
|
||||||
barrelElevation = target->getPosition().alt + RANDOM_MINUS_ONE_TO_ONE * (ShotsScatter::LOW - shotsScatter) * 1000;
|
barrelElevation = target->getPosition().alt + RANDOM_MINUS_ONE_TO_ONE * (ShotsScatter::LOW - shotsScatter) * 1000;
|
||||||
taskString += "Flak box mode.";
|
taskString += "Flak box mode";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
taskString += "Scenic AAA. Bearing: " + to_string((int)round(randomBearing)) + "deg";
|
taskString += "Scenic AAA. Bearing: " + to_string((int)round(randomBearing)) + "deg";
|
||||||
|
|||||||
@@ -148,6 +148,9 @@ void Unit::update(json::value json, double dt)
|
|||||||
if (json.has_number_field(L"health"))
|
if (json.has_number_field(L"health"))
|
||||||
setHealth(static_cast<unsigned char>(json[L"health"].as_number().to_uint32()));
|
setHealth(static_cast<unsigned char>(json[L"health"].as_number().to_uint32()));
|
||||||
|
|
||||||
|
if (json.has_boolean_field(L"airborne"))
|
||||||
|
setAirborne(json[L"airborne"].as_bool());
|
||||||
|
|
||||||
runAILoop();
|
runAILoop();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -304,7 +307,7 @@ void Unit::getData(stringstream& ss, unsigned long long time)
|
|||||||
case DataIndex::racetrackLength: appendNumeric(ss, datumIndex, racetrackLength); break;
|
case DataIndex::racetrackLength: appendNumeric(ss, datumIndex, racetrackLength); break;
|
||||||
case DataIndex::racetrackAnchor: appendNumeric(ss, datumIndex, racetrackAnchor); break;
|
case DataIndex::racetrackAnchor: appendNumeric(ss, datumIndex, racetrackAnchor); break;
|
||||||
case DataIndex::racetrackBearing: appendNumeric(ss, datumIndex, racetrackBearing); break;
|
case DataIndex::racetrackBearing: appendNumeric(ss, datumIndex, racetrackBearing); break;
|
||||||
case DataIndex::timeToNextTasking: appendNumeric(ss, datumIndex, timeToNextTasking); break;
|
//case DataIndex::timeToNextTasking: appendNumeric(ss, datumIndex, timeToNextTasking); break; Useful for debugging, but useless in production and very data hungry
|
||||||
case DataIndex::barrelHeight: appendNumeric(ss, datumIndex, barrelHeight); break;
|
case DataIndex::barrelHeight: appendNumeric(ss, datumIndex, barrelHeight); break;
|
||||||
case DataIndex::muzzleVelocity: appendNumeric(ss, datumIndex, muzzleVelocity); break;
|
case DataIndex::muzzleVelocity: appendNumeric(ss, datumIndex, muzzleVelocity); break;
|
||||||
case DataIndex::aimTime: appendNumeric(ss, datumIndex, aimTime); break;
|
case DataIndex::aimTime: appendNumeric(ss, datumIndex, aimTime); break;
|
||||||
@@ -315,6 +318,7 @@ void Unit::getData(stringstream& ss, unsigned long long time)
|
|||||||
case DataIndex::targetingRange: appendNumeric(ss, datumIndex, targetingRange); break;
|
case DataIndex::targetingRange: appendNumeric(ss, datumIndex, targetingRange); break;
|
||||||
case DataIndex::aimMethodRange: appendNumeric(ss, datumIndex, aimMethodRange); break;
|
case DataIndex::aimMethodRange: appendNumeric(ss, datumIndex, aimMethodRange); break;
|
||||||
case DataIndex::acquisitionRange: appendNumeric(ss, datumIndex, acquisitionRange); break;
|
case DataIndex::acquisitionRange: appendNumeric(ss, datumIndex, acquisitionRange); break;
|
||||||
|
case DataIndex::airborne: appendNumeric(ss, datumIndex, airborne); break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -151,7 +151,7 @@ void UnitsManager::deleteUnit(unsigned int ID, bool explosion, string explosionT
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Unit* UnitsManager::getClosestUnit(Unit* unit, unsigned char coalition, vector<string> categories, double &distance) {
|
Unit* UnitsManager::getClosestUnit(Unit* unit, unsigned char coalition, vector<string> categories, double &distance, bool airborneOnly) {
|
||||||
Unit* closestUnit = nullptr;
|
Unit* closestUnit = nullptr;
|
||||||
distance = 0;
|
distance = 0;
|
||||||
|
|
||||||
@@ -167,6 +167,9 @@ Unit* UnitsManager::getClosestUnit(Unit* unit, unsigned char coalition, vector<s
|
|||||||
|
|
||||||
/* Check if the unit belongs to the desired coalition, is alive, and is of the category requested */
|
/* Check if the unit belongs to the desired coalition, is alive, and is of the category requested */
|
||||||
if (requestedCategory && p.second->getCoalition() == coalition && p.second->getAlive()) {
|
if (requestedCategory && p.second->getCoalition() == coalition && p.second->getAlive()) {
|
||||||
|
/* Check if the unit is airborne */
|
||||||
|
if (airborneOnly && !p.second->getAirborne())
|
||||||
|
continue;
|
||||||
/* Compute the distance from the unit to the tested unit */
|
/* Compute the distance from the unit to the tested unit */
|
||||||
double dist;
|
double dist;
|
||||||
double bearing1;
|
double bearing1;
|
||||||
@@ -194,10 +197,13 @@ Unit* UnitsManager::getClosestUnit(Unit* unit, unsigned char coalition, vector<s
|
|||||||
return closestUnit;
|
return closestUnit;
|
||||||
}
|
}
|
||||||
|
|
||||||
map<Unit*, double> UnitsManager::getUnitsInRange(Unit* unit, unsigned char coalition, vector<string> categories, double range) {
|
map<Unit*, double> UnitsManager::getUnitsInRange(Unit* unit, unsigned char coalition, vector<string> categories, double range, bool airborneOnly) {
|
||||||
map<Unit*, double> unitsInRange;
|
map<Unit*, double> unitsInRange;
|
||||||
|
|
||||||
for (auto const& p : units) {
|
for (auto const& p : units) {
|
||||||
|
if (airborneOnly && !p.second->getAirborne())
|
||||||
|
continue;
|
||||||
|
|
||||||
/* Check if the units category is of the correct type */
|
/* Check if the units category is of the correct type */
|
||||||
bool requestedCategory = false;
|
bool requestedCategory = false;
|
||||||
for (auto const& category : categories) {
|
for (auto const& category : categories) {
|
||||||
|
|||||||
@@ -513,6 +513,7 @@ export enum DataIndexes {
|
|||||||
targetingRange,
|
targetingRange,
|
||||||
aimMethodRange,
|
aimMethodRange,
|
||||||
acquisitionRange,
|
acquisitionRange,
|
||||||
|
airborne,
|
||||||
endOfData = 255,
|
endOfData = 255,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -283,6 +283,7 @@ export interface UnitData {
|
|||||||
targetingRange: number;
|
targetingRange: number;
|
||||||
aimMethodRange: number;
|
aimMethodRange: number;
|
||||||
acquisitionRange: number;
|
acquisitionRange: number;
|
||||||
|
airborne: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface LoadoutItemBlueprint {
|
export interface LoadoutItemBlueprint {
|
||||||
|
|||||||
@@ -2269,11 +2269,13 @@ export function UnitControlMenu(props: { open: boolean; onClose: () => void }) {
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className="my-auto text-sm text-gray-400">{selectedUnits[0].getTask()}</div>
|
<div className="my-auto text-sm text-gray-400">{selectedUnits[0].getTask()}</div>
|
||||||
{([UnitState.SIMULATE_FIRE_FIGHT, UnitState.MISS_ON_PURPOSE, UnitState.SCENIC_AAA] as string[]).includes(selectedUnits[0].getState()) && (
|
{/* Useful for debugging but very data hungry
|
||||||
|
|
||||||
|
([UnitState.SIMULATE_FIRE_FIGHT, UnitState.MISS_ON_PURPOSE, UnitState.SCENIC_AAA] as string[]).includes(selectedUnits[0].getState()) && (
|
||||||
<div className="my-auto text-sm text-gray-400">
|
<div className="my-auto text-sm text-gray-400">
|
||||||
Time to next tasking: {zeroAppend(selectedUnits[0].getTimeToNextTasking(), 0, true, 2)}s
|
Time to next tasking: {zeroAppend(selectedUnits[0].getTimeToNextTasking(), 0, true, 2)}s
|
||||||
</div>
|
</div>
|
||||||
)}
|
)*/}
|
||||||
|
|
||||||
<div className="flex content-center gap-2">
|
<div className="flex content-center gap-2">
|
||||||
<OlLocation
|
<OlLocation
|
||||||
|
|||||||
@@ -154,6 +154,7 @@ export abstract class Unit extends CustomMarker {
|
|||||||
#racetrackLength: number = 0;
|
#racetrackLength: number = 0;
|
||||||
#racetrackAnchor: LatLng = new LatLng(0, 0);
|
#racetrackAnchor: LatLng = new LatLng(0, 0);
|
||||||
#racetrackBearing: number = 0;
|
#racetrackBearing: number = 0;
|
||||||
|
#airborne: boolean = false;
|
||||||
|
|
||||||
/* Other members used to draw the unit, mostly ancillary stuff like targets, ranges and so on */
|
/* Other members used to draw the unit, mostly ancillary stuff like targets, ranges and so on */
|
||||||
#blueprint: UnitBlueprint | null = null;
|
#blueprint: UnitBlueprint | null = null;
|
||||||
@@ -391,6 +392,9 @@ export abstract class Unit extends CustomMarker {
|
|||||||
getAcquisitionRange() {
|
getAcquisitionRange() {
|
||||||
return this.#acquisitionRange;
|
return this.#acquisitionRange;
|
||||||
}
|
}
|
||||||
|
getAirborne() {
|
||||||
|
return this.#airborne;
|
||||||
|
}
|
||||||
|
|
||||||
static getConstructor(type: string) {
|
static getConstructor(type: string) {
|
||||||
if (type === "GroundUnit") return GroundUnit;
|
if (type === "GroundUnit") return GroundUnit;
|
||||||
@@ -754,6 +758,9 @@ export abstract class Unit extends CustomMarker {
|
|||||||
case DataIndexes.acquisitionRange:
|
case DataIndexes.acquisitionRange:
|
||||||
this.#acquisitionRange = dataExtractor.extractFloat64();
|
this.#acquisitionRange = dataExtractor.extractFloat64();
|
||||||
break;
|
break;
|
||||||
|
case DataIndexes.airborne:
|
||||||
|
this.#airborne = dataExtractor.extractBool();
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -874,6 +881,7 @@ export abstract class Unit extends CustomMarker {
|
|||||||
targetingRange: this.#targetingRange,
|
targetingRange: this.#targetingRange,
|
||||||
aimMethodRange: this.#aimMethodRange,
|
aimMethodRange: this.#aimMethodRange,
|
||||||
acquisitionRange: this.#acquisitionRange,
|
acquisitionRange: this.#acquisitionRange,
|
||||||
|
airborne: this.#airborne
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1962,7 +1970,7 @@ export abstract class Unit extends CustomMarker {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#drawRacetrack() {
|
#drawRacetrack() {
|
||||||
if (getApp().getMap().getOptions().showRacetracks) {
|
if (getApp().getMap().getOptions().showRacetracks && this.getAirborne()) {
|
||||||
let groundspeed = this.#speed;
|
let groundspeed = this.#speed;
|
||||||
|
|
||||||
// Determine racetrack length
|
// Determine racetrack length
|
||||||
|
|||||||
@@ -1236,6 +1236,7 @@ function Olympus.setUnitsData(arg, time)
|
|||||||
local position = unit:getPosition()
|
local position = unit:getPosition()
|
||||||
local heading = math.atan2( position.x.z, position.x.x )
|
local heading = math.atan2( position.x.z, position.x.x )
|
||||||
local velocity = unit:getVelocity();
|
local velocity = unit:getVelocity();
|
||||||
|
local airborne = unit:inAir()
|
||||||
|
|
||||||
-- Fill the data table
|
-- Fill the data table
|
||||||
table["name"] = unit:getTypeName()
|
table["name"] = unit:getTypeName()
|
||||||
@@ -1248,6 +1249,7 @@ function Olympus.setUnitsData(arg, time)
|
|||||||
table["horizontalVelocity"] = math.sqrt(velocity.x * velocity.x + velocity.z * velocity.z)
|
table["horizontalVelocity"] = math.sqrt(velocity.x * velocity.x + velocity.z * velocity.z)
|
||||||
table["verticalVelocity"] = velocity.y
|
table["verticalVelocity"] = velocity.y
|
||||||
table["heading"] = heading
|
table["heading"] = heading
|
||||||
|
table["airborne"] = airborne
|
||||||
|
|
||||||
-- Track angles are wrong because of weird reference systems, approximate it using latitude and longitude differences
|
-- Track angles are wrong because of weird reference systems, approximate it using latitude and longitude differences
|
||||||
if (table["horizontalVelocity"] > 1) then
|
if (table["horizontalVelocity"] > 1) then
|
||||||
|
|||||||
Reference in New Issue
Block a user