diff --git a/Moose Development/Moose/Core/Database.lua b/Moose Development/Moose/Core/Database.lua index cd395d6cd..e77fe527c 100644 --- a/Moose Development/Moose/Core/Database.lua +++ b/Moose Development/Moose/Core/Database.lua @@ -188,6 +188,8 @@ function DATABASE:AddUnit( DCSUnitName, force ) -- Register unit self.UNITS[DCSunitName]=UNIT:Register(DCSunitName) + else + self.UNITS[DCSunitName]:ResetOptionCacheIfDCSObjectChanged() end return self.UNITS[DCSunitName] @@ -804,6 +806,8 @@ function DATABASE:AddGroup( GroupName, force ) if not self.GROUPS[GroupName] or force == true then self:T( { "Add GROUP:", GroupName } ) self.GROUPS[GroupName] = GROUP:Register( GroupName ) + else + self.GROUPS[GroupName]:ResetOptionCacheIfDCSObjectChanged() end return self.GROUPS[GroupName] diff --git a/Moose Development/Moose/Core/Event.lua b/Moose Development/Moose/Core/Event.lua index 71270e026..e0c647f2f 100644 --- a/Moose Development/Moose/Core/Event.lua +++ b/Moose Development/Moose/Core/Event.lua @@ -278,7 +278,6 @@ EVENTS = { SimulationUnfreeze = world.event.S_EVENT_SIMULATION_UNFREEZE or -1, HumanAircraftRepairStart = world.event.S_EVENT_HUMAN_AIRCRAFT_REPAIR_START or -1, HumanAircraftRepairFinish = world.event.S_EVENT_HUMAN_AIRCRAFT_REPAIR_FINISH or -1, - GroupChangeOption = world.event.S_EVENT_GROUP_CHANGE_OPTION or -1, -- dynamic cargo NewDynamicCargo = world.event.S_EVENT_NEW_DYNAMIC_CARGO or -1, DynamicCargoLoaded = world.event.S_EVENT_DYNAMIC_CARGO_LOADED or -1, @@ -292,25 +291,23 @@ EVENTS = { -- -- * A (Object.Category.)UNIT : A UNIT object type is involved in the Event. -- * A (Object.Category.)STATIC : A STATIC object type is involved in the Event. --- * A GROUP : A DCS Group object is involved in the Event. -- -- @type EVENTDATA -- @field #number id The identifier of the event. -- --- @field DCS#Unit initiator (UNIT/STATIC/SCENERY/GROUP) The initiating @{DCS#Unit} or @{DCS#StaticObject}. For `S_EVENT_GROUP_CHANGE_OPTION`, this is a DCS Group. +-- @field DCS#Unit initiator (UNIT/STATIC/SCENERY) The initiating @{DCS#Unit} or @{DCS#StaticObject}. -- @field DCS#Object.Category IniObjectCategory (UNIT/STATIC/SCENERY) The initiator object category ( Object.Category.UNIT or Object.Category.STATIC ). -- @field DCS#Unit IniDCSUnit (UNIT/STATIC) The initiating @{DCS#Unit} or @{DCS#StaticObject}. -- @field #string IniDCSUnitName (UNIT/STATIC) The initiating Unit name. -- @field Wrapper.Unit#UNIT IniUnit (UNIT/STATIC) The initiating MOOSE wrapper @{Wrapper.Unit#UNIT} of the initiator Unit object. -- @field #string IniUnitName (UNIT/STATIC) The initiating UNIT name (same as IniDCSUnitName). --- @field DCS#Group IniDCSGroup (UNIT/GROUP) The initiating @{DCS#Group}. --- @field #string IniDCSGroupName (UNIT/GROUP) The initiating Group name. --- @field Wrapper.Group#GROUP IniGroup (UNIT/GROUP) The initiating MOOSE wrapper @{Wrapper.Group#GROUP} of the initiator Group object. --- @field #string IniGroupName (UNIT/GROUP) The initiating GROUP name (same as IniDCSGroupName). --- @field DCS#Group.Category IniGroupCategory (GROUP) The category of the initiating group. +-- @field DCS#Group IniDCSGroup (UNIT) The initiating {DCSGroup#Group}. +-- @field #string IniDCSGroupName (UNIT) The initiating Group name. +-- @field Wrapper.Group#GROUP IniGroup (UNIT) The initiating MOOSE wrapper @{Wrapper.Group#GROUP} of the initiator Group object. +-- @field #string IniGroupName UNIT) The initiating GROUP name (same as IniDCSGroupName). -- @field #string IniPlayerName (UNIT) The name of the initiating player in case the Unit is a client or player slot. -- @field #string IniPlayerUCID (UNIT) The UCID of the initiating player in case the Unit is a client or player slot and on a multi-player server. --- @field DCS#coalition.side IniCoalition (UNIT/GROUP) The coalition of the initiator. +-- @field DCS#coalition.side IniCoalition (UNIT) The coalition of the initiator. -- @field DCS#Unit.Category IniCategory (UNIT) The category of the initiator. -- @field #string IniTypeName (UNIT) The type name of the initiator. -- @@ -737,12 +734,6 @@ local _EVENTMETA = { Side = "I", Event = "OnEventHumanAircraftRepairFinish", Text = "S_EVENT_HUMAN_AIRCRAFT_REPAIR_FINISH" - }, - [EVENTS.GroupChangeOption] = { - Order = 1, - Side = "I", - Event = "OnEventGroupChangeOption", - Text = "S_EVENT_GROUP_CHANGE_OPTION" }, -- dynamic cargo [EVENTS.NewDynamicCargo] = { @@ -1243,16 +1234,7 @@ function EVENT:onEvent( Event ) if Event.initiator then - if Event.id == EVENTS.GroupChangeOption then - Event.IniDCSGroup = Event.initiator - Event.IniDCSGroupName = Group.getName(Event.initiator) - Event.IniGroupName = Event.IniDCSGroupName - Event.IniGroup = GROUP:FindByName(Event.IniDCSGroupName) - Event.IniCoalition = Group.getCoalition(Event.initiator) - Event.IniGroupCategory = Group.getCategory(Event.initiator) - else - Event.IniObjectCategory = Object.getCategory(Event.initiator) - end + Event.IniObjectCategory = Object.getCategory(Event.initiator) if Event.IniObjectCategory == Object.Category.STATIC then --- @@ -1681,7 +1663,9 @@ function EVENT:onEvent( Event ) self:T( { EventMeta.Text, Event } ) end else - self:E(string.format("WARNING: Could not get EVENTMETA data for event ID=%d! Is this an unknown/new DCS event?", tostring(Event.id))) + if Event.id ~= 61 then --- TODO Event 61 is new, but seems to have no real data to be useable, something like option changed. + self:E(string.format("WARNING: Could not get EVENTMETA data for event ID=%d! Is this an unknown/new DCS event?", tostring(Event.id))) + end end Event = nil diff --git a/Moose Development/Moose/Core/Spawn.lua b/Moose Development/Moose/Core/Spawn.lua index 6a498797a..2c931e26b 100644 --- a/Moose Development/Moose/Core/Spawn.lua +++ b/Moose Development/Moose/Core/Spawn.lua @@ -1880,6 +1880,11 @@ function SPAWN:SpawnWithIndex( SpawnIndex, NoBirth ) -- SpawnTemplate.uncontrolled = self.SpawnUnControlled -- end -- end + + + if self.BeforeTemplateSpawnFunc then + self:BeforeTemplateSpawnFunc(SpawnTemplate, SpawnIndex) + end end if not NoBirth then @@ -1995,6 +2000,31 @@ function SPAWN:SpawnScheduleStop() return self end +--- Allows to place a CallFunction hook just before spawning the group to tweak the template. +-- The provided method will be called just before a new group is spawned, including its given parameters. +-- The first parameter of the BeforeTemplateSpawnFunc is the raw Template used to spawn the group, the second is the SpawnIndex. +-- @param #SPAWN self +-- @param #function BeforeTemplateSpawnFunc The function to be called before the group spawns. +-- @return #SPAWN +-- @usage +-- +-- -- Declare SpawnObject and call a function when a new Group is spawned. +-- local SpawnObject = SPAWN:New( "SpawnObject" ) +-- :InitLimit( 2, 10 ) +-- :OnBeforeTemplateSpawnGroup( function( Spawn, SpawnTemplate, SpawnIndex ) + -- Tweaking the template units +-- end +-- ) +-- :SpawnScheduled( 300, 0.3 ) +-- +function SPAWN:OnBeforeTemplateSpawnGroup( BeforeTemplateSpawnFunc ) + --self:F( "OnBeforeTemplateSpawnGroup" ) + + self.BeforeTemplateSpawnFunc = BeforeTemplateSpawnFunc + + return self +end + --- Allows to place a CallFunction hook when a new group spawns. -- The provided method will be called when a new group is spawned, including its given parameters. -- The first parameter of the SpawnFunction is the @{Wrapper.Group#GROUP} that was spawned. diff --git a/Moose Development/Moose/Functional/Mantis.lua b/Moose Development/Moose/Functional/Mantis.lua index a85774d7e..2e34ba601 100644 --- a/Moose Development/Moose/Functional/Mantis.lua +++ b/Moose Development/Moose/Functional/Mantis.lua @@ -1890,20 +1890,22 @@ do --- [Internal] Check if any EWR or AWACS is still alive -- @param #MANTIS self -- @return #boolean outcome - function MANTIS:_CheckAnyEWRAlive() - self:T(self.lid .. "_CheckAnyEWRAlive") - local alive = false - if self.EWR_Group:CountAlive() > 0 then - alive = true - end - if not alive and self.AWACS_Prefix then - local awacs = GROUP:FindByName(self.AWACS_Prefix) - if awacs and awacs:IsAlive() then - alive = true + function MANTIS:_CheckAnyEWRAlive() + self:T(self.lid .. "_CheckAnyEWRAlive") + + for _, group in pairs(self.EWR_Group:GetSet()) do + if group and group:IsAlive() then + return true + end end + if self.AWACS_Prefix then + local awacs = GROUP:FindByName(self.AWACS_Prefix) + if awacs and awacs:IsAlive() then + return true + end + end + return false end - return alive - end --- [Internal] Function to determine state of the advanced mode -- @param #MANTIS self diff --git a/Moose Development/Moose/Functional/RAT.lua b/Moose Development/Moose/Functional/RAT.lua index 93acb9615..fe1d2b81e 100644 --- a/Moose Development/Moose/Functional/RAT.lua +++ b/Moose Development/Moose/Functional/RAT.lua @@ -4068,8 +4068,8 @@ end -- @param #RAT self -- @param Core.Event#EVENTDATA EventData function RAT:_OnBirth(EventData) - self:F3(EventData) - self:T3(self.lid.."Captured event birth!") + self:F2(EventData) + self:T2(self.lid.."Captured event birth!") local SpawnGroup = EventData.IniGroup --Wrapper.Group#GROUP diff --git a/Moose Development/Moose/Ops/AirWing.lua b/Moose Development/Moose/Ops/AirWing.lua index f3a22b5f7..96d05a74b 100644 --- a/Moose Development/Moose/Ops/AirWing.lua +++ b/Moose Development/Moose/Ops/AirWing.lua @@ -189,13 +189,14 @@ AIRWING = { --- AIRWING class version. -- @field #string version -AIRWING.version="0.9.7" +AIRWING.version="0.9.8" ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -- ToDo list ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -- TODO: Check that airbase has enough parking spots if a request is BIG. +-- DONE: Allow groupping parameter for CAP flights -- DONE: Allow (moving) zones as base for patrol points. -- DONE: Spawn in air ==> Needs WAREHOUSE update. -- DONE: Spawn hot. @@ -233,6 +234,7 @@ function AIRWING:New(warehousename, airwingname) -- Defaults: self.nflightsCAP=0 + self.nCAPgrouping=1 self.nflightsAWACS=0 self.nflightsRecon=0 self.nflightsTANKERboom=0 @@ -765,9 +767,11 @@ end --- Set number of CAP flights constantly carried out. -- @param #AIRWING self -- @param #number n (Optional) Number of flights. Default 1. +-- @param #number grouping (optional) Number of assets per flight. Default 1. -- @return #AIRWING self -function AIRWING:SetNumberCAP(n) +function AIRWING:SetNumberCAP(n,grouping) self.nflightsCAP=n or 1 + self.nCAPgrouping = grouping or 1 return self end @@ -1295,11 +1299,13 @@ function AIRWING:CheckCAP() if self.capOptionPatrolRaceTrack then missionCAP=AUFTRAG:NewPATROL_RACETRACK(patrol.coord,altitude,patrol.speed,patrol.heading,patrol.leg, self.capFormation) + missionCAP:SetRequiredAssets(self.nCAPgrouping,self.nCAPgrouping) else missionCAP=AUFTRAG:NewGCICAP(patrol.coord, altitude, patrol.speed, patrol.heading, patrol.leg) - + missionCAP:SetRequiredAssets(self.nCAPgrouping,self.nCAPgrouping) + end if self.capOptionVaryStartTime then diff --git a/Moose Development/Moose/Ops/Airboss.lua b/Moose Development/Moose/Ops/Airboss.lua index 304233b81..dedb4725c 100644 --- a/Moose Development/Moose/Ops/Airboss.lua +++ b/Moose Development/Moose/Ops/Airboss.lua @@ -10410,7 +10410,7 @@ function AIRBOSS:_Groove( playerData ) -- Wait until player passed the 0.75 NM distance. local _advice = true - if playerData.TIG0 == nil and playerData.difficulty ~= AIRBOSS.Difficulty.EASY then -- rho>RXX + if (playerData.TIG0 == nil or playerData.TIG0 == 0) and playerData.difficulty ~= AIRBOSS.Difficulty.EASY then -- rho>RXX _advice = false end diff --git a/Moose Development/Moose/Ops/EasyGCICAP.lua b/Moose Development/Moose/Ops/EasyGCICAP.lua index d1d499ddb..d26aa6f43 100644 --- a/Moose Development/Moose/Ops/EasyGCICAP.lua +++ b/Moose Development/Moose/Ops/EasyGCICAP.lua @@ -288,7 +288,7 @@ EASYGCICAP = { --- EASYGCICAP class version. -- @field #string version -EASYGCICAP.version="0.1.38" +EASYGCICAP.version="0.1.39" ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -- @@ -796,8 +796,9 @@ function EASYGCICAP:_AddAirwing(Airbasename, Alias) CAP_Wing:SetRespawnAfterDestroyed() --- #DONE avoid wings with no CAP points starting CAP anyhow; AirWing uses this to start CAP and creates points when there are none. - if counttable(self.ManagedCP) >0 then - CAP_Wing:SetNumberCAP(self.capgrouping) + local nCapPoints = counttable(self.ManagedCP) + if nCapPoints >0 then + CAP_Wing:SetNumberCAP(nCapPoints,self.capgrouping) end CAP_Wing:SetCapCloseRaceTrack(true) diff --git a/Moose Development/Moose/Ops/FlightControl.lua b/Moose Development/Moose/Ops/FlightControl.lua index 1bb0383cf..551996165 100644 --- a/Moose Development/Moose/Ops/FlightControl.lua +++ b/Moose Development/Moose/Ops/FlightControl.lua @@ -19,7 +19,7 @@ -- ### Author: **funkyfranky** -- -- === --- @module OPS.FlightControl +-- @module Ops.FlightControl -- @image OPS_FlightControl.png diff --git a/Moose Development/Moose/Wrapper/Controllable.lua b/Moose Development/Moose/Wrapper/Controllable.lua index 43c96254a..823f17990 100644 --- a/Moose Development/Moose/Wrapper/Controllable.lua +++ b/Moose Development/Moose/Wrapper/Controllable.lua @@ -14,6 +14,7 @@ --- @type CONTROLLABLE -- @field DCS#Controllable DCSControllable The DCS controllable class. -- @field #string ControllableName The name of the controllable. +-- @field #table ControllableOptions The Cache of controllable options. -- @extends Wrapper.Positionable#POSITIONABLE --- Wrapper class to handle the "DCS Controllable objects", which are Groups and Units: @@ -203,7 +204,8 @@ function CONTROLLABLE:New( ControllableName ) local self = BASE:Inherit( self, POSITIONABLE:New( ControllableName ) ) -- #CONTROLLABLE -- self:F( ControllableName ) self.ControllableName = ControllableName - + -- Options Cache for Event ID 61 (ED DCS Release Aug 2026) + self.ControllableOptions = {} self.TaskScheduler = SCHEDULER:New( self ) return self end @@ -3281,19 +3283,57 @@ end -- @param #number OptionValue Value of the option -- @return #CONTROLLABLE self function CONTROLLABLE:SetOption( OptionID, OptionValue ) + local ID = tostring(OptionID) + if OptionValue ~= nil and self.ControllableOptions and self.ControllableOptions[ID] == OptionValue then + return self + end local DCSControllable = self:GetDCSObject() if DCSControllable then - local Controller = self:_GetController() - + local Controller = DCSControllable:getController() Controller:setOption( OptionID, OptionValue ) - + self.ControllableOptions = self.ControllableOptions or {} + self.ControllableOptions[ID] = OptionValue + self.ControllableOptionDCSObject = DCSControllable return self end return nil end +--- Query a (cached) option. Requires the option has been set with Moose(!) before. +-- @param #CONTROLLABLE self +-- @param #number OptionID ID/Type of the option. +-- @return #number OptionValue or nil if not chached (yet) +function CONTROLLABLE:QueryCachedOption(OptionID) + local ID = tostring(OptionID) + if self.ControllableOptions then + return self.ControllableOptions[ID] + end + return nil +end + +--- Reset cached options for this controllable. +-- @param #CONTROLLABLE self +-- @return #CONTROLLABLE self +function CONTROLLABLE:ResetOptionCache() + self.ControllableOptions = {} + self.ControllableOptionDCSObject = self:GetDCSObject() + return self +end + +--- Reset cached options when the underlying DCS object has changed. +-- @param #CONTROLLABLE self +-- @return #CONTROLLABLE self +function CONTROLLABLE:ResetOptionCacheIfDCSObjectChanged() + local DCSControllable = self:GetDCSObject() + if self.ControllableOptionDCSObject ~= DCSControllable then + self.ControllableOptions = {} + self.ControllableOptionDCSObject = DCSControllable + end + return self +end + --- Set option for Rules of Engagement (ROE). -- @param #CONTROLLABLE self -- @param #number ROEvalue ROE value. See ENUMS.ROE. @@ -3307,11 +3347,11 @@ function CONTROLLABLE:OptionROE( ROEvalue ) local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ROE, ROEvalue ) + self:SetOption( AI.Option.Air.id.ROE, ROEvalue ) elseif self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ROE, ROEvalue ) + self:SetOption( AI.Option.Ground.id.ROE, ROEvalue ) elseif self:IsShip() then - Controller:setOption( AI.Option.Naval.id.ROE, ROEvalue ) + self:SetOption( AI.Option.Naval.id.ROE, ROEvalue ) end return self @@ -3349,11 +3389,11 @@ function CONTROLLABLE:OptionROEHoldFire() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.WEAPON_HOLD ) + self:SetOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.WEAPON_HOLD ) elseif self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ROE, AI.Option.Ground.val.ROE.WEAPON_HOLD ) + self:SetOption( AI.Option.Ground.id.ROE, AI.Option.Ground.val.ROE.WEAPON_HOLD ) elseif self:IsShip() then - Controller:setOption( AI.Option.Naval.id.ROE, AI.Option.Naval.val.ROE.WEAPON_HOLD ) + self:SetOption( AI.Option.Naval.id.ROE, AI.Option.Naval.val.ROE.WEAPON_HOLD ) end return self @@ -3391,11 +3431,11 @@ function CONTROLLABLE:OptionROEReturnFire() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.RETURN_FIRE ) + self:SetOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.RETURN_FIRE ) elseif self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ROE, AI.Option.Ground.val.ROE.RETURN_FIRE ) + self:SetOption( AI.Option.Ground.id.ROE, AI.Option.Ground.val.ROE.RETURN_FIRE ) elseif self:IsShip() then - Controller:setOption( AI.Option.Naval.id.ROE, AI.Option.Naval.val.ROE.RETURN_FIRE ) + self:SetOption( AI.Option.Naval.id.ROE, AI.Option.Naval.val.ROE.RETURN_FIRE ) end return self @@ -3433,11 +3473,11 @@ function CONTROLLABLE:OptionROEOpenFire() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.OPEN_FIRE ) + self:SetOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.OPEN_FIRE ) elseif self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ROE, AI.Option.Ground.val.ROE.OPEN_FIRE ) + self:SetOption( AI.Option.Ground.id.ROE, AI.Option.Ground.val.ROE.OPEN_FIRE ) elseif self:IsShip() then - Controller:setOption( AI.Option.Naval.id.ROE, AI.Option.Naval.val.ROE.OPEN_FIRE ) + self:SetOption( AI.Option.Naval.id.ROE, AI.Option.Naval.val.ROE.OPEN_FIRE ) end return self @@ -3476,7 +3516,7 @@ function CONTROLLABLE:OptionROEOpenFireWeaponFree() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.OPEN_FIRE_WEAPON_FREE ) + self:SetOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.OPEN_FIRE_WEAPON_FREE ) end return self @@ -3514,7 +3554,7 @@ function CONTROLLABLE:OptionROEWeaponFree() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.WEAPON_FREE ) + self:SetOption( AI.Option.Air.id.ROE, AI.Option.Air.val.ROE.WEAPON_FREE ) end return self @@ -3552,7 +3592,7 @@ function CONTROLLABLE:OptionROTNoReaction() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.NO_REACTION ) + self:SetOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.NO_REACTION ) end return self @@ -3573,7 +3613,7 @@ function CONTROLLABLE:OptionROT( ROTvalue ) local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.REACTION_ON_THREAT, ROTvalue ) + self:SetOption( AI.Option.Air.id.REACTION_ON_THREAT, ROTvalue ) end return self @@ -3611,7 +3651,7 @@ function CONTROLLABLE:OptionROTPassiveDefense() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.PASSIVE_DEFENCE ) + self:SetOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.PASSIVE_DEFENCE ) end return self @@ -3631,7 +3671,7 @@ function CONTROLLABLE:OptionPreferVerticalLanding() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.PREFER_VERTICAL, true ) + self:SetOption( AI.Option.Air.id.PREFER_VERTICAL, true ) end return self @@ -3651,7 +3691,7 @@ function CONTROLLABLE:OptionAllowFormationSideSwap() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ALLOW_FORMATION_SIDE_SWAP, true ) + self:SetOption( AI.Option.Air.id.ALLOW_FORMATION_SIDE_SWAP, true ) end return self @@ -3671,7 +3711,7 @@ function CONTROLLABLE:OptionAIRunwayLineUp() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( 37, true ) + self:SetOption( 37, true ) end return self @@ -3691,7 +3731,7 @@ function CONTROLLABLE:OptionDisengageAndRTBAfterFormationLoss() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( 38, 1 ) + self:SetOption( 38, 1 ) end return self @@ -3729,7 +3769,7 @@ function CONTROLLABLE:OptionROTEvadeFire() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.EVADE_FIRE ) + self:SetOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.EVADE_FIRE ) end return self @@ -3767,7 +3807,7 @@ function CONTROLLABLE:OptionROTVertical() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.BYPASS_AND_ESCAPE ) + self:SetOption( AI.Option.Air.id.REACTION_ON_THREAT, AI.Option.Air.val.REACTION_ON_THREAT.BYPASS_AND_ESCAPE ) end return self @@ -3787,10 +3827,10 @@ function CONTROLLABLE:OptionAlarmStateAuto() local Controller = self:_GetController() if self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ALARM_STATE, AI.Option.Ground.val.ALARM_STATE.AUTO ) + self:SetOption( AI.Option.Ground.id.ALARM_STATE, AI.Option.Ground.val.ALARM_STATE.AUTO ) elseif self:IsShip() then - -- Controller:setOption(AI.Option.Naval.id.ALARM_STATE, AI.Option.Naval.val.ALARM_STATE.AUTO) - Controller:setOption( 9, 0 ) + -- self:SetOption(AI.Option.Naval.id.ALARM_STATE, AI.Option.Naval.val.ALARM_STATE.AUTO) + self:SetOption( 9, 0 ) end return self @@ -3810,11 +3850,11 @@ function CONTROLLABLE:OptionAlarmStateGreen() local Controller = self:_GetController() if self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ALARM_STATE, AI.Option.Ground.val.ALARM_STATE.GREEN ) + self:SetOption( AI.Option.Ground.id.ALARM_STATE, AI.Option.Ground.val.ALARM_STATE.GREEN ) elseif self:IsShip() then -- AI.Option.Naval.id.ALARM_STATE does not seem to exist! - -- Controller:setOption( AI.Option.Naval.id.ALARM_STATE, AI.Option.Naval.val.ALARM_STATE.GREEN ) - Controller:setOption( 9, 1 ) + -- self:SetOption( AI.Option.Naval.id.ALARM_STATE, AI.Option.Naval.val.ALARM_STATE.GREEN ) + self:SetOption( 9, 1 ) end return self @@ -3834,10 +3874,10 @@ function CONTROLLABLE:OptionAlarmStateRed() local Controller = self:_GetController() if self:IsGround() then - Controller:setOption( AI.Option.Ground.id.ALARM_STATE, AI.Option.Ground.val.ALARM_STATE.RED ) + self:SetOption( AI.Option.Ground.id.ALARM_STATE, AI.Option.Ground.val.ALARM_STATE.RED ) elseif self:IsShip() then - -- Controller:setOption(AI.Option.Naval.id.ALARM_STATE, AI.Option.Naval.val.ALARM_STATE.RED) - Controller:setOption( 9, 2 ) + -- self:SetOption(AI.Option.Naval.id.ALARM_STATE, AI.Option.Naval.val.ALARM_STATE.RED) + self:SetOption( 9, 2 ) end return self @@ -3864,7 +3904,7 @@ function CONTROLLABLE:OptionRTBBingoFuel( RTB ) -- R2.2 local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.RTB_ON_BINGO, RTB ) + self:SetOption( AI.Option.Air.id.RTB_ON_BINGO, RTB ) end return self @@ -3885,7 +3925,7 @@ function CONTROLLABLE:OptionRTBAmmo( WeaponsFlag ) local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.RTB_ON_OUT_OF_AMMO, WeaponsFlag ) + self:SetOption( AI.Option.Air.id.RTB_ON_OUT_OF_AMMO, WeaponsFlag ) end return self @@ -3905,7 +3945,7 @@ function CONTROLLABLE:OptionAllowJettisonWeaponsOnThreat() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.PROHIBIT_JETT, false ) + self:SetOption( AI.Option.Air.id.PROHIBIT_JETT, false ) end return self @@ -3925,7 +3965,7 @@ function CONTROLLABLE:OptionKeepWeaponsOnThreat() local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.PROHIBIT_JETT, true ) + self:SetOption( AI.Option.Air.id.PROHIBIT_JETT, true ) end return self @@ -3965,7 +4005,7 @@ function CONTROLLABLE:OptionEvasionOfARM(Seconds) if self:IsGround() then if Seconds == nil then Seconds = false end - Controller:setOption( AI.Option.Ground.id.EVASION_OF_ARM, Seconds) + self:SetOption( AI.Option.Ground.id.EVASION_OF_ARM, Seconds) end end @@ -3986,7 +4026,7 @@ function CONTROLLABLE:OptionFormationInterval(meters) if self:IsGround() then if meters == nil or meters > 100 or meters < 0 then meters = 50 end - Controller:setOption( 30, meters) + self:SetOption( 30, meters) end end @@ -4006,7 +4046,7 @@ function CONTROLLABLE:OptionECM( ECMvalue ) local Controller = self:_GetController() if self:IsAir() then - Controller:setOption( AI.Option.Air.id.ECM_USING, ECMvalue or 1 ) + self:SetOption( AI.Option.Air.id.ECM_USING, ECMvalue or 1 ) end end @@ -4192,11 +4232,11 @@ function CONTROLLABLE:OptionRestrictBurner( RestrictBurner ) -- Issue https://github.com/FlightControl-Master/MOOSE/issues/1216 if RestrictBurner == true then if self:IsAir() then - Controller:setOption( 16, true ) + self:SetOption( 16, true ) end else if self:IsAir() then - Controller:setOption( 16, false ) + self:SetOption( 16, false ) end end diff --git a/Moose Development/Moose/Wrapper/Group.lua b/Moose Development/Moose/Wrapper/Group.lua index 21101fc00..307b1a874 100644 --- a/Moose Development/Moose/Wrapper/Group.lua +++ b/Moose Development/Moose/Wrapper/Group.lua @@ -2271,6 +2271,9 @@ function GROUP:Respawn( Template, Reset ) -- Reset events. self:ResetEvents() + + -- Reset options. + self:ResetOptionCache() return self end diff --git a/Moose Development/Moose/Wrapper/Scenery.lua b/Moose Development/Moose/Wrapper/Scenery.lua index 0a32ebd4f..2e205d421 100644 --- a/Moose Development/Moose/Wrapper/Scenery.lua +++ b/Moose Development/Moose/Wrapper/Scenery.lua @@ -290,7 +290,7 @@ function SCENERY:FindByName(Name, Coordinate, Radius, Role, Zone) --BASE:I("Coordinate x = "..Coordinate.x .. " y = "..Coordinate.y.." z = "..Coordinate.z) local findme = self:_FindByName(Name) - if findme then return findme end + if findme and findme:GetDCSObject() then return findme end local radius = Radius or 100 local name = Name or "unknown"