diff --git a/Moose Development/Moose/AI/AI_Balancer.lua b/Moose Development/Moose/AI/AI_Balancer.lua index e8d91a3bc..52adb5978 100644 --- a/Moose Development/Moose/AI/AI_Balancer.lua +++ b/Moose Development/Moose/AI/AI_Balancer.lua @@ -1,10 +1,9 @@ ---- SP:N MP:Y AI:Y HU:N TYP:A -- This module contains the AI_BALANCER class. AI Balancing will replace in multi player missions +--- Single-Player:**No** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**All** -- **AI Balancing will replace in multi player missions -- non-occupied human slots with AI groups, in order to provide an engaging simulation environment, --- even when there are hardly any players in the mission. +-- even when there are hardly any players in the mission.** -- -- ![Banner Image](..\Presentations\AI_Balancer\Dia1.JPG) -- --- Examples can be found in the test missions. -- -- === -- @@ -73,6 +72,8 @@ -- -- Hereby the change log: -- +-- 2017-01-17: There is still a problem with AI being destroyed, but not respawned. Need to check further upon that. +-- -- 2017-01-08: AI_BALANCER:**InitSpawnInterval( Earliest, Latest )** added. -- -- === @@ -82,7 +83,6 @@ -- ### Contributions: -- -- * **[Dutch_Baron](https://forums.eagle.ru/member.php?u=112075)**: Working together with James has resulted in the creation of the AI_BALANCER class. James has shared his ideas on balancing AI with air units, and together we made a first design which you can use now :-) --- -- * **SNAFU**: Had a couple of mails with the guys to validate, if the same concept in the GCI/CAP script could be reworked within MOOSE. None of the script code has been used however within the new AI_BALANCER moose class. -- -- ### Authors: @@ -231,16 +231,15 @@ end --- @param #AI_BALANCER self function AI_BALANCER:onenterMonitoring( SetGroup ) - self:E( { self.SetClient:Count() } ) - self.SetClient:Flush() + self:T2( { self.SetClient:Count() } ) + --self.SetClient:Flush() self.SetClient:ForEachClient( --- @param Wrapper.Client#CLIENT Client function( Client ) - self:E(Client.ClientName) + self:T3(Client.ClientName) local AIGroup = self.Set:Get( Client.UnitName ) -- Wrapper.Group#GROUP - self:E({Client:IsAlive()}) if Client:IsAlive() then if AIGroup and AIGroup:IsAlive() == true then @@ -255,16 +254,16 @@ function AI_BALANCER:onenterMonitoring( SetGroup ) local PlayerInRange = { Value = false } local RangeZone = ZONE_RADIUS:New( 'RangeZone', AIGroup:GetVec2(), self.ReturnTresholdRange ) - self:E( RangeZone ) + self:T2( RangeZone ) _DATABASE:ForEachPlayer( --- @param Wrapper.Unit#UNIT RangeTestUnit function( RangeTestUnit, RangeZone, AIGroup, PlayerInRange ) - self:E( { PlayerInRange, RangeTestUnit.UnitName, RangeZone.ZoneName } ) + self:T2( { PlayerInRange, RangeTestUnit.UnitName, RangeZone.ZoneName } ) if RangeTestUnit:IsInZone( RangeZone ) == true then - self:E( "in zone" ) + self:T2( "in zone" ) if RangeTestUnit:GetCoalition() ~= AIGroup:GetCoalition() then - self:E( "in range" ) + self:T2( "in range" ) PlayerInRange.Value = true end end @@ -285,7 +284,7 @@ function AI_BALANCER:onenterMonitoring( SetGroup ) end else if not AIGroup or not AIGroup:IsAlive() == true then - self:E( "Client " .. Client.UnitName .. " not alive." ) + self:T( "Client " .. Client.UnitName .. " not alive." ) if not self.SpawnQueue[Client.UnitName] then -- Spawn a new AI taking into account the spawn interval Earliest, Latest self:__Spawn( math.random( self.Earliest, self.Latest ), Client.UnitName ) diff --git a/Moose Development/Moose/AI/AI_CAP.lua b/Moose Development/Moose/AI/AI_CAP.lua new file mode 100644 index 000000000..c8f7186f9 --- /dev/null +++ b/Moose Development/Moose/AI/AI_CAP.lua @@ -0,0 +1,550 @@ +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Execute Combat Air Patrol (CAP).** +-- +-- ![Banner Image](..\Presentations\AI_Cap\Dia1.JPG) +-- +-- +-- === +-- +-- # 1) @{#AI_CAP_ZONE} class, extends @{AI.AI_Cap#AI_PATROL_ZONE} +-- +-- The @{#AI_CAP_ZONE} class implements the core functions to patrol a @{Zone} by an AI @{Controllable} or @{Group} +-- and automatically engage any airborne enemies that are within a certain range or within a certain zone. +-- +-- ![Process](..\Presentations\AI_Cap\Dia3.JPG) +-- +-- The AI_CAP_ZONE is assigned a @(Group) and this must be done before the AI_CAP_ZONE process can be started using the **Start** event. +-- +-- ![Process](..\Presentations\AI_Cap\Dia4.JPG) +-- +-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- +-- ![Process](..\Presentations\AI_Cap\Dia5.JPG) +-- +-- This cycle will continue. +-- +-- ![Process](..\Presentations\AI_Cap\Dia6.JPG) +-- +-- During the patrol, the AI will detect enemy targets, which are reported through the **Detected** event. +-- +-- ![Process](..\Presentations\AI_Cap\Dia9.JPG) +-- +-- When enemies are detected, the AI will automatically engage the enemy. +-- +-- ![Process](..\Presentations\AI_Cap\Dia10.JPG) +-- +-- Until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. +-- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. +-- +-- ![Process](..\Presentations\AI_Cap\Dia13.JPG) +-- +-- ## 1.1) AI_CAP_ZONE constructor +-- +-- * @{#AI_CAP_ZONE.New}(): Creates a new AI_CAP_ZONE object. +-- +-- ## 1.2) AI_CAP_ZONE is a FSM +-- +-- ![Process](..\Presentations\AI_Cap\Dia2.JPG) +-- +-- ### 1.2.1) AI_CAP_ZONE States +-- +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Engaging** ( Group ): The AI is engaging the bogeys. +-- * **Returning** ( Group ): The AI is returning to Base.. +-- +-- ### 1.2.2) AI_CAP_ZONE Events +-- +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **Engage** ( Group ): Let the AI engage the bogeys. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. +-- +-- ## 1.3) Set the Range of Engagement +-- +-- ![Range](..\Presentations\AI_Cap\Dia11.JPG) +-- +-- An optional range can be set in meters, +-- that will define when the AI will engage with the detected airborne enemy targets. +-- The range can be beyond or smaller than the range of the Patrol Zone. +-- The range is applied at the position of the AI. +-- Use the method @{AI.AI_Cap#AI_CAP_ZONE.SetEngageRange}() to define that range. +-- +-- ## 1.4) Set the Zone of Engagement +-- +-- ![Zone](..\Presentations\AI_Cap\Dia12.JPG) +-- +-- An optional @{Zone} can be set, +-- that will define when the AI will engage with the detected airborne enemy targets. +-- Use the method @{AI.AI_Cap#AI_CAP_ZONE.SetEngageZone}() to define that Zone. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** +-- +-- The underlying change log documents the API changes. Please read this carefully. The following notation is used: +-- +-- * **Added** parts are expressed in bold type face. +-- * _Removed_ parts are expressed in italic type face. +-- +-- Hereby the change log: +-- +-- 2017-01-15: Initial class and API. +-- +-- === +-- +-- # **AUTHORS and CONTRIBUTIONS** +-- +-- ### Contributions: +-- +-- * **[Quax](https://forums.eagle.ru/member.php?u=90530)**: Concept, Advice & Testing. +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Concept, Advice & Testing. +-- * **[Gunterlund](http://forums.eagle.ru:8080/member.php?u=75036)**: Test case revision. +-- +-- ### Authors: +-- +-- * **FlightControl**: Concept, Design & Programming. +-- +-- @module AI_Cap + + +--- AI_CAP_ZONE class +-- @type AI_CAP_ZONE +-- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. +-- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. +-- @extends AI.AI_Patrol#AI_PATROL_ZONE +AI_CAP_ZONE = { + ClassName = "AI_CAP_ZONE", +} + + + +--- Creates a new AI_CAP_ZONE object +-- @param #AI_CAP_ZONE self +-- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. +-- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. +-- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) + + -- Inherits from BASE + local self = BASE:Inherit( self, AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAP_ZONE + + self.Accomplished = false + self.Engaging = false + + self:AddTransition( { "Patrolling", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Engage. + -- @function [parent=#AI_CAP_ZONE] OnBeforeEngage + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Engage. + -- @function [parent=#AI_CAP_ZONE] OnAfterEngage + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAP_ZONE] Engage + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAP_ZONE] __Engage + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Engaging. +-- @function [parent=#AI_CAP_ZONE] OnLeaveEngaging +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Engaging. +-- @function [parent=#AI_CAP_ZONE] OnEnterEngaging +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Fired. + -- @function [parent=#AI_CAP_ZONE] OnBeforeFired + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Fired. + -- @function [parent=#AI_CAP_ZONE] OnAfterFired + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAP_ZONE] Fired + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAP_ZONE] __Fired + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Destroy", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] OnBeforeDestroy + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] OnAfterDestroy + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] Destroy + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] __Destroy + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + + self:AddTransition( "Engaging", "Abort", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Abort. + -- @function [parent=#AI_CAP_ZONE] OnBeforeAbort + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Abort. + -- @function [parent=#AI_CAP_ZONE] OnAfterAbort + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAP_ZONE] Abort + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAP_ZONE] __Abort + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "Engaging", "Accomplish", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] OnBeforeAccomplish + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] OnAfterAccomplish + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] Accomplish + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] __Accomplish + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + return self +end + + +--- Set the Engage Zone which defines where the AI will engage bogies. +-- @param #AI_CAP_ZONE self +-- @param Core.Zone#ZONE EngageZone The zone where the AI is performing CAP. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:SetEngageZone( EngageZone ) + self:F2() + + if EngageZone then + self.EngageZone = EngageZone + else + self.EngageZone = nil + end +end + +--- Set the Engage Range when the AI will engage with airborne enemies. +-- @param #AI_CAP_ZONE self +-- @param #number EngageRange The Engage Range. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:SetEngageRange( EngageRange ) + self:F2() + + if EngageRange then + self.EngageRange = EngageRange + else + self.EngageRange = nil + end +end + +--- onafter State Transition for Event Start. +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterStart( Controllable, From, Event, To ) + + + self:Route() + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every DetectInterval in the EngageZone. + + self:EventOnDead( self.OnDead ) + + Controllable:OptionROEOpenFire() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + +end + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +function _NewEngageCapRoute( AIControllable ) + + AIControllable:T( "NewEngageRoute" ) + local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Cap#AI_CAP_ZONE + EngageZone:__Engage( 1 ) +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onbeforeEngage( Controllable, From, Event, To ) + + if self.Accomplished == true then + return false + end +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterDetected( Controllable, From, Event, To ) + + if From ~= "Engaging" then + + local Engage = false + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() and DetectedUnit:IsAir() then + Engage = true + break + end + end + + if Engage == true then + self:E( 'Detected -> Engaging' ) + self:__Engage( 1 ) + end + end +end + + + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterEngage( Controllable, From, Event, To ) + + if Controllable:IsAlive() then + + self:Detect( self.EngageZone ) + + local EngageRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = CurrentRoutePoint + + + --- Find a random 2D point in PatrolZone. + local ToTargetVec2 = self.PatrolZone:GetRandomVec2() + self:T2( ToTargetVec2 ) + + --- Define Speed and Altitude. + local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) + self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) + + --- Obtain a 3D @{Point} from the 2D point + altitude. + local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) + + --- Create a route point of type air. + local ToPatrolRoutePoint = ToTargetPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToTargetSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = ToPatrolRoutePoint + + Controllable:OptionROEOpenFire() + Controllable:OptionROTPassiveDefense() + + local AttackTasks = {} + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() and DetectedUnit:IsAir() then + if self.EngageZone then + if DetectedUnit:IsInZone( self.EngageZone ) then + self:E( {"Within Zone and Engaging ", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + if self.EngageRange then + if DetectedUnit:GetPointVec3():Get2DDistance(Controllable:GetPointVec3() ) <= self.EngageRange then + self:E( {"Within Range and Engaging", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + end + else + self.DetectedUnits[DetectedUnit] = nil + end + end + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( EngageRoute ) + + + if #AttackTasks == 0 then + self:E("No targets found -> Going back to Patrolling") + self:Accomplish() + self:Route() + else + EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) + + --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... + self.Controllable:SetState( self.Controllable, "EngageZone", self ) + + self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageCapRoute" ) + + end + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 2 ) + + end +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @param Core.Event#EVENTDATA EventData +function AI_CAP_ZONE:onafterDestroy( Controllable, From, Event, To, EventData ) + + if EventData.IniUnit then + self.DetectedUnits[EventData.IniUnit] = nil + end + + Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterAccomplish( Controllable, From, Event, To ) + self.Accomplished = true + self.DetectUnits = false +end + +--- @param #AI_CAP_ZONE self +-- @param Core.Event#EVENTDATA EventData +function AI_CAP_ZONE:OnDead( EventData ) + self:T( { "EventDead", EventData } ) + + if EventData.IniDCSUnit then + self:__Destroy( 1, EventData ) + end +end + + diff --git a/Moose Development/Moose/AI/AI_CAS.lua b/Moose Development/Moose/AI/AI_CAS.lua index 073ad1974..ac60b1ea5 100644 --- a/Moose Development/Moose/AI/AI_CAS.lua +++ b/Moose Development/Moose/AI/AI_CAS.lua @@ -1,47 +1,96 @@ ---- SP:Y MP:Y AI:Y HU:N TYP:Air -- This module contains the AI_CAS_ZONE class. +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Provide Close Air Support to friendly ground troops.** -- +-- ![Banner Image](..\Presentations\AI_Cas\Dia1.JPG) +-- +-- -- === -- --- 1) @{#AI_CAS_ZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} --- ================================================================ --- The @{#AI_CAS_ZONE} class implements the core functions to CAS a @{Zone} by an AIR @{Controllable} @{Group}. +-- # 1) @{#AI_CAS_ZONE} class, extends @{AI.AI_Patrol#AI_PATROL_ZONE} +-- +-- @{#AI_CAS_ZONE} derives from the @{AI.AI_Patrol#AI_PATROL_ZONE}, inheriting its methods and behaviour. +-- +-- The @{#AI_CAS_ZONE} class implements the core functions to provide Close Air Support in an Engage @{Zone} by an AIR @{Controllable} or @{Group}. +-- The AI_CAS_ZONE runs a process. It holds an AI in a Patrol Zone and when the AI is commanded to engage, it will fly to an Engage Zone. +-- +-- ![HoldAndEngage](..\Presentations\AI_Cas\Dia3.JPG) +-- +-- The AI_CAS_ZONE is assigned a @(Group) and this must be done before the AI_CAS_ZONE process can be started through the **Start** event. +-- +-- ![Start Event](..\Presentations\AI_Cas\Dia4.JPG) +-- +-- Upon started, The AI will **Route** itself towards the random 3D point within a patrol zone, +-- using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- This cycle will continue until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. +-- +-- ![Route Event](..\Presentations\AI_Cas\Dia5.JPG) +-- +-- When the AI is commanded to provide Close Air Support (through the event **Engage**), the AI will fly towards the Engage Zone. +-- Any target that is detected in the Engage Zone will be reported and will be destroyed by the AI. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia6.JPG) +-- +-- The AI will detect the targets and will only destroy the targets within the Engage Zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia7.JPG) +-- +-- Every target that is destroyed, is reported< by the AI. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia8.JPG) +-- +-- Note that the AI does not know when the Engage Zone is cleared, and therefore will keep circling in the zone. -- --- 1.1) AI_CAS_ZONE constructor: --- ---------------------------- +-- ![Engage Event](..\Presentations\AI_Cas\Dia9.JPG) +-- +-- Until it is notified through the event **Accomplish**, which is to be triggered by an observing party: +-- +-- * a FAC +-- * a timed event +-- * a menu option selected by a human +-- * a condition +-- * others ... +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia10.JPG) +-- +-- When the AI has accomplished the CAS, it will fly back to the Patrol Zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia11.JPG) +-- +-- It will keep patrolling there, until it is notified to RTB or move to another CAS Zone. +-- It can be notified to go RTB through the **RTB** event. +-- +-- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia12.JPG) +-- +-- # 1.1) AI_CAS_ZONE constructor -- -- * @{#AI_CAS_ZONE.New}(): Creates a new AI_CAS_ZONE object. -- --- 1.2) AI_CAS_ZONE state machine: --- ---------------------------------- --- The AI_CAS_ZONE is a state machine: it manages the different events and states of the AIControllable it is controlling. --- --- ### 1.2.1) AI_CAS_ZONE Events: --- --- * @{#AI_CAS_ZONE.TakeOff}( AIControllable ): The AI is taking-off from an airfield. --- * @{#AI_CAS_ZONE.Hold}( AIControllable ): The AI is holding in airspace at a zone. --- * @{#AI_CAS_ZONE.Engage}( AIControllable ): The AI is engaging the targets. --- * @{#AI_CAS_ZONE.WeaponReleased}( AIControllable ): The AI has released a weapon to the target. --- * @{#AI_CAS_ZONE.Destroy}( AIControllable ): The AI has destroyed a target. --- * @{#AI_CAS_ZONE.Complete}( AIControllable ): The AI has destroyed all defined targets. --- * @{#AI_CAS_ZONE.RTB}( AIControllable ): The AI is returning to the home base. --- --- ### 1.2.2) AI_CAS_ZONE States: --- --- --- ### 1.2.3) AI_CAS_ZONE state transition methods: --- --- --- 1.3) Manage the AI_CAS_ZONE parameters: --- ------------------------------------------ --- The following methods are available to modify the parameters of an AI_CAS_ZONE object: --- --- * @{#AI_CAS_ZONE.SetControllable}(): Set the AIControllable. --- * @{#AI_CAS_ZONE.GetControllable}(): Get the AIControllable. --- +-- ## 1.2) AI_CAS_ZONE is a FSM +-- +-- ![Process](..\Presentations\AI_Cas\Dia2.JPG) +-- +-- ### 1.2.1) AI_CAS_ZONE States +-- +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Engaging** ( Group ): The AI is engaging the targets in the Engage Zone, executing CAS. +-- * **Returning** ( Group ): The AI is returning to Base.. +-- +-- ### 1.2.2) AI_CAS_ZONE Events +-- +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **Engage** ( Group ): Engage the AI to provide CAS in the Engage Zone, destroying any target it finds. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. +-- -- ==== -- --- **API CHANGE HISTORY** --- ====================== +-- # **API CHANGE HISTORY** -- -- The underlying change log documents the API changes. Please read this carefully. The following notation is used: -- @@ -50,31 +99,30 @@ -- -- Hereby the change log: -- --- 2017-01-12: Initial class and API. +-- 2017-01-15: Initial class and API. -- -- === -- --- AUTHORS and CONTRIBUTIONS --- ========================= +-- # **AUTHORS and CONTRIBUTIONS** -- -- ### Contributions: -- --- * **Quax**: Concept & Testing. --- * **Pikey**: Concept & Testing. +-- * **[Quax](https://forums.eagle.ru/member.php?u=90530)**: Concept, Advice & Testing. +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Concept, Advice & Testing. +-- * **[Gunterlund](http://forums.eagle.ru:8080/member.php?u=75036)**: Test case revision. -- -- ### Authors: -- -- * **FlightControl**: Concept, Design & Programming. -- --- --- @module Cas +-- @module AI_Cas --- AI_CAS_ZONE class -- @type AI_CAS_ZONE -- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. -- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. --- @extends AI.AI_Patrol#AI_PATROLZONE +-- @extends AI.AI_Patrol#AI_CAS_ZONE AI_CAS_ZONE = { ClassName = "AI_CAS_ZONE", } @@ -93,179 +141,118 @@ AI_CAS_ZONE = { function AI_CAS_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed, EngageZone ) -- Inherits from BASE - local self = BASE:Inherit( self, AI_PATROLZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAS_ZONE + local self = BASE:Inherit( self, AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAS_ZONE - self.PatrolZone = PatrolZone - self.PatrolFloorAltitude = PatrolFloorAltitude - self.PatrolCeilingAltitude = PatrolCeilingAltitude - self.PatrolMinSpeed = PatrolMinSpeed - self.PatrolMaxSpeed = PatrolMaxSpeed - self.EngageZone = EngageZone + self.Accomplished = false - do self:AddTransition( { "Patrol", "Route", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + self:SetDetectionZone( self.EngageZone ) + + self:AddTransition( { "Patrolling", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - --- OnLeave State Transition for Holding. - -- @function [parent=#AI_CAS_ZONE] OnLeaveHolding - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Engage. - -- @function [parent=#AI_CAS_ZONE] OnBeforeEngage - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Engage. - -- @function [parent=#AI_CAS_ZONE] OnAfterEngage - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Engage. - -- @function [parent=#AI_CAS_ZONE] Engage - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Engage - -- @function [parent=#AI_CAS_ZONE] __Engage - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - - do self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Fired. - -- @function [parent=#AI_CAS_ZONE] OnBeforeFired - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Fired. - -- @function [parent=#AI_CAS_ZONE] OnAfterFired - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean - - --- Embedded Event Trigger for Fired. - -- @function [parent=#AI_CAS_ZONE] Fired - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Fired - -- @function [parent=#AI_CAS_ZONE] __Fired - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - do self:AddTransition( "Engaging", "Destroy", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Destroy. - -- @function [parent=#AI_CAS_ZONE] OnBeforeDestroy - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Destroy. - -- @function [parent=#AI_CAS_ZONE] OnAfterDestroy - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Destroy. - -- @function [parent=#AI_CAS_ZONE] Destroy - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Destroy - -- @function [parent=#AI_CAS_ZONE] __Destroy - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - -do self:AddTransition( "Engaging", "Abort", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging + --- OnBefore Transition Handler for Event Engage. + -- @function [parent=#AI_CAS_ZONE] OnBeforeEngage -- @param #AI_CAS_ZONE self -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. -- @param #string From The From State string. -- @param #string Event The Event string. -- @param #string To The To State string. -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_CAS_ZONE] OnEnterPatrol + + --- OnAfter Transition Handler for Event Engage. + -- @function [parent=#AI_CAS_ZONE] OnAfterEngage -- @param #AI_CAS_ZONE self -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. -- @param #string From The From State string. -- @param #string Event The Event string. -- @param #string To The To State string. - - --- OnBefore State Transition for Abort. + + --- Synchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAS_ZONE] Engage + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAS_ZONE] __Engage + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Engaging. +-- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Engaging. +-- @function [parent=#AI_CAS_ZONE] OnEnterEngaging +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Fired. + -- @function [parent=#AI_CAS_ZONE] OnBeforeFired + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Fired. + -- @function [parent=#AI_CAS_ZONE] OnAfterFired + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAS_ZONE] Fired + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAS_ZONE] __Fired + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Destroy", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] OnBeforeDestroy + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] OnAfterDestroy + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] Destroy + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] __Destroy + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + + self:AddTransition( "Engaging", "Abort", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Abort. -- @function [parent=#AI_CAS_ZONE] OnBeforeAbort -- @param #AI_CAS_ZONE self -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. @@ -273,78 +260,72 @@ do self:AddTransition( "Engaging", "Abort", "Patrol" ) -- FSM_CONTROLLABLE Trans -- @param #string Event The Event string. -- @param #string To The To State string. -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Abort. + + --- OnAfter Transition Handler for Event Abort. -- @function [parent=#AI_CAS_ZONE] OnAfterAbort -- @param #AI_CAS_ZONE self -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. -- @param #string From The From State string. -- @param #string Event The Event string. -- @param #string To The To State string. - - --- Embedded Event Trigger for Abort. + + --- Synchronous Event Trigger for Event Abort. -- @function [parent=#AI_CAS_ZONE] Abort -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Abort + + --- Asynchronous Event Trigger for Event Abort. -- @function [parent=#AI_CAS_ZONE] __Abort -- @param #AI_CAS_ZONE self -- @param #number Delay The delay in seconds. -end -- AI_CAS_ZONE + self:AddTransition( "Engaging", "Accomplish", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - do self:AddTransition( "Engaging", "Completed", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + --- OnBefore Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] OnBeforeAccomplish + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_CAS_ZONE] OnEnterPatrol - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. + --- OnAfter Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] OnAfterAccomplish + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. - --- OnBefore State Transition for Completed. - -- @function [parent=#AI_CAS_ZONE] OnBeforeCompleted - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. + --- Synchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] Accomplish + -- @param #AI_CAS_ZONE self - --- OnAfter State Transition for Completed. - -- @function [parent=#AI_CAS_ZONE] OnAfterCompleted - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Completed. - -- @function [parent=#AI_CAS_ZONE] Completed - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Completed - -- @function [parent=#AI_CAS_ZONE] __Completed - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE + --- Asynchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] __Accomplish + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. return self end +--- Set the Engage Zone where the AI is performing CAS. Note that if the EngageZone is changed, the AI needs to re-detect targets. +-- @param #AI_CAS_ZONE self +-- @param Core.Zone#ZONE EngageZone The zone where the AI is performing CAS. +-- @return #AI_CAS_ZONE self +function AI_CAS_ZONE:SetEngageZone( EngageZone ) + self:F2() + + if EngageZone then + self.EngageZone = EngageZone + else + self.EngageZone = nil + end +end + + + --- onafter State Transition for Event Start. -- @param #AI_CAS_ZONE self -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. @@ -354,25 +335,45 @@ end function AI_CAS_ZONE:onafterStart( Controllable, From, Event, To ) - if Controllable:IsAlive() then - self:__Route( 1 ) - end - + self:Route() + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every DetectInterval in the EngageZone. + self:EventOnDead( self.OnDead ) Controllable:OptionROEHoldFire() Controllable:OptionROTVertical() + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + end --- @param Wrapper.Controllable#CONTROLLABLE AIControllable function _NewEngageRoute( AIControllable ) AIControllable:T( "NewEngageRoute" ) - local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Patrol#AI_PATROLZONE + local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Cas#AI_CAS_ZONE EngageZone:__Engage( 1 ) end +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onbeforeEngage( Controllable, From, Event, To ) + + if self.Accomplished == true then + return false + end +end + --- @param #AI_CAS_ZONE self -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. @@ -383,7 +384,27 @@ function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) if Controllable:IsAlive() then + self:Detect( self.EngageZone ) + local EngageRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = CurrentRoutePoint + if self.Controllable:IsNotInZone( self.EngageZone ) then @@ -435,7 +456,7 @@ function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) true ) - ToTargetPointVec3:SmokeRed() + ToTargetPointVec3:SmokeBlue() EngageRoute[#EngageRoute+1] = ToTargetRoutePoint @@ -445,21 +466,16 @@ function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) local AttackTasks = {} - local DetectedTargets = Controllable:GetDetectedTargets() - for TargetID, Target in pairs( DetectedTargets ) do - local TargetObject = Target.object - self:T( TargetObject ) - if TargetObject and TargetObject:isExist() and TargetObject.id_ < 50000000 then - - local TargetUnit = UNIT:Find( TargetObject ) - local TargetUnitName = TargetUnit:GetName() - - if TargetUnit:IsInZone( self.EngageZone ) then - self:E( {"Engaging ", TargetUnit } ) - --local EngageTask = Controllable:EnRouteTaskEngageUnit( TargetUnit, 1 ) - AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( TargetUnit ) + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() then + if DetectedUnit:IsInZone( self.EngageZone ) then + self:E( {"Engaging ", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) end - + else + self.DetectedUnits[DetectedUnit] = nil end end @@ -474,7 +490,7 @@ function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageRoute" ) --- NOW ROUTE THE GROUP! - self.Controllable:WayPointExecute( 1, 5 ) + self.Controllable:WayPointExecute( 1, 2 ) end end @@ -483,11 +499,26 @@ end -- @param #string From The From State string. -- @param #string Event The Event string. -- @param #string To The To State string. -function AI_CAS_ZONE:onafterDestroy( Controllable, From, Event, To ) +-- @param Core.Event#EVENTDATA EventData +function AI_CAS_ZONE:onafterDestroy( Controllable, From, Event, To, EventData ) + if EventData.IniUnit then + self.DetectedUnits[EventData.IniUnit] = nil + end + Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) end +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterAccomplish( Controllable, From, Event, To ) + self.Accomplished = true + self.DetectUnits = false +end + --- @param #AI_CAS_ZONE self -- @param Core.Event#EVENTDATA EventData function AI_CAS_ZONE:OnDead( EventData ) diff --git a/Moose Development/Moose/AI/AI_Cargo.lua b/Moose Development/Moose/AI/AI_Cargo.lua index e8963c927..903181661 100644 --- a/Moose Development/Moose/AI/AI_Cargo.lua +++ b/Moose Development/Moose/AI/AI_Cargo.lua @@ -1,4 +1,4 @@ ---- Management of logical cargo objects, that can be transported from and to transportation carriers. +--- Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Ground -- Management of logical cargo objects, that can be transported from and to transportation carriers. -- -- === -- diff --git a/Moose Development/Moose/AI/AI_Patrol.lua b/Moose Development/Moose/AI/AI_Patrol.lua index 8d3ccf4e3..9edc140a8 100644 --- a/Moose Development/Moose/AI/AI_Patrol.lua +++ b/Moose Development/Moose/AI/AI_Patrol.lua @@ -1,110 +1,122 @@ ---- (AI) (FSM) Make AI patrol routes or zones. +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Air Patrolling or Staging.** +-- +-- ![Banner Image](..\Presentations\AI_Patrol\Dia1.JPG) +-- -- -- === -- --- 1) @{#AI_PATROLZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} --- ================================================================ --- The @{#AI_PATROLZONE} class implements the core functions to patrol a @{Zone} by an AIR @{Controllable} @{Group}. --- The patrol algorithm works that for each airplane patrolling, upon arrival at the patrol zone, --- a random point is selected as the route point within the 3D space, within the given boundary limits. --- The airplane will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. --- Upon arrival at the random 3D point, a new 3D random point will be selected within the patrol zone using the given limits. --- This cycle will continue until a fuel treshold has been reached by the airplane. +-- # 1) @{#AI_PATROL_ZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} +-- +-- The @{#AI_PATROL_ZONE} class implements the core functions to patrol a @{Zone} by an AI @{Controllable} or @{Group}. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia3.JPG) +-- +-- The AI_PATROL_ZONE is assigned a @(Group) and this must be done before the AI_PATROL_ZONE process can be started using the **Start** event. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia4.JPG) +-- +-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia5.JPG) +-- +-- This cycle will continue. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia6.JPG) +-- +-- During the patrol, the AI will detect enemy targets, which are reported through the **Detected** event. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia9.JPG) +-- +---- Note that the enemy is not engaged! To model enemy engagement, either tailor the **Detected** event, or +-- use derived AI_ classes to model AI offensive or defensive behaviour. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia10.JPG) +-- +-- Until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. -- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. -- --- 1.1) AI_PATROLZONE constructor: --- ---------------------------- +-- ![Process](..\Presentations\AI_Patrol\Dia11.JPG) +-- +-- ## 1.1) AI_PATROL_ZONE constructor -- --- * @{#AI_PATROLZONE.New}(): Creates a new AI_PATROLZONE object. +-- * @{#AI_PATROL_ZONE.New}(): Creates a new AI_PATROL_ZONE object. -- --- 1.2) AI_PATROLZONE state machine: --- ---------------------------------- --- The AI_PATROLZONE is a state machine: it manages the different events and states of the AIControllable it is controlling. +-- ## 1.2) AI_PATROL_ZONE is a FSM -- --- ### 1.2.1) AI_PATROLZONE Events: +-- ![Process](..\Presentations\AI_Patrol\Dia2.JPG) -- --- * @{#AI_PATROLZONE.Route}( AIControllable ): A new 3D route point is selected and the AIControllable will fly towards that point with the given speed. --- * @{#AI_PATROLZONE.Patrol}( AIControllable ): The AIControllable reports it is patrolling. This event is called every 30 seconds. --- * @{#AI_PATROLZONE.RTB}( AIControllable ): The AIControllable will report return to base. --- * @{#AI_PATROLZONE.End}( AIControllable ): The end of the AI_PATROLZONE process. --- * @{#AI_PATROLZONE.Dead}( AIControllable ): The AIControllable is dead. The AI_PATROLZONE process will be ended. +-- ### 1.2.1) AI_PATROL_ZONE States -- --- ### 1.2.2) AI_PATROLZONE States: +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Returning** ( Group ): The AI is returning to Base.. -- --- * **Route**: A new 3D route point is selected and the AIControllable will fly towards that point with the given speed. --- * **Patrol**: The AIControllable is patrolling. This state is set every 30 seconds, so every 30 seconds, a state transition method can be used. --- * **RTB**: The AIControllable reports it wants to return to the base. --- * **Dead**: The AIControllable is dead ... --- * **End**: The process has come to an end. --- --- ### 1.2.3) AI_PATROLZONE state transition methods: +-- ### 1.2.2) AI_PATROL_ZONE Events -- --- State transition functions can be set **by the mission designer** customizing or improving the behaviour of the state. --- There are 2 moments when state transition methods will be called by the state machine: --- --- * **Before** the state transition. --- The state transition method needs to start with the name **OnBefore + the name of the state**. --- If the state transition method returns false, then the processing of the state transition will not be done! --- If you want to change the behaviour of the AIControllable at this event, return false, --- but then you'll need to specify your own logic using the AIControllable! --- --- * **After** the state transition. --- The state transition method needs to start with the name **OnAfter + the name of the state**. --- These state transition methods need to provide a return value, which is specified at the function description. --- --- An example how to manage a state transition for an AI_PATROLZONE object **Patrol** for the state **RTB**: --- --- local PatrolZoneGroup = GROUP:FindByName( "Patrol Zone" ) --- local PatrolZone = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) --- --- local PatrolSpawn = SPAWN:New( "Patrol Group" ) --- local PatrolGroup = PatrolSpawn:Spawn() --- --- local Patrol = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 300, 600 ) --- Patrol:SetControllable( PatrolGroup ) --- Patrol:ManageFuel( 0.2, 60 ) --- --- **OnBefore**RTB( AIGroup ) will be called by the AI_PATROLZONE object when the AIGroup reports RTB, but **before** the RTB default action is processed by the AI_PATROLZONE object. --- --- --- State transition function for the AI_PATROLZONE **Patrol** object --- -- @param #AI_PATROLZONE self --- -- @param Wrapper.Controllable#CONTROLLABLE AIGroup --- -- @return #boolean If false is returned, then the OnAfter state transition method will not be called. --- function Patrol:OnBeforeRTB( AIGroup ) --- AIGroup:MessageToRed( "Returning to base", 20 ) --- end --- --- **OnAfter**RTB( AIGroup ) will be called by the AI_PATROLZONE object when the AIGroup reports RTB, but **after** the RTB default action was processed by the AI_PATROLZONE object. --- --- --- State transition function for the AI_PATROLZONE **Patrol** object --- -- @param #AI_PATROLZONE self --- -- @param Wrapper.Controllable#CONTROLLABLE AIGroup --- -- @return #Wrapper.Controllable#CONTROLLABLE The new AIGroup object that is set to be patrolling the zone. --- function Patrol:OnAfterRTB( AIGroup ) --- return PatrolSpawn:Spawn() --- end +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. -- --- 1.3) Manage the AI_PATROLZONE parameters: --- ------------------------------------------ --- The following methods are available to modify the parameters of a AI_PATROLZONE object: +-- ## 1.3) Set or Get the AI controllable -- --- * @{#AI_PATROLZONE.SetControllable}(): Set the AIControllable. --- * @{#AI_PATROLZONE.GetControllable}(): Get the AIControllable. --- * @{#AI_PATROLZONE.SetSpeed}(): Set the patrol speed of the AI, for the next patrol. --- * @{#AI_PATROLZONE.SetAltitude}(): Set altitude of the AI, for the next patrol. +-- * @{#AI_PATROL_ZONE.SetControllable}(): Set the AIControllable. +-- * @{#AI_PATROL_ZONE.GetControllable}(): Get the AIControllable. +-- +-- ## 1.4) Set the Speed and Altitude boundaries of the AI controllable +-- +-- * @{#AI_PATROL_ZONE.SetSpeed}(): Set the patrol speed boundaries of the AI, for the next patrol. +-- * @{#AI_PATROL_ZONE.SetAltitude}(): Set altitude boundaries of the AI, for the next patrol. -- --- 1.3) Manage the out of fuel in the AI_PATROLZONE: --- ---------------------------------------------- --- When the AIControllable is out of fuel, it is required that a new AIControllable is started, before the old AIControllable can return to the home base. +-- ## 1.5) Manage the detection process of the AI controllable +-- +-- The detection process of the AI controllable can be manipulated. +-- Detection requires an amount of CPU power, which has an impact on your mission performance. +-- Only put detection on when absolutely necessary, and the frequency of the detection can also be set. +-- +-- * @{#AI_PATROL_ZONE.SetDetectionOn}(): Set the detection on. The AI will detect for targets. +-- * @{#AI_PATROL_ZONE.SetDetectionOff}(): Set the detection off, the AI will not detect for targets. The existing target list will NOT be erased. +-- +-- The detection frequency can be set with @{#AI_PATROL_ZONE.SetDetectionInterval}( seconds ), where the amount of seconds specify how much seconds will be waited before the next detection. +-- Use the method @{#AI_PATROL_ZONE.GetDetectedUnits}() to obtain a list of the @{Unit}s detected by the AI. +-- +-- The detection can be filtered to potential targets in a specific zone. +-- Use the method @{#AI_PATROL_ZONE.SetDetectionZone}() to set the zone where targets need to be detected. +-- Note that when the zone is too far away, or the AI is not heading towards the zone, or the AI is too high, no targets may be detected +-- according the weather conditions. +-- +-- ## 1.6) Manage the "out of fuel" in the AI_PATROL_ZONE +-- +-- When the AI is out of fuel, it is required that a new AI is started, before the old AI can return to the home base. -- Therefore, with a parameter and a calculation of the distance to the home base, the fuel treshold is calculated. --- When the fuel treshold is reached, the AIControllable will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROLZONE. --- Once the time is finished, the old AIControllable will return to the base. --- Use the method @{#AI_PATROLZONE.ManageFuel}() to have this proces in place. +-- When the fuel treshold is reached, the AI will continue for a given time its patrol task in orbit, +-- while a new AI is targetted to the AI_PATROL_ZONE. +-- Once the time is finished, the old AI will return to the base. +-- Use the method @{#AI_PATROL_ZONE.ManageFuel}() to have this proces in place. +-- +-- ## 1.7) Manage "damage" behaviour of the AI in the AI_PATROL_ZONE +-- +-- When the AI is damaged, it is required that a new AIControllable is started. However, damage cannon be foreseen early on. +-- Therefore, when the damage treshold is reached, the AI will return immediately to the home base (RTB). +-- Use the method @{#AI_PATROL_ZONE.ManageDamage}() to have this proces in place. -- -- ==== -- --- **API CHANGE HISTORY** --- ====================== +-- # **OPEN ISSUES** +-- +-- 2017-01-17: When Spawned AI is located at an airbase, it will be routed first back to the airbase after take-off. +-- +-- 2016-01-17: +-- -- Fixed problem with AI returning to base too early and unexpected. +-- -- ReSpawning of AI will reset the AI_PATROL and derived classes. +-- -- Checked the correct workings of SCHEDULER, and it DOES work correctly. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** -- -- The underlying change log documents the API changes. Please read this carefully. The following notation is used: -- @@ -113,257 +125,282 @@ -- -- Hereby the change log: -- +-- 2017-01-17: Rename of class: **AI\_PATROL\_ZONE** is the new name for the old _AI\_PATROLZONE_. +-- +-- 2017-01-15: Complete revision. AI_PATROL_ZONE is the base class for other AI_PATROL like classes. +-- -- 2016-09-01: Initial class and API. -- -- === -- --- AUTHORS and CONTRIBUTIONS --- ========================= +-- # **AUTHORS and CONTRIBUTIONS** -- -- ### Contributions: -- --- * **DutchBaron**: Testing. --- * **Pikey**: Testing and API concept review. +-- * **[Dutch_Baron](https://forums.eagle.ru/member.php?u=112075)**: Working together with James has resulted in the creation of the AI_BALANCER class. James has shared his ideas on balancing AI with air units, and together we made a first design which you can use now :-) +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Testing and API concept review. -- -- ### Authors: -- -- * **FlightControl**: Design & Programming. -- --- -- @module AI_Patrol ---- AI_PATROLZONE class --- @type AI_PATROLZONE +--- AI_PATROL_ZONE class +-- @type AI_PATROL_ZONE -- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. -- @field Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. -- @field Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @field Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. -- @field Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @field Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @field Functional.Spawn#SPAWN CoordTest -- @extends Core.Fsm#FSM_CONTROLLABLE -AI_PATROLZONE = { - ClassName = "AI_PATROLZONE", +AI_PATROL_ZONE = { + ClassName = "AI_PATROL_ZONE", } - - ---- Creates a new AI_PATROLZONE object --- @param #AI_PATROLZONE self +--- Creates a new AI_PATROL_ZONE object +-- @param #AI_PATROL_ZONE self -- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. -- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @return #AI_PATROLZONE self +-- @return #AI_PATROL_ZONE self -- @usage --- -- Define a new AI_PATROLZONE Object. This PatrolArea will patrol an AIControllable within PatrolZone between 3000 and 6000 meters, with a variying speed between 600 and 900 km/h. +-- -- Define a new AI_PATROL_ZONE Object. This PatrolArea will patrol an AIControllable within PatrolZone between 3000 and 6000 meters, with a variying speed between 600 and 900 km/h. -- PatrolZone = ZONE:New( 'PatrolZone' ) -- PatrolSpawn = SPAWN:New( 'Patrol Group' ) --- PatrolArea = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 600, 900 ) -function AI_PATROLZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) +-- PatrolArea = AI_PATROL_ZONE:New( PatrolZone, 3000, 6000, 600, 900 ) +function AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) -- Inherits from BASE - local self = BASE:Inherit( self, FSM_CONTROLLABLE:New() ) -- Core.Fsm#FSM_CONTROLLABLE + local self = BASE:Inherit( self, FSM_CONTROLLABLE:New() ) -- #AI_PATROL_ZONE - self.PatrolZone = PatrolZone + self.PatrolZone = PatrolZone self.PatrolFloorAltitude = PatrolFloorAltitude self.PatrolCeilingAltitude = PatrolCeilingAltitude self.PatrolMinSpeed = PatrolMinSpeed self.PatrolMaxSpeed = PatrolMaxSpeed - self.PatrolFuelTresholdPercentage = 0.2 + self:SetDetectionOn() + self.CheckStatus = true - self:SetStartState( "None" ) + self:ManageFuel( .2, 60 ) + self:ManageDamage( 1 ) + + self:SetDetectionInterval( 30 ) -do self:AddTransition( "*", "Start", "Route" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. + self.DetectedUnits = {} -- This table contains the targets detected during patrol. + + self:SetStartState( "None" ) - --- OnLeave State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnLeaveRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. + self:AddTransition( "None", "Start", "Patrolling" ) - --- OnEnter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnEnterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnBefore Transition Handler for Event Start. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeStart +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Start. +-- @function [parent=#AI_PATROL_ZONE] OnAfterStart +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Start. - -- @function [parent=#AI_PATROLZONE] OnBeforeStart - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Start. +-- @function [parent=#AI_PATROL_ZONE] Start +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Start. - -- @function [parent=#AI_PATROLZONE] OnAfterStart - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Start. +-- @function [parent=#AI_PATROL_ZONE] __Start +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Patrolling. +-- @function [parent=#AI_PATROL_ZONE] OnLeavePatrolling +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Patrolling. +-- @function [parent=#AI_PATROL_ZONE] OnEnterPatrolling +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Patrolling", "Route", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event Route. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeRoute +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Route. +-- @function [parent=#AI_PATROL_ZONE] OnAfterRoute +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Start. - -- @function [parent=#AI_PATROLZONE] Start - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event Route. +-- @function [parent=#AI_PATROL_ZONE] Route +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Start - -- @function [parent=#AI_PATROLZONE] __Start - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event Route. +-- @function [parent=#AI_PATROL_ZONE] __Route +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE + self:AddTransition( "*", "Status", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. -do self:AddTransition( "*", "Route", "Route" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnBefore Transition Handler for Event Status. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeStatus +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnLeaveRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnEnterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnAfter Transition Handler for Event Status. +-- @function [parent=#AI_PATROL_ZONE] OnAfterStatus +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnBeforeRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Status. +-- @function [parent=#AI_PATROL_ZONE] Status +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnAfterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Status. +-- @function [parent=#AI_PATROL_ZONE] __Status +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Detect", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeDetect +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] OnAfterDetect +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Route. - -- @function [parent=#AI_PATROLZONE] Route - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] Detect +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Route - -- @function [parent=#AI_PATROLZONE] __Route - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] __Detect +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE + self:AddTransition( "*", "Detected", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. -do self:AddTransition( "*", "Patrol", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnBefore Transition Handler for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeDetected +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnLeavePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnEnterPatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnAfter Transition Handler for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] OnAfterDetected +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnBeforePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] Detected +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnAfterPatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] __Detected +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "RTB", "Returning" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeRTB +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] OnAfterRTB +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Patrol. - -- @function [parent=#AI_PATROLZONE] Patrol - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] RTB +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Patrol - -- @function [parent=#AI_PATROLZONE] __Patrol - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] __RTB +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE +--- OnLeave Transition Handler for State Returning. +-- @function [parent=#AI_PATROL_ZONE] OnLeaveReturning +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. -do self:AddTransition( "Patrol", "RTB", "RTB" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnEnter Transition Handler for State Returning. +-- @function [parent=#AI_PATROL_ZONE] OnEnterReturning +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnLeave State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnLeavePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnEnterRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnBeforeRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnAfterRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for RTB. - -- @function [parent=#AI_PATROLZONE] RTB - -- @param #AI_PATROLZONE self - - --- Delayed Event Trigger for RTB - -- @function [parent=#AI_PATROLZONE] __RTB - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. - -end -- AI_PATROLZONE + self:AddTransition( "*", "Reset", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. return self end @@ -372,11 +409,11 @@ end --- Sets (modifies) the minimum and maximum speed of the patrol. --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:SetSpeed( PatrolMinSpeed, PatrolMaxSpeed ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetSpeed( PatrolMinSpeed, PatrolMaxSpeed ) self:F2( { PatrolMinSpeed, PatrolMaxSpeed } ) self.PatrolMinSpeed = PatrolMinSpeed @@ -386,39 +423,92 @@ end --- Sets the floor and ceiling altitude of the patrol. --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:SetAltitude( PatrolFloorAltitude, PatrolCeilingAltitude ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetAltitude( PatrolFloorAltitude, PatrolCeilingAltitude ) self:F2( { PatrolFloorAltitude, PatrolCeilingAltitude } ) self.PatrolFloorAltitude = PatrolFloorAltitude self.PatrolCeilingAltitude = PatrolCeilingAltitude end +-- * @{#AI_PATROL_ZONE.SetDetectionOn}(): Set the detection on. The AI will detect for targets. +-- * @{#AI_PATROL_ZONE.SetDetectionOff}(): Set the detection off, the AI will not detect for targets. The existing target list will NOT be erased. +--- Set the detection on. The AI will detect for targets. +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionOn() + self:F2() + + self.DetectUnits = true +end ---- @param Wrapper.Controllable#CONTROLLABLE AIControllable -function _NewPatrolRoute( AIControllable ) +--- Set the detection off. The AI will NOT detect for targets. +-- However, the list of already detected targets will be kept and can be enquired! +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionOff() + self:F2() + + self.DetectUnits = false +end - AIControllable:T( "NewPatrolRoute" ) - local PatrolZone = AIControllable:GetState( AIControllable, "PatrolZone" ) -- PatrolCore.Zone#AI_PATROLZONE - PatrolZone:__Route( 1 ) +--- Set the interval in seconds between each detection executed by the AI. +-- The list of already detected targets will be kept and updated. +-- Newly detected targets will be added, but already detected targets that were +-- not detected in this cycle, will NOT be removed! +-- The default interval is 30 seconds. +-- @param #AI_PATROL_ZONE self +-- @param #number Seconds The interval in seconds. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionInterval( Seconds ) + self:F2() + + if Seconds then + self.DetectInterval = Seconds + else + self.DetectInterval = 30 + end +end + +--- Set the detection zone where the AI is detecting targets. +-- @param #AI_PATROL_ZONE self +-- @param Core.Zone#ZONE DetectionZone The zone where to detect targets. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionZone( DetectionZone ) + self:F2() + + if DetectionZone then + self.DetectZone = DetectionZone + else + self.DetectZone = nil + end +end + +--- Gets a list of @{Wrapper.Unit#UNIT}s that were detected by the AI. +-- No filtering is applied, so, ANY detected UNIT can be in this list. +-- It is up to the mission designer to use the @{Unit} class and methods to filter the targets. +-- @param #AI_PATROL_ZONE self +-- @return #table The list of @{Wrapper.Unit#UNIT}s +function AI_PATROL_ZONE:GetDetectedUnits() + self:F2() + + return self.DetectedUnits end - - ---- When the AIControllable is out of fuel, it is required that a new AIControllable is started, before the old AIControllable can return to the home base. +--- When the AI is out of fuel, it is required that a new AI is started, before the old AI can return to the home base. -- Therefore, with a parameter and a calculation of the distance to the home base, the fuel treshold is calculated. --- When the fuel treshold is reached, the AIControllable will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROLZONE. --- Once the time is finished, the old AIControllable will return to the base. --- @param #AI_PATROLZONE self +-- When the fuel treshold is reached, the AI will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROL_ZONE. +-- Once the time is finished, the old AI will return to the base. +-- @param #AI_PATROL_ZONE self -- @param #number PatrolFuelTresholdPercentage The treshold in percentage (between 0 and 1) when the AIControllable is considered to get out of fuel. -- @param #number PatrolOutOfFuelOrbitTime The amount of seconds the out of fuel AIControllable will orbit before returning to the base. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuelOrbitTime ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuelOrbitTime ) self.PatrolManageFuel = true self.PatrolFuelTresholdPercentage = PatrolFuelTresholdPercentage @@ -427,60 +517,165 @@ function AI_PATROLZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuel return self end +--- When the AI is damaged beyond a certain treshold, it is required that the AI returns to the home base. +-- However, damage cannot be foreseen early on. +-- Therefore, when the damage treshold is reached, +-- the AI will return immediately to the home base (RTB). +-- Note that for groups, the average damage of the complete group will be calculated. +-- So, in a group of 4 airplanes, 2 lost and 2 with damage 0.2, the damage treshold will be 0.25. +-- @param #AI_PATROL_ZONE self +-- @param #number PatrolDamageTreshold The treshold in percentage (between 0 and 1) when the AI is considered to be damaged. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:ManageDamage( PatrolDamageTreshold ) + + self.PatrolManageDamage = true + self.PatrolDamageTreshold = PatrolDamageTreshold + + return self +end + --- Defines a new patrol route using the @{Process_PatrolZone} parameters and settings. --- @param #AI_PATROLZONE self --- @return #AI_PATROLZONE self -function AI_PATROLZONE:onenterRoute() +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_PATROL_ZONE:onafterStart( Controllable, From, Event, To ) + self:F2() + + self:__Route( 5 ) -- Route to the patrol point. The asynchronous trigger is important, because a spawned group and units takes at least one second to come live. + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every 30 seconds. + + Controllable:OptionROEHoldFire() + Controllable:OptionROTVertical() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + +end + + +--- @param #AI_PATROL_ZONE self +--- @param Wrapper.Controllable#CONTROLLABLE Controllable +function AI_PATROL_ZONE:onbeforeDetect( Controllable, From, Event, To ) + + return self.DetectUnits +end + +--- @param #AI_PATROL_ZONE self +--- @param Wrapper.Controllable#CONTROLLABLE Controllable +function AI_PATROL_ZONE:onafterDetect( Controllable, From, Event, To ) + + local Detected = false + + local DetectedTargets = Controllable:GetDetectedTargets() + for TargetID, Target in pairs( DetectedTargets or {} ) do + local TargetObject = Target.object + self:T( TargetObject ) + if TargetObject and TargetObject:isExist() and TargetObject.id_ < 50000000 then + + local TargetUnit = UNIT:Find( TargetObject ) + local TargetUnitName = TargetUnit:GetName() + + if self.DetectionZone then + if TargetUnit:IsInZone( self.DetectionZone ) then + self:T( {"Detected ", TargetUnit } ) + self.DetectedUnits[TargetUnit] = TargetUnit + Detected = true + end + else + self.DetectedUnits[TargetUnit] = TargetUnit + Detected = true + end + end + end + + if Detected == true then + self:__Detected( 1 ) + end + + self:__Detect( self.DetectInterval ) +end + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +-- This statis method is called from the route path within the last task at the last waaypoint of the Controllable. +-- Note that this method is required, as triggers the next route when patrolling for the Controllable. +function AI_PATROL_ZONE:_NewPatrolRoute( AIControllable ) + + local PatrolZone = AIControllable:GetState( AIControllable, "PatrolZone" ) -- PatrolCore.Zone#AI_PATROL_ZONE + PatrolZone:__Route( 1 ) +end + + +--- Defines a new patrol route using the @{Process_PatrolZone} parameters and settings. +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_PATROL_ZONE:onafterRoute( Controllable, From, Event, To ) self:F2() - local PatrolRoute = {} + -- When RTB, don't allow anymore the routing. + if From == "RTB" then + return + end + if self.Controllable:IsAlive() then - --- Determine if the AIControllable is within the PatrolZone. + -- Determine if the AIControllable is within the PatrolZone. -- If not, make a waypoint within the to that the AIControllable will fly at maximum speed to that point. --- --- Calculate the current route point. --- local CurrentVec2 = self.Controllable:GetVec2() --- local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() --- local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) --- local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( --- POINT_VEC3.RoutePointAltType.BARO, --- POINT_VEC3.RoutePointType.TurningPoint, --- POINT_VEC3.RoutePointAction.TurningPoint, --- ToPatrolZoneSpeed, --- true --- ) --- --- PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + local PatrolRoute = {} + + -- Calculate the current route point of the controllable as the start point of the route. + -- However, when the controllable is not in the air, + -- the controllable current waypoint is probably the airbase... + -- Thus, if we would take the current waypoint as the startpoint, upon take-off, the controllable flies + -- immediately back to the airbase, and this is not correct. + -- Therefore, when on a runway, get as the current route point a random point within the PatrolZone. + -- This will make the plane fly immediately to the patrol zone. - self:T2( PatrolRoute ) - - if self.Controllable:IsNotInZone( self.PatrolZone ) then - --- Find a random 2D point in PatrolZone. - local ToPatrolZoneVec2 = self.PatrolZone:GetRandomVec2() - self:T2( ToPatrolZoneVec2 ) - - --- Define Speed and Altitude. - local ToPatrolZoneAltitude = math.random( self.PatrolFloorAltitude, self.PatrolCeilingAltitude ) + if self.Controllable:InAir() == false then + self:E( "Not in the air, finding route path within PatrolZone" ) + local CurrentVec2 = self.Controllable:GetVec2() + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) local ToPatrolZoneSpeed = self.PatrolMaxSpeed - self:T2( ToPatrolZoneSpeed ) - - --- Obtain a 3D @{Point} from the 2D point + altitude. - local ToPatrolZonePointVec3 = POINT_VEC3:New( ToPatrolZoneVec2.x, ToPatrolZoneAltitude, ToPatrolZoneVec2.y ) - - --- Create a route point of type air. - local ToPatrolZoneRoutePoint = ToPatrolZonePointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToPatrolZoneSpeed, - true - ) - - PatrolRoute[#PatrolRoute+1] = ToPatrolZoneRoutePoint - - end + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TakeOffParking, + POINT_VEC3.RoutePointAction.FromParkingArea, + ToPatrolZoneSpeed, + true + ) + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + else + self:E( "In the air, finding route path within PatrolZone" ) + local CurrentVec2 = self.Controllable:GetVec2() + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToPatrolZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToPatrolZoneSpeed, + true + ) + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + end + --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. @@ -505,6 +700,8 @@ function AI_PATROLZONE:onenterRoute() true ) + --self.CoordTest:SpawnFromVec3( ToTargetPointVec3:GetVec3() ) + --ToTargetPointVec3:SmokeRed() PatrolRoute[#PatrolRoute+1] = ToTargetRoutePoint @@ -514,25 +711,31 @@ function AI_PATROLZONE:onenterRoute() --- Do a trick, link the NewPatrolRoute function of the PATROLGROUP object to the AIControllable in a temporary variable ... self.Controllable:SetState( self.Controllable, "PatrolZone", self ) - self.Controllable:WayPointFunction( #PatrolRoute, 1, "_NewPatrolRoute" ) + self.Controllable:WayPointFunction( #PatrolRoute, 1, "AI_PATROL_ZONE:_NewPatrolRoute" ) --- NOW ROUTE THE GROUP! - self.Controllable:WayPointExecute( 1, 5 ) - - self:__Patrol( 30 ) + self.Controllable:WayPointExecute( 1, 2 ) end - + end +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onbeforeStatus() ---- @param #AI_PATROLZONE self -function AI_PATROLZONE:onenterPatrol() + return self.CheckStatus +end + +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onafterStatus() self:F2() if self.Controllable and self.Controllable:IsAlive() then + local RTB = false + local Fuel = self.Controllable:GetUnit(1):GetFuel() if Fuel < self.PatrolFuelTresholdPercentage then + self:E( self.Controllable:GetName() .. " is out of fuel:" .. Fuel .. ", RTB!" ) local OldAIControllable = self.Controllable local AIControllableTemplate = self.Controllable:GetTemplate() @@ -540,10 +743,59 @@ function AI_PATROLZONE:onenterPatrol() local TimedOrbitTask = OldAIControllable:TaskControlled( OrbitTask, OldAIControllable:TaskCondition(nil,nil,nil,nil,self.PatrolOutOfFuelOrbitTime,nil ) ) OldAIControllable:SetTask( TimedOrbitTask, 10 ) + RTB = true + else + end + + -- TODO: Check GROUP damage function. + local Damage = self.Controllable:GetLife() + if Damage <= self.PatrolDamageTreshold then + self:E( self.Controllable:GetName() .. " is damaged:" .. Damage .. ", RTB!" ) + RTB = true + end + + if RTB == true then self:RTB() else - self:__Patrol( 30 ) -- Execute the Patrol event after 30 seconds. + self:__Status( 30 ) -- Execute the Patrol event after 30 seconds. end end - +end + +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onafterRTB() + self:F2() + + if self.Controllable and self.Controllable:IsAlive() then + + self:SetDetectionOff() + self.CheckStatus = false + + local PatrolRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToPatrolZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToPatrolZoneSpeed, + true + ) + + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( PatrolRoute ) + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 1 ) + + end + end diff --git a/Moose Development/Moose/Core/Fsm.lua b/Moose Development/Moose/Core/Fsm.lua index 2d1948aee..382ca1cad 100644 --- a/Moose Development/Moose/Core/Fsm.lua +++ b/Moose Development/Moose/Core/Fsm.lua @@ -535,14 +535,21 @@ do -- FSM function FSM._handler( self, EventName, ... ) - self:E( { EventName, ... } ) - local Can, to = self:can( EventName ) - self:E( { From = self.current, Event = EventName, To = to, Can = Can } ) + + if to == "*" then + to = self.current + end if Can then local from = self.current local params = { from, EventName, to, ... } + + if self.Controllable then + self:E( "FSM Transition for " .. self.Controllable.ControllableName .. " :" .. self.current .. " --> " .. EventName .. " --> " .. to ) + else + self:E( "FSM Transition:" .. self.current .. " --> " .. EventName .. " --> " .. to ) + end if self:_call_handler("onbefore" .. EventName, params) == false or self:_call_handler("OnBefore" .. EventName, params) == false @@ -592,6 +599,9 @@ do -- FSM self:_call_handler("onstatechange", params) end + else + self:E( "Cannot execute transition." ) + self:E( { From = self.current, Event = EventName, To = to, Can = Can } ) end return nil @@ -667,7 +677,6 @@ do -- FSM end function FSM:can(e) - self:E( { e, self.Events, self.Events[e] } ) local Event = self.Events[e] self:F3( { self.current, Event } ) local To = Event and Event.map[self.current] or Event.map['*'] @@ -736,7 +745,7 @@ do -- FSM_CONTROLLABLE end if self[handler] then - self:E( "Calling " .. handler ) + self:F3( "Calling " .. handler ) return xpcall( function() return self[handler]( self, self.Controllable, unpack( params ) ) end, ErrorHandler ) --return self[handler]( self, self.Controllable, unpack( params ) ) end @@ -1027,7 +1036,7 @@ do -- FSM_SET function FSM_SET:_call_handler( handler, params ) if self[handler] then - self:E( "Calling " .. handler ) + self:T( "Calling " .. handler ) return self[handler]( self, self.Set, unpack( params ) ) end end diff --git a/Moose Development/Moose/Core/Point.lua b/Moose Development/Moose/Core/Point.lua index 4269fb4cc..39801e785 100644 --- a/Moose Development/Moose/Core/Point.lua +++ b/Moose Development/Moose/Core/Point.lua @@ -74,9 +74,11 @@ POINT_VEC3 = { BARO = "BARO", }, RoutePointType = { + TakeOffParking = "TakeOffParking", TurningPoint = "Turning Point", }, RoutePointAction = { + FromParkingArea = "From Parking Area", TurningPoint = "Turning Point", }, } @@ -99,10 +101,12 @@ do -- POINT_VEC3 --- RoutePoint Types -- @type POINT_VEC3.RoutePointType +-- @field TakeOffParking "TakeOffParking" -- @field TurningPoint "Turning Point" --- RoutePoint Actions -- @type POINT_VEC3.RoutePointAction +-- @field FromParkingArea "From Parking Area" -- @field TurningPoint "Turning Point" -- Constructor. diff --git a/Moose Development/Moose/Core/ScheduleDispatcher.lua b/Moose Development/Moose/Core/ScheduleDispatcher.lua index fc2933cde..277fb7b8e 100644 --- a/Moose Development/Moose/Core/ScheduleDispatcher.lua +++ b/Moose Development/Moose/Core/ScheduleDispatcher.lua @@ -68,10 +68,10 @@ function SCHEDULEDISPATCHER:AddSchedule( Scheduler, ScheduleFunction, ScheduleAr if Scheduler.MasterObject then self.ObjectSchedulers[self.CallID] = Scheduler - self:E( { CallID = self.CallID, ObjectScheduler = tostring(self.ObjectSchedulers[self.CallID]), MasterObject = tostring(Scheduler.MasterObject) } ) + self:F3( { CallID = self.CallID, ObjectScheduler = tostring(self.ObjectSchedulers[self.CallID]), MasterObject = tostring(Scheduler.MasterObject) } ) else self.PersistentSchedulers[self.CallID] = Scheduler - self:E( { CallID = self.CallID, PersistentScheduler = self.PersistentSchedulers[self.CallID] } ) + self:F3( { CallID = self.CallID, PersistentScheduler = self.PersistentSchedulers[self.CallID] } ) end self.Schedule = self.Schedule or setmetatable( {}, { __mode = "k" } ) diff --git a/Moose Development/Moose/Core/Scheduler.lua b/Moose Development/Moose/Core/Scheduler.lua index 39604c2b7..2b68e54bd 100644 --- a/Moose Development/Moose/Core/Scheduler.lua +++ b/Moose Development/Moose/Core/Scheduler.lua @@ -102,7 +102,7 @@ function SCHEDULER:Schedule( SchedulerObject, SchedulerFunction, SchedulerArgume if SchedulerObject and SchedulerObject.ClassName and SchedulerObject.ClassID then ObjectName = SchedulerObject.ClassName .. SchedulerObject.ClassID end - self:E( { "Schedule :", ObjectName, tostring( SchedulerObject ), Start, Repeat, RandomizeFactor, Stop } ) + self:F3( { "Schedule :", ObjectName, tostring( SchedulerObject ), Start, Repeat, RandomizeFactor, Stop } ) self.SchedulerObject = SchedulerObject local ScheduleID = _SCHEDULEDISPATCHER:AddSchedule( diff --git a/Moose Development/Moose/Functional/Spawn.lua b/Moose Development/Moose/Functional/Spawn.lua index 0f4a09686..6560044d5 100644 --- a/Moose Development/Moose/Functional/Spawn.lua +++ b/Moose Development/Moose/Functional/Spawn.lua @@ -602,11 +602,14 @@ function SPAWN:ReSpawn( SpawnIndex ) local SpawnGroup = self:SpawnWithIndex( SpawnIndex ) if SpawnGroup and WayPoints then -- If there were WayPoints set, then Re-Execute those WayPoints! - self:E( WayPoints ) SpawnGroup:WayPointInitialize( WayPoints ) SpawnGroup:WayPointExecute( 1, 5 ) end + if SpawnGroup.ReSpawnFunction then + SpawnGroup:ReSpawnFunction() + end + return SpawnGroup end diff --git a/Moose Development/Moose/Moose.lua b/Moose Development/Moose/Moose.lua index 710bc0da7..ed13ffe2e 100644 --- a/Moose Development/Moose/Moose.lua +++ b/Moose Development/Moose/Moose.lua @@ -42,8 +42,9 @@ Include.File( "Functional/Detection" ) --- AI Classes Include.File( "AI/AI_Balancer" ) Include.File( "AI/AI_Patrol" ) -Include.File( "AI/AI_Cargo" ) +Include.File( "AI/AI_Cap" ) Include.File( "AI/AI_Cas" ) +Include.File( "AI/AI_Cargo" ) --- Actions Include.File( "Actions/Act_Assign" ) diff --git a/Moose Development/Moose/Wrapper/Controllable.lua b/Moose Development/Moose/Wrapper/Controllable.lua index b2a32f951..fd9ec7dec 100644 --- a/Moose Development/Moose/Wrapper/Controllable.lua +++ b/Moose Development/Moose/Wrapper/Controllable.lua @@ -166,6 +166,58 @@ function CONTROLLABLE:_GetController() return nil end +-- Get methods + +--- Returns the UNITs wrappers of the DCS Units of the Controllable (default is a GROUP). +-- @param #CONTROLLABLE self +-- @return #list The UNITs wrappers. +function CONTROLLABLE:GetUnits() + self:F2( { self.ControllableName } ) + local DCSControllable = self:GetDCSObject() + + if DCSControllable then + local DCSUnits = DCSControllable:getUnits() + local Units = {} + for Index, UnitData in pairs( DCSUnits ) do + Units[#Units+1] = UNIT:Find( UnitData ) + end + self:T3( Units ) + return Units + end + + return nil +end + + +--- Returns the health. Dead controllables have health <= 1.0. +-- @param #CONTROLLABLE self +-- @return #number The controllable health value (unit or group average). +-- @return #nil The controllable is not existing or alive. +function CONTROLLABLE:GetLife() + self:F2( self.ControllableName ) + + local DCSControllable = self:GetDCSObject() + + if DCSControllable then + local UnitLife = 0 + local Units = self:GetUnits() + if #Units == 1 then + local Unit = Units[1] -- Wrapper.Unit#UNIT + UnitLife = Unit:GetLife() + else + local UnitLifeTotal = 0 + for UnitID, Unit in pairs( Units ) do + local Unit = Unit -- Wrapper.Unit#UNIT + UnitLifeTotal = UnitLifeTotal + Unit:GetLife() + end + UnitLife = UnitLifeTotal / #Units + end + return UnitLife + end + + return nil +end + -- Tasks @@ -225,7 +277,7 @@ function CONTROLLABLE:SetTask( DCSTask, WaitTime ) if DCSControllable then local Controller = self:_GetController() - self:E(Controller) + self:T3( Controller ) -- When a controllable SPAWNs, it takes about a second to get the controllable in the simulator. Setting tasks to unspawned controllables provides unexpected results. -- Therefore we schedule the functions to set the mission and options for the Controllable. @@ -305,6 +357,10 @@ function CONTROLLABLE:TaskCombo( DCSTasks ) tasks = DCSTasks } } + + for TaskID, Task in ipairs( DCSTasks ) do + self:E( Task ) + end self:T3( { DCSTaskCombo } ) return DCSTaskCombo @@ -490,22 +546,24 @@ function CONTROLLABLE:TaskAttackUnit( AttackUnit, WeaponType, WeaponExpend, Atta -- } local DCSTask - DCSTask = { id = 'AttackUnit', + DCSTask = { + id = 'AttackUnit', params = { - altitudeEnabled = false, + altitudeEnabled = true, unitId = AttackUnit:GetID(), attackQtyLimit = AttackQtyLimit or false, - attackQty = AttackQty or 1, + attackQty = AttackQty or 2, expend = WeaponExpend or "Auto", altitude = 2000, - directionEnabled = false, - groupAttack = false, - weaponType = WeaponType or 1073741822, + directionEnabled = true, + groupAttack = true, + --weaponType = WeaponType or 1073741822, direction = Direction or 0, - }, - }, + } + } - self:E( { DCSTask } ) + self:E( DCSTask ) + return DCSTask end @@ -2217,6 +2275,4 @@ function CONTROLLABLE:WayPointExecute( WayPoint, WaitTime ) return self end --- Message APIs - - +-- Message APIs \ No newline at end of file diff --git a/Moose Development/Moose/Wrapper/Group.lua b/Moose Development/Moose/Wrapper/Group.lua index 1115e8869..8bcd18dfe 100644 --- a/Moose Development/Moose/Wrapper/Group.lua +++ b/Moose Development/Moose/Wrapper/Group.lua @@ -205,6 +205,23 @@ function GROUP:GetDCSObject() return nil end +--- Returns the @{Dcs.DCSTypes#Position3} position vectors indicating the point and direction vectors in 3D of the POSITIONABLE within the mission. +-- @param Wrapper.Positionable#POSITIONABLE self +-- @return Dcs.DCSTypes#Position The 3D position vectors of the POSITIONABLE. +-- @return #nil The POSITIONABLE is not existing or alive. +function GROUP:GetPositionVec3() -- Overridden from POSITIONABLE:GetPositionVec3() + self:F2( self.PositionableName ) + + local DCSPositionable = self:GetDCSObject() + + if DCSPositionable then + local PositionablePosition = DCSPositionable:getUnits()[1]:getPosition().p + self:T3( PositionablePosition ) + return PositionablePosition + end + + return nil +end --- Returns if the DCS Group is alive. -- When the group exists at run-time, this method will return true, otherwise false. @@ -391,26 +408,6 @@ function GROUP:GetInitialSize() return nil end ---- Returns the UNITs wrappers of the DCS Units of the DCS Group. --- @param #GROUP self --- @return #table The UNITs wrappers. -function GROUP:GetUnits() - self:F2( { self.GroupName } ) - local DCSGroup = self:GetDCSObject() - - if DCSGroup then - local DCSUnits = DCSGroup:getUnits() - local Units = {} - for Index, UnitData in pairs( DCSUnits ) do - Units[#Units+1] = UNIT:Find( UnitData ) - end - self:T3( Units ) - return Units - end - - return nil -end - --- Returns the DCS Units of the DCS Group. -- @param #GROUP self @@ -882,4 +879,30 @@ function GROUP:CalculateThreatLevelA2G() return MaxThreatLevelA2G end +--- Returns true if the first unit of the GROUP is in the air. +-- @param Wrapper.Group#GROUP self +-- @return #boolean true if in the first unit of the group is in the air. +-- @return #nil The GROUP is not existing or not alive. +function GROUP:InAir() + self:F2( self.GroupName ) + + local DCSGroup = self:GetDCSObject() + + if DCSGroup then + local DCSUnit = DCSGroup:getUnit(1) + if DCSUnit then + local GroupInAir = DCSGroup:getUnit(1):inAir() + self:T3( GroupInAir ) + return GroupInAir + end + end + + return nil +end + +function GROUP:OnReSpawn( ReSpawnFunction ) + + self.ReSpawnFunction = ReSpawnFunction +end + diff --git a/Moose Development/Moose/Wrapper/Positionable.lua b/Moose Development/Moose/Wrapper/Positionable.lua index 696f64c10..18886abd8 100644 --- a/Moose Development/Moose/Wrapper/Positionable.lua +++ b/Moose Development/Moose/Wrapper/Positionable.lua @@ -45,6 +45,7 @@ POSITIONABLE = { function POSITIONABLE:New( PositionableName ) local self = BASE:Inherit( self, IDENTIFIABLE:New( PositionableName ) ) + self.PositionableName = PositionableName return self end @@ -53,12 +54,12 @@ end -- @return Dcs.DCSTypes#Position The 3D position vectors of the POSITIONABLE. -- @return #nil The POSITIONABLE is not existing or alive. function POSITIONABLE:GetPositionVec3() - self:F2( self.PositionableName ) + self:E( self.PositionableName ) local DCSPositionable = self:GetDCSObject() if DCSPositionable then - local PositionablePosition = DCSPositionable:getPosition() + local PositionablePosition = DCSPositionable:getPosition().p self:T3( PositionablePosition ) return PositionablePosition end @@ -110,6 +111,27 @@ function POSITIONABLE:GetPointVec2() return nil end +--- Returns a POINT_VEC3 object indicating the point in 3D of the POSITIONABLE within the mission. +-- @param Wrapper.Positionable#POSITIONABLE self +-- @return Core.Point#POINT_VEC3 The 3D point vector of the POSITIONABLE. +-- @return #nil The POSITIONABLE is not existing or alive. +function POSITIONABLE:GetPointVec3() + self:F2( self.PositionableName ) + + local DCSPositionable = self:GetDCSObject() + + if DCSPositionable then + local PositionableVec3 = self:GetPositionVec3() + + local PositionablePointVec3 = POINT_VEC3:NewFromVec3( PositionableVec3 ) + + self:T2( PositionablePointVec3 ) + return PositionablePointVec3 + end + + return nil +end + --- Returns a random @{Dcs.DCSTypes#Vec3} vector within a range, indicating the point in 3D of the POSITIONABLE within the mission. -- @param Wrapper.Positionable#POSITIONABLE self @@ -219,20 +241,13 @@ end --- Returns true if the POSITIONABLE is in the air. +-- Polymorphic, is overridden in GROUP and UNIT. -- @param Wrapper.Positionable#POSITIONABLE self -- @return #boolean true if in the air. -- @return #nil The POSITIONABLE is not existing or alive. function POSITIONABLE:InAir() self:F2( self.PositionableName ) - local DCSPositionable = self:GetDCSObject() - - if DCSPositionable then - local PositionableInAir = DCSPositionable:inAir() - self:T3( PositionableInAir ) - return PositionableInAir - end - return nil end diff --git a/Moose Development/Moose/Wrapper/Unit.lua b/Moose Development/Moose/Wrapper/Unit.lua index 65657e3c5..2b9d30b89 100644 --- a/Moose Development/Moose/Wrapper/Unit.lua +++ b/Moose Development/Moose/Wrapper/Unit.lua @@ -467,6 +467,25 @@ function UNIT:GetFuel() return nil end +--- Returns the UNIT in a UNIT list of one element. +-- @param #UNIT self +-- @return #list The UNITs wrappers. +function UNIT:GetUnits() + self:F2( { self.UnitName } ) + local DCSUnit = self:GetDCSObject() + + if DCSUnit then + local DCSUnits = DCSUnit:getUnits() + local Units = {} + Units[1] = UNIT:Find( DCSUnit ) + self:T3( Units ) + return Units + end + + return nil +end + + --- Returns the unit's health. Dead units has health <= 1.0. -- @param #UNIT self -- @return #number The Unit's health value. @@ -799,3 +818,21 @@ function UNIT:IsShip() return nil end +--- Returns true if the UNIT is in the air. +-- @param Wrapper.Positionable#UNIT self +-- @return #boolean true if in the air. +-- @return #nil The UNIT is not existing or alive. +function UNIT:InAir() + self:F2( self.UnitName ) + + local DCSUnit = self:GetDCSObject() + + if DCSUnit then + local UnitInAir = DCSUnit:inAir() + self:T3( UnitInAir ) + return UnitInAir + end + + return nil +end + diff --git a/Moose Mission Setup/Moose Mission Update/l10n/DEFAULT/Moose.lua b/Moose Mission Setup/Moose Mission Update/l10n/DEFAULT/Moose.lua index 1e630b10b..e02bdb889 100644 --- a/Moose Mission Setup/Moose Mission Update/l10n/DEFAULT/Moose.lua +++ b/Moose Mission Setup/Moose Mission Update/l10n/DEFAULT/Moose.lua @@ -1,5 +1,5 @@ env.info( '*** MOOSE STATIC INCLUDE START *** ' ) -env.info( 'Moose Generation Timestamp: 20170113_2007' ) +env.info( 'Moose Generation Timestamp: 20170117_1202' ) local base = _G Include = {} @@ -3890,7 +3890,7 @@ function SCHEDULER:Schedule( SchedulerObject, SchedulerFunction, SchedulerArgume if SchedulerObject and SchedulerObject.ClassName and SchedulerObject.ClassID then ObjectName = SchedulerObject.ClassName .. SchedulerObject.ClassID end - self:E( { "Schedule :", ObjectName, tostring( SchedulerObject ), Start, Repeat, RandomizeFactor, Stop } ) + self:F3( { "Schedule :", ObjectName, tostring( SchedulerObject ), Start, Repeat, RandomizeFactor, Stop } ) self.SchedulerObject = SchedulerObject local ScheduleID = _SCHEDULEDISPATCHER:AddSchedule( @@ -4019,10 +4019,10 @@ function SCHEDULEDISPATCHER:AddSchedule( Scheduler, ScheduleFunction, ScheduleAr if Scheduler.MasterObject then self.ObjectSchedulers[self.CallID] = Scheduler - self:E( { CallID = self.CallID, ObjectScheduler = tostring(self.ObjectSchedulers[self.CallID]), MasterObject = tostring(Scheduler.MasterObject) } ) + self:F3( { CallID = self.CallID, ObjectScheduler = tostring(self.ObjectSchedulers[self.CallID]), MasterObject = tostring(Scheduler.MasterObject) } ) else self.PersistentSchedulers[self.CallID] = Scheduler - self:E( { CallID = self.CallID, PersistentScheduler = self.PersistentSchedulers[self.CallID] } ) + self:F3( { CallID = self.CallID, PersistentScheduler = self.PersistentSchedulers[self.CallID] } ) end self.Schedule = self.Schedule or setmetatable( {}, { __mode = "k" } ) @@ -9795,9 +9795,11 @@ POINT_VEC3 = { BARO = "BARO", }, RoutePointType = { + TakeOffParking = "TakeOffParking", TurningPoint = "Turning Point", }, RoutePointAction = { + FromParkingArea = "From Parking Area", TurningPoint = "Turning Point", }, } @@ -9820,10 +9822,12 @@ do -- POINT_VEC3 --- RoutePoint Types -- @type POINT_VEC3.RoutePointType +-- @field TakeOffParking "TakeOffParking" -- @field TurningPoint "Turning Point" --- RoutePoint Actions -- @type POINT_VEC3.RoutePointAction +-- @field FromParkingArea "From Parking Area" -- @field TurningPoint "Turning Point" -- Constructor. @@ -11245,14 +11249,21 @@ do -- FSM function FSM._handler( self, EventName, ... ) - self:E( { EventName, ... } ) - local Can, to = self:can( EventName ) - self:E( { From = self.current, Event = EventName, To = to, Can = Can } ) + + if to == "*" then + to = self.current + end if Can then local from = self.current local params = { from, EventName, to, ... } + + if self.Controllable then + self:E( "FSM Transition for " .. self.Controllable.ControllableName .. " :" .. self.current .. " --> " .. EventName .. " --> " .. to ) + else + self:E( "FSM Transition:" .. self.current .. " --> " .. EventName .. " --> " .. to ) + end if self:_call_handler("onbefore" .. EventName, params) == false or self:_call_handler("OnBefore" .. EventName, params) == false @@ -11302,6 +11313,9 @@ do -- FSM self:_call_handler("onstatechange", params) end + else + self:E( "Cannot execute transition." ) + self:E( { From = self.current, Event = EventName, To = to, Can = Can } ) end return nil @@ -11377,7 +11391,6 @@ do -- FSM end function FSM:can(e) - self:E( { e, self.Events, self.Events[e] } ) local Event = self.Events[e] self:F3( { self.current, Event } ) local To = Event and Event.map[self.current] or Event.map['*'] @@ -11446,7 +11459,7 @@ do -- FSM_CONTROLLABLE end if self[handler] then - self:E( "Calling " .. handler ) + self:F3( "Calling " .. handler ) return xpcall( function() return self[handler]( self, self.Controllable, unpack( params ) ) end, ErrorHandler ) --return self[handler]( self, self.Controllable, unpack( params ) ) end @@ -11737,7 +11750,7 @@ do -- FSM_SET function FSM_SET:_call_handler( handler, params ) if self[handler] then - self:E( "Calling " .. handler ) + self:T( "Calling " .. handler ) return self[handler]( self, self.Set, unpack( params ) ) end end @@ -12105,6 +12118,7 @@ POSITIONABLE = { function POSITIONABLE:New( PositionableName ) local self = BASE:Inherit( self, IDENTIFIABLE:New( PositionableName ) ) + self.PositionableName = PositionableName return self end @@ -12113,12 +12127,12 @@ end -- @return Dcs.DCSTypes#Position The 3D position vectors of the POSITIONABLE. -- @return #nil The POSITIONABLE is not existing or alive. function POSITIONABLE:GetPositionVec3() - self:F2( self.PositionableName ) + self:E( self.PositionableName ) local DCSPositionable = self:GetDCSObject() if DCSPositionable then - local PositionablePosition = DCSPositionable:getPosition() + local PositionablePosition = DCSPositionable:getPosition().p self:T3( PositionablePosition ) return PositionablePosition end @@ -12170,6 +12184,27 @@ function POSITIONABLE:GetPointVec2() return nil end +--- Returns a POINT_VEC3 object indicating the point in 3D of the POSITIONABLE within the mission. +-- @param Wrapper.Positionable#POSITIONABLE self +-- @return Core.Point#POINT_VEC3 The 3D point vector of the POSITIONABLE. +-- @return #nil The POSITIONABLE is not existing or alive. +function POSITIONABLE:GetPointVec3() + self:F2( self.PositionableName ) + + local DCSPositionable = self:GetDCSObject() + + if DCSPositionable then + local PositionableVec3 = self:GetPositionVec3() + + local PositionablePointVec3 = POINT_VEC3:NewFromVec3( PositionableVec3 ) + + self:T2( PositionablePointVec3 ) + return PositionablePointVec3 + end + + return nil +end + --- Returns a random @{Dcs.DCSTypes#Vec3} vector within a range, indicating the point in 3D of the POSITIONABLE within the mission. -- @param Wrapper.Positionable#POSITIONABLE self @@ -12279,20 +12314,13 @@ end --- Returns true if the POSITIONABLE is in the air. +-- Polymorphic, is overridden in GROUP and UNIT. -- @param Wrapper.Positionable#POSITIONABLE self -- @return #boolean true if in the air. -- @return #nil The POSITIONABLE is not existing or alive. function POSITIONABLE:InAir() self:F2( self.PositionableName ) - local DCSPositionable = self:GetDCSObject() - - if DCSPositionable then - local PositionableInAir = DCSPositionable:inAir() - self:T3( PositionableInAir ) - return PositionableInAir - end - return nil end @@ -12648,6 +12676,58 @@ function CONTROLLABLE:_GetController() return nil end +-- Get methods + +--- Returns the UNITs wrappers of the DCS Units of the Controllable (default is a GROUP). +-- @param #CONTROLLABLE self +-- @return #list The UNITs wrappers. +function CONTROLLABLE:GetUnits() + self:F2( { self.ControllableName } ) + local DCSControllable = self:GetDCSObject() + + if DCSControllable then + local DCSUnits = DCSControllable:getUnits() + local Units = {} + for Index, UnitData in pairs( DCSUnits ) do + Units[#Units+1] = UNIT:Find( UnitData ) + end + self:T3( Units ) + return Units + end + + return nil +end + + +--- Returns the health. Dead controllables have health <= 1.0. +-- @param #CONTROLLABLE self +-- @return #number The controllable health value (unit or group average). +-- @return #nil The controllable is not existing or alive. +function CONTROLLABLE:GetLife() + self:F2( self.ControllableName ) + + local DCSControllable = self:GetDCSObject() + + if DCSControllable then + local UnitLife = 0 + local Units = self:GetUnits() + if #Units == 1 then + local Unit = Units[1] -- Wrapper.Unit#UNIT + UnitLife = Unit:GetLife() + else + local UnitLifeTotal = 0 + for UnitID, Unit in pairs( Units ) do + local Unit = Unit -- Wrapper.Unit#UNIT + UnitLifeTotal = UnitLifeTotal + Unit:GetLife() + end + UnitLife = UnitLifeTotal / #Units + end + return UnitLife + end + + return nil +end + -- Tasks @@ -12707,7 +12787,7 @@ function CONTROLLABLE:SetTask( DCSTask, WaitTime ) if DCSControllable then local Controller = self:_GetController() - self:E(Controller) + self:T3( Controller ) -- When a controllable SPAWNs, it takes about a second to get the controllable in the simulator. Setting tasks to unspawned controllables provides unexpected results. -- Therefore we schedule the functions to set the mission and options for the Controllable. @@ -12787,6 +12867,10 @@ function CONTROLLABLE:TaskCombo( DCSTasks ) tasks = DCSTasks } } + + for TaskID, Task in ipairs( DCSTasks ) do + self:E( Task ) + end self:T3( { DCSTaskCombo } ) return DCSTaskCombo @@ -12972,22 +13056,24 @@ function CONTROLLABLE:TaskAttackUnit( AttackUnit, WeaponType, WeaponExpend, Atta -- } local DCSTask - DCSTask = { id = 'AttackUnit', + DCSTask = { + id = 'AttackUnit', params = { - altitudeEnabled = false, + altitudeEnabled = true, unitId = AttackUnit:GetID(), attackQtyLimit = AttackQtyLimit or false, - attackQty = AttackQty or 1, + attackQty = AttackQty or 2, expend = WeaponExpend or "Auto", altitude = 2000, - directionEnabled = false, - groupAttack = false, - weaponType = WeaponType or 1073741822, + directionEnabled = true, + groupAttack = true, + --weaponType = WeaponType or 1073741822, direction = Direction or 0, - }, - }, + } + } - self:E( { DCSTask } ) + self:E( DCSTask ) + return DCSTask end @@ -14699,10 +14785,7 @@ function CONTROLLABLE:WayPointExecute( WayPoint, WaitTime ) return self end --- Message APIs - - ---- This module contains the GROUP class. +-- Message APIs--- This module contains the GROUP class. -- -- 1) @{Wrapper.Group#GROUP} class, extends @{Wrapper.Controllable#CONTROLLABLE} -- ============================================================= @@ -14909,6 +14992,23 @@ function GROUP:GetDCSObject() return nil end +--- Returns the @{Dcs.DCSTypes#Position3} position vectors indicating the point and direction vectors in 3D of the POSITIONABLE within the mission. +-- @param Wrapper.Positionable#POSITIONABLE self +-- @return Dcs.DCSTypes#Position The 3D position vectors of the POSITIONABLE. +-- @return #nil The POSITIONABLE is not existing or alive. +function GROUP:GetPositionVec3() -- Overridden from POSITIONABLE:GetPositionVec3() + self:F2( self.PositionableName ) + + local DCSPositionable = self:GetDCSObject() + + if DCSPositionable then + local PositionablePosition = DCSPositionable:getUnits()[1]:getPosition().p + self:T3( PositionablePosition ) + return PositionablePosition + end + + return nil +end --- Returns if the DCS Group is alive. -- When the group exists at run-time, this method will return true, otherwise false. @@ -15095,26 +15195,6 @@ function GROUP:GetInitialSize() return nil end ---- Returns the UNITs wrappers of the DCS Units of the DCS Group. --- @param #GROUP self --- @return #table The UNITs wrappers. -function GROUP:GetUnits() - self:F2( { self.GroupName } ) - local DCSGroup = self:GetDCSObject() - - if DCSGroup then - local DCSUnits = DCSGroup:getUnits() - local Units = {} - for Index, UnitData in pairs( DCSUnits ) do - Units[#Units+1] = UNIT:Find( UnitData ) - end - self:T3( Units ) - return Units - end - - return nil -end - --- Returns the DCS Units of the DCS Group. -- @param #GROUP self @@ -15586,6 +15666,32 @@ function GROUP:CalculateThreatLevelA2G() return MaxThreatLevelA2G end +--- Returns true if the first unit of the GROUP is in the air. +-- @param Wrapper.Group#GROUP self +-- @return #boolean true if in the first unit of the group is in the air. +-- @return #nil The GROUP is not existing or not alive. +function GROUP:InAir() + self:F2( self.GroupName ) + + local DCSGroup = self:GetDCSObject() + + if DCSGroup then + local DCSUnit = DCSGroup:getUnit(1) + if DCSUnit then + local GroupInAir = DCSGroup:getUnit(1):inAir() + self:T3( GroupInAir ) + return GroupInAir + end + end + + return nil +end + +function GROUP:OnReSpawn( ReSpawnFunction ) + + self.ReSpawnFunction = ReSpawnFunction +end + --- This module contains the UNIT class. -- @@ -16056,6 +16162,25 @@ function UNIT:GetFuel() return nil end +--- Returns the UNIT in a UNIT list of one element. +-- @param #UNIT self +-- @return #list The UNITs wrappers. +function UNIT:GetUnits() + self:F2( { self.UnitName } ) + local DCSUnit = self:GetDCSObject() + + if DCSUnit then + local DCSUnits = DCSUnit:getUnits() + local Units = {} + Units[1] = UNIT:Find( DCSUnit ) + self:T3( Units ) + return Units + end + + return nil +end + + --- Returns the unit's health. Dead units has health <= 1.0. -- @param #UNIT self -- @return #number The Unit's health value. @@ -16388,6 +16513,24 @@ function UNIT:IsShip() return nil end +--- Returns true if the UNIT is in the air. +-- @param Wrapper.Positionable#UNIT self +-- @return #boolean true if in the air. +-- @return #nil The UNIT is not existing or alive. +function UNIT:InAir() + self:F2( self.UnitName ) + + local DCSUnit = self:GetDCSObject() + + if DCSUnit then + local UnitInAir = DCSUnit:inAir() + self:T3( UnitInAir ) + return UnitInAir + end + + return nil +end + --- This module contains the CLIENT class. -- -- 1) @{Wrapper.Client#CLIENT} class, extends @{Wrapper.Unit#UNIT} @@ -18801,11 +18944,14 @@ function SPAWN:ReSpawn( SpawnIndex ) local SpawnGroup = self:SpawnWithIndex( SpawnIndex ) if SpawnGroup and WayPoints then -- If there were WayPoints set, then Re-Execute those WayPoints! - self:E( WayPoints ) SpawnGroup:WayPointInitialize( WayPoints ) SpawnGroup:WayPointExecute( 1, 5 ) end + if SpawnGroup.ReSpawnFunction then + SpawnGroup:ReSpawnFunction() + end + return SpawnGroup end @@ -24206,13 +24352,12 @@ function DETECTION_AREAS:CreateDetectionSets() end ---- SP:N MP:Y AI:Y HU:N TYP:A -- This module contains the AI_BALANCER class. AI Balancing will replace in multi player missions +--- Single-Player:**No** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**All** -- **AI Balancing will replace in multi player missions -- non-occupied human slots with AI groups, in order to provide an engaging simulation environment, --- even when there are hardly any players in the mission. +-- even when there are hardly any players in the mission.** -- -- ![Banner Image](..\Presentations\AI_Balancer\Dia1.JPG) -- --- Examples can be found in the test missions. -- -- === -- @@ -24281,6 +24426,8 @@ end -- -- Hereby the change log: -- +-- 2017-01-17: There is still a problem with AI being destroyed, but not respawned. Need to check further upon that. +-- -- 2017-01-08: AI_BALANCER:**InitSpawnInterval( Earliest, Latest )** added. -- -- === @@ -24290,7 +24437,6 @@ end -- ### Contributions: -- -- * **[Dutch_Baron](https://forums.eagle.ru/member.php?u=112075)**: Working together with James has resulted in the creation of the AI_BALANCER class. James has shared his ideas on balancing AI with air units, and together we made a first design which you can use now :-) --- -- * **SNAFU**: Had a couple of mails with the guys to validate, if the same concept in the GCI/CAP script could be reworked within MOOSE. None of the script code has been used however within the new AI_BALANCER moose class. -- -- ### Authors: @@ -24439,16 +24585,15 @@ end --- @param #AI_BALANCER self function AI_BALANCER:onenterMonitoring( SetGroup ) - self:E( { self.SetClient:Count() } ) - self.SetClient:Flush() + self:T2( { self.SetClient:Count() } ) + --self.SetClient:Flush() self.SetClient:ForEachClient( --- @param Wrapper.Client#CLIENT Client function( Client ) - self:E(Client.ClientName) + self:T3(Client.ClientName) local AIGroup = self.Set:Get( Client.UnitName ) -- Wrapper.Group#GROUP - self:E({Client:IsAlive()}) if Client:IsAlive() then if AIGroup and AIGroup:IsAlive() == true then @@ -24463,16 +24608,16 @@ function AI_BALANCER:onenterMonitoring( SetGroup ) local PlayerInRange = { Value = false } local RangeZone = ZONE_RADIUS:New( 'RangeZone', AIGroup:GetVec2(), self.ReturnTresholdRange ) - self:E( RangeZone ) + self:T2( RangeZone ) _DATABASE:ForEachPlayer( --- @param Wrapper.Unit#UNIT RangeTestUnit function( RangeTestUnit, RangeZone, AIGroup, PlayerInRange ) - self:E( { PlayerInRange, RangeTestUnit.UnitName, RangeZone.ZoneName } ) + self:T2( { PlayerInRange, RangeTestUnit.UnitName, RangeZone.ZoneName } ) if RangeTestUnit:IsInZone( RangeZone ) == true then - self:E( "in zone" ) + self:T2( "in zone" ) if RangeTestUnit:GetCoalition() ~= AIGroup:GetCoalition() then - self:E( "in range" ) + self:T2( "in range" ) PlayerInRange.Value = true end end @@ -24493,7 +24638,7 @@ function AI_BALANCER:onenterMonitoring( SetGroup ) end else if not AIGroup or not AIGroup:IsAlive() == true then - self:E( "Client " .. Client.UnitName .. " not alive." ) + self:T( "Client " .. Client.UnitName .. " not alive." ) if not self.SpawnQueue[Client.UnitName] then -- Spawn a new AI taking into account the spawn interval Earliest, Latest self:__Spawn( math.random( self.Earliest, self.Latest ), Client.UnitName ) @@ -24511,113 +24656,125 @@ end ---- (AI) (FSM) Make AI patrol routes or zones. +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Air Patrolling or Staging.** +-- +-- ![Banner Image](..\Presentations\AI_Patrol\Dia1.JPG) +-- -- -- === -- --- 1) @{#AI_PATROLZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} --- ================================================================ --- The @{#AI_PATROLZONE} class implements the core functions to patrol a @{Zone} by an AIR @{Controllable} @{Group}. --- The patrol algorithm works that for each airplane patrolling, upon arrival at the patrol zone, --- a random point is selected as the route point within the 3D space, within the given boundary limits. --- The airplane will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. --- Upon arrival at the random 3D point, a new 3D random point will be selected within the patrol zone using the given limits. --- This cycle will continue until a fuel treshold has been reached by the airplane. +-- # 1) @{#AI_PATROL_ZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} +-- +-- The @{#AI_PATROL_ZONE} class implements the core functions to patrol a @{Zone} by an AI @{Controllable} or @{Group}. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia3.JPG) +-- +-- The AI_PATROL_ZONE is assigned a @(Group) and this must be done before the AI_PATROL_ZONE process can be started using the **Start** event. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia4.JPG) +-- +-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia5.JPG) +-- +-- This cycle will continue. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia6.JPG) +-- +-- During the patrol, the AI will detect enemy targets, which are reported through the **Detected** event. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia9.JPG) +-- +---- Note that the enemy is not engaged! To model enemy engagement, either tailor the **Detected** event, or +-- use derived AI_ classes to model AI offensive or defensive behaviour. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia10.JPG) +-- +-- Until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. -- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. -- --- 1.1) AI_PATROLZONE constructor: --- ---------------------------- +-- ![Process](..\Presentations\AI_Patrol\Dia11.JPG) +-- +-- ## 1.1) AI_PATROL_ZONE constructor -- --- * @{#AI_PATROLZONE.New}(): Creates a new AI_PATROLZONE object. +-- * @{#AI_PATROL_ZONE.New}(): Creates a new AI_PATROL_ZONE object. -- --- 1.2) AI_PATROLZONE state machine: --- ---------------------------------- --- The AI_PATROLZONE is a state machine: it manages the different events and states of the AIControllable it is controlling. +-- ## 1.2) AI_PATROL_ZONE is a FSM -- --- ### 1.2.1) AI_PATROLZONE Events: +-- ![Process](..\Presentations\AI_Patrol\Dia2.JPG) -- --- * @{#AI_PATROLZONE.Route}( AIControllable ): A new 3D route point is selected and the AIControllable will fly towards that point with the given speed. --- * @{#AI_PATROLZONE.Patrol}( AIControllable ): The AIControllable reports it is patrolling. This event is called every 30 seconds. --- * @{#AI_PATROLZONE.RTB}( AIControllable ): The AIControllable will report return to base. --- * @{#AI_PATROLZONE.End}( AIControllable ): The end of the AI_PATROLZONE process. --- * @{#AI_PATROLZONE.Dead}( AIControllable ): The AIControllable is dead. The AI_PATROLZONE process will be ended. +-- ### 1.2.1) AI_PATROL_ZONE States -- --- ### 1.2.2) AI_PATROLZONE States: +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Returning** ( Group ): The AI is returning to Base.. -- --- * **Route**: A new 3D route point is selected and the AIControllable will fly towards that point with the given speed. --- * **Patrol**: The AIControllable is patrolling. This state is set every 30 seconds, so every 30 seconds, a state transition method can be used. --- * **RTB**: The AIControllable reports it wants to return to the base. --- * **Dead**: The AIControllable is dead ... --- * **End**: The process has come to an end. --- --- ### 1.2.3) AI_PATROLZONE state transition methods: +-- ### 1.2.2) AI_PATROL_ZONE Events -- --- State transition functions can be set **by the mission designer** customizing or improving the behaviour of the state. --- There are 2 moments when state transition methods will be called by the state machine: --- --- * **Before** the state transition. --- The state transition method needs to start with the name **OnBefore + the name of the state**. --- If the state transition method returns false, then the processing of the state transition will not be done! --- If you want to change the behaviour of the AIControllable at this event, return false, --- but then you'll need to specify your own logic using the AIControllable! --- --- * **After** the state transition. --- The state transition method needs to start with the name **OnAfter + the name of the state**. --- These state transition methods need to provide a return value, which is specified at the function description. --- --- An example how to manage a state transition for an AI_PATROLZONE object **Patrol** for the state **RTB**: --- --- local PatrolZoneGroup = GROUP:FindByName( "Patrol Zone" ) --- local PatrolZone = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) --- --- local PatrolSpawn = SPAWN:New( "Patrol Group" ) --- local PatrolGroup = PatrolSpawn:Spawn() --- --- local Patrol = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 300, 600 ) --- Patrol:SetControllable( PatrolGroup ) --- Patrol:ManageFuel( 0.2, 60 ) --- --- **OnBefore**RTB( AIGroup ) will be called by the AI_PATROLZONE object when the AIGroup reports RTB, but **before** the RTB default action is processed by the AI_PATROLZONE object. --- --- --- State transition function for the AI_PATROLZONE **Patrol** object --- -- @param #AI_PATROLZONE self --- -- @param Wrapper.Controllable#CONTROLLABLE AIGroup --- -- @return #boolean If false is returned, then the OnAfter state transition method will not be called. --- function Patrol:OnBeforeRTB( AIGroup ) --- AIGroup:MessageToRed( "Returning to base", 20 ) --- end --- --- **OnAfter**RTB( AIGroup ) will be called by the AI_PATROLZONE object when the AIGroup reports RTB, but **after** the RTB default action was processed by the AI_PATROLZONE object. --- --- --- State transition function for the AI_PATROLZONE **Patrol** object --- -- @param #AI_PATROLZONE self --- -- @param Wrapper.Controllable#CONTROLLABLE AIGroup --- -- @return #Wrapper.Controllable#CONTROLLABLE The new AIGroup object that is set to be patrolling the zone. --- function Patrol:OnAfterRTB( AIGroup ) --- return PatrolSpawn:Spawn() --- end +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. -- --- 1.3) Manage the AI_PATROLZONE parameters: --- ------------------------------------------ --- The following methods are available to modify the parameters of a AI_PATROLZONE object: +-- ## 1.3) Set or Get the AI controllable -- --- * @{#AI_PATROLZONE.SetControllable}(): Set the AIControllable. --- * @{#AI_PATROLZONE.GetControllable}(): Get the AIControllable. --- * @{#AI_PATROLZONE.SetSpeed}(): Set the patrol speed of the AI, for the next patrol. --- * @{#AI_PATROLZONE.SetAltitude}(): Set altitude of the AI, for the next patrol. +-- * @{#AI_PATROL_ZONE.SetControllable}(): Set the AIControllable. +-- * @{#AI_PATROL_ZONE.GetControllable}(): Get the AIControllable. +-- +-- ## 1.4) Set the Speed and Altitude boundaries of the AI controllable +-- +-- * @{#AI_PATROL_ZONE.SetSpeed}(): Set the patrol speed boundaries of the AI, for the next patrol. +-- * @{#AI_PATROL_ZONE.SetAltitude}(): Set altitude boundaries of the AI, for the next patrol. -- --- 1.3) Manage the out of fuel in the AI_PATROLZONE: --- ---------------------------------------------- --- When the AIControllable is out of fuel, it is required that a new AIControllable is started, before the old AIControllable can return to the home base. +-- ## 1.5) Manage the detection process of the AI controllable +-- +-- The detection process of the AI controllable can be manipulated. +-- Detection requires an amount of CPU power, which has an impact on your mission performance. +-- Only put detection on when absolutely necessary, and the frequency of the detection can also be set. +-- +-- * @{#AI_PATROL_ZONE.SetDetectionOn}(): Set the detection on. The AI will detect for targets. +-- * @{#AI_PATROL_ZONE.SetDetectionOff}(): Set the detection off, the AI will not detect for targets. The existing target list will NOT be erased. +-- +-- The detection frequency can be set with @{#AI_PATROL_ZONE.SetDetectionInterval}( seconds ), where the amount of seconds specify how much seconds will be waited before the next detection. +-- Use the method @{#AI_PATROL_ZONE.GetDetectedUnits}() to obtain a list of the @{Unit}s detected by the AI. +-- +-- The detection can be filtered to potential targets in a specific zone. +-- Use the method @{#AI_PATROL_ZONE.SetDetectionZone}() to set the zone where targets need to be detected. +-- Note that when the zone is too far away, or the AI is not heading towards the zone, or the AI is too high, no targets may be detected +-- according the weather conditions. +-- +-- ## 1.6) Manage the "out of fuel" in the AI_PATROL_ZONE +-- +-- When the AI is out of fuel, it is required that a new AI is started, before the old AI can return to the home base. -- Therefore, with a parameter and a calculation of the distance to the home base, the fuel treshold is calculated. --- When the fuel treshold is reached, the AIControllable will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROLZONE. --- Once the time is finished, the old AIControllable will return to the base. --- Use the method @{#AI_PATROLZONE.ManageFuel}() to have this proces in place. +-- When the fuel treshold is reached, the AI will continue for a given time its patrol task in orbit, +-- while a new AI is targetted to the AI_PATROL_ZONE. +-- Once the time is finished, the old AI will return to the base. +-- Use the method @{#AI_PATROL_ZONE.ManageFuel}() to have this proces in place. +-- +-- ## 1.7) Manage "damage" behaviour of the AI in the AI_PATROL_ZONE +-- +-- When the AI is damaged, it is required that a new AIControllable is started. However, damage cannon be foreseen early on. +-- Therefore, when the damage treshold is reached, the AI will return immediately to the home base (RTB). +-- Use the method @{#AI_PATROL_ZONE.ManageDamage}() to have this proces in place. -- -- ==== -- --- **API CHANGE HISTORY** --- ====================== +-- # **OPEN ISSUES** +-- +-- 2017-01-17: When Spawned AI is located at an airbase, it will be routed first back to the airbase after take-off. +-- +-- 2016-01-17: +-- -- Fixed problem with AI returning to base too early and unexpected. +-- -- ReSpawning of AI will reset the AI_PATROL and derived classes. +-- -- Checked the correct workings of SCHEDULER, and it DOES work correctly. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** -- -- The underlying change log documents the API changes. Please read this carefully. The following notation is used: -- @@ -24626,257 +24783,282 @@ end -- -- Hereby the change log: -- +-- 2017-01-17: Rename of class: **AI\_PATROL\_ZONE** is the new name for the old _AI\_PATROLZONE_. +-- +-- 2017-01-15: Complete revision. AI_PATROL_ZONE is the base class for other AI_PATROL like classes. +-- -- 2016-09-01: Initial class and API. -- -- === -- --- AUTHORS and CONTRIBUTIONS --- ========================= +-- # **AUTHORS and CONTRIBUTIONS** -- -- ### Contributions: -- --- * **DutchBaron**: Testing. --- * **Pikey**: Testing and API concept review. +-- * **[Dutch_Baron](https://forums.eagle.ru/member.php?u=112075)**: Working together with James has resulted in the creation of the AI_BALANCER class. James has shared his ideas on balancing AI with air units, and together we made a first design which you can use now :-) +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Testing and API concept review. -- -- ### Authors: -- -- * **FlightControl**: Design & Programming. -- --- -- @module AI_Patrol ---- AI_PATROLZONE class --- @type AI_PATROLZONE +--- AI_PATROL_ZONE class +-- @type AI_PATROL_ZONE -- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. -- @field Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. -- @field Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @field Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. -- @field Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @field Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @field Functional.Spawn#SPAWN CoordTest -- @extends Core.Fsm#FSM_CONTROLLABLE -AI_PATROLZONE = { - ClassName = "AI_PATROLZONE", +AI_PATROL_ZONE = { + ClassName = "AI_PATROL_ZONE", } - - ---- Creates a new AI_PATROLZONE object --- @param #AI_PATROLZONE self +--- Creates a new AI_PATROL_ZONE object +-- @param #AI_PATROL_ZONE self -- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. -- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @return #AI_PATROLZONE self +-- @return #AI_PATROL_ZONE self -- @usage --- -- Define a new AI_PATROLZONE Object. This PatrolArea will patrol an AIControllable within PatrolZone between 3000 and 6000 meters, with a variying speed between 600 and 900 km/h. +-- -- Define a new AI_PATROL_ZONE Object. This PatrolArea will patrol an AIControllable within PatrolZone between 3000 and 6000 meters, with a variying speed between 600 and 900 km/h. -- PatrolZone = ZONE:New( 'PatrolZone' ) -- PatrolSpawn = SPAWN:New( 'Patrol Group' ) --- PatrolArea = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 600, 900 ) -function AI_PATROLZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) +-- PatrolArea = AI_PATROL_ZONE:New( PatrolZone, 3000, 6000, 600, 900 ) +function AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) -- Inherits from BASE - local self = BASE:Inherit( self, FSM_CONTROLLABLE:New() ) -- Core.Fsm#FSM_CONTROLLABLE + local self = BASE:Inherit( self, FSM_CONTROLLABLE:New() ) -- #AI_PATROL_ZONE - self.PatrolZone = PatrolZone + self.PatrolZone = PatrolZone self.PatrolFloorAltitude = PatrolFloorAltitude self.PatrolCeilingAltitude = PatrolCeilingAltitude self.PatrolMinSpeed = PatrolMinSpeed self.PatrolMaxSpeed = PatrolMaxSpeed - self.PatrolFuelTresholdPercentage = 0.2 + self:SetDetectionOn() + self.CheckStatus = true - self:SetStartState( "None" ) + self:ManageFuel( .2, 60 ) + self:ManageDamage( 1 ) + + self:SetDetectionInterval( 30 ) -do self:AddTransition( "*", "Start", "Route" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. + self.DetectedUnits = {} -- This table contains the targets detected during patrol. + + self:SetStartState( "None" ) - --- OnLeave State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnLeaveRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. + self:AddTransition( "None", "Start", "Patrolling" ) - --- OnEnter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnEnterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnBefore Transition Handler for Event Start. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeStart +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Start. +-- @function [parent=#AI_PATROL_ZONE] OnAfterStart +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Start. - -- @function [parent=#AI_PATROLZONE] OnBeforeStart - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Start. +-- @function [parent=#AI_PATROL_ZONE] Start +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Start. - -- @function [parent=#AI_PATROLZONE] OnAfterStart - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Start. +-- @function [parent=#AI_PATROL_ZONE] __Start +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Patrolling. +-- @function [parent=#AI_PATROL_ZONE] OnLeavePatrolling +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Patrolling. +-- @function [parent=#AI_PATROL_ZONE] OnEnterPatrolling +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Patrolling", "Route", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event Route. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeRoute +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Route. +-- @function [parent=#AI_PATROL_ZONE] OnAfterRoute +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Start. - -- @function [parent=#AI_PATROLZONE] Start - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event Route. +-- @function [parent=#AI_PATROL_ZONE] Route +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Start - -- @function [parent=#AI_PATROLZONE] __Start - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event Route. +-- @function [parent=#AI_PATROL_ZONE] __Route +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE + self:AddTransition( "*", "Status", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. -do self:AddTransition( "*", "Route", "Route" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnBefore Transition Handler for Event Status. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeStatus +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnLeaveRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnEnterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnAfter Transition Handler for Event Status. +-- @function [parent=#AI_PATROL_ZONE] OnAfterStatus +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnBeforeRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Status. +-- @function [parent=#AI_PATROL_ZONE] Status +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnAfterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Status. +-- @function [parent=#AI_PATROL_ZONE] __Status +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Detect", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeDetect +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] OnAfterDetect +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Route. - -- @function [parent=#AI_PATROLZONE] Route - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] Detect +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Route - -- @function [parent=#AI_PATROLZONE] __Route - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] __Detect +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE + self:AddTransition( "*", "Detected", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. -do self:AddTransition( "*", "Patrol", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnBefore Transition Handler for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeDetected +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnLeavePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnEnterPatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnAfter Transition Handler for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] OnAfterDetected +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnBeforePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] Detected +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnAfterPatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] __Detected +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "RTB", "Returning" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeRTB +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] OnAfterRTB +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Patrol. - -- @function [parent=#AI_PATROLZONE] Patrol - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] RTB +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Patrol - -- @function [parent=#AI_PATROLZONE] __Patrol - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] __RTB +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE +--- OnLeave Transition Handler for State Returning. +-- @function [parent=#AI_PATROL_ZONE] OnLeaveReturning +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. -do self:AddTransition( "Patrol", "RTB", "RTB" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnEnter Transition Handler for State Returning. +-- @function [parent=#AI_PATROL_ZONE] OnEnterReturning +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnLeave State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnLeavePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnEnterRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnBeforeRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnAfterRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for RTB. - -- @function [parent=#AI_PATROLZONE] RTB - -- @param #AI_PATROLZONE self - - --- Delayed Event Trigger for RTB - -- @function [parent=#AI_PATROLZONE] __RTB - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. - -end -- AI_PATROLZONE + self:AddTransition( "*", "Reset", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. return self end @@ -24885,11 +25067,11 @@ end --- Sets (modifies) the minimum and maximum speed of the patrol. --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:SetSpeed( PatrolMinSpeed, PatrolMaxSpeed ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetSpeed( PatrolMinSpeed, PatrolMaxSpeed ) self:F2( { PatrolMinSpeed, PatrolMaxSpeed } ) self.PatrolMinSpeed = PatrolMinSpeed @@ -24899,39 +25081,92 @@ end --- Sets the floor and ceiling altitude of the patrol. --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:SetAltitude( PatrolFloorAltitude, PatrolCeilingAltitude ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetAltitude( PatrolFloorAltitude, PatrolCeilingAltitude ) self:F2( { PatrolFloorAltitude, PatrolCeilingAltitude } ) self.PatrolFloorAltitude = PatrolFloorAltitude self.PatrolCeilingAltitude = PatrolCeilingAltitude end +-- * @{#AI_PATROL_ZONE.SetDetectionOn}(): Set the detection on. The AI will detect for targets. +-- * @{#AI_PATROL_ZONE.SetDetectionOff}(): Set the detection off, the AI will not detect for targets. The existing target list will NOT be erased. +--- Set the detection on. The AI will detect for targets. +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionOn() + self:F2() + + self.DetectUnits = true +end ---- @param Wrapper.Controllable#CONTROLLABLE AIControllable -function _NewPatrolRoute( AIControllable ) +--- Set the detection off. The AI will NOT detect for targets. +-- However, the list of already detected targets will be kept and can be enquired! +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionOff() + self:F2() + + self.DetectUnits = false +end - AIControllable:T( "NewPatrolRoute" ) - local PatrolZone = AIControllable:GetState( AIControllable, "PatrolZone" ) -- PatrolCore.Zone#AI_PATROLZONE - PatrolZone:__Route( 1 ) +--- Set the interval in seconds between each detection executed by the AI. +-- The list of already detected targets will be kept and updated. +-- Newly detected targets will be added, but already detected targets that were +-- not detected in this cycle, will NOT be removed! +-- The default interval is 30 seconds. +-- @param #AI_PATROL_ZONE self +-- @param #number Seconds The interval in seconds. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionInterval( Seconds ) + self:F2() + + if Seconds then + self.DetectInterval = Seconds + else + self.DetectInterval = 30 + end +end + +--- Set the detection zone where the AI is detecting targets. +-- @param #AI_PATROL_ZONE self +-- @param Core.Zone#ZONE DetectionZone The zone where to detect targets. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionZone( DetectionZone ) + self:F2() + + if DetectionZone then + self.DetectZone = DetectionZone + else + self.DetectZone = nil + end +end + +--- Gets a list of @{Wrapper.Unit#UNIT}s that were detected by the AI. +-- No filtering is applied, so, ANY detected UNIT can be in this list. +-- It is up to the mission designer to use the @{Unit} class and methods to filter the targets. +-- @param #AI_PATROL_ZONE self +-- @return #table The list of @{Wrapper.Unit#UNIT}s +function AI_PATROL_ZONE:GetDetectedUnits() + self:F2() + + return self.DetectedUnits end - - ---- When the AIControllable is out of fuel, it is required that a new AIControllable is started, before the old AIControllable can return to the home base. +--- When the AI is out of fuel, it is required that a new AI is started, before the old AI can return to the home base. -- Therefore, with a parameter and a calculation of the distance to the home base, the fuel treshold is calculated. --- When the fuel treshold is reached, the AIControllable will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROLZONE. --- Once the time is finished, the old AIControllable will return to the base. --- @param #AI_PATROLZONE self +-- When the fuel treshold is reached, the AI will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROL_ZONE. +-- Once the time is finished, the old AI will return to the base. +-- @param #AI_PATROL_ZONE self -- @param #number PatrolFuelTresholdPercentage The treshold in percentage (between 0 and 1) when the AIControllable is considered to get out of fuel. -- @param #number PatrolOutOfFuelOrbitTime The amount of seconds the out of fuel AIControllable will orbit before returning to the base. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuelOrbitTime ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuelOrbitTime ) self.PatrolManageFuel = true self.PatrolFuelTresholdPercentage = PatrolFuelTresholdPercentage @@ -24940,60 +25175,165 @@ function AI_PATROLZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuel return self end +--- When the AI is damaged beyond a certain treshold, it is required that the AI returns to the home base. +-- However, damage cannot be foreseen early on. +-- Therefore, when the damage treshold is reached, +-- the AI will return immediately to the home base (RTB). +-- Note that for groups, the average damage of the complete group will be calculated. +-- So, in a group of 4 airplanes, 2 lost and 2 with damage 0.2, the damage treshold will be 0.25. +-- @param #AI_PATROL_ZONE self +-- @param #number PatrolDamageTreshold The treshold in percentage (between 0 and 1) when the AI is considered to be damaged. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:ManageDamage( PatrolDamageTreshold ) + + self.PatrolManageDamage = true + self.PatrolDamageTreshold = PatrolDamageTreshold + + return self +end + --- Defines a new patrol route using the @{Process_PatrolZone} parameters and settings. --- @param #AI_PATROLZONE self --- @return #AI_PATROLZONE self -function AI_PATROLZONE:onenterRoute() +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_PATROL_ZONE:onafterStart( Controllable, From, Event, To ) + self:F2() + + self:__Route( 5 ) -- Route to the patrol point. The asynchronous trigger is important, because a spawned group and units takes at least one second to come live. + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every 30 seconds. + + Controllable:OptionROEHoldFire() + Controllable:OptionROTVertical() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + +end + + +--- @param #AI_PATROL_ZONE self +--- @param Wrapper.Controllable#CONTROLLABLE Controllable +function AI_PATROL_ZONE:onbeforeDetect( Controllable, From, Event, To ) + + return self.DetectUnits +end + +--- @param #AI_PATROL_ZONE self +--- @param Wrapper.Controllable#CONTROLLABLE Controllable +function AI_PATROL_ZONE:onafterDetect( Controllable, From, Event, To ) + + local Detected = false + + local DetectedTargets = Controllable:GetDetectedTargets() + for TargetID, Target in pairs( DetectedTargets or {} ) do + local TargetObject = Target.object + self:T( TargetObject ) + if TargetObject and TargetObject:isExist() and TargetObject.id_ < 50000000 then + + local TargetUnit = UNIT:Find( TargetObject ) + local TargetUnitName = TargetUnit:GetName() + + if self.DetectionZone then + if TargetUnit:IsInZone( self.DetectionZone ) then + self:T( {"Detected ", TargetUnit } ) + self.DetectedUnits[TargetUnit] = TargetUnit + Detected = true + end + else + self.DetectedUnits[TargetUnit] = TargetUnit + Detected = true + end + end + end + + if Detected == true then + self:__Detected( 1 ) + end + + self:__Detect( self.DetectInterval ) +end + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +-- This statis method is called from the route path within the last task at the last waaypoint of the Controllable. +-- Note that this method is required, as triggers the next route when patrolling for the Controllable. +function AI_PATROL_ZONE:_NewPatrolRoute( AIControllable ) + + local PatrolZone = AIControllable:GetState( AIControllable, "PatrolZone" ) -- PatrolCore.Zone#AI_PATROL_ZONE + PatrolZone:__Route( 1 ) +end + + +--- Defines a new patrol route using the @{Process_PatrolZone} parameters and settings. +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_PATROL_ZONE:onafterRoute( Controllable, From, Event, To ) self:F2() - local PatrolRoute = {} + -- When RTB, don't allow anymore the routing. + if From == "RTB" then + return + end + if self.Controllable:IsAlive() then - --- Determine if the AIControllable is within the PatrolZone. + -- Determine if the AIControllable is within the PatrolZone. -- If not, make a waypoint within the to that the AIControllable will fly at maximum speed to that point. --- --- Calculate the current route point. --- local CurrentVec2 = self.Controllable:GetVec2() --- local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() --- local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) --- local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( --- POINT_VEC3.RoutePointAltType.BARO, --- POINT_VEC3.RoutePointType.TurningPoint, --- POINT_VEC3.RoutePointAction.TurningPoint, --- ToPatrolZoneSpeed, --- true --- ) --- --- PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + local PatrolRoute = {} + + -- Calculate the current route point of the controllable as the start point of the route. + -- However, when the controllable is not in the air, + -- the controllable current waypoint is probably the airbase... + -- Thus, if we would take the current waypoint as the startpoint, upon take-off, the controllable flies + -- immediately back to the airbase, and this is not correct. + -- Therefore, when on a runway, get as the current route point a random point within the PatrolZone. + -- This will make the plane fly immediately to the patrol zone. - self:T2( PatrolRoute ) - - if self.Controllable:IsNotInZone( self.PatrolZone ) then - --- Find a random 2D point in PatrolZone. - local ToPatrolZoneVec2 = self.PatrolZone:GetRandomVec2() - self:T2( ToPatrolZoneVec2 ) - - --- Define Speed and Altitude. - local ToPatrolZoneAltitude = math.random( self.PatrolFloorAltitude, self.PatrolCeilingAltitude ) + if self.Controllable:InAir() == false then + self:E( "Not in the air, finding route path within PatrolZone" ) + local CurrentVec2 = self.Controllable:GetVec2() + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) local ToPatrolZoneSpeed = self.PatrolMaxSpeed - self:T2( ToPatrolZoneSpeed ) - - --- Obtain a 3D @{Point} from the 2D point + altitude. - local ToPatrolZonePointVec3 = POINT_VEC3:New( ToPatrolZoneVec2.x, ToPatrolZoneAltitude, ToPatrolZoneVec2.y ) - - --- Create a route point of type air. - local ToPatrolZoneRoutePoint = ToPatrolZonePointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToPatrolZoneSpeed, - true - ) - - PatrolRoute[#PatrolRoute+1] = ToPatrolZoneRoutePoint - - end + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TakeOffParking, + POINT_VEC3.RoutePointAction.FromParkingArea, + ToPatrolZoneSpeed, + true + ) + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + else + self:E( "In the air, finding route path within PatrolZone" ) + local CurrentVec2 = self.Controllable:GetVec2() + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToPatrolZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToPatrolZoneSpeed, + true + ) + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + end + --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. @@ -25018,6 +25358,8 @@ function AI_PATROLZONE:onenterRoute() true ) + --self.CoordTest:SpawnFromVec3( ToTargetPointVec3:GetVec3() ) + --ToTargetPointVec3:SmokeRed() PatrolRoute[#PatrolRoute+1] = ToTargetRoutePoint @@ -25027,25 +25369,31 @@ function AI_PATROLZONE:onenterRoute() --- Do a trick, link the NewPatrolRoute function of the PATROLGROUP object to the AIControllable in a temporary variable ... self.Controllable:SetState( self.Controllable, "PatrolZone", self ) - self.Controllable:WayPointFunction( #PatrolRoute, 1, "_NewPatrolRoute" ) + self.Controllable:WayPointFunction( #PatrolRoute, 1, "AI_PATROL_ZONE:_NewPatrolRoute" ) --- NOW ROUTE THE GROUP! - self.Controllable:WayPointExecute( 1, 5 ) - - self:__Patrol( 30 ) + self.Controllable:WayPointExecute( 1, 2 ) end - + end +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onbeforeStatus() ---- @param #AI_PATROLZONE self -function AI_PATROLZONE:onenterPatrol() + return self.CheckStatus +end + +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onafterStatus() self:F2() if self.Controllable and self.Controllable:IsAlive() then + local RTB = false + local Fuel = self.Controllable:GetUnit(1):GetFuel() if Fuel < self.PatrolFuelTresholdPercentage then + self:E( self.Controllable:GetName() .. " is out of fuel:" .. Fuel .. ", RTB!" ) local OldAIControllable = self.Controllable local AIControllableTemplate = self.Controllable:GetTemplate() @@ -25053,14 +25401,1145 @@ function AI_PATROLZONE:onenterPatrol() local TimedOrbitTask = OldAIControllable:TaskControlled( OrbitTask, OldAIControllable:TaskCondition(nil,nil,nil,nil,self.PatrolOutOfFuelOrbitTime,nil ) ) OldAIControllable:SetTask( TimedOrbitTask, 10 ) + RTB = true + else + end + + -- TODO: Check GROUP damage function. + local Damage = self.Controllable:GetLife() + if Damage <= self.PatrolDamageTreshold then + self:E( self.Controllable:GetName() .. " is damaged:" .. Damage .. ", RTB!" ) + RTB = true + end + + if RTB == true then self:RTB() else - self:__Patrol( 30 ) -- Execute the Patrol event after 30 seconds. + self:__Status( 30 ) -- Execute the Patrol event after 30 seconds. end end +end + +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onafterRTB() + self:F2() + + if self.Controllable and self.Controllable:IsAlive() then + + self:SetDetectionOff() + self.CheckStatus = false + + local PatrolRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToPatrolZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToPatrolZoneSpeed, + true + ) + + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( PatrolRoute ) + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 1 ) + + end + +end +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Provide Close Air Support to friendly ground troops.** +-- +-- ![Banner Image](..\Presentations\AI_Cas\Dia1.JPG) +-- +-- +-- === +-- +-- # 1) @{#AI_CAS_ZONE} class, extends @{AI.AI_Patrol#AI_PATROL_ZONE} +-- +-- @{#AI_CAS_ZONE} derives from the @{AI.AI_Patrol#AI_PATROL_ZONE}, inheriting its methods and behaviour. +-- +-- The @{#AI_CAS_ZONE} class implements the core functions to provide Close Air Support in an Engage @{Zone} by an AIR @{Controllable} or @{Group}. +-- The AI_CAS_ZONE runs a process. It holds an AI in a Patrol Zone and when the AI is commanded to engage, it will fly to an Engage Zone. +-- +-- ![HoldAndEngage](..\Presentations\AI_Cas\Dia3.JPG) +-- +-- The AI_CAS_ZONE is assigned a @(Group) and this must be done before the AI_CAS_ZONE process can be started through the **Start** event. +-- +-- ![Start Event](..\Presentations\AI_Cas\Dia4.JPG) +-- +-- Upon started, The AI will **Route** itself towards the random 3D point within a patrol zone, +-- using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- This cycle will continue until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. +-- +-- ![Route Event](..\Presentations\AI_Cas\Dia5.JPG) +-- +-- When the AI is commanded to provide Close Air Support (through the event **Engage**), the AI will fly towards the Engage Zone. +-- Any target that is detected in the Engage Zone will be reported and will be destroyed by the AI. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia6.JPG) +-- +-- The AI will detect the targets and will only destroy the targets within the Engage Zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia7.JPG) +-- +-- Every target that is destroyed, is reported< by the AI. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia8.JPG) +-- +-- Note that the AI does not know when the Engage Zone is cleared, and therefore will keep circling in the zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia9.JPG) +-- +-- Until it is notified through the event **Accomplish**, which is to be triggered by an observing party: +-- +-- * a FAC +-- * a timed event +-- * a menu option selected by a human +-- * a condition +-- * others ... +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia10.JPG) +-- +-- When the AI has accomplished the CAS, it will fly back to the Patrol Zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia11.JPG) +-- +-- It will keep patrolling there, until it is notified to RTB or move to another CAS Zone. +-- It can be notified to go RTB through the **RTB** event. +-- +-- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia12.JPG) +-- +-- # 1.1) AI_CAS_ZONE constructor +-- +-- * @{#AI_CAS_ZONE.New}(): Creates a new AI_CAS_ZONE object. +-- +-- ## 1.2) AI_CAS_ZONE is a FSM +-- +-- ![Process](..\Presentations\AI_Cas\Dia2.JPG) +-- +-- ### 1.2.1) AI_CAS_ZONE States +-- +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Engaging** ( Group ): The AI is engaging the targets in the Engage Zone, executing CAS. +-- * **Returning** ( Group ): The AI is returning to Base.. +-- +-- ### 1.2.2) AI_CAS_ZONE Events +-- +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **Engage** ( Group ): Engage the AI to provide CAS in the Engage Zone, destroying any target it finds. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** +-- +-- The underlying change log documents the API changes. Please read this carefully. The following notation is used: +-- +-- * **Added** parts are expressed in bold type face. +-- * _Removed_ parts are expressed in italic type face. +-- +-- Hereby the change log: +-- +-- 2017-01-15: Initial class and API. +-- +-- === +-- +-- # **AUTHORS and CONTRIBUTIONS** +-- +-- ### Contributions: +-- +-- * **[Quax](https://forums.eagle.ru/member.php?u=90530)**: Concept, Advice & Testing. +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Concept, Advice & Testing. +-- * **[Gunterlund](http://forums.eagle.ru:8080/member.php?u=75036)**: Test case revision. +-- +-- ### Authors: +-- +-- * **FlightControl**: Concept, Design & Programming. +-- +-- @module AI_Cas + + +--- AI_CAS_ZONE class +-- @type AI_CAS_ZONE +-- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. +-- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. +-- @extends AI.AI_Patrol#AI_CAS_ZONE +AI_CAS_ZONE = { + ClassName = "AI_CAS_ZONE", +} + + + +--- Creates a new AI_CAS_ZONE object +-- @param #AI_CAS_ZONE self +-- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. +-- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. +-- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @param Core.Zone#ZONE EngageZone +-- @return #AI_CAS_ZONE self +function AI_CAS_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed, EngageZone ) + + -- Inherits from BASE + local self = BASE:Inherit( self, AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAS_ZONE + + self.EngageZone = EngageZone + self.Accomplished = false + + self:SetDetectionZone( self.EngageZone ) + + self:AddTransition( { "Patrolling", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Engage. + -- @function [parent=#AI_CAS_ZONE] OnBeforeEngage + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Engage. + -- @function [parent=#AI_CAS_ZONE] OnAfterEngage + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAS_ZONE] Engage + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAS_ZONE] __Engage + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Engaging. +-- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Engaging. +-- @function [parent=#AI_CAS_ZONE] OnEnterEngaging +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Fired. + -- @function [parent=#AI_CAS_ZONE] OnBeforeFired + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Fired. + -- @function [parent=#AI_CAS_ZONE] OnAfterFired + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAS_ZONE] Fired + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAS_ZONE] __Fired + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Destroy", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] OnBeforeDestroy + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] OnAfterDestroy + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] Destroy + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] __Destroy + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + + self:AddTransition( "Engaging", "Abort", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Abort. + -- @function [parent=#AI_CAS_ZONE] OnBeforeAbort + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Abort. + -- @function [parent=#AI_CAS_ZONE] OnAfterAbort + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAS_ZONE] Abort + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAS_ZONE] __Abort + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "Engaging", "Accomplish", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] OnBeforeAccomplish + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] OnAfterAccomplish + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] Accomplish + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] __Accomplish + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + return self +end + + +--- Set the Engage Zone where the AI is performing CAS. Note that if the EngageZone is changed, the AI needs to re-detect targets. +-- @param #AI_CAS_ZONE self +-- @param Core.Zone#ZONE EngageZone The zone where the AI is performing CAS. +-- @return #AI_CAS_ZONE self +function AI_CAS_ZONE:SetEngageZone( EngageZone ) + self:F2() + + if EngageZone then + self.EngageZone = EngageZone + else + self.EngageZone = nil + end +end + + + +--- onafter State Transition for Event Start. +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterStart( Controllable, From, Event, To ) + + + self:Route() + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every DetectInterval in the EngageZone. + + self:EventOnDead( self.OnDead ) + + Controllable:OptionROEHoldFire() + Controllable:OptionROTVertical() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) end ---- Management of logical cargo objects, that can be transported from and to transportation carriers. + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +function _NewEngageRoute( AIControllable ) + + AIControllable:T( "NewEngageRoute" ) + local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Cas#AI_CAS_ZONE + EngageZone:__Engage( 1 ) +end + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onbeforeEngage( Controllable, From, Event, To ) + + if self.Accomplished == true then + return false + end +end + + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) + + if Controllable:IsAlive() then + + self:Detect( self.EngageZone ) + + local EngageRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = CurrentRoutePoint + + + if self.Controllable:IsNotInZone( self.EngageZone ) then + + -- Find a random 2D point in EngageZone. + local ToEngageZoneVec2 = self.EngageZone:GetRandomVec2() + self:T2( ToEngageZoneVec2 ) + + -- Define Speed and Altitude. + local ToEngageZoneAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + self:T2( ToEngageZoneSpeed ) + + -- Obtain a 3D @{Point} from the 2D point + altitude. + local ToEngageZonePointVec3 = POINT_VEC3:New( ToEngageZoneVec2.x, ToEngageZoneAltitude, ToEngageZoneVec2.y ) + + -- Create a route point of type air. + local ToEngageZoneRoutePoint = ToEngageZonePointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = ToEngageZoneRoutePoint + + end + + --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. + + --- Find a random 2D point in EngageZone. + local ToTargetVec2 = self.EngageZone:GetRandomVec2() + self:T2( ToTargetVec2 ) + + --- Define Speed and Altitude. + local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) + self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) + + --- Obtain a 3D @{Point} from the 2D point + altitude. + local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) + + --- Create a route point of type air. + local ToTargetRoutePoint = ToTargetPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToTargetSpeed, + true + ) + + ToTargetPointVec3:SmokeBlue() + + EngageRoute[#EngageRoute+1] = ToTargetRoutePoint + + + Controllable:OptionROEOpenFire() + Controllable:OptionROTPassiveDefense() + + local AttackTasks = {} + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() then + if DetectedUnit:IsInZone( self.EngageZone ) then + self:E( {"Engaging ", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + self.DetectedUnits[DetectedUnit] = nil + end + end + + EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( EngageRoute ) + + --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... + self.Controllable:SetState( self.Controllable, "EngageZone", self ) + + self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageRoute" ) + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 2 ) + end +end + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @param Core.Event#EVENTDATA EventData +function AI_CAS_ZONE:onafterDestroy( Controllable, From, Event, To, EventData ) + + if EventData.IniUnit then + self.DetectedUnits[EventData.IniUnit] = nil + end + + Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) +end + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterAccomplish( Controllable, From, Event, To ) + self.Accomplished = true + self.DetectUnits = false +end + +--- @param #AI_CAS_ZONE self +-- @param Core.Event#EVENTDATA EventData +function AI_CAS_ZONE:OnDead( EventData ) + self:T( { "EventDead", EventData } ) + + if EventData.IniDCSUnit then + self:__Destroy( 1, EventData ) + end +end + + +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Execute Combat Air Patrol (CAP).** +-- +-- ![Banner Image](..\Presentations\AI_Cap\Dia1.JPG) +-- +-- +-- === +-- +-- # 1) @{#AI_CAP_ZONE} class, extends @{AI.AI_Cap#AI_PATROL_ZONE} +-- +-- The @{#AI_CAP_ZONE} class implements the core functions to patrol a @{Zone} by an AI @{Controllable} or @{Group} +-- and automatically engage any airborne enemies that are within a certain range or within a certain zone. +-- +-- ![Process](..\Presentations\AI_Cap\Dia3.JPG) +-- +-- The AI_CAP_ZONE is assigned a @(Group) and this must be done before the AI_CAP_ZONE process can be started using the **Start** event. +-- +-- ![Process](..\Presentations\AI_Cap\Dia4.JPG) +-- +-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- +-- ![Process](..\Presentations\AI_Cap\Dia5.JPG) +-- +-- This cycle will continue. +-- +-- ![Process](..\Presentations\AI_Cap\Dia6.JPG) +-- +-- During the patrol, the AI will detect enemy targets, which are reported through the **Detected** event. +-- +-- ![Process](..\Presentations\AI_Cap\Dia9.JPG) +-- +-- When enemies are detected, the AI will automatically engage the enemy. +-- +-- ![Process](..\Presentations\AI_Cap\Dia10.JPG) +-- +-- Until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. +-- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. +-- +-- ![Process](..\Presentations\AI_Cap\Dia13.JPG) +-- +-- ## 1.1) AI_CAP_ZONE constructor +-- +-- * @{#AI_CAP_ZONE.New}(): Creates a new AI_CAP_ZONE object. +-- +-- ## 1.2) AI_CAP_ZONE is a FSM +-- +-- ![Process](..\Presentations\AI_Cap\Dia2.JPG) +-- +-- ### 1.2.1) AI_CAP_ZONE States +-- +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Engaging** ( Group ): The AI is engaging the bogeys. +-- * **Returning** ( Group ): The AI is returning to Base.. +-- +-- ### 1.2.2) AI_CAP_ZONE Events +-- +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **Engage** ( Group ): Let the AI engage the bogeys. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. +-- +-- ## 1.3) Set the Range of Engagement +-- +-- ![Range](..\Presentations\AI_Cap\Dia11.JPG) +-- +-- An optional range can be set in meters, +-- that will define when the AI will engage with the detected airborne enemy targets. +-- The range can be beyond or smaller than the range of the Patrol Zone. +-- The range is applied at the position of the AI. +-- Use the method @{AI.AI_Cap#AI_CAP_ZONE.SetEngageRange}() to define that range. +-- +-- ## 1.4) Set the Zone of Engagement +-- +-- ![Zone](..\Presentations\AI_Cap\Dia12.JPG) +-- +-- An optional @{Zone} can be set, +-- that will define when the AI will engage with the detected airborne enemy targets. +-- Use the method @{AI.AI_Cap#AI_CAP_ZONE.SetEngageZone}() to define that Zone. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** +-- +-- The underlying change log documents the API changes. Please read this carefully. The following notation is used: +-- +-- * **Added** parts are expressed in bold type face. +-- * _Removed_ parts are expressed in italic type face. +-- +-- Hereby the change log: +-- +-- 2017-01-15: Initial class and API. +-- +-- === +-- +-- # **AUTHORS and CONTRIBUTIONS** +-- +-- ### Contributions: +-- +-- * **[Quax](https://forums.eagle.ru/member.php?u=90530)**: Concept, Advice & Testing. +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Concept, Advice & Testing. +-- * **[Gunterlund](http://forums.eagle.ru:8080/member.php?u=75036)**: Test case revision. +-- +-- ### Authors: +-- +-- * **FlightControl**: Concept, Design & Programming. +-- +-- @module AI_Cap + + +--- AI_CAP_ZONE class +-- @type AI_CAP_ZONE +-- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. +-- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. +-- @extends AI.AI_Patrol#AI_PATROL_ZONE +AI_CAP_ZONE = { + ClassName = "AI_CAP_ZONE", +} + + + +--- Creates a new AI_CAP_ZONE object +-- @param #AI_CAP_ZONE self +-- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. +-- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. +-- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) + + -- Inherits from BASE + local self = BASE:Inherit( self, AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAP_ZONE + + self.Accomplished = false + self.Engaging = false + + self:AddTransition( { "Patrolling", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Engage. + -- @function [parent=#AI_CAP_ZONE] OnBeforeEngage + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Engage. + -- @function [parent=#AI_CAP_ZONE] OnAfterEngage + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAP_ZONE] Engage + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAP_ZONE] __Engage + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Engaging. +-- @function [parent=#AI_CAP_ZONE] OnLeaveEngaging +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Engaging. +-- @function [parent=#AI_CAP_ZONE] OnEnterEngaging +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Fired. + -- @function [parent=#AI_CAP_ZONE] OnBeforeFired + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Fired. + -- @function [parent=#AI_CAP_ZONE] OnAfterFired + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAP_ZONE] Fired + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAP_ZONE] __Fired + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Destroy", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] OnBeforeDestroy + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] OnAfterDestroy + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] Destroy + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] __Destroy + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + + self:AddTransition( "Engaging", "Abort", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Abort. + -- @function [parent=#AI_CAP_ZONE] OnBeforeAbort + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Abort. + -- @function [parent=#AI_CAP_ZONE] OnAfterAbort + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAP_ZONE] Abort + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAP_ZONE] __Abort + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "Engaging", "Accomplish", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] OnBeforeAccomplish + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] OnAfterAccomplish + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] Accomplish + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] __Accomplish + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + return self +end + + +--- Set the Engage Zone which defines where the AI will engage bogies. +-- @param #AI_CAP_ZONE self +-- @param Core.Zone#ZONE EngageZone The zone where the AI is performing CAP. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:SetEngageZone( EngageZone ) + self:F2() + + if EngageZone then + self.EngageZone = EngageZone + else + self.EngageZone = nil + end +end + +--- Set the Engage Range when the AI will engage with airborne enemies. +-- @param #AI_CAP_ZONE self +-- @param #number EngageRange The Engage Range. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:SetEngageRange( EngageRange ) + self:F2() + + if EngageRange then + self.EngageRange = EngageRange + else + self.EngageRange = nil + end +end + +--- onafter State Transition for Event Start. +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterStart( Controllable, From, Event, To ) + + + self:Route() + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every DetectInterval in the EngageZone. + + self:EventOnDead( self.OnDead ) + + Controllable:OptionROEOpenFire() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + +end + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +function _NewEngageCapRoute( AIControllable ) + + AIControllable:T( "NewEngageRoute" ) + local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Cap#AI_CAP_ZONE + EngageZone:__Engage( 1 ) +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onbeforeEngage( Controllable, From, Event, To ) + + if self.Accomplished == true then + return false + end +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterDetected( Controllable, From, Event, To ) + + if From ~= "Engaging" then + + local Engage = false + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() and DetectedUnit:IsAir() then + Engage = true + break + end + end + + if Engage == true then + self:E( 'Detected -> Engaging' ) + self:__Engage( 1 ) + end + end +end + + + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterEngage( Controllable, From, Event, To ) + + if Controllable:IsAlive() then + + self:Detect( self.EngageZone ) + + local EngageRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = CurrentRoutePoint + + + --- Find a random 2D point in PatrolZone. + local ToTargetVec2 = self.PatrolZone:GetRandomVec2() + self:T2( ToTargetVec2 ) + + --- Define Speed and Altitude. + local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) + self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) + + --- Obtain a 3D @{Point} from the 2D point + altitude. + local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) + + --- Create a route point of type air. + local ToPatrolRoutePoint = ToTargetPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToTargetSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = ToPatrolRoutePoint + + Controllable:OptionROEOpenFire() + Controllable:OptionROTPassiveDefense() + + local AttackTasks = {} + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() and DetectedUnit:IsAir() then + if self.EngageZone then + if DetectedUnit:IsInZone( self.EngageZone ) then + self:E( {"Within Zone and Engaging ", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + if self.EngageRange then + if DetectedUnit:GetPointVec3():Get2DDistance(Controllable:GetPointVec3() ) <= self.EngageRange then + self:E( {"Within Range and Engaging", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + end + else + self.DetectedUnits[DetectedUnit] = nil + end + end + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( EngageRoute ) + + + if #AttackTasks == 0 then + self:E("No targets found -> Going back to Patrolling") + self:Accomplish() + self:Route() + else + EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) + + --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... + self.Controllable:SetState( self.Controllable, "EngageZone", self ) + + self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageCapRoute" ) + + end + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 2 ) + + end +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @param Core.Event#EVENTDATA EventData +function AI_CAP_ZONE:onafterDestroy( Controllable, From, Event, To, EventData ) + + if EventData.IniUnit then + self.DetectedUnits[EventData.IniUnit] = nil + end + + Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterAccomplish( Controllable, From, Event, To ) + self.Accomplished = true + self.DetectUnits = false +end + +--- @param #AI_CAP_ZONE self +-- @param Core.Event#EVENTDATA EventData +function AI_CAP_ZONE:OnDead( EventData ) + self:T( { "EventDead", EventData } ) + + if EventData.IniDCSUnit then + self:__Destroy( 1, EventData ) + end +end + + +--- Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Ground -- Management of logical cargo objects, that can be transported from and to transportation carriers. -- -- === -- @@ -26085,507 +27564,6 @@ end -- AI_CARGO_GROUPED ---- SP:Y MP:Y AI:Y HU:N TYP:Air -- This module contains the AI_CAS_ZONE class. --- --- === --- --- 1) @{#AI_CAS_ZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} --- ================================================================ --- The @{#AI_CAS_ZONE} class implements the core functions to CAS a @{Zone} by an AIR @{Controllable} @{Group}. --- --- 1.1) AI_CAS_ZONE constructor: --- ---------------------------- --- --- * @{#AI_CAS_ZONE.New}(): Creates a new AI_CAS_ZONE object. --- --- 1.2) AI_CAS_ZONE state machine: --- ---------------------------------- --- The AI_CAS_ZONE is a state machine: it manages the different events and states of the AIControllable it is controlling. --- --- ### 1.2.1) AI_CAS_ZONE Events: --- --- * @{#AI_CAS_ZONE.TakeOff}( AIControllable ): The AI is taking-off from an airfield. --- * @{#AI_CAS_ZONE.Hold}( AIControllable ): The AI is holding in airspace at a zone. --- * @{#AI_CAS_ZONE.Engage}( AIControllable ): The AI is engaging the targets. --- * @{#AI_CAS_ZONE.WeaponReleased}( AIControllable ): The AI has released a weapon to the target. --- * @{#AI_CAS_ZONE.Destroy}( AIControllable ): The AI has destroyed a target. --- * @{#AI_CAS_ZONE.Complete}( AIControllable ): The AI has destroyed all defined targets. --- * @{#AI_CAS_ZONE.RTB}( AIControllable ): The AI is returning to the home base. --- --- ### 1.2.2) AI_CAS_ZONE States: --- --- --- ### 1.2.3) AI_CAS_ZONE state transition methods: --- --- --- 1.3) Manage the AI_CAS_ZONE parameters: --- ------------------------------------------ --- The following methods are available to modify the parameters of an AI_CAS_ZONE object: --- --- * @{#AI_CAS_ZONE.SetControllable}(): Set the AIControllable. --- * @{#AI_CAS_ZONE.GetControllable}(): Get the AIControllable. --- --- ==== --- --- **API CHANGE HISTORY** --- ====================== --- --- The underlying change log documents the API changes. Please read this carefully. The following notation is used: --- --- * **Added** parts are expressed in bold type face. --- * _Removed_ parts are expressed in italic type face. --- --- Hereby the change log: --- --- 2017-01-12: Initial class and API. --- --- === --- --- AUTHORS and CONTRIBUTIONS --- ========================= --- --- ### Contributions: --- --- * **Quax**: Concept & Testing. --- * **Pikey**: Concept & Testing. --- --- ### Authors: --- --- * **FlightControl**: Concept, Design & Programming. --- --- --- @module Cas - - ---- AI_CAS_ZONE class --- @type AI_CAS_ZONE --- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. --- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. --- @extends AI.AI_Patrol#AI_PATROLZONE -AI_CAS_ZONE = { - ClassName = "AI_CAS_ZONE", -} - - - ---- Creates a new AI_CAS_ZONE object --- @param #AI_CAS_ZONE self --- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. --- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. --- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. --- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. --- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @param Core.Zone#ZONE EngageZone --- @return #AI_CAS_ZONE self -function AI_CAS_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed, EngageZone ) - - -- Inherits from BASE - local self = BASE:Inherit( self, AI_PATROLZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAS_ZONE - - self.PatrolZone = PatrolZone - self.PatrolFloorAltitude = PatrolFloorAltitude - self.PatrolCeilingAltitude = PatrolCeilingAltitude - self.PatrolMinSpeed = PatrolMinSpeed - self.PatrolMaxSpeed = PatrolMaxSpeed - - self.EngageZone = EngageZone - - do self:AddTransition( { "Patrol", "Route", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Holding. - -- @function [parent=#AI_CAS_ZONE] OnLeaveHolding - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Engage. - -- @function [parent=#AI_CAS_ZONE] OnBeforeEngage - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Engage. - -- @function [parent=#AI_CAS_ZONE] OnAfterEngage - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Engage. - -- @function [parent=#AI_CAS_ZONE] Engage - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Engage - -- @function [parent=#AI_CAS_ZONE] __Engage - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - - do self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Fired. - -- @function [parent=#AI_CAS_ZONE] OnBeforeFired - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Fired. - -- @function [parent=#AI_CAS_ZONE] OnAfterFired - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean - - --- Embedded Event Trigger for Fired. - -- @function [parent=#AI_CAS_ZONE] Fired - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Fired - -- @function [parent=#AI_CAS_ZONE] __Fired - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - do self:AddTransition( "Engaging", "Destroy", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Destroy. - -- @function [parent=#AI_CAS_ZONE] OnBeforeDestroy - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Destroy. - -- @function [parent=#AI_CAS_ZONE] OnAfterDestroy - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Destroy. - -- @function [parent=#AI_CAS_ZONE] Destroy - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Destroy - -- @function [parent=#AI_CAS_ZONE] __Destroy - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - -do self:AddTransition( "Engaging", "Abort", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_CAS_ZONE] OnEnterPatrol - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Abort. - -- @function [parent=#AI_CAS_ZONE] OnBeforeAbort - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Abort. - -- @function [parent=#AI_CAS_ZONE] OnAfterAbort - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Abort. - -- @function [parent=#AI_CAS_ZONE] Abort - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Abort - -- @function [parent=#AI_CAS_ZONE] __Abort - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - -end -- AI_CAS_ZONE - - - do self:AddTransition( "Engaging", "Completed", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_CAS_ZONE] OnEnterPatrol - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Completed. - -- @function [parent=#AI_CAS_ZONE] OnBeforeCompleted - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Completed. - -- @function [parent=#AI_CAS_ZONE] OnAfterCompleted - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Completed. - -- @function [parent=#AI_CAS_ZONE] Completed - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Completed - -- @function [parent=#AI_CAS_ZONE] __Completed - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - return self -end - - ---- onafter State Transition for Event Start. --- @param #AI_CAS_ZONE self --- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. --- @param #string From The From State string. --- @param #string Event The Event string. --- @param #string To The To State string. -function AI_CAS_ZONE:onafterStart( Controllable, From, Event, To ) - - - if Controllable:IsAlive() then - self:__Route( 1 ) - end - - self:EventOnDead( self.OnDead ) - - Controllable:OptionROEHoldFire() - Controllable:OptionROTVertical() - -end - ---- @param Wrapper.Controllable#CONTROLLABLE AIControllable -function _NewEngageRoute( AIControllable ) - - AIControllable:T( "NewEngageRoute" ) - local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Patrol#AI_PATROLZONE - EngageZone:__Engage( 1 ) -end - - ---- @param #AI_CAS_ZONE self --- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. --- @param #string From The From State string. --- @param #string Event The Event string. --- @param #string To The To State string. -function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) - - if Controllable:IsAlive() then - - local EngageRoute = {} - - if self.Controllable:IsNotInZone( self.EngageZone ) then - - -- Find a random 2D point in EngageZone. - local ToEngageZoneVec2 = self.EngageZone:GetRandomVec2() - self:T2( ToEngageZoneVec2 ) - - -- Define Speed and Altitude. - local ToEngageZoneAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) - local ToEngageZoneSpeed = self.PatrolMaxSpeed - self:T2( ToEngageZoneSpeed ) - - -- Obtain a 3D @{Point} from the 2D point + altitude. - local ToEngageZonePointVec3 = POINT_VEC3:New( ToEngageZoneVec2.x, ToEngageZoneAltitude, ToEngageZoneVec2.y ) - - -- Create a route point of type air. - local ToEngageZoneRoutePoint = ToEngageZonePointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToEngageZoneSpeed, - true - ) - - EngageRoute[#EngageRoute+1] = ToEngageZoneRoutePoint - - end - - --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. - - --- Find a random 2D point in EngageZone. - local ToTargetVec2 = self.EngageZone:GetRandomVec2() - self:T2( ToTargetVec2 ) - - --- Define Speed and Altitude. - local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) - local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) - self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) - - --- Obtain a 3D @{Point} from the 2D point + altitude. - local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) - - --- Create a route point of type air. - local ToTargetRoutePoint = ToTargetPointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToTargetSpeed, - true - ) - - ToTargetPointVec3:SmokeRed() - - EngageRoute[#EngageRoute+1] = ToTargetRoutePoint - - - Controllable:OptionROEOpenFire() - Controllable:OptionROTPassiveDefense() - - local AttackTasks = {} - - local DetectedTargets = Controllable:GetDetectedTargets() - for TargetID, Target in pairs( DetectedTargets ) do - local TargetObject = Target.object - self:T( TargetObject ) - if TargetObject and TargetObject:isExist() and TargetObject.id_ < 50000000 then - - local TargetUnit = UNIT:Find( TargetObject ) - local TargetUnitName = TargetUnit:GetName() - - if TargetUnit:IsInZone( self.EngageZone ) then - self:E( {"Engaging ", TargetUnit } ) - --local EngageTask = Controllable:EnRouteTaskEngageUnit( TargetUnit, 1 ) - AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( TargetUnit ) - end - - end - end - - EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) - - --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... - self.Controllable:WayPointInitialize( EngageRoute ) - - --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... - self.Controllable:SetState( self.Controllable, "EngageZone", self ) - - self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageRoute" ) - - --- NOW ROUTE THE GROUP! - self.Controllable:WayPointExecute( 1, 5 ) - end -end - ---- @param #AI_CAS_ZONE self --- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. --- @param #string From The From State string. --- @param #string Event The Event string. --- @param #string To The To State string. -function AI_CAS_ZONE:onafterDestroy( Controllable, From, Event, To ) - - Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) -end - ---- @param #AI_CAS_ZONE self --- @param Core.Event#EVENTDATA EventData -function AI_CAS_ZONE:OnDead( EventData ) - self:T( { "EventDead", EventData } ) - - if EventData.IniDCSUnit then - self:__Destroy( 1, EventData ) - end -end - - --- (SP) (MP) (FSM) Accept or reject process for player (task) assignments. -- -- === @@ -30552,8 +31530,9 @@ Include.File( "Functional/Detection" ) --- AI Classes Include.File( "AI/AI_Balancer" ) Include.File( "AI/AI_Patrol" ) -Include.File( "AI/AI_Cargo" ) +Include.File( "AI/AI_Cap" ) Include.File( "AI/AI_Cas" ) +Include.File( "AI/AI_Cargo" ) --- Actions Include.File( "Actions/Act_Assign" ) diff --git a/Moose Mission Setup/Moose.lua b/Moose Mission Setup/Moose.lua index 1e630b10b..e02bdb889 100644 --- a/Moose Mission Setup/Moose.lua +++ b/Moose Mission Setup/Moose.lua @@ -1,5 +1,5 @@ env.info( '*** MOOSE STATIC INCLUDE START *** ' ) -env.info( 'Moose Generation Timestamp: 20170113_2007' ) +env.info( 'Moose Generation Timestamp: 20170117_1202' ) local base = _G Include = {} @@ -3890,7 +3890,7 @@ function SCHEDULER:Schedule( SchedulerObject, SchedulerFunction, SchedulerArgume if SchedulerObject and SchedulerObject.ClassName and SchedulerObject.ClassID then ObjectName = SchedulerObject.ClassName .. SchedulerObject.ClassID end - self:E( { "Schedule :", ObjectName, tostring( SchedulerObject ), Start, Repeat, RandomizeFactor, Stop } ) + self:F3( { "Schedule :", ObjectName, tostring( SchedulerObject ), Start, Repeat, RandomizeFactor, Stop } ) self.SchedulerObject = SchedulerObject local ScheduleID = _SCHEDULEDISPATCHER:AddSchedule( @@ -4019,10 +4019,10 @@ function SCHEDULEDISPATCHER:AddSchedule( Scheduler, ScheduleFunction, ScheduleAr if Scheduler.MasterObject then self.ObjectSchedulers[self.CallID] = Scheduler - self:E( { CallID = self.CallID, ObjectScheduler = tostring(self.ObjectSchedulers[self.CallID]), MasterObject = tostring(Scheduler.MasterObject) } ) + self:F3( { CallID = self.CallID, ObjectScheduler = tostring(self.ObjectSchedulers[self.CallID]), MasterObject = tostring(Scheduler.MasterObject) } ) else self.PersistentSchedulers[self.CallID] = Scheduler - self:E( { CallID = self.CallID, PersistentScheduler = self.PersistentSchedulers[self.CallID] } ) + self:F3( { CallID = self.CallID, PersistentScheduler = self.PersistentSchedulers[self.CallID] } ) end self.Schedule = self.Schedule or setmetatable( {}, { __mode = "k" } ) @@ -9795,9 +9795,11 @@ POINT_VEC3 = { BARO = "BARO", }, RoutePointType = { + TakeOffParking = "TakeOffParking", TurningPoint = "Turning Point", }, RoutePointAction = { + FromParkingArea = "From Parking Area", TurningPoint = "Turning Point", }, } @@ -9820,10 +9822,12 @@ do -- POINT_VEC3 --- RoutePoint Types -- @type POINT_VEC3.RoutePointType +-- @field TakeOffParking "TakeOffParking" -- @field TurningPoint "Turning Point" --- RoutePoint Actions -- @type POINT_VEC3.RoutePointAction +-- @field FromParkingArea "From Parking Area" -- @field TurningPoint "Turning Point" -- Constructor. @@ -11245,14 +11249,21 @@ do -- FSM function FSM._handler( self, EventName, ... ) - self:E( { EventName, ... } ) - local Can, to = self:can( EventName ) - self:E( { From = self.current, Event = EventName, To = to, Can = Can } ) + + if to == "*" then + to = self.current + end if Can then local from = self.current local params = { from, EventName, to, ... } + + if self.Controllable then + self:E( "FSM Transition for " .. self.Controllable.ControllableName .. " :" .. self.current .. " --> " .. EventName .. " --> " .. to ) + else + self:E( "FSM Transition:" .. self.current .. " --> " .. EventName .. " --> " .. to ) + end if self:_call_handler("onbefore" .. EventName, params) == false or self:_call_handler("OnBefore" .. EventName, params) == false @@ -11302,6 +11313,9 @@ do -- FSM self:_call_handler("onstatechange", params) end + else + self:E( "Cannot execute transition." ) + self:E( { From = self.current, Event = EventName, To = to, Can = Can } ) end return nil @@ -11377,7 +11391,6 @@ do -- FSM end function FSM:can(e) - self:E( { e, self.Events, self.Events[e] } ) local Event = self.Events[e] self:F3( { self.current, Event } ) local To = Event and Event.map[self.current] or Event.map['*'] @@ -11446,7 +11459,7 @@ do -- FSM_CONTROLLABLE end if self[handler] then - self:E( "Calling " .. handler ) + self:F3( "Calling " .. handler ) return xpcall( function() return self[handler]( self, self.Controllable, unpack( params ) ) end, ErrorHandler ) --return self[handler]( self, self.Controllable, unpack( params ) ) end @@ -11737,7 +11750,7 @@ do -- FSM_SET function FSM_SET:_call_handler( handler, params ) if self[handler] then - self:E( "Calling " .. handler ) + self:T( "Calling " .. handler ) return self[handler]( self, self.Set, unpack( params ) ) end end @@ -12105,6 +12118,7 @@ POSITIONABLE = { function POSITIONABLE:New( PositionableName ) local self = BASE:Inherit( self, IDENTIFIABLE:New( PositionableName ) ) + self.PositionableName = PositionableName return self end @@ -12113,12 +12127,12 @@ end -- @return Dcs.DCSTypes#Position The 3D position vectors of the POSITIONABLE. -- @return #nil The POSITIONABLE is not existing or alive. function POSITIONABLE:GetPositionVec3() - self:F2( self.PositionableName ) + self:E( self.PositionableName ) local DCSPositionable = self:GetDCSObject() if DCSPositionable then - local PositionablePosition = DCSPositionable:getPosition() + local PositionablePosition = DCSPositionable:getPosition().p self:T3( PositionablePosition ) return PositionablePosition end @@ -12170,6 +12184,27 @@ function POSITIONABLE:GetPointVec2() return nil end +--- Returns a POINT_VEC3 object indicating the point in 3D of the POSITIONABLE within the mission. +-- @param Wrapper.Positionable#POSITIONABLE self +-- @return Core.Point#POINT_VEC3 The 3D point vector of the POSITIONABLE. +-- @return #nil The POSITIONABLE is not existing or alive. +function POSITIONABLE:GetPointVec3() + self:F2( self.PositionableName ) + + local DCSPositionable = self:GetDCSObject() + + if DCSPositionable then + local PositionableVec3 = self:GetPositionVec3() + + local PositionablePointVec3 = POINT_VEC3:NewFromVec3( PositionableVec3 ) + + self:T2( PositionablePointVec3 ) + return PositionablePointVec3 + end + + return nil +end + --- Returns a random @{Dcs.DCSTypes#Vec3} vector within a range, indicating the point in 3D of the POSITIONABLE within the mission. -- @param Wrapper.Positionable#POSITIONABLE self @@ -12279,20 +12314,13 @@ end --- Returns true if the POSITIONABLE is in the air. +-- Polymorphic, is overridden in GROUP and UNIT. -- @param Wrapper.Positionable#POSITIONABLE self -- @return #boolean true if in the air. -- @return #nil The POSITIONABLE is not existing or alive. function POSITIONABLE:InAir() self:F2( self.PositionableName ) - local DCSPositionable = self:GetDCSObject() - - if DCSPositionable then - local PositionableInAir = DCSPositionable:inAir() - self:T3( PositionableInAir ) - return PositionableInAir - end - return nil end @@ -12648,6 +12676,58 @@ function CONTROLLABLE:_GetController() return nil end +-- Get methods + +--- Returns the UNITs wrappers of the DCS Units of the Controllable (default is a GROUP). +-- @param #CONTROLLABLE self +-- @return #list The UNITs wrappers. +function CONTROLLABLE:GetUnits() + self:F2( { self.ControllableName } ) + local DCSControllable = self:GetDCSObject() + + if DCSControllable then + local DCSUnits = DCSControllable:getUnits() + local Units = {} + for Index, UnitData in pairs( DCSUnits ) do + Units[#Units+1] = UNIT:Find( UnitData ) + end + self:T3( Units ) + return Units + end + + return nil +end + + +--- Returns the health. Dead controllables have health <= 1.0. +-- @param #CONTROLLABLE self +-- @return #number The controllable health value (unit or group average). +-- @return #nil The controllable is not existing or alive. +function CONTROLLABLE:GetLife() + self:F2( self.ControllableName ) + + local DCSControllable = self:GetDCSObject() + + if DCSControllable then + local UnitLife = 0 + local Units = self:GetUnits() + if #Units == 1 then + local Unit = Units[1] -- Wrapper.Unit#UNIT + UnitLife = Unit:GetLife() + else + local UnitLifeTotal = 0 + for UnitID, Unit in pairs( Units ) do + local Unit = Unit -- Wrapper.Unit#UNIT + UnitLifeTotal = UnitLifeTotal + Unit:GetLife() + end + UnitLife = UnitLifeTotal / #Units + end + return UnitLife + end + + return nil +end + -- Tasks @@ -12707,7 +12787,7 @@ function CONTROLLABLE:SetTask( DCSTask, WaitTime ) if DCSControllable then local Controller = self:_GetController() - self:E(Controller) + self:T3( Controller ) -- When a controllable SPAWNs, it takes about a second to get the controllable in the simulator. Setting tasks to unspawned controllables provides unexpected results. -- Therefore we schedule the functions to set the mission and options for the Controllable. @@ -12787,6 +12867,10 @@ function CONTROLLABLE:TaskCombo( DCSTasks ) tasks = DCSTasks } } + + for TaskID, Task in ipairs( DCSTasks ) do + self:E( Task ) + end self:T3( { DCSTaskCombo } ) return DCSTaskCombo @@ -12972,22 +13056,24 @@ function CONTROLLABLE:TaskAttackUnit( AttackUnit, WeaponType, WeaponExpend, Atta -- } local DCSTask - DCSTask = { id = 'AttackUnit', + DCSTask = { + id = 'AttackUnit', params = { - altitudeEnabled = false, + altitudeEnabled = true, unitId = AttackUnit:GetID(), attackQtyLimit = AttackQtyLimit or false, - attackQty = AttackQty or 1, + attackQty = AttackQty or 2, expend = WeaponExpend or "Auto", altitude = 2000, - directionEnabled = false, - groupAttack = false, - weaponType = WeaponType or 1073741822, + directionEnabled = true, + groupAttack = true, + --weaponType = WeaponType or 1073741822, direction = Direction or 0, - }, - }, + } + } - self:E( { DCSTask } ) + self:E( DCSTask ) + return DCSTask end @@ -14699,10 +14785,7 @@ function CONTROLLABLE:WayPointExecute( WayPoint, WaitTime ) return self end --- Message APIs - - ---- This module contains the GROUP class. +-- Message APIs--- This module contains the GROUP class. -- -- 1) @{Wrapper.Group#GROUP} class, extends @{Wrapper.Controllable#CONTROLLABLE} -- ============================================================= @@ -14909,6 +14992,23 @@ function GROUP:GetDCSObject() return nil end +--- Returns the @{Dcs.DCSTypes#Position3} position vectors indicating the point and direction vectors in 3D of the POSITIONABLE within the mission. +-- @param Wrapper.Positionable#POSITIONABLE self +-- @return Dcs.DCSTypes#Position The 3D position vectors of the POSITIONABLE. +-- @return #nil The POSITIONABLE is not existing or alive. +function GROUP:GetPositionVec3() -- Overridden from POSITIONABLE:GetPositionVec3() + self:F2( self.PositionableName ) + + local DCSPositionable = self:GetDCSObject() + + if DCSPositionable then + local PositionablePosition = DCSPositionable:getUnits()[1]:getPosition().p + self:T3( PositionablePosition ) + return PositionablePosition + end + + return nil +end --- Returns if the DCS Group is alive. -- When the group exists at run-time, this method will return true, otherwise false. @@ -15095,26 +15195,6 @@ function GROUP:GetInitialSize() return nil end ---- Returns the UNITs wrappers of the DCS Units of the DCS Group. --- @param #GROUP self --- @return #table The UNITs wrappers. -function GROUP:GetUnits() - self:F2( { self.GroupName } ) - local DCSGroup = self:GetDCSObject() - - if DCSGroup then - local DCSUnits = DCSGroup:getUnits() - local Units = {} - for Index, UnitData in pairs( DCSUnits ) do - Units[#Units+1] = UNIT:Find( UnitData ) - end - self:T3( Units ) - return Units - end - - return nil -end - --- Returns the DCS Units of the DCS Group. -- @param #GROUP self @@ -15586,6 +15666,32 @@ function GROUP:CalculateThreatLevelA2G() return MaxThreatLevelA2G end +--- Returns true if the first unit of the GROUP is in the air. +-- @param Wrapper.Group#GROUP self +-- @return #boolean true if in the first unit of the group is in the air. +-- @return #nil The GROUP is not existing or not alive. +function GROUP:InAir() + self:F2( self.GroupName ) + + local DCSGroup = self:GetDCSObject() + + if DCSGroup then + local DCSUnit = DCSGroup:getUnit(1) + if DCSUnit then + local GroupInAir = DCSGroup:getUnit(1):inAir() + self:T3( GroupInAir ) + return GroupInAir + end + end + + return nil +end + +function GROUP:OnReSpawn( ReSpawnFunction ) + + self.ReSpawnFunction = ReSpawnFunction +end + --- This module contains the UNIT class. -- @@ -16056,6 +16162,25 @@ function UNIT:GetFuel() return nil end +--- Returns the UNIT in a UNIT list of one element. +-- @param #UNIT self +-- @return #list The UNITs wrappers. +function UNIT:GetUnits() + self:F2( { self.UnitName } ) + local DCSUnit = self:GetDCSObject() + + if DCSUnit then + local DCSUnits = DCSUnit:getUnits() + local Units = {} + Units[1] = UNIT:Find( DCSUnit ) + self:T3( Units ) + return Units + end + + return nil +end + + --- Returns the unit's health. Dead units has health <= 1.0. -- @param #UNIT self -- @return #number The Unit's health value. @@ -16388,6 +16513,24 @@ function UNIT:IsShip() return nil end +--- Returns true if the UNIT is in the air. +-- @param Wrapper.Positionable#UNIT self +-- @return #boolean true if in the air. +-- @return #nil The UNIT is not existing or alive. +function UNIT:InAir() + self:F2( self.UnitName ) + + local DCSUnit = self:GetDCSObject() + + if DCSUnit then + local UnitInAir = DCSUnit:inAir() + self:T3( UnitInAir ) + return UnitInAir + end + + return nil +end + --- This module contains the CLIENT class. -- -- 1) @{Wrapper.Client#CLIENT} class, extends @{Wrapper.Unit#UNIT} @@ -18801,11 +18944,14 @@ function SPAWN:ReSpawn( SpawnIndex ) local SpawnGroup = self:SpawnWithIndex( SpawnIndex ) if SpawnGroup and WayPoints then -- If there were WayPoints set, then Re-Execute those WayPoints! - self:E( WayPoints ) SpawnGroup:WayPointInitialize( WayPoints ) SpawnGroup:WayPointExecute( 1, 5 ) end + if SpawnGroup.ReSpawnFunction then + SpawnGroup:ReSpawnFunction() + end + return SpawnGroup end @@ -24206,13 +24352,12 @@ function DETECTION_AREAS:CreateDetectionSets() end ---- SP:N MP:Y AI:Y HU:N TYP:A -- This module contains the AI_BALANCER class. AI Balancing will replace in multi player missions +--- Single-Player:**No** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**All** -- **AI Balancing will replace in multi player missions -- non-occupied human slots with AI groups, in order to provide an engaging simulation environment, --- even when there are hardly any players in the mission. +-- even when there are hardly any players in the mission.** -- -- ![Banner Image](..\Presentations\AI_Balancer\Dia1.JPG) -- --- Examples can be found in the test missions. -- -- === -- @@ -24281,6 +24426,8 @@ end -- -- Hereby the change log: -- +-- 2017-01-17: There is still a problem with AI being destroyed, but not respawned. Need to check further upon that. +-- -- 2017-01-08: AI_BALANCER:**InitSpawnInterval( Earliest, Latest )** added. -- -- === @@ -24290,7 +24437,6 @@ end -- ### Contributions: -- -- * **[Dutch_Baron](https://forums.eagle.ru/member.php?u=112075)**: Working together with James has resulted in the creation of the AI_BALANCER class. James has shared his ideas on balancing AI with air units, and together we made a first design which you can use now :-) --- -- * **SNAFU**: Had a couple of mails with the guys to validate, if the same concept in the GCI/CAP script could be reworked within MOOSE. None of the script code has been used however within the new AI_BALANCER moose class. -- -- ### Authors: @@ -24439,16 +24585,15 @@ end --- @param #AI_BALANCER self function AI_BALANCER:onenterMonitoring( SetGroup ) - self:E( { self.SetClient:Count() } ) - self.SetClient:Flush() + self:T2( { self.SetClient:Count() } ) + --self.SetClient:Flush() self.SetClient:ForEachClient( --- @param Wrapper.Client#CLIENT Client function( Client ) - self:E(Client.ClientName) + self:T3(Client.ClientName) local AIGroup = self.Set:Get( Client.UnitName ) -- Wrapper.Group#GROUP - self:E({Client:IsAlive()}) if Client:IsAlive() then if AIGroup and AIGroup:IsAlive() == true then @@ -24463,16 +24608,16 @@ function AI_BALANCER:onenterMonitoring( SetGroup ) local PlayerInRange = { Value = false } local RangeZone = ZONE_RADIUS:New( 'RangeZone', AIGroup:GetVec2(), self.ReturnTresholdRange ) - self:E( RangeZone ) + self:T2( RangeZone ) _DATABASE:ForEachPlayer( --- @param Wrapper.Unit#UNIT RangeTestUnit function( RangeTestUnit, RangeZone, AIGroup, PlayerInRange ) - self:E( { PlayerInRange, RangeTestUnit.UnitName, RangeZone.ZoneName } ) + self:T2( { PlayerInRange, RangeTestUnit.UnitName, RangeZone.ZoneName } ) if RangeTestUnit:IsInZone( RangeZone ) == true then - self:E( "in zone" ) + self:T2( "in zone" ) if RangeTestUnit:GetCoalition() ~= AIGroup:GetCoalition() then - self:E( "in range" ) + self:T2( "in range" ) PlayerInRange.Value = true end end @@ -24493,7 +24638,7 @@ function AI_BALANCER:onenterMonitoring( SetGroup ) end else if not AIGroup or not AIGroup:IsAlive() == true then - self:E( "Client " .. Client.UnitName .. " not alive." ) + self:T( "Client " .. Client.UnitName .. " not alive." ) if not self.SpawnQueue[Client.UnitName] then -- Spawn a new AI taking into account the spawn interval Earliest, Latest self:__Spawn( math.random( self.Earliest, self.Latest ), Client.UnitName ) @@ -24511,113 +24656,125 @@ end ---- (AI) (FSM) Make AI patrol routes or zones. +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Air Patrolling or Staging.** +-- +-- ![Banner Image](..\Presentations\AI_Patrol\Dia1.JPG) +-- -- -- === -- --- 1) @{#AI_PATROLZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} --- ================================================================ --- The @{#AI_PATROLZONE} class implements the core functions to patrol a @{Zone} by an AIR @{Controllable} @{Group}. --- The patrol algorithm works that for each airplane patrolling, upon arrival at the patrol zone, --- a random point is selected as the route point within the 3D space, within the given boundary limits. --- The airplane will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. --- Upon arrival at the random 3D point, a new 3D random point will be selected within the patrol zone using the given limits. --- This cycle will continue until a fuel treshold has been reached by the airplane. +-- # 1) @{#AI_PATROL_ZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} +-- +-- The @{#AI_PATROL_ZONE} class implements the core functions to patrol a @{Zone} by an AI @{Controllable} or @{Group}. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia3.JPG) +-- +-- The AI_PATROL_ZONE is assigned a @(Group) and this must be done before the AI_PATROL_ZONE process can be started using the **Start** event. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia4.JPG) +-- +-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia5.JPG) +-- +-- This cycle will continue. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia6.JPG) +-- +-- During the patrol, the AI will detect enemy targets, which are reported through the **Detected** event. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia9.JPG) +-- +---- Note that the enemy is not engaged! To model enemy engagement, either tailor the **Detected** event, or +-- use derived AI_ classes to model AI offensive or defensive behaviour. +-- +-- ![Process](..\Presentations\AI_Patrol\Dia10.JPG) +-- +-- Until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. -- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. -- --- 1.1) AI_PATROLZONE constructor: --- ---------------------------- +-- ![Process](..\Presentations\AI_Patrol\Dia11.JPG) +-- +-- ## 1.1) AI_PATROL_ZONE constructor -- --- * @{#AI_PATROLZONE.New}(): Creates a new AI_PATROLZONE object. +-- * @{#AI_PATROL_ZONE.New}(): Creates a new AI_PATROL_ZONE object. -- --- 1.2) AI_PATROLZONE state machine: --- ---------------------------------- --- The AI_PATROLZONE is a state machine: it manages the different events and states of the AIControllable it is controlling. +-- ## 1.2) AI_PATROL_ZONE is a FSM -- --- ### 1.2.1) AI_PATROLZONE Events: +-- ![Process](..\Presentations\AI_Patrol\Dia2.JPG) -- --- * @{#AI_PATROLZONE.Route}( AIControllable ): A new 3D route point is selected and the AIControllable will fly towards that point with the given speed. --- * @{#AI_PATROLZONE.Patrol}( AIControllable ): The AIControllable reports it is patrolling. This event is called every 30 seconds. --- * @{#AI_PATROLZONE.RTB}( AIControllable ): The AIControllable will report return to base. --- * @{#AI_PATROLZONE.End}( AIControllable ): The end of the AI_PATROLZONE process. --- * @{#AI_PATROLZONE.Dead}( AIControllable ): The AIControllable is dead. The AI_PATROLZONE process will be ended. +-- ### 1.2.1) AI_PATROL_ZONE States -- --- ### 1.2.2) AI_PATROLZONE States: +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Returning** ( Group ): The AI is returning to Base.. -- --- * **Route**: A new 3D route point is selected and the AIControllable will fly towards that point with the given speed. --- * **Patrol**: The AIControllable is patrolling. This state is set every 30 seconds, so every 30 seconds, a state transition method can be used. --- * **RTB**: The AIControllable reports it wants to return to the base. --- * **Dead**: The AIControllable is dead ... --- * **End**: The process has come to an end. --- --- ### 1.2.3) AI_PATROLZONE state transition methods: +-- ### 1.2.2) AI_PATROL_ZONE Events -- --- State transition functions can be set **by the mission designer** customizing or improving the behaviour of the state. --- There are 2 moments when state transition methods will be called by the state machine: --- --- * **Before** the state transition. --- The state transition method needs to start with the name **OnBefore + the name of the state**. --- If the state transition method returns false, then the processing of the state transition will not be done! --- If you want to change the behaviour of the AIControllable at this event, return false, --- but then you'll need to specify your own logic using the AIControllable! --- --- * **After** the state transition. --- The state transition method needs to start with the name **OnAfter + the name of the state**. --- These state transition methods need to provide a return value, which is specified at the function description. --- --- An example how to manage a state transition for an AI_PATROLZONE object **Patrol** for the state **RTB**: --- --- local PatrolZoneGroup = GROUP:FindByName( "Patrol Zone" ) --- local PatrolZone = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) --- --- local PatrolSpawn = SPAWN:New( "Patrol Group" ) --- local PatrolGroup = PatrolSpawn:Spawn() --- --- local Patrol = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 300, 600 ) --- Patrol:SetControllable( PatrolGroup ) --- Patrol:ManageFuel( 0.2, 60 ) --- --- **OnBefore**RTB( AIGroup ) will be called by the AI_PATROLZONE object when the AIGroup reports RTB, but **before** the RTB default action is processed by the AI_PATROLZONE object. --- --- --- State transition function for the AI_PATROLZONE **Patrol** object --- -- @param #AI_PATROLZONE self --- -- @param Wrapper.Controllable#CONTROLLABLE AIGroup --- -- @return #boolean If false is returned, then the OnAfter state transition method will not be called. --- function Patrol:OnBeforeRTB( AIGroup ) --- AIGroup:MessageToRed( "Returning to base", 20 ) --- end --- --- **OnAfter**RTB( AIGroup ) will be called by the AI_PATROLZONE object when the AIGroup reports RTB, but **after** the RTB default action was processed by the AI_PATROLZONE object. --- --- --- State transition function for the AI_PATROLZONE **Patrol** object --- -- @param #AI_PATROLZONE self --- -- @param Wrapper.Controllable#CONTROLLABLE AIGroup --- -- @return #Wrapper.Controllable#CONTROLLABLE The new AIGroup object that is set to be patrolling the zone. --- function Patrol:OnAfterRTB( AIGroup ) --- return PatrolSpawn:Spawn() --- end +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. -- --- 1.3) Manage the AI_PATROLZONE parameters: --- ------------------------------------------ --- The following methods are available to modify the parameters of a AI_PATROLZONE object: +-- ## 1.3) Set or Get the AI controllable -- --- * @{#AI_PATROLZONE.SetControllable}(): Set the AIControllable. --- * @{#AI_PATROLZONE.GetControllable}(): Get the AIControllable. --- * @{#AI_PATROLZONE.SetSpeed}(): Set the patrol speed of the AI, for the next patrol. --- * @{#AI_PATROLZONE.SetAltitude}(): Set altitude of the AI, for the next patrol. +-- * @{#AI_PATROL_ZONE.SetControllable}(): Set the AIControllable. +-- * @{#AI_PATROL_ZONE.GetControllable}(): Get the AIControllable. +-- +-- ## 1.4) Set the Speed and Altitude boundaries of the AI controllable +-- +-- * @{#AI_PATROL_ZONE.SetSpeed}(): Set the patrol speed boundaries of the AI, for the next patrol. +-- * @{#AI_PATROL_ZONE.SetAltitude}(): Set altitude boundaries of the AI, for the next patrol. -- --- 1.3) Manage the out of fuel in the AI_PATROLZONE: --- ---------------------------------------------- --- When the AIControllable is out of fuel, it is required that a new AIControllable is started, before the old AIControllable can return to the home base. +-- ## 1.5) Manage the detection process of the AI controllable +-- +-- The detection process of the AI controllable can be manipulated. +-- Detection requires an amount of CPU power, which has an impact on your mission performance. +-- Only put detection on when absolutely necessary, and the frequency of the detection can also be set. +-- +-- * @{#AI_PATROL_ZONE.SetDetectionOn}(): Set the detection on. The AI will detect for targets. +-- * @{#AI_PATROL_ZONE.SetDetectionOff}(): Set the detection off, the AI will not detect for targets. The existing target list will NOT be erased. +-- +-- The detection frequency can be set with @{#AI_PATROL_ZONE.SetDetectionInterval}( seconds ), where the amount of seconds specify how much seconds will be waited before the next detection. +-- Use the method @{#AI_PATROL_ZONE.GetDetectedUnits}() to obtain a list of the @{Unit}s detected by the AI. +-- +-- The detection can be filtered to potential targets in a specific zone. +-- Use the method @{#AI_PATROL_ZONE.SetDetectionZone}() to set the zone where targets need to be detected. +-- Note that when the zone is too far away, or the AI is not heading towards the zone, or the AI is too high, no targets may be detected +-- according the weather conditions. +-- +-- ## 1.6) Manage the "out of fuel" in the AI_PATROL_ZONE +-- +-- When the AI is out of fuel, it is required that a new AI is started, before the old AI can return to the home base. -- Therefore, with a parameter and a calculation of the distance to the home base, the fuel treshold is calculated. --- When the fuel treshold is reached, the AIControllable will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROLZONE. --- Once the time is finished, the old AIControllable will return to the base. --- Use the method @{#AI_PATROLZONE.ManageFuel}() to have this proces in place. +-- When the fuel treshold is reached, the AI will continue for a given time its patrol task in orbit, +-- while a new AI is targetted to the AI_PATROL_ZONE. +-- Once the time is finished, the old AI will return to the base. +-- Use the method @{#AI_PATROL_ZONE.ManageFuel}() to have this proces in place. +-- +-- ## 1.7) Manage "damage" behaviour of the AI in the AI_PATROL_ZONE +-- +-- When the AI is damaged, it is required that a new AIControllable is started. However, damage cannon be foreseen early on. +-- Therefore, when the damage treshold is reached, the AI will return immediately to the home base (RTB). +-- Use the method @{#AI_PATROL_ZONE.ManageDamage}() to have this proces in place. -- -- ==== -- --- **API CHANGE HISTORY** --- ====================== +-- # **OPEN ISSUES** +-- +-- 2017-01-17: When Spawned AI is located at an airbase, it will be routed first back to the airbase after take-off. +-- +-- 2016-01-17: +-- -- Fixed problem with AI returning to base too early and unexpected. +-- -- ReSpawning of AI will reset the AI_PATROL and derived classes. +-- -- Checked the correct workings of SCHEDULER, and it DOES work correctly. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** -- -- The underlying change log documents the API changes. Please read this carefully. The following notation is used: -- @@ -24626,257 +24783,282 @@ end -- -- Hereby the change log: -- +-- 2017-01-17: Rename of class: **AI\_PATROL\_ZONE** is the new name for the old _AI\_PATROLZONE_. +-- +-- 2017-01-15: Complete revision. AI_PATROL_ZONE is the base class for other AI_PATROL like classes. +-- -- 2016-09-01: Initial class and API. -- -- === -- --- AUTHORS and CONTRIBUTIONS --- ========================= +-- # **AUTHORS and CONTRIBUTIONS** -- -- ### Contributions: -- --- * **DutchBaron**: Testing. --- * **Pikey**: Testing and API concept review. +-- * **[Dutch_Baron](https://forums.eagle.ru/member.php?u=112075)**: Working together with James has resulted in the creation of the AI_BALANCER class. James has shared his ideas on balancing AI with air units, and together we made a first design which you can use now :-) +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Testing and API concept review. -- -- ### Authors: -- -- * **FlightControl**: Design & Programming. -- --- -- @module AI_Patrol ---- AI_PATROLZONE class --- @type AI_PATROLZONE +--- AI_PATROL_ZONE class +-- @type AI_PATROL_ZONE -- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. -- @field Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. -- @field Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @field Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. -- @field Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @field Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @field Functional.Spawn#SPAWN CoordTest -- @extends Core.Fsm#FSM_CONTROLLABLE -AI_PATROLZONE = { - ClassName = "AI_PATROLZONE", +AI_PATROL_ZONE = { + ClassName = "AI_PATROL_ZONE", } - - ---- Creates a new AI_PATROLZONE object --- @param #AI_PATROLZONE self +--- Creates a new AI_PATROL_ZONE object +-- @param #AI_PATROL_ZONE self -- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. -- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @return #AI_PATROLZONE self +-- @return #AI_PATROL_ZONE self -- @usage --- -- Define a new AI_PATROLZONE Object. This PatrolArea will patrol an AIControllable within PatrolZone between 3000 and 6000 meters, with a variying speed between 600 and 900 km/h. +-- -- Define a new AI_PATROL_ZONE Object. This PatrolArea will patrol an AIControllable within PatrolZone between 3000 and 6000 meters, with a variying speed between 600 and 900 km/h. -- PatrolZone = ZONE:New( 'PatrolZone' ) -- PatrolSpawn = SPAWN:New( 'Patrol Group' ) --- PatrolArea = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 600, 900 ) -function AI_PATROLZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) +-- PatrolArea = AI_PATROL_ZONE:New( PatrolZone, 3000, 6000, 600, 900 ) +function AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) -- Inherits from BASE - local self = BASE:Inherit( self, FSM_CONTROLLABLE:New() ) -- Core.Fsm#FSM_CONTROLLABLE + local self = BASE:Inherit( self, FSM_CONTROLLABLE:New() ) -- #AI_PATROL_ZONE - self.PatrolZone = PatrolZone + self.PatrolZone = PatrolZone self.PatrolFloorAltitude = PatrolFloorAltitude self.PatrolCeilingAltitude = PatrolCeilingAltitude self.PatrolMinSpeed = PatrolMinSpeed self.PatrolMaxSpeed = PatrolMaxSpeed - self.PatrolFuelTresholdPercentage = 0.2 + self:SetDetectionOn() + self.CheckStatus = true - self:SetStartState( "None" ) + self:ManageFuel( .2, 60 ) + self:ManageDamage( 1 ) + + self:SetDetectionInterval( 30 ) -do self:AddTransition( "*", "Start", "Route" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. + self.DetectedUnits = {} -- This table contains the targets detected during patrol. + + self:SetStartState( "None" ) - --- OnLeave State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnLeaveRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. + self:AddTransition( "None", "Start", "Patrolling" ) - --- OnEnter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnEnterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnBefore Transition Handler for Event Start. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeStart +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Start. +-- @function [parent=#AI_PATROL_ZONE] OnAfterStart +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Start. - -- @function [parent=#AI_PATROLZONE] OnBeforeStart - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Start. +-- @function [parent=#AI_PATROL_ZONE] Start +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Start. - -- @function [parent=#AI_PATROLZONE] OnAfterStart - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Start. +-- @function [parent=#AI_PATROL_ZONE] __Start +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Patrolling. +-- @function [parent=#AI_PATROL_ZONE] OnLeavePatrolling +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Patrolling. +-- @function [parent=#AI_PATROL_ZONE] OnEnterPatrolling +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Patrolling", "Route", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event Route. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeRoute +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Route. +-- @function [parent=#AI_PATROL_ZONE] OnAfterRoute +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Start. - -- @function [parent=#AI_PATROLZONE] Start - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event Route. +-- @function [parent=#AI_PATROL_ZONE] Route +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Start - -- @function [parent=#AI_PATROLZONE] __Start - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event Route. +-- @function [parent=#AI_PATROL_ZONE] __Route +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE + self:AddTransition( "*", "Status", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. -do self:AddTransition( "*", "Route", "Route" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnBefore Transition Handler for Event Status. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeStatus +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnLeaveRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnEnterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnAfter Transition Handler for Event Status. +-- @function [parent=#AI_PATROL_ZONE] OnAfterStatus +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnBeforeRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Status. +-- @function [parent=#AI_PATROL_ZONE] Status +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Route. - -- @function [parent=#AI_PATROLZONE] OnAfterRoute - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Status. +-- @function [parent=#AI_PATROL_ZONE] __Status +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Detect", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeDetect +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] OnAfterDetect +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Route. - -- @function [parent=#AI_PATROLZONE] Route - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] Detect +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Route - -- @function [parent=#AI_PATROLZONE] __Route - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event Detect. +-- @function [parent=#AI_PATROL_ZONE] __Detect +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE + self:AddTransition( "*", "Detected", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. -do self:AddTransition( "*", "Patrol", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnBefore Transition Handler for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeDetected +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. - --- OnLeave State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnLeavePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnEnterPatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- OnAfter Transition Handler for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] OnAfterDetected +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnBefore State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnBeforePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. +--- Synchronous Event Trigger for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] Detected +-- @param #AI_PATROL_ZONE self - --- OnAfter State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnAfterPatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. +--- Asynchronous Event Trigger for Event Detected. +-- @function [parent=#AI_PATROL_ZONE] __Detected +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "RTB", "Returning" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. + +--- OnBefore Transition Handler for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] OnBeforeRTB +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnAfter Transition Handler for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] OnAfterRTB +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- Embedded Event Trigger for Patrol. - -- @function [parent=#AI_PATROLZONE] Patrol - -- @param #AI_PATROLZONE self +--- Synchronous Event Trigger for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] RTB +-- @param #AI_PATROL_ZONE self - --- Delayed Event Trigger for Patrol - -- @function [parent=#AI_PATROLZONE] __Patrol - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. +--- Asynchronous Event Trigger for Event RTB. +-- @function [parent=#AI_PATROL_ZONE] __RTB +-- @param #AI_PATROL_ZONE self +-- @param #number Delay The delay in seconds. -end -- AI_PATROLZONE +--- OnLeave Transition Handler for State Returning. +-- @function [parent=#AI_PATROL_ZONE] OnLeaveReturning +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. -do self:AddTransition( "Patrol", "RTB", "RTB" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROLZONE. +--- OnEnter Transition Handler for State Returning. +-- @function [parent=#AI_PATROL_ZONE] OnEnterReturning +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. - --- OnLeave State Transition for Patrol. - -- @function [parent=#AI_PATROLZONE] OnLeavePatrol - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnEnterRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnBeforeRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for RTB. - -- @function [parent=#AI_PATROLZONE] OnAfterRTB - -- @param #AI_PATROLZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for RTB. - -- @function [parent=#AI_PATROLZONE] RTB - -- @param #AI_PATROLZONE self - - --- Delayed Event Trigger for RTB - -- @function [parent=#AI_PATROLZONE] __RTB - -- @param #AI_PATROLZONE self - -- @param #number Delay The delay in seconds. - -end -- AI_PATROLZONE + self:AddTransition( "*", "Reset", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_PATROL_ZONE. return self end @@ -24885,11 +25067,11 @@ end --- Sets (modifies) the minimum and maximum speed of the patrol. --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. -- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:SetSpeed( PatrolMinSpeed, PatrolMaxSpeed ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetSpeed( PatrolMinSpeed, PatrolMaxSpeed ) self:F2( { PatrolMinSpeed, PatrolMaxSpeed } ) self.PatrolMinSpeed = PatrolMinSpeed @@ -24899,39 +25081,92 @@ end --- Sets the floor and ceiling altitude of the patrol. --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. -- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:SetAltitude( PatrolFloorAltitude, PatrolCeilingAltitude ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetAltitude( PatrolFloorAltitude, PatrolCeilingAltitude ) self:F2( { PatrolFloorAltitude, PatrolCeilingAltitude } ) self.PatrolFloorAltitude = PatrolFloorAltitude self.PatrolCeilingAltitude = PatrolCeilingAltitude end +-- * @{#AI_PATROL_ZONE.SetDetectionOn}(): Set the detection on. The AI will detect for targets. +-- * @{#AI_PATROL_ZONE.SetDetectionOff}(): Set the detection off, the AI will not detect for targets. The existing target list will NOT be erased. +--- Set the detection on. The AI will detect for targets. +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionOn() + self:F2() + + self.DetectUnits = true +end ---- @param Wrapper.Controllable#CONTROLLABLE AIControllable -function _NewPatrolRoute( AIControllable ) +--- Set the detection off. The AI will NOT detect for targets. +-- However, the list of already detected targets will be kept and can be enquired! +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionOff() + self:F2() + + self.DetectUnits = false +end - AIControllable:T( "NewPatrolRoute" ) - local PatrolZone = AIControllable:GetState( AIControllable, "PatrolZone" ) -- PatrolCore.Zone#AI_PATROLZONE - PatrolZone:__Route( 1 ) +--- Set the interval in seconds between each detection executed by the AI. +-- The list of already detected targets will be kept and updated. +-- Newly detected targets will be added, but already detected targets that were +-- not detected in this cycle, will NOT be removed! +-- The default interval is 30 seconds. +-- @param #AI_PATROL_ZONE self +-- @param #number Seconds The interval in seconds. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionInterval( Seconds ) + self:F2() + + if Seconds then + self.DetectInterval = Seconds + else + self.DetectInterval = 30 + end +end + +--- Set the detection zone where the AI is detecting targets. +-- @param #AI_PATROL_ZONE self +-- @param Core.Zone#ZONE DetectionZone The zone where to detect targets. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:SetDetectionZone( DetectionZone ) + self:F2() + + if DetectionZone then + self.DetectZone = DetectionZone + else + self.DetectZone = nil + end +end + +--- Gets a list of @{Wrapper.Unit#UNIT}s that were detected by the AI. +-- No filtering is applied, so, ANY detected UNIT can be in this list. +-- It is up to the mission designer to use the @{Unit} class and methods to filter the targets. +-- @param #AI_PATROL_ZONE self +-- @return #table The list of @{Wrapper.Unit#UNIT}s +function AI_PATROL_ZONE:GetDetectedUnits() + self:F2() + + return self.DetectedUnits end - - ---- When the AIControllable is out of fuel, it is required that a new AIControllable is started, before the old AIControllable can return to the home base. +--- When the AI is out of fuel, it is required that a new AI is started, before the old AI can return to the home base. -- Therefore, with a parameter and a calculation of the distance to the home base, the fuel treshold is calculated. --- When the fuel treshold is reached, the AIControllable will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROLZONE. --- Once the time is finished, the old AIControllable will return to the base. --- @param #AI_PATROLZONE self +-- When the fuel treshold is reached, the AI will continue for a given time its patrol task in orbit, while a new AIControllable is targetted to the AI_PATROL_ZONE. +-- Once the time is finished, the old AI will return to the base. +-- @param #AI_PATROL_ZONE self -- @param #number PatrolFuelTresholdPercentage The treshold in percentage (between 0 and 1) when the AIControllable is considered to get out of fuel. -- @param #number PatrolOutOfFuelOrbitTime The amount of seconds the out of fuel AIControllable will orbit before returning to the base. --- @return #AI_PATROLZONE self -function AI_PATROLZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuelOrbitTime ) +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuelOrbitTime ) self.PatrolManageFuel = true self.PatrolFuelTresholdPercentage = PatrolFuelTresholdPercentage @@ -24940,60 +25175,165 @@ function AI_PATROLZONE:ManageFuel( PatrolFuelTresholdPercentage, PatrolOutOfFuel return self end +--- When the AI is damaged beyond a certain treshold, it is required that the AI returns to the home base. +-- However, damage cannot be foreseen early on. +-- Therefore, when the damage treshold is reached, +-- the AI will return immediately to the home base (RTB). +-- Note that for groups, the average damage of the complete group will be calculated. +-- So, in a group of 4 airplanes, 2 lost and 2 with damage 0.2, the damage treshold will be 0.25. +-- @param #AI_PATROL_ZONE self +-- @param #number PatrolDamageTreshold The treshold in percentage (between 0 and 1) when the AI is considered to be damaged. +-- @return #AI_PATROL_ZONE self +function AI_PATROL_ZONE:ManageDamage( PatrolDamageTreshold ) + + self.PatrolManageDamage = true + self.PatrolDamageTreshold = PatrolDamageTreshold + + return self +end + --- Defines a new patrol route using the @{Process_PatrolZone} parameters and settings. --- @param #AI_PATROLZONE self --- @return #AI_PATROLZONE self -function AI_PATROLZONE:onenterRoute() +-- @param #AI_PATROL_ZONE self +-- @return #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_PATROL_ZONE:onafterStart( Controllable, From, Event, To ) + self:F2() + + self:__Route( 5 ) -- Route to the patrol point. The asynchronous trigger is important, because a spawned group and units takes at least one second to come live. + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every 30 seconds. + + Controllable:OptionROEHoldFire() + Controllable:OptionROTVertical() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + +end + + +--- @param #AI_PATROL_ZONE self +--- @param Wrapper.Controllable#CONTROLLABLE Controllable +function AI_PATROL_ZONE:onbeforeDetect( Controllable, From, Event, To ) + + return self.DetectUnits +end + +--- @param #AI_PATROL_ZONE self +--- @param Wrapper.Controllable#CONTROLLABLE Controllable +function AI_PATROL_ZONE:onafterDetect( Controllable, From, Event, To ) + + local Detected = false + + local DetectedTargets = Controllable:GetDetectedTargets() + for TargetID, Target in pairs( DetectedTargets or {} ) do + local TargetObject = Target.object + self:T( TargetObject ) + if TargetObject and TargetObject:isExist() and TargetObject.id_ < 50000000 then + + local TargetUnit = UNIT:Find( TargetObject ) + local TargetUnitName = TargetUnit:GetName() + + if self.DetectionZone then + if TargetUnit:IsInZone( self.DetectionZone ) then + self:T( {"Detected ", TargetUnit } ) + self.DetectedUnits[TargetUnit] = TargetUnit + Detected = true + end + else + self.DetectedUnits[TargetUnit] = TargetUnit + Detected = true + end + end + end + + if Detected == true then + self:__Detected( 1 ) + end + + self:__Detect( self.DetectInterval ) +end + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +-- This statis method is called from the route path within the last task at the last waaypoint of the Controllable. +-- Note that this method is required, as triggers the next route when patrolling for the Controllable. +function AI_PATROL_ZONE:_NewPatrolRoute( AIControllable ) + + local PatrolZone = AIControllable:GetState( AIControllable, "PatrolZone" ) -- PatrolCore.Zone#AI_PATROL_ZONE + PatrolZone:__Route( 1 ) +end + + +--- Defines a new patrol route using the @{Process_PatrolZone} parameters and settings. +-- @param #AI_PATROL_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_PATROL_ZONE:onafterRoute( Controllable, From, Event, To ) self:F2() - local PatrolRoute = {} + -- When RTB, don't allow anymore the routing. + if From == "RTB" then + return + end + if self.Controllable:IsAlive() then - --- Determine if the AIControllable is within the PatrolZone. + -- Determine if the AIControllable is within the PatrolZone. -- If not, make a waypoint within the to that the AIControllable will fly at maximum speed to that point. --- --- Calculate the current route point. --- local CurrentVec2 = self.Controllable:GetVec2() --- local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() --- local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) --- local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( --- POINT_VEC3.RoutePointAltType.BARO, --- POINT_VEC3.RoutePointType.TurningPoint, --- POINT_VEC3.RoutePointAction.TurningPoint, --- ToPatrolZoneSpeed, --- true --- ) --- --- PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + local PatrolRoute = {} + + -- Calculate the current route point of the controllable as the start point of the route. + -- However, when the controllable is not in the air, + -- the controllable current waypoint is probably the airbase... + -- Thus, if we would take the current waypoint as the startpoint, upon take-off, the controllable flies + -- immediately back to the airbase, and this is not correct. + -- Therefore, when on a runway, get as the current route point a random point within the PatrolZone. + -- This will make the plane fly immediately to the patrol zone. - self:T2( PatrolRoute ) - - if self.Controllable:IsNotInZone( self.PatrolZone ) then - --- Find a random 2D point in PatrolZone. - local ToPatrolZoneVec2 = self.PatrolZone:GetRandomVec2() - self:T2( ToPatrolZoneVec2 ) - - --- Define Speed and Altitude. - local ToPatrolZoneAltitude = math.random( self.PatrolFloorAltitude, self.PatrolCeilingAltitude ) + if self.Controllable:InAir() == false then + self:E( "Not in the air, finding route path within PatrolZone" ) + local CurrentVec2 = self.Controllable:GetVec2() + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) local ToPatrolZoneSpeed = self.PatrolMaxSpeed - self:T2( ToPatrolZoneSpeed ) - - --- Obtain a 3D @{Point} from the 2D point + altitude. - local ToPatrolZonePointVec3 = POINT_VEC3:New( ToPatrolZoneVec2.x, ToPatrolZoneAltitude, ToPatrolZoneVec2.y ) - - --- Create a route point of type air. - local ToPatrolZoneRoutePoint = ToPatrolZonePointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToPatrolZoneSpeed, - true - ) - - PatrolRoute[#PatrolRoute+1] = ToPatrolZoneRoutePoint - - end + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TakeOffParking, + POINT_VEC3.RoutePointAction.FromParkingArea, + ToPatrolZoneSpeed, + true + ) + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + else + self:E( "In the air, finding route path within PatrolZone" ) + local CurrentVec2 = self.Controllable:GetVec2() + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToPatrolZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToPatrolZoneSpeed, + true + ) + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + end + --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. @@ -25018,6 +25358,8 @@ function AI_PATROLZONE:onenterRoute() true ) + --self.CoordTest:SpawnFromVec3( ToTargetPointVec3:GetVec3() ) + --ToTargetPointVec3:SmokeRed() PatrolRoute[#PatrolRoute+1] = ToTargetRoutePoint @@ -25027,25 +25369,31 @@ function AI_PATROLZONE:onenterRoute() --- Do a trick, link the NewPatrolRoute function of the PATROLGROUP object to the AIControllable in a temporary variable ... self.Controllable:SetState( self.Controllable, "PatrolZone", self ) - self.Controllable:WayPointFunction( #PatrolRoute, 1, "_NewPatrolRoute" ) + self.Controllable:WayPointFunction( #PatrolRoute, 1, "AI_PATROL_ZONE:_NewPatrolRoute" ) --- NOW ROUTE THE GROUP! - self.Controllable:WayPointExecute( 1, 5 ) - - self:__Patrol( 30 ) + self.Controllable:WayPointExecute( 1, 2 ) end - + end +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onbeforeStatus() ---- @param #AI_PATROLZONE self -function AI_PATROLZONE:onenterPatrol() + return self.CheckStatus +end + +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onafterStatus() self:F2() if self.Controllable and self.Controllable:IsAlive() then + local RTB = false + local Fuel = self.Controllable:GetUnit(1):GetFuel() if Fuel < self.PatrolFuelTresholdPercentage then + self:E( self.Controllable:GetName() .. " is out of fuel:" .. Fuel .. ", RTB!" ) local OldAIControllable = self.Controllable local AIControllableTemplate = self.Controllable:GetTemplate() @@ -25053,14 +25401,1145 @@ function AI_PATROLZONE:onenterPatrol() local TimedOrbitTask = OldAIControllable:TaskControlled( OrbitTask, OldAIControllable:TaskCondition(nil,nil,nil,nil,self.PatrolOutOfFuelOrbitTime,nil ) ) OldAIControllable:SetTask( TimedOrbitTask, 10 ) + RTB = true + else + end + + -- TODO: Check GROUP damage function. + local Damage = self.Controllable:GetLife() + if Damage <= self.PatrolDamageTreshold then + self:E( self.Controllable:GetName() .. " is damaged:" .. Damage .. ", RTB!" ) + RTB = true + end + + if RTB == true then self:RTB() else - self:__Patrol( 30 ) -- Execute the Patrol event after 30 seconds. + self:__Status( 30 ) -- Execute the Patrol event after 30 seconds. end end +end + +--- @param #AI_PATROL_ZONE self +function AI_PATROL_ZONE:onafterRTB() + self:F2() + + if self.Controllable and self.Controllable:IsAlive() then + + self:SetDetectionOff() + self.CheckStatus = false + + local PatrolRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToPatrolZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToPatrolZoneSpeed, + true + ) + + PatrolRoute[#PatrolRoute+1] = CurrentRoutePoint + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( PatrolRoute ) + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 1 ) + + end + +end +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Provide Close Air Support to friendly ground troops.** +-- +-- ![Banner Image](..\Presentations\AI_Cas\Dia1.JPG) +-- +-- +-- === +-- +-- # 1) @{#AI_CAS_ZONE} class, extends @{AI.AI_Patrol#AI_PATROL_ZONE} +-- +-- @{#AI_CAS_ZONE} derives from the @{AI.AI_Patrol#AI_PATROL_ZONE}, inheriting its methods and behaviour. +-- +-- The @{#AI_CAS_ZONE} class implements the core functions to provide Close Air Support in an Engage @{Zone} by an AIR @{Controllable} or @{Group}. +-- The AI_CAS_ZONE runs a process. It holds an AI in a Patrol Zone and when the AI is commanded to engage, it will fly to an Engage Zone. +-- +-- ![HoldAndEngage](..\Presentations\AI_Cas\Dia3.JPG) +-- +-- The AI_CAS_ZONE is assigned a @(Group) and this must be done before the AI_CAS_ZONE process can be started through the **Start** event. +-- +-- ![Start Event](..\Presentations\AI_Cas\Dia4.JPG) +-- +-- Upon started, The AI will **Route** itself towards the random 3D point within a patrol zone, +-- using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- This cycle will continue until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. +-- +-- ![Route Event](..\Presentations\AI_Cas\Dia5.JPG) +-- +-- When the AI is commanded to provide Close Air Support (through the event **Engage**), the AI will fly towards the Engage Zone. +-- Any target that is detected in the Engage Zone will be reported and will be destroyed by the AI. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia6.JPG) +-- +-- The AI will detect the targets and will only destroy the targets within the Engage Zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia7.JPG) +-- +-- Every target that is destroyed, is reported< by the AI. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia8.JPG) +-- +-- Note that the AI does not know when the Engage Zone is cleared, and therefore will keep circling in the zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia9.JPG) +-- +-- Until it is notified through the event **Accomplish**, which is to be triggered by an observing party: +-- +-- * a FAC +-- * a timed event +-- * a menu option selected by a human +-- * a condition +-- * others ... +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia10.JPG) +-- +-- When the AI has accomplished the CAS, it will fly back to the Patrol Zone. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia11.JPG) +-- +-- It will keep patrolling there, until it is notified to RTB or move to another CAS Zone. +-- It can be notified to go RTB through the **RTB** event. +-- +-- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. +-- +-- ![Engage Event](..\Presentations\AI_Cas\Dia12.JPG) +-- +-- # 1.1) AI_CAS_ZONE constructor +-- +-- * @{#AI_CAS_ZONE.New}(): Creates a new AI_CAS_ZONE object. +-- +-- ## 1.2) AI_CAS_ZONE is a FSM +-- +-- ![Process](..\Presentations\AI_Cas\Dia2.JPG) +-- +-- ### 1.2.1) AI_CAS_ZONE States +-- +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Engaging** ( Group ): The AI is engaging the targets in the Engage Zone, executing CAS. +-- * **Returning** ( Group ): The AI is returning to Base.. +-- +-- ### 1.2.2) AI_CAS_ZONE Events +-- +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **Engage** ( Group ): Engage the AI to provide CAS in the Engage Zone, destroying any target it finds. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** +-- +-- The underlying change log documents the API changes. Please read this carefully. The following notation is used: +-- +-- * **Added** parts are expressed in bold type face. +-- * _Removed_ parts are expressed in italic type face. +-- +-- Hereby the change log: +-- +-- 2017-01-15: Initial class and API. +-- +-- === +-- +-- # **AUTHORS and CONTRIBUTIONS** +-- +-- ### Contributions: +-- +-- * **[Quax](https://forums.eagle.ru/member.php?u=90530)**: Concept, Advice & Testing. +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Concept, Advice & Testing. +-- * **[Gunterlund](http://forums.eagle.ru:8080/member.php?u=75036)**: Test case revision. +-- +-- ### Authors: +-- +-- * **FlightControl**: Concept, Design & Programming. +-- +-- @module AI_Cas + + +--- AI_CAS_ZONE class +-- @type AI_CAS_ZONE +-- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. +-- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. +-- @extends AI.AI_Patrol#AI_CAS_ZONE +AI_CAS_ZONE = { + ClassName = "AI_CAS_ZONE", +} + + + +--- Creates a new AI_CAS_ZONE object +-- @param #AI_CAS_ZONE self +-- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. +-- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. +-- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @param Core.Zone#ZONE EngageZone +-- @return #AI_CAS_ZONE self +function AI_CAS_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed, EngageZone ) + + -- Inherits from BASE + local self = BASE:Inherit( self, AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAS_ZONE + + self.EngageZone = EngageZone + self.Accomplished = false + + self:SetDetectionZone( self.EngageZone ) + + self:AddTransition( { "Patrolling", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Engage. + -- @function [parent=#AI_CAS_ZONE] OnBeforeEngage + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Engage. + -- @function [parent=#AI_CAS_ZONE] OnAfterEngage + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAS_ZONE] Engage + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAS_ZONE] __Engage + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Engaging. +-- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Engaging. +-- @function [parent=#AI_CAS_ZONE] OnEnterEngaging +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Fired. + -- @function [parent=#AI_CAS_ZONE] OnBeforeFired + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Fired. + -- @function [parent=#AI_CAS_ZONE] OnAfterFired + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAS_ZONE] Fired + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAS_ZONE] __Fired + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Destroy", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] OnBeforeDestroy + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] OnAfterDestroy + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] Destroy + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAS_ZONE] __Destroy + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + + self:AddTransition( "Engaging", "Abort", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Abort. + -- @function [parent=#AI_CAS_ZONE] OnBeforeAbort + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Abort. + -- @function [parent=#AI_CAS_ZONE] OnAfterAbort + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAS_ZONE] Abort + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAS_ZONE] __Abort + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "Engaging", "Accomplish", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. + + --- OnBefore Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] OnBeforeAccomplish + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] OnAfterAccomplish + -- @param #AI_CAS_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] Accomplish + -- @param #AI_CAS_ZONE self + + --- Asynchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAS_ZONE] __Accomplish + -- @param #AI_CAS_ZONE self + -- @param #number Delay The delay in seconds. + + return self +end + + +--- Set the Engage Zone where the AI is performing CAS. Note that if the EngageZone is changed, the AI needs to re-detect targets. +-- @param #AI_CAS_ZONE self +-- @param Core.Zone#ZONE EngageZone The zone where the AI is performing CAS. +-- @return #AI_CAS_ZONE self +function AI_CAS_ZONE:SetEngageZone( EngageZone ) + self:F2() + + if EngageZone then + self.EngageZone = EngageZone + else + self.EngageZone = nil + end +end + + + +--- onafter State Transition for Event Start. +-- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterStart( Controllable, From, Event, To ) + + + self:Route() + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every DetectInterval in the EngageZone. + + self:EventOnDead( self.OnDead ) + + Controllable:OptionROEHoldFire() + Controllable:OptionROTVertical() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) end ---- Management of logical cargo objects, that can be transported from and to transportation carriers. + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +function _NewEngageRoute( AIControllable ) + + AIControllable:T( "NewEngageRoute" ) + local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Cas#AI_CAS_ZONE + EngageZone:__Engage( 1 ) +end + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onbeforeEngage( Controllable, From, Event, To ) + + if self.Accomplished == true then + return false + end +end + + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) + + if Controllable:IsAlive() then + + self:Detect( self.EngageZone ) + + local EngageRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = CurrentRoutePoint + + + if self.Controllable:IsNotInZone( self.EngageZone ) then + + -- Find a random 2D point in EngageZone. + local ToEngageZoneVec2 = self.EngageZone:GetRandomVec2() + self:T2( ToEngageZoneVec2 ) + + -- Define Speed and Altitude. + local ToEngageZoneAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + self:T2( ToEngageZoneSpeed ) + + -- Obtain a 3D @{Point} from the 2D point + altitude. + local ToEngageZonePointVec3 = POINT_VEC3:New( ToEngageZoneVec2.x, ToEngageZoneAltitude, ToEngageZoneVec2.y ) + + -- Create a route point of type air. + local ToEngageZoneRoutePoint = ToEngageZonePointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = ToEngageZoneRoutePoint + + end + + --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. + + --- Find a random 2D point in EngageZone. + local ToTargetVec2 = self.EngageZone:GetRandomVec2() + self:T2( ToTargetVec2 ) + + --- Define Speed and Altitude. + local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) + self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) + + --- Obtain a 3D @{Point} from the 2D point + altitude. + local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) + + --- Create a route point of type air. + local ToTargetRoutePoint = ToTargetPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToTargetSpeed, + true + ) + + ToTargetPointVec3:SmokeBlue() + + EngageRoute[#EngageRoute+1] = ToTargetRoutePoint + + + Controllable:OptionROEOpenFire() + Controllable:OptionROTPassiveDefense() + + local AttackTasks = {} + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() then + if DetectedUnit:IsInZone( self.EngageZone ) then + self:E( {"Engaging ", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + self.DetectedUnits[DetectedUnit] = nil + end + end + + EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( EngageRoute ) + + --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... + self.Controllable:SetState( self.Controllable, "EngageZone", self ) + + self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageRoute" ) + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 2 ) + end +end + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @param Core.Event#EVENTDATA EventData +function AI_CAS_ZONE:onafterDestroy( Controllable, From, Event, To, EventData ) + + if EventData.IniUnit then + self.DetectedUnits[EventData.IniUnit] = nil + end + + Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) +end + +--- @param #AI_CAS_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAS_ZONE:onafterAccomplish( Controllable, From, Event, To ) + self.Accomplished = true + self.DetectUnits = false +end + +--- @param #AI_CAS_ZONE self +-- @param Core.Event#EVENTDATA EventData +function AI_CAS_ZONE:OnDead( EventData ) + self:T( { "EventDead", EventData } ) + + if EventData.IniDCSUnit then + self:__Destroy( 1, EventData ) + end +end + + +--- Single-Player:**Yes** / Mulit-Player:**Yes** / AI:**Yes** / Human:**No** / Types:**Air** -- **Execute Combat Air Patrol (CAP).** +-- +-- ![Banner Image](..\Presentations\AI_Cap\Dia1.JPG) +-- +-- +-- === +-- +-- # 1) @{#AI_CAP_ZONE} class, extends @{AI.AI_Cap#AI_PATROL_ZONE} +-- +-- The @{#AI_CAP_ZONE} class implements the core functions to patrol a @{Zone} by an AI @{Controllable} or @{Group} +-- and automatically engage any airborne enemies that are within a certain range or within a certain zone. +-- +-- ![Process](..\Presentations\AI_Cap\Dia3.JPG) +-- +-- The AI_CAP_ZONE is assigned a @(Group) and this must be done before the AI_CAP_ZONE process can be started using the **Start** event. +-- +-- ![Process](..\Presentations\AI_Cap\Dia4.JPG) +-- +-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. +-- Upon arrival at the 3D point, a new random 3D point will be selected within the patrol zone using the given limits. +-- +-- ![Process](..\Presentations\AI_Cap\Dia5.JPG) +-- +-- This cycle will continue. +-- +-- ![Process](..\Presentations\AI_Cap\Dia6.JPG) +-- +-- During the patrol, the AI will detect enemy targets, which are reported through the **Detected** event. +-- +-- ![Process](..\Presentations\AI_Cap\Dia9.JPG) +-- +-- When enemies are detected, the AI will automatically engage the enemy. +-- +-- ![Process](..\Presentations\AI_Cap\Dia10.JPG) +-- +-- Until a fuel or damage treshold has been reached by the AI, or when the AI is commanded to RTB. +-- When the fuel treshold has been reached, the airplane will fly towards the nearest friendly airbase and will land. +-- +-- ![Process](..\Presentations\AI_Cap\Dia13.JPG) +-- +-- ## 1.1) AI_CAP_ZONE constructor +-- +-- * @{#AI_CAP_ZONE.New}(): Creates a new AI_CAP_ZONE object. +-- +-- ## 1.2) AI_CAP_ZONE is a FSM +-- +-- ![Process](..\Presentations\AI_Cap\Dia2.JPG) +-- +-- ### 1.2.1) AI_CAP_ZONE States +-- +-- * **None** ( Group ): The process is not started yet. +-- * **Patrolling** ( Group ): The AI is patrolling the Patrol Zone. +-- * **Engaging** ( Group ): The AI is engaging the bogeys. +-- * **Returning** ( Group ): The AI is returning to Base.. +-- +-- ### 1.2.2) AI_CAP_ZONE Events +-- +-- * **Start** ( Group ): Start the process. +-- * **Route** ( Group ): Route the AI to a new random 3D point within the Patrol Zone. +-- * **Engage** ( Group ): Let the AI engage the bogeys. +-- * **RTB** ( Group ): Route the AI to the home base. +-- * **Detect** ( Group ): The AI is detecting targets. +-- * **Detected** ( Group ): The AI has detected new targets. +-- * **Status** ( Group ): The AI is checking status (fuel and damage). When the tresholds have been reached, the AI will RTB. +-- +-- ## 1.3) Set the Range of Engagement +-- +-- ![Range](..\Presentations\AI_Cap\Dia11.JPG) +-- +-- An optional range can be set in meters, +-- that will define when the AI will engage with the detected airborne enemy targets. +-- The range can be beyond or smaller than the range of the Patrol Zone. +-- The range is applied at the position of the AI. +-- Use the method @{AI.AI_Cap#AI_CAP_ZONE.SetEngageRange}() to define that range. +-- +-- ## 1.4) Set the Zone of Engagement +-- +-- ![Zone](..\Presentations\AI_Cap\Dia12.JPG) +-- +-- An optional @{Zone} can be set, +-- that will define when the AI will engage with the detected airborne enemy targets. +-- Use the method @{AI.AI_Cap#AI_CAP_ZONE.SetEngageZone}() to define that Zone. +-- +-- ==== +-- +-- # **API CHANGE HISTORY** +-- +-- The underlying change log documents the API changes. Please read this carefully. The following notation is used: +-- +-- * **Added** parts are expressed in bold type face. +-- * _Removed_ parts are expressed in italic type face. +-- +-- Hereby the change log: +-- +-- 2017-01-15: Initial class and API. +-- +-- === +-- +-- # **AUTHORS and CONTRIBUTIONS** +-- +-- ### Contributions: +-- +-- * **[Quax](https://forums.eagle.ru/member.php?u=90530)**: Concept, Advice & Testing. +-- * **[Pikey](https://forums.eagle.ru/member.php?u=62835)**: Concept, Advice & Testing. +-- * **[Gunterlund](http://forums.eagle.ru:8080/member.php?u=75036)**: Test case revision. +-- +-- ### Authors: +-- +-- * **FlightControl**: Concept, Design & Programming. +-- +-- @module AI_Cap + + +--- AI_CAP_ZONE class +-- @type AI_CAP_ZONE +-- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. +-- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. +-- @extends AI.AI_Patrol#AI_PATROL_ZONE +AI_CAP_ZONE = { + ClassName = "AI_CAP_ZONE", +} + + + +--- Creates a new AI_CAP_ZONE object +-- @param #AI_CAP_ZONE self +-- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. +-- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. +-- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. +-- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) + + -- Inherits from BASE + local self = BASE:Inherit( self, AI_PATROL_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAP_ZONE + + self.Accomplished = false + self.Engaging = false + + self:AddTransition( { "Patrolling", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Engage. + -- @function [parent=#AI_CAP_ZONE] OnBeforeEngage + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Engage. + -- @function [parent=#AI_CAP_ZONE] OnAfterEngage + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAP_ZONE] Engage + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Engage. + -- @function [parent=#AI_CAP_ZONE] __Engage + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + +--- OnLeave Transition Handler for State Engaging. +-- @function [parent=#AI_CAP_ZONE] OnLeaveEngaging +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @return #boolean Return false to cancel Transition. + +--- OnEnter Transition Handler for State Engaging. +-- @function [parent=#AI_CAP_ZONE] OnEnterEngaging +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. + + self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Fired. + -- @function [parent=#AI_CAP_ZONE] OnBeforeFired + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Fired. + -- @function [parent=#AI_CAP_ZONE] OnAfterFired + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAP_ZONE] Fired + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Fired. + -- @function [parent=#AI_CAP_ZONE] __Fired + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "*", "Destroy", "*" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] OnBeforeDestroy + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] OnAfterDestroy + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] Destroy + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Destroy. + -- @function [parent=#AI_CAP_ZONE] __Destroy + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + + self:AddTransition( "Engaging", "Abort", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Abort. + -- @function [parent=#AI_CAP_ZONE] OnBeforeAbort + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Abort. + -- @function [parent=#AI_CAP_ZONE] OnAfterAbort + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAP_ZONE] Abort + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Abort. + -- @function [parent=#AI_CAP_ZONE] __Abort + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + self:AddTransition( "Engaging", "Accomplish", "Patrolling" ) -- FSM_CONTROLLABLE Transition for type #AI_CAP_ZONE. + + --- OnBefore Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] OnBeforeAccomplish + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + -- @return #boolean Return false to cancel Transition. + + --- OnAfter Transition Handler for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] OnAfterAccomplish + -- @param #AI_CAP_ZONE self + -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. + -- @param #string From The From State string. + -- @param #string Event The Event string. + -- @param #string To The To State string. + + --- Synchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] Accomplish + -- @param #AI_CAP_ZONE self + + --- Asynchronous Event Trigger for Event Accomplish. + -- @function [parent=#AI_CAP_ZONE] __Accomplish + -- @param #AI_CAP_ZONE self + -- @param #number Delay The delay in seconds. + + return self +end + + +--- Set the Engage Zone which defines where the AI will engage bogies. +-- @param #AI_CAP_ZONE self +-- @param Core.Zone#ZONE EngageZone The zone where the AI is performing CAP. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:SetEngageZone( EngageZone ) + self:F2() + + if EngageZone then + self.EngageZone = EngageZone + else + self.EngageZone = nil + end +end + +--- Set the Engage Range when the AI will engage with airborne enemies. +-- @param #AI_CAP_ZONE self +-- @param #number EngageRange The Engage Range. +-- @return #AI_CAP_ZONE self +function AI_CAP_ZONE:SetEngageRange( EngageRange ) + self:F2() + + if EngageRange then + self.EngageRange = EngageRange + else + self.EngageRange = nil + end +end + +--- onafter State Transition for Event Start. +-- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterStart( Controllable, From, Event, To ) + + + self:Route() + self:__Status( 30 ) -- Check status status every 30 seconds. + self:__Detect( self.DetectInterval ) -- Detect for new targets every DetectInterval in the EngageZone. + + self:EventOnDead( self.OnDead ) + + Controllable:OptionROEOpenFire() + + self.Controllable:OnReSpawn( + function( PatrolGroup ) + self:E( "ReSpawn" ) + self:__Reset() + self:__Route( 5 ) + end + ) + +end + +--- @param Wrapper.Controllable#CONTROLLABLE AIControllable +function _NewEngageCapRoute( AIControllable ) + + AIControllable:T( "NewEngageRoute" ) + local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Cap#AI_CAP_ZONE + EngageZone:__Engage( 1 ) +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onbeforeEngage( Controllable, From, Event, To ) + + if self.Accomplished == true then + return false + end +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterDetected( Controllable, From, Event, To ) + + if From ~= "Engaging" then + + local Engage = false + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() and DetectedUnit:IsAir() then + Engage = true + break + end + end + + if Engage == true then + self:E( 'Detected -> Engaging' ) + self:__Engage( 1 ) + end + end +end + + + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterEngage( Controllable, From, Event, To ) + + if Controllable:IsAlive() then + + self:Detect( self.EngageZone ) + + local EngageRoute = {} + + --- Calculate the current route point. + local CurrentVec2 = self.Controllable:GetVec2() + + --TODO: Create GetAltitude function for GROUP, and delete GetUnit(1). + local CurrentAltitude = self.Controllable:GetUnit(1):GetAltitude() + local CurrentPointVec3 = POINT_VEC3:New( CurrentVec2.x, CurrentAltitude, CurrentVec2.y ) + local ToEngageZoneSpeed = self.PatrolMaxSpeed + local CurrentRoutePoint = CurrentPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToEngageZoneSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = CurrentRoutePoint + + + --- Find a random 2D point in PatrolZone. + local ToTargetVec2 = self.PatrolZone:GetRandomVec2() + self:T2( ToTargetVec2 ) + + --- Define Speed and Altitude. + local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) + local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) + self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) + + --- Obtain a 3D @{Point} from the 2D point + altitude. + local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) + + --- Create a route point of type air. + local ToPatrolRoutePoint = ToTargetPointVec3:RoutePointAir( + POINT_VEC3.RoutePointAltType.BARO, + POINT_VEC3.RoutePointType.TurningPoint, + POINT_VEC3.RoutePointAction.TurningPoint, + ToTargetSpeed, + true + ) + + EngageRoute[#EngageRoute+1] = ToPatrolRoutePoint + + Controllable:OptionROEOpenFire() + Controllable:OptionROTPassiveDefense() + + local AttackTasks = {} + + for DetectedUnitID, DetectedUnit in pairs( self.DetectedUnits ) do + local DetectedUnit = DetectedUnit -- Wrapper.Unit#UNIT + self:T( DetectedUnit ) + if DetectedUnit:IsAlive() and DetectedUnit:IsAir() then + if self.EngageZone then + if DetectedUnit:IsInZone( self.EngageZone ) then + self:E( {"Within Zone and Engaging ", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + if self.EngageRange then + if DetectedUnit:GetPointVec3():Get2DDistance(Controllable:GetPointVec3() ) <= self.EngageRange then + self:E( {"Within Range and Engaging", DetectedUnit } ) + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + else + AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( DetectedUnit ) + end + end + else + self.DetectedUnits[DetectedUnit] = nil + end + end + + --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... + self.Controllable:WayPointInitialize( EngageRoute ) + + + if #AttackTasks == 0 then + self:E("No targets found -> Going back to Patrolling") + self:Accomplish() + self:Route() + else + EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) + + --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... + self.Controllable:SetState( self.Controllable, "EngageZone", self ) + + self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageCapRoute" ) + + end + + --- NOW ROUTE THE GROUP! + self.Controllable:WayPointExecute( 1, 2 ) + + end +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +-- @param Core.Event#EVENTDATA EventData +function AI_CAP_ZONE:onafterDestroy( Controllable, From, Event, To, EventData ) + + if EventData.IniUnit then + self.DetectedUnits[EventData.IniUnit] = nil + end + + Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) +end + +--- @param #AI_CAP_ZONE self +-- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. +-- @param #string From The From State string. +-- @param #string Event The Event string. +-- @param #string To The To State string. +function AI_CAP_ZONE:onafterAccomplish( Controllable, From, Event, To ) + self.Accomplished = true + self.DetectUnits = false +end + +--- @param #AI_CAP_ZONE self +-- @param Core.Event#EVENTDATA EventData +function AI_CAP_ZONE:OnDead( EventData ) + self:T( { "EventDead", EventData } ) + + if EventData.IniDCSUnit then + self:__Destroy( 1, EventData ) + end +end + + +--- Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Ground -- Management of logical cargo objects, that can be transported from and to transportation carriers. -- -- === -- @@ -26085,507 +27564,6 @@ end -- AI_CARGO_GROUPED ---- SP:Y MP:Y AI:Y HU:N TYP:Air -- This module contains the AI_CAS_ZONE class. --- --- === --- --- 1) @{#AI_CAS_ZONE} class, extends @{Core.Fsm#FSM_CONTROLLABLE} --- ================================================================ --- The @{#AI_CAS_ZONE} class implements the core functions to CAS a @{Zone} by an AIR @{Controllable} @{Group}. --- --- 1.1) AI_CAS_ZONE constructor: --- ---------------------------- --- --- * @{#AI_CAS_ZONE.New}(): Creates a new AI_CAS_ZONE object. --- --- 1.2) AI_CAS_ZONE state machine: --- ---------------------------------- --- The AI_CAS_ZONE is a state machine: it manages the different events and states of the AIControllable it is controlling. --- --- ### 1.2.1) AI_CAS_ZONE Events: --- --- * @{#AI_CAS_ZONE.TakeOff}( AIControllable ): The AI is taking-off from an airfield. --- * @{#AI_CAS_ZONE.Hold}( AIControllable ): The AI is holding in airspace at a zone. --- * @{#AI_CAS_ZONE.Engage}( AIControllable ): The AI is engaging the targets. --- * @{#AI_CAS_ZONE.WeaponReleased}( AIControllable ): The AI has released a weapon to the target. --- * @{#AI_CAS_ZONE.Destroy}( AIControllable ): The AI has destroyed a target. --- * @{#AI_CAS_ZONE.Complete}( AIControllable ): The AI has destroyed all defined targets. --- * @{#AI_CAS_ZONE.RTB}( AIControllable ): The AI is returning to the home base. --- --- ### 1.2.2) AI_CAS_ZONE States: --- --- --- ### 1.2.3) AI_CAS_ZONE state transition methods: --- --- --- 1.3) Manage the AI_CAS_ZONE parameters: --- ------------------------------------------ --- The following methods are available to modify the parameters of an AI_CAS_ZONE object: --- --- * @{#AI_CAS_ZONE.SetControllable}(): Set the AIControllable. --- * @{#AI_CAS_ZONE.GetControllable}(): Get the AIControllable. --- --- ==== --- --- **API CHANGE HISTORY** --- ====================== --- --- The underlying change log documents the API changes. Please read this carefully. The following notation is used: --- --- * **Added** parts are expressed in bold type face. --- * _Removed_ parts are expressed in italic type face. --- --- Hereby the change log: --- --- 2017-01-12: Initial class and API. --- --- === --- --- AUTHORS and CONTRIBUTIONS --- ========================= --- --- ### Contributions: --- --- * **Quax**: Concept & Testing. --- * **Pikey**: Concept & Testing. --- --- ### Authors: --- --- * **FlightControl**: Concept, Design & Programming. --- --- --- @module Cas - - ---- AI_CAS_ZONE class --- @type AI_CAS_ZONE --- @field Wrapper.Controllable#CONTROLLABLE AIControllable The @{Controllable} patrolling. --- @field Core.Zone#ZONE_BASE TargetZone The @{Zone} where the patrol needs to be executed. --- @extends AI.AI_Patrol#AI_PATROLZONE -AI_CAS_ZONE = { - ClassName = "AI_CAS_ZONE", -} - - - ---- Creates a new AI_CAS_ZONE object --- @param #AI_CAS_ZONE self --- @param Core.Zone#ZONE_BASE PatrolZone The @{Zone} where the patrol needs to be executed. --- @param Dcs.DCSTypes#Altitude PatrolFloorAltitude The lowest altitude in meters where to execute the patrol. --- @param Dcs.DCSTypes#Altitude PatrolCeilingAltitude The highest altitude in meters where to execute the patrol. --- @param Dcs.DCSTypes#Speed PatrolMinSpeed The minimum speed of the @{Controllable} in km/h. --- @param Dcs.DCSTypes#Speed PatrolMaxSpeed The maximum speed of the @{Controllable} in km/h. --- @param Core.Zone#ZONE EngageZone --- @return #AI_CAS_ZONE self -function AI_CAS_ZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed, EngageZone ) - - -- Inherits from BASE - local self = BASE:Inherit( self, AI_PATROLZONE:New( PatrolZone, PatrolFloorAltitude, PatrolCeilingAltitude, PatrolMinSpeed, PatrolMaxSpeed ) ) -- #AI_CAS_ZONE - - self.PatrolZone = PatrolZone - self.PatrolFloorAltitude = PatrolFloorAltitude - self.PatrolCeilingAltitude = PatrolCeilingAltitude - self.PatrolMinSpeed = PatrolMinSpeed - self.PatrolMaxSpeed = PatrolMaxSpeed - - self.EngageZone = EngageZone - - do self:AddTransition( { "Patrol", "Route", "Engaging" }, "Engage", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Holding. - -- @function [parent=#AI_CAS_ZONE] OnLeaveHolding - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Engage. - -- @function [parent=#AI_CAS_ZONE] OnBeforeEngage - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Engage. - -- @function [parent=#AI_CAS_ZONE] OnAfterEngage - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Engage. - -- @function [parent=#AI_CAS_ZONE] Engage - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Engage - -- @function [parent=#AI_CAS_ZONE] __Engage - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - - do self:AddTransition( "Engaging", "Fired", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Fired. - -- @function [parent=#AI_CAS_ZONE] OnBeforeFired - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Fired. - -- @function [parent=#AI_CAS_ZONE] OnAfterFired - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean - - --- Embedded Event Trigger for Fired. - -- @function [parent=#AI_CAS_ZONE] Fired - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Fired - -- @function [parent=#AI_CAS_ZONE] __Fired - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - do self:AddTransition( "Engaging", "Destroy", "Engaging" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnEnterEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Destroy. - -- @function [parent=#AI_CAS_ZONE] OnBeforeDestroy - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Destroy. - -- @function [parent=#AI_CAS_ZONE] OnAfterDestroy - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Destroy. - -- @function [parent=#AI_CAS_ZONE] Destroy - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Destroy - -- @function [parent=#AI_CAS_ZONE] __Destroy - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - -do self:AddTransition( "Engaging", "Abort", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_CAS_ZONE] OnEnterPatrol - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Abort. - -- @function [parent=#AI_CAS_ZONE] OnBeforeAbort - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Abort. - -- @function [parent=#AI_CAS_ZONE] OnAfterAbort - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Abort. - -- @function [parent=#AI_CAS_ZONE] Abort - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Abort - -- @function [parent=#AI_CAS_ZONE] __Abort - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - -end -- AI_CAS_ZONE - - - do self:AddTransition( "Engaging", "Completed", "Patrol" ) -- FSM_CONTROLLABLE Transition for type #AI_CAS_ZONE. - - --- OnLeave State Transition for Engaging. - -- @function [parent=#AI_CAS_ZONE] OnLeaveEngaging - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnEnter State Transition for Patrol. - -- @function [parent=#AI_CAS_ZONE] OnEnterPatrol - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- OnBefore State Transition for Completed. - -- @function [parent=#AI_CAS_ZONE] OnBeforeCompleted - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - -- @return #boolean Return false to cancel Transition. - - --- OnAfter State Transition for Completed. - -- @function [parent=#AI_CAS_ZONE] OnAfterCompleted - -- @param #AI_CAS_ZONE self - -- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. - -- @param #string From The From State string. - -- @param #string Event The Event string. - -- @param #string To The To State string. - - --- Embedded Event Trigger for Completed. - -- @function [parent=#AI_CAS_ZONE] Completed - -- @param #AI_CAS_ZONE self - - --- Delayed Event Trigger for Completed - -- @function [parent=#AI_CAS_ZONE] __Completed - -- @param #AI_CAS_ZONE self - -- @param #number Delay The delay in seconds. - - end -- AI_CAS_ZONE - - return self -end - - ---- onafter State Transition for Event Start. --- @param #AI_CAS_ZONE self --- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. --- @param #string From The From State string. --- @param #string Event The Event string. --- @param #string To The To State string. -function AI_CAS_ZONE:onafterStart( Controllable, From, Event, To ) - - - if Controllable:IsAlive() then - self:__Route( 1 ) - end - - self:EventOnDead( self.OnDead ) - - Controllable:OptionROEHoldFire() - Controllable:OptionROTVertical() - -end - ---- @param Wrapper.Controllable#CONTROLLABLE AIControllable -function _NewEngageRoute( AIControllable ) - - AIControllable:T( "NewEngageRoute" ) - local EngageZone = AIControllable:GetState( AIControllable, "EngageZone" ) -- AI.AI_Patrol#AI_PATROLZONE - EngageZone:__Engage( 1 ) -end - - ---- @param #AI_CAS_ZONE self --- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. --- @param #string From The From State string. --- @param #string Event The Event string. --- @param #string To The To State string. -function AI_CAS_ZONE:onafterEngage( Controllable, From, Event, To ) - - if Controllable:IsAlive() then - - local EngageRoute = {} - - if self.Controllable:IsNotInZone( self.EngageZone ) then - - -- Find a random 2D point in EngageZone. - local ToEngageZoneVec2 = self.EngageZone:GetRandomVec2() - self:T2( ToEngageZoneVec2 ) - - -- Define Speed and Altitude. - local ToEngageZoneAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) - local ToEngageZoneSpeed = self.PatrolMaxSpeed - self:T2( ToEngageZoneSpeed ) - - -- Obtain a 3D @{Point} from the 2D point + altitude. - local ToEngageZonePointVec3 = POINT_VEC3:New( ToEngageZoneVec2.x, ToEngageZoneAltitude, ToEngageZoneVec2.y ) - - -- Create a route point of type air. - local ToEngageZoneRoutePoint = ToEngageZonePointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToEngageZoneSpeed, - true - ) - - EngageRoute[#EngageRoute+1] = ToEngageZoneRoutePoint - - end - - --- Define a random point in the @{Zone}. The AI will fly to that point within the zone. - - --- Find a random 2D point in EngageZone. - local ToTargetVec2 = self.EngageZone:GetRandomVec2() - self:T2( ToTargetVec2 ) - - --- Define Speed and Altitude. - local ToTargetAltitude = math.random( self.EngageFloorAltitude, self.EngageCeilingAltitude ) - local ToTargetSpeed = math.random( self.PatrolMinSpeed, self.PatrolMaxSpeed ) - self:T2( { self.PatrolMinSpeed, self.PatrolMaxSpeed, ToTargetSpeed } ) - - --- Obtain a 3D @{Point} from the 2D point + altitude. - local ToTargetPointVec3 = POINT_VEC3:New( ToTargetVec2.x, ToTargetAltitude, ToTargetVec2.y ) - - --- Create a route point of type air. - local ToTargetRoutePoint = ToTargetPointVec3:RoutePointAir( - POINT_VEC3.RoutePointAltType.BARO, - POINT_VEC3.RoutePointType.TurningPoint, - POINT_VEC3.RoutePointAction.TurningPoint, - ToTargetSpeed, - true - ) - - ToTargetPointVec3:SmokeRed() - - EngageRoute[#EngageRoute+1] = ToTargetRoutePoint - - - Controllable:OptionROEOpenFire() - Controllable:OptionROTPassiveDefense() - - local AttackTasks = {} - - local DetectedTargets = Controllable:GetDetectedTargets() - for TargetID, Target in pairs( DetectedTargets ) do - local TargetObject = Target.object - self:T( TargetObject ) - if TargetObject and TargetObject:isExist() and TargetObject.id_ < 50000000 then - - local TargetUnit = UNIT:Find( TargetObject ) - local TargetUnitName = TargetUnit:GetName() - - if TargetUnit:IsInZone( self.EngageZone ) then - self:E( {"Engaging ", TargetUnit } ) - --local EngageTask = Controllable:EnRouteTaskEngageUnit( TargetUnit, 1 ) - AttackTasks[#AttackTasks+1] = Controllable:TaskAttackUnit( TargetUnit ) - end - - end - end - - EngageRoute[1].task = Controllable:TaskCombo( AttackTasks ) - - --- Now we're going to do something special, we're going to call a function from a waypoint action at the AIControllable... - self.Controllable:WayPointInitialize( EngageRoute ) - - --- Do a trick, link the NewEngageRoute function of the object to the AIControllable in a temporary variable ... - self.Controllable:SetState( self.Controllable, "EngageZone", self ) - - self.Controllable:WayPointFunction( #EngageRoute, 1, "_NewEngageRoute" ) - - --- NOW ROUTE THE GROUP! - self.Controllable:WayPointExecute( 1, 5 ) - end -end - ---- @param #AI_CAS_ZONE self --- @param Wrapper.Controllable#CONTROLLABLE Controllable The Controllable Object managed by the FSM. --- @param #string From The From State string. --- @param #string Event The Event string. --- @param #string To The To State string. -function AI_CAS_ZONE:onafterDestroy( Controllable, From, Event, To ) - - Controllable:MessageToAll( "Destroyed a target", 15 , "Destroyed!" ) -end - ---- @param #AI_CAS_ZONE self --- @param Core.Event#EVENTDATA EventData -function AI_CAS_ZONE:OnDead( EventData ) - self:T( { "EventDead", EventData } ) - - if EventData.IniDCSUnit then - self:__Destroy( 1, EventData ) - end -end - - --- (SP) (MP) (FSM) Accept or reject process for player (task) assignments. -- -- === @@ -30552,8 +31530,9 @@ Include.File( "Functional/Detection" ) --- AI Classes Include.File( "AI/AI_Balancer" ) Include.File( "AI/AI_Patrol" ) -Include.File( "AI/AI_Cargo" ) +Include.File( "AI/AI_Cap" ) Include.File( "AI/AI_Cas" ) +Include.File( "AI/AI_Cargo" ) --- Actions Include.File( "Actions/Act_Assign" ) diff --git a/Moose Mission Setup/Moose_Create.bat b/Moose Mission Setup/Moose_Create.bat index 9ef11dac0..ea27cb4f9 100644 --- a/Moose Mission Setup/Moose_Create.bat +++ b/Moose Mission Setup/Moose_Create.bat @@ -80,8 +80,9 @@ COPY /b Moose.lua + %1\Functional\Detection.lua Moose.lua rem AI Classes COPY /b Moose.lua + %1\AI\AI_Balancer.lua Moose.lua COPY /b Moose.lua + %1\AI\AI_Patrol.lua Moose.lua +COPY /b Moose.lua + %1\AI\AI_Cas.lua Moose.lua +COPY /b Moose.lua + %1\AI\AI_Cap.lua Moose.lua COPY /b Moose.lua + %1\AI\AI_Cargo.lua Moose.lua -COPY /b Moose.lua + %1\AI\AI_CAS.lua Moose.lua rem Actions diff --git a/Moose Test Missions/ABP - Airbase Police/APL-001 - Caucasus/APL-001 - Caucasus.miz b/Moose Test Missions/ABP - Airbase Police/APL-001 - Caucasus/APL-001 - Caucasus.miz index 7c1651c33..69b8190b6 100644 Binary files a/Moose Test Missions/ABP - Airbase Police/APL-001 - Caucasus/APL-001 - Caucasus.miz and b/Moose Test Missions/ABP - Airbase Police/APL-001 - Caucasus/APL-001 - Caucasus.miz differ diff --git a/Moose Test Missions/ABP - Airbase Police/APL-002 - Nevada/APL-002 - Nevada.miz b/Moose Test Missions/ABP - Airbase Police/APL-002 - Nevada/APL-002 - Nevada.miz index 859de5057..1f42080a9 100644 Binary files a/Moose Test Missions/ABP - Airbase Police/APL-002 - Nevada/APL-002 - Nevada.miz and b/Moose Test Missions/ABP - Airbase Police/APL-002 - Nevada/APL-002 - Nevada.miz differ diff --git a/Moose Test Missions/ACL - Airbase Cleaner/ACL-001 - Airbase CleanUp/ACL-001 - Airbase CleanUp.miz b/Moose Test Missions/ACL - Airbase Cleaner/ACL-001 - Airbase CleanUp/ACL-001 - Airbase CleanUp.miz index c095b2872..196e7125e 100644 Binary files a/Moose Test Missions/ACL - Airbase Cleaner/ACL-001 - Airbase CleanUp/ACL-001 - Airbase CleanUp.miz and b/Moose Test Missions/ACL - Airbase Cleaner/ACL-001 - Airbase CleanUp/ACL-001 - Airbase CleanUp.miz differ diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.lua b/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.lua index 7af0df386..5315ae2e7 100644 --- a/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.lua +++ b/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.lua @@ -1,8 +1,4 @@ ---- AI Spawning and Decomissioning --- --- === --- --- Name: Spawned AI +-- Name: AIB-001 - Spawned AI -- Author: FlightControl -- Date Created: 07 Dec 2016 -- @@ -18,10 +14,6 @@ -- 1. If no player is logging into the red slots, 2 red AI planes should be alive. -- 2. If a player joins one red slot, one red AI plane should return to the nearest home base. -- 3. If two players join the red slots, no AI plane should be spawned, and all airborne AI planes should return to the nearest home base. --- --- # Status: TESTED 07 Dec 2016 --- --- @module TEST.AI_BALANCER.T001 -- Define the SET of CLIENTs from the red coalition. This SET is filled during startup. local RU_PlanesClientSet = SET_CLIENT:New():FilterCountries( "RUSSIA" ):FilterCategories( "plane" ) diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.miz b/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.miz index 0696929e0..d081431ac 100644 Binary files a/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.miz and b/Moose Test Missions/AIB - AI Balancing/AIB-001 - Spawned AI/AIB-001 - Spawned AI.miz differ diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.lua b/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.lua index 4e708331a..158a8f5ee 100644 --- a/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.lua +++ b/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.lua @@ -1,8 +1,4 @@ ---- AI Patrolling --- --- === --- --- Name: Patrol AI +-- Name: AIB-002 - Patrol AI.lua -- Author: FlightControl -- Date Created: 7 December 2016 -- @@ -39,7 +35,7 @@ function RU_AI_Balancer:OnAfterSpawned( SetGroup, From, Event, To, AIGroup ) local PatrolZone = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) - PatrolZones[AIGroup] = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 400, 600 ) + PatrolZones[AIGroup] = AI_PATROL_ZONE:New( PatrolZone, 3000, 6000, 400, 600 ) PatrolZones[AIGroup]:ManageFuel( 0.2, 60 ) PatrolZones[AIGroup]:SetControllable( AIGroup ) PatrolZones[AIGroup]:__Start( 5 ) diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.miz b/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.miz index 98af7ed6c..ff179b0c7 100644 Binary files a/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.miz and b/Moose Test Missions/AIB - AI Balancing/AIB-002 - Patrol AI/AIB-002 - Patrol AI.miz differ diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.lua b/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.lua index a647bedee..2f4a137ab 100644 --- a/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.lua +++ b/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.lua @@ -15,10 +15,10 @@ US_AI_Balancer = AI_BALANCER:New( US_PlanesClientSet, US_PlanesSpawn ) --local PatrolZoneGroup = GROUP:FindByName( "Patrol Zone Blue" ) --local PatrolZoneBlue = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) ---local PatrolZoneB = AI_PATROLZONE:New( PatrolZoneBlue, 3000, 6000, 900, 1100 ):ManageFuel( 0.2, 180 ) +--local PatrolZoneB = AI_PATROL_ZONE:New( PatrolZoneBlue, 3000, 6000, 900, 1100 ):ManageFuel( 0.2, 180 ) --US_AI_Balancer:SetPatrolZone( PatrolZoneB ) -- --local PatrolZoneGroup = GROUP:FindByName( "Patrol Zone Red" ) --local PatrolZoneRed = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) ---local PatrolZoneR = AI_PATROLZONE:New( PatrolZoneRed, 3000, 6000, 900, 1100 ):ManageFuel( 0.2, 180 ) +--local PatrolZoneR = AI_PATROL_ZONE:New( PatrolZoneRed, 3000, 6000, 900, 1100 ):ManageFuel( 0.2, 180 ) --RU_AI_Balancer:SetPatrolZone( PatrolZoneR ) diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.miz b/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.miz index 6507cc658..3a89510dd 100644 Binary files a/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.miz and b/Moose Test Missions/AIB - AI Balancing/AIB-003 - Two coalitions InitCleanUp test/AIB-003 - Two coalitions InitCleanUp test.miz differ diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.lua b/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.lua index f65e27f88..222c56980 100644 --- a/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.lua +++ b/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.lua @@ -1,4 +1,4 @@ --- Name: Respawn Test when Destroyed +-- Name: AIB-004 - Respawn Test when Destroyed.lua -- Author: FlightControl -- Date Created: 7 January 2017 -- @@ -19,7 +19,7 @@ -- 2. If a player joins one red slot, one red AI plane should return to the nearest home base. -- 3. If two players join the red slots, no AI plane should be spawned, and all airborne AI planes should return to the nearest home base. -- 4. Monitor that once a red AI is destroyed, that it ReSpawns... --- + -- Define the SET of CLIENTs from the red coalition. This SET is filled during startup. local RU_PlanesClientSet = SET_CLIENT:New():FilterCountries( "RUSSIA" ):FilterCategories( "plane" ) @@ -38,7 +38,7 @@ function RU_AI_Balancer:OnAfterSpawned( SetGroup, From, Event, To, AIGroup ) local PatrolZone = ZONE_POLYGON:New( "PatrolZone", PatrolZoneGroup ) - local Patrol = AI_PATROLZONE:New( PatrolZone, 3000, 6000, 400, 600 ) + local Patrol = AI_PATROL_ZONE:New( PatrolZone, 3000, 6000, 400, 600 ) Patrol:ManageFuel( 0.2, 60 ) Patrol:SetControllable( AIGroup ) Patrol:__Start( 5 ) diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.miz b/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.miz index 66df9bf37..ecc8c46cd 100644 Binary files a/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.miz and b/Moose Test Missions/AIB - AI Balancing/AIB-004 - Respawn Test when Destroyed/AIB-004 - Respawn Test when Destroyed.miz differ diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.lua index f7501afd4..eab2c2e22 100644 --- a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.lua +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.lua @@ -1,4 +1,4 @@ --- Name: AIB-006 - Declutter AI at Airbases +-- Name: AIB-005 - Patrol AI and Randomize Zones -- Author: FlightControl -- Date Created: 10 Jan 2016 -- @@ -25,7 +25,7 @@ local RU_PlanesClientSet = SET_CLIENT:New():FilterCountries( "RUSSIA" ):FilterCa -- Define the SPAWN object for the red AI plane template. -- We use InitCleanUp to check every 20 seconds, if there are no planes blocked at the airbase, waithing for take-off. -- If a blocked plane exists, this red plane will be ReSpawned. -local RU_PlanesSpawn = SPAWN:New( "AI RU" ):InitCleanUp( 60 ) +local RU_PlanesSpawn = SPAWN:New( "AI RU" ):InitCleanUp( 20 ) -- Start the AI_BALANCER, using the SET of red CLIENTs, and the SPAWN object as a parameter. local RU_AI_Balancer = AI_BALANCER:New( RU_PlanesClientSet, RU_PlanesSpawn ) @@ -43,9 +43,9 @@ local PatrolZoneArray = { PatrolZone1, PatrolZone2 } function RU_AI_Balancer:OnAfterSpawned( SetGroup, From, Event, To, AIGroup ) - local Patrol = AI_PATROLZONE:New( PatrolZoneArray[math.random( 1, 2 )], 3000, 6000, 400, 600 ) + local Patrol = AI_PATROL_ZONE:New( PatrolZoneArray[math.random( 1, 2 )], 3000, 6000, 400, 600 ) Patrol:ManageFuel( 0.2, 60 ) Patrol:SetControllable( AIGroup ) - Patrol:__Start( 5 ) + Patrol:Start() end diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.miz b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.miz index 2a2027ce4..772b3d939 100644 Binary files a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.miz and b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones.miz differ diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Config/View/Server.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/Server.lua similarity index 100% rename from Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Config/View/Server.lua rename to Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/Server.lua diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/SnapViews.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/SnapViews.lua new file mode 100644 index 000000000..412686113 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/SnapViews.lua @@ -0,0 +1,2780 @@ +SnapViews = {} +SnapViews["A-10A"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 65.000000,--FOV + hAngle = 0.000000, + vAngle = -26.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 49.626770,--FOV + hAngle = 0.000000, + vAngle = -90.631294, + x_trans = 0.180499, + y_trans = -0.137064, + z_trans = -0.250000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 30.395041,--FOV + hAngle = 0.000000, + vAngle = -94.329208, + x_trans = 0.372718, + y_trans = -0.054055, + z_trans = 0.250000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 55.238567,--FOV + hAngle = 0.000000, + vAngle = -90.631294, + x_trans = 0.158523, + y_trans = -0.137064, + z_trans = 0.250000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 35.000000,--FOV + hAngle = 0.000000, + vAngle = -10.651850, + x_trans = 0.327622, + y_trans = -0.278207, + z_trans = -0.244799, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 34.340549,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 35.000000,--FOV + hAngle = 0.000000, + vAngle = -10.651850, + x_trans = 0.327622, + y_trans = -0.278207, + z_trans = 0.244799, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 68.628296,--FOV + hAngle = 68.292320, + vAngle = -11.477349, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 68.628296,--FOV + hAngle = 0.000000, + vAngle = 30.227919, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 68.628296,--FOV + hAngle = -67.172974, + vAngle = -11.477349, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 70.000000,--FOV + hAngle = 20.000000, + vAngle = 8.000000, + x_trans = 0.360000, + y_trans = -0.041337, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 70.000000,--FOV + hAngle = -20.000000, + vAngle = 8.000000, + x_trans = 0.360000, + y_trans = -0.041337, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 75.000000,--FOV + hAngle = 0.000000, + vAngle = -23.000000, + x_trans = 0.360000, + y_trans = -0.041337, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["A-10C"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 65.000000,--FOV + hAngle = 0.000000, + vAngle = -26.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 49.626770,--FOV + hAngle = 0.000000, + vAngle = -90.631294, + x_trans = 0.180499, + y_trans = -0.137064, + z_trans = -0.250000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 30.395041,--FOV + hAngle = 0.000000, + vAngle = -94.329208, + x_trans = 0.372718, + y_trans = -0.054055, + z_trans = 0.250000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 55.238567,--FOV + hAngle = 0.000000, + vAngle = -90.631294, + x_trans = 0.158523, + y_trans = -0.137064, + z_trans = 0.250000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 35.000000,--FOV + hAngle = 0.000000, + vAngle = -10.651850, + x_trans = 0.327622, + y_trans = -0.278207, + z_trans = -0.244799, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 34.340549,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 35.000000,--FOV + hAngle = 0.000000, + vAngle = -10.651850, + x_trans = 0.327622, + y_trans = -0.278207, + z_trans = 0.244799, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 68.628296,--FOV + hAngle = 68.292320, + vAngle = -11.477349, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 68.628296,--FOV + hAngle = 0.000000, + vAngle = 30.227919, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 68.628296,--FOV + hAngle = -67.172974, + vAngle = -11.477349, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 70.000000,--FOV + hAngle = 20.000000, + vAngle = 8.000000, + x_trans = 0.360000, + y_trans = -0.041337, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 70.000000,--FOV + hAngle = -20.000000, + vAngle = 8.000000, + x_trans = 0.360000, + y_trans = -0.041337, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 75.000000,--FOV + hAngle = 0.000000, + vAngle = -23.000000, + x_trans = 0.360000, + y_trans = -0.041337, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Bf-109K-4"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["C-101CC"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +[2] = {-- player slot 2 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["C-101EB"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +[2] = {-- player slot 2 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["F-15C"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 70.611748,--FOV + hAngle = -1.240272, + vAngle = -33.850250, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 32.704346,--FOV + hAngle = 25.696522, + vAngle = -34.778103, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 32.704346,--FOV + hAngle = 0.000000, + vAngle = -47.845268, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 36.106045,--FOV + hAngle = -28.878576, + vAngle = -36.780628, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 88.727844,--FOV + hAngle = 128.508865, + vAngle = 13.131046, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 41.928593,--FOV + hAngle = 0.000000, + vAngle = -4.630446, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 88.727844,--FOV + hAngle = -128.508865, + vAngle = 13.131046, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 88.727844,--FOV + hAngle = 81.648369, + vAngle = -9.500000, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 88.727844,--FOV + hAngle = 0.000000, + vAngle = 34.180634, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 88.727844,--FOV + hAngle = -80.997551, + vAngle = -9.500000, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 56.032040,--FOV + hAngle = 14.803060, + vAngle = 3.332499, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 56.032040,--FOV + hAngle = -14.414484, + vAngle = 3.332499, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 88.727844,--FOV + hAngle = 0.000000, + vAngle = -9.678451, + x_trans = 0.264295, + y_trans = -0.064373, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["FW-190D9"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Hawk"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Ka-50"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 67.452896,--FOV + hAngle = 0.000000, + vAngle = -40.067383, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 37.846794,--FOV + hAngle = 51.644135, + vAngle = -51.870411, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 36.178646,--FOV + hAngle = -1.912186, + vAngle = -34.446247, + x_trans = 0.000000, + y_trans = -0.025421, + z_trans = 0.073226, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 73.605141,--FOV + hAngle = -90.361992, + vAngle = -44.103138, + x_trans = 0.169696, + y_trans = -0.073508, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 91.348198,--FOV + hAngle = 109.752129, + vAngle = 1.484382, + x_trans = 0.190306, + y_trans = 0.044778, + z_trans = -0.150335, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 42.512844,--FOV + hAngle = 0.000000, + vAngle = -4.478010, + x_trans = 0.154018, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 91.348198,--FOV + hAngle = -108.852020, + vAngle = 0.085984, + x_trans = 0.190306, + y_trans = 0.044778, + z_trans = 0.139404, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 89.777542,--FOV + hAngle = 16.411518, + vAngle = -27.209915, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = -0.218292, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 88.727844,--FOV + hAngle = 0.000000, + vAngle = 34.042202, + x_trans = 0.142145, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 59.208893,--FOV + hAngle = -32.128311, + vAngle = -5.720805, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 56.032040,--FOV + hAngle = 14.803060, + vAngle = 3.332499, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 56.032040,--FOV + hAngle = -14.414484, + vAngle = 3.332499, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 89.777542,--FOV + hAngle = 0.000000, + vAngle = -15.592758, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["MQ-9 Reaper"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = 0.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["MiG-29A"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 76.124840,--FOV + hAngle = -2.623254, + vAngle = -26.566959, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 34.911949,--FOV + hAngle = 24.601770, + vAngle = -32.350807, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 26.184198,--FOV + hAngle = 12.026249, + vAngle = -40.075508, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 39.454399,--FOV + hAngle = -26.664328, + vAngle = -32.355324, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 81.240005,--FOV + hAngle = 131.503998, + vAngle = 10.804660, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 44.201855,--FOV + hAngle = 0.000000, + vAngle = -2.378299, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 81.240005,--FOV + hAngle = -131.503998, + vAngle = 10.804660, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 81.240005,--FOV + hAngle = 76.013145, + vAngle = 2.248441, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 81.240005,--FOV + hAngle = 0.000000, + vAngle = 36.304676, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 81.240005,--FOV + hAngle = -74.774559, + vAngle = 2.248441, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 68.250000,--FOV + hAngle = 13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 68.250000,--FOV + hAngle = -13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 81.240005,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["MiG-29G"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 76.124840,--FOV + hAngle = -2.623254, + vAngle = -26.566959, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 34.911949,--FOV + hAngle = 24.601770, + vAngle = -32.350807, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 26.184198,--FOV + hAngle = 12.026249, + vAngle = -40.075508, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 39.454399,--FOV + hAngle = -26.664328, + vAngle = -32.355324, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 81.240005,--FOV + hAngle = 131.503998, + vAngle = 10.804660, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 44.201855,--FOV + hAngle = 0.000000, + vAngle = -2.378299, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 81.240005,--FOV + hAngle = -131.503998, + vAngle = 10.804660, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 81.240005,--FOV + hAngle = 76.013145, + vAngle = 2.248441, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 81.240005,--FOV + hAngle = 0.000000, + vAngle = 36.304676, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 81.240005,--FOV + hAngle = -74.774559, + vAngle = 2.248441, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 68.250000,--FOV + hAngle = 13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 68.250000,--FOV + hAngle = -13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 81.240005,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["MiG-29K"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 65.000000,--FOV + hAngle = 0.000000, + vAngle = -26.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 30.000000,--FOV + hAngle = 20.000000, + vAngle = -43.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 30.000000,--FOV + hAngle = 0.000000, + vAngle = -43.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 30.000000,--FOV + hAngle = -20.000000, + vAngle = -43.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 30.000000,--FOV + hAngle = 20.000000, + vAngle = -23.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 30.000000,--FOV + hAngle = 0.000000, + vAngle = -23.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 30.000000,--FOV + hAngle = -20.000000, + vAngle = -23.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 30.000000,--FOV + hAngle = 20.000000, + vAngle = 2.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 30.000000,--FOV + hAngle = 0.000000, + vAngle = 2.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 30.000000,--FOV + hAngle = -20.000000, + vAngle = 2.000000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 68.250000,--FOV + hAngle = 13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 68.250000,--FOV + hAngle = -13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 60.000000,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["MiG-29S"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 76.124840,--FOV + hAngle = -2.623254, + vAngle = -26.566959, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 34.911949,--FOV + hAngle = 24.601770, + vAngle = -32.350807, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 26.184198,--FOV + hAngle = 12.026249, + vAngle = -40.075508, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 39.454399,--FOV + hAngle = -26.664328, + vAngle = -32.355324, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 81.240005,--FOV + hAngle = 131.503998, + vAngle = 10.804660, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 44.201855,--FOV + hAngle = 0.000000, + vAngle = -2.378299, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 81.240005,--FOV + hAngle = -131.503998, + vAngle = 10.804660, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 81.240005,--FOV + hAngle = 76.013145, + vAngle = 2.248441, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 81.240005,--FOV + hAngle = 0.000000, + vAngle = 36.304676, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 81.240005,--FOV + hAngle = -74.774559, + vAngle = 2.248441, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 68.250000,--FOV + hAngle = 13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 68.250000,--FOV + hAngle = -13.070938, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 81.240005,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["P-51D"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = -45.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 80.000000,--FOV + hAngle = 45.000000, + vAngle = -45.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = -75.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 80.000000,--FOV + hAngle = -45.000000, + vAngle = -45.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 91.040001,--FOV + hAngle = 157.332764, + vAngle = -28.359503, + x_trans = 0.063872, + y_trans = 0.082888, + z_trans = -0.116148, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 50.000000,--FOV + hAngle = 0.000000, + vAngle = -8.722581, + x_trans = 0.212078, + y_trans = 0.057813, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 80.000000,--FOV + hAngle = -143.000000, + vAngle = 0.000000, + x_trans = 0.350000, + y_trans = 0.059000, + z_trans = 0.100000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 80.000000,--FOV + hAngle = 45.000000, + vAngle = -5.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = 10.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 80.000000,--FOV + hAngle = -45.000000, + vAngle = -5.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = 10.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 80.000000,--FOV + hAngle = -20.000000, + vAngle = 8.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Su-25"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 68.767799,--FOV + hAngle = 1.929517, + vAngle = -30.846605, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 29.223452,--FOV + hAngle = 37.489525, + vAngle = -38.883888, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 40.635601,--FOV + hAngle = -0.438357, + vAngle = -33.138290, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 24.797405,--FOV + hAngle = -34.382549, + vAngle = -34.808853, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 69.302101,--FOV + hAngle = 89.405373, + vAngle = 1.213156, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 29.761202,--FOV + hAngle = 0.000000, + vAngle = -6.880077, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 69.302101,--FOV + hAngle = -89.691940, + vAngle = 4.554290, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 69.302101,--FOV + hAngle = 52.113377, + vAngle = -3.970644, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 72.856201,--FOV + hAngle = 0.000000, + vAngle = 30.866713, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 69.302101,--FOV + hAngle = -50.664936, + vAngle = -3.970644, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 47.680202,--FOV + hAngle = 43.054649, + vAngle = -7.799250, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 47.680202,--FOV + hAngle = -41.743240, + vAngle = -7.799250, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 69.302101,--FOV + hAngle = 0.000000, + vAngle = -15.137112, + x_trans = 0.050000, + y_trans = 0.010000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Su-25T"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 80.663399,--FOV + hAngle = 0.000000, + vAngle = -30.619938, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 39.764698,--FOV + hAngle = 28.661316, + vAngle = -41.406044, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 38.090847,--FOV + hAngle = -24.622110, + vAngle = -45.153934, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 36.062012,--FOV + hAngle = -20.779360, + vAngle = -23.755520, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 80.663399,--FOV + hAngle = 99.816956, + vAngle = 8.032285, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 58.718098,--FOV + hAngle = 0.000000, + vAngle = -5.000803, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 80.663399,--FOV + hAngle = -99.999687, + vAngle = 8.032285, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 80.663399,--FOV + hAngle = 58.382488, + vAngle = -6.648195, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 94.037704,--FOV + hAngle = 0.000000, + vAngle = 41.421227, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 80.663399,--FOV + hAngle = -57.531212, + vAngle = -6.648195, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.203396,--FOV + hAngle = 55.124939, + vAngle = -8.400513, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.203396,--FOV + hAngle = -52.633553, + vAngle = -8.400513, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 90.000000,--FOV + hAngle = 0.000000, + vAngle = -18.382137, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Su-25TM"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 80.663399,--FOV + hAngle = 0.000000, + vAngle = -30.619938, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 39.764698,--FOV + hAngle = 28.661316, + vAngle = -41.406044, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 38.090847,--FOV + hAngle = -24.622110, + vAngle = -45.153934, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 33.645596,--FOV + hAngle = -36.653450, + vAngle = -23.703861, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 80.663399,--FOV + hAngle = 99.816956, + vAngle = 8.032285, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 58.718098,--FOV + hAngle = 0.000000, + vAngle = -5.000803, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 80.663399,--FOV + hAngle = -99.999687, + vAngle = 8.032285, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 80.663399,--FOV + hAngle = 58.382488, + vAngle = -6.648195, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 94.037704,--FOV + hAngle = 0.000000, + vAngle = 41.421227, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 80.663399,--FOV + hAngle = -57.531212, + vAngle = -6.648195, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 60.203396,--FOV + hAngle = 55.124939, + vAngle = -8.400513, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 60.203396,--FOV + hAngle = -52.633553, + vAngle = -8.400513, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 90.000000,--FOV + hAngle = 0.000000, + vAngle = -18.382137, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Su-27"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 89.752197,--FOV + hAngle = 7.104492, + vAngle = 52.525635, + x_trans = 0.016405, + y_trans = 0.011140, + z_trans = -0.053543, + rollAngle = -7.110901, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 33.361835,--FOV + hAngle = 41.045925, + vAngle = -40.805656, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 30.427544,--FOV + hAngle = 0.000000, + vAngle = -41.808968, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 34.392349,--FOV + hAngle = -32.597401, + vAngle = -35.293747, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 87.468338,--FOV + hAngle = 129.012665, + vAngle = 14.547977, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 43.977936,--FOV + hAngle = 0.000000, + vAngle = -4.951577, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 87.468338,--FOV + hAngle = -129.012665, + vAngle = 14.491872, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 87.468338,--FOV + hAngle = 82.862923, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 87.468338,--FOV + hAngle = 0.000000, + vAngle = 38.979362, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 87.468338,--FOV + hAngle = -82.461266, + vAngle = -12.843998, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 68.786629,--FOV + hAngle = 15.618313, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 69.165199,--FOV + hAngle = -15.683434, + vAngle = 8.549150, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 87.468338,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.113927, + y_trans = -0.004946, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["Su-33"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 71.824692,--FOV + hAngle = 0.000000, + vAngle = -32.458889, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 33.361835,--FOV + hAngle = 41.045925, + vAngle = -40.805656, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 30.427544,--FOV + hAngle = 0.000000, + vAngle = -41.808968, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 34.392349,--FOV + hAngle = -32.597401, + vAngle = -35.293747, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 87.468338,--FOV + hAngle = 129.012665, + vAngle = 14.547977, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 43.977936,--FOV + hAngle = 0.000000, + vAngle = -4.951577, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 87.468338,--FOV + hAngle = -129.012665, + vAngle = 14.491872, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 87.468338,--FOV + hAngle = 82.862923, + vAngle = -9.500000, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 87.468338,--FOV + hAngle = 0.000000, + vAngle = 38.979362, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 87.468338,--FOV + hAngle = -82.461266, + vAngle = -12.843998, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 68.786629,--FOV + hAngle = 15.618313, + vAngle = 7.522498, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 69.165199,--FOV + hAngle = -15.683434, + vAngle = 8.549150, + x_trans = 0.000000, + y_trans = 0.000000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 87.468338,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.113927, + y_trans = -0.004946, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} +SnapViews["TF-51D"] = { +[1] = {-- player slot 1 + [1] = {--LWin + Num0 : Snap View 0 + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = -45.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [2] = {--LWin + Num1 : Snap View 1 + viewAngle = 80.000000,--FOV + hAngle = 45.000000, + vAngle = -45.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [3] = {--LWin + Num2 : Snap View 2 + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = -75.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [4] = {--LWin + Num3 : Snap View 3 + viewAngle = 80.000000,--FOV + hAngle = -45.000000, + vAngle = -45.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [5] = {--LWin + Num4 : Snap View 4 + viewAngle = 91.040001,--FOV + hAngle = 157.332764, + vAngle = -28.359503, + x_trans = 0.063872, + y_trans = 0.082888, + z_trans = -0.116148, + rollAngle = 0.000000, + }, + [6] = {--LWin + Num5 : Snap View 5 + viewAngle = 50.000000,--FOV + hAngle = 0.000000, + vAngle = -8.722581, + x_trans = 0.212078, + y_trans = 0.057813, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [7] = {--LWin + Num6 : Snap View 6 + viewAngle = 80.000000,--FOV + hAngle = -143.000000, + vAngle = 0.000000, + x_trans = 0.350000, + y_trans = 0.059000, + z_trans = 0.100000, + rollAngle = 0.000000, + }, + [8] = {--LWin + Num7 : Snap View 7 + viewAngle = 80.000000,--FOV + hAngle = 45.000000, + vAngle = -5.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [9] = {--LWin + Num8 : Snap View 8 + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = 10.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [10] = {--LWin + Num9 : Snap View 9 + viewAngle = 80.000000,--FOV + hAngle = -45.000000, + vAngle = -5.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [11] = {--look at left mirror + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = 10.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [12] = {--look at right mirror + viewAngle = 80.000000,--FOV + hAngle = -20.000000, + vAngle = 8.000000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, + [13] = {--default view + viewAngle = 80.000000,--FOV + hAngle = 0.000000, + vAngle = -9.500000, + x_trans = 0.120000, + y_trans = 0.059000, + z_trans = 0.000000, + rollAngle = 0.000000, + }, +}, +} diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Config/View/SnapViewsDefault.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/SnapViewsDefault.lua similarity index 100% rename from Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Config/View/SnapViewsDefault.lua rename to Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/SnapViewsDefault.lua diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Config/View/View.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/View.lua similarity index 100% rename from Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Config/View/View.lua rename to Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Config/View/View.lua diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Scripts/World/GPS_GNSS.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Scripts/World/GPS_GNSS.lua similarity index 100% rename from Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/Scripts/World/GPS_GNSS.lua rename to Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Scripts/World/GPS_GNSS.lua diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Scripts/World/birds.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Scripts/World/birds.lua new file mode 100644 index 000000000..8aee1f700 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/Scripts/World/birds.lua @@ -0,0 +1,27 @@ +birds_avail = true --Birds availability. false - there is no birds +birds_maximum_hrad = 200 --Maximum altitude above ground al sea level bird could be met +birds_maximum_absolute_height = 8000 --Maximum absolute altitude bird could be met +birds_minimum_velocity = 40 --Minimum velocity bird could be met +birds_delta_time = 3.55 +birds_probability = {0.006333333*150, + 0.004166667*150, + 0.001966667*150, + 0.001090909*150, + 0.000741818*150, + 0.0006*150, + 0.000510545*150, + 0.000447273*150, + 0.000389455*150, + 0.000349091*150, + 0.000310909*150, + 0.000282545*150, + 0.000250909*150, + 0.000220364*150, + 0.000196364*150, + 0.000174545*150, + 0.000152727*150, + 0.000128727*150, + 0.000103636*150, + 7.63636E-05*150, + 0*150 +} diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/VHF_RADIO/SETTINGS.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/VHF_RADIO/SETTINGS.lua new file mode 100644 index 000000000..92c6a42c4 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/VHF_RADIO/SETTINGS.lua @@ -0,0 +1,14 @@ +settings= +{ + ["dials"]= + { + ["channel"]=-1, + }, + ["presets"]= + { + [1]=124000000, + [2]=124000000, + [3]=131000000, + [4]=139000000, + }, +} diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/AIB-005 - Patrol AI and Randomize Zones.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/AIB-005 - Patrol AI and Randomize Zones.lua new file mode 100644 index 000000000..eab2c2e22 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/AIB-005 - Patrol AI and Randomize Zones.lua @@ -0,0 +1,51 @@ +-- Name: AIB-005 - Patrol AI and Randomize Zones +-- Author: FlightControl +-- Date Created: 10 Jan 2016 +-- +-- # Situation: +-- +-- For the red coalition, 2 client slots are foreseen. +-- For those players that have not joined the mission, red AI is spawned. +-- The red AI should start patrolling an area until fuel is empty and return to the home base. +-- For each AI being spawned, ensure that they fly to a random zone defined within the mission editor. +-- Right now there are two patrol zones defined, so the AI should start patrolliing in one of these zones. +-- +-- # Test cases: +-- +-- 1. If no player is logging into the red slots, 2 red AI planes should be alive. +-- 2. If a player joins one red slot, one red AI plane should return to the nearest home base. +-- 3. If two players join the red slots, no AI plane should be spawned, and all airborne AI planes should return to the nearest home base. +-- 4. Spawned AI should take-off from the airbase, and start patrolling the area around Anapa. +-- 5. When the AI is out-of-fuel, it should report it is returning to the home base, and land at Anapa. +-- 6. Ensure that you see the AI patrol in one of the two zones ... + +-- Define the SET of CLIENTs from the red coalition. This SET is filled during startup. +local RU_PlanesClientSet = SET_CLIENT:New():FilterCountries( "RUSSIA" ):FilterCategories( "plane" ) + +-- Define the SPAWN object for the red AI plane template. +-- We use InitCleanUp to check every 20 seconds, if there are no planes blocked at the airbase, waithing for take-off. +-- If a blocked plane exists, this red plane will be ReSpawned. +local RU_PlanesSpawn = SPAWN:New( "AI RU" ):InitCleanUp( 20 ) + +-- Start the AI_BALANCER, using the SET of red CLIENTs, and the SPAWN object as a parameter. +local RU_AI_Balancer = AI_BALANCER:New( RU_PlanesClientSet, RU_PlanesSpawn ) + +-- Create the first polygon zone ... +local PatrolZoneGroup1 = GROUP:FindByName( "PatrolZone1" ) +local PatrolZone1 = ZONE_POLYGON:New( "PatrolZone1", PatrolZoneGroup1 ) + +-- Create the second polygon zone ... +local PatrolZoneGroup2 = GROUP:FindByName( "PatrolZone2" ) +local PatrolZone2 = ZONE_POLYGON:New( "PatrolZone2", PatrolZoneGroup2 ) + +-- Now, create an array of these zones ... +local PatrolZoneArray = { PatrolZone1, PatrolZone2 } + +function RU_AI_Balancer:OnAfterSpawned( SetGroup, From, Event, To, AIGroup ) + + local Patrol = AI_PATROL_ZONE:New( PatrolZoneArray[math.random( 1, 2 )], 3000, 6000, 400, 600 ) + Patrol:ManageFuel( 0.2, 60 ) + Patrol:SetControllable( AIGroup ) + Patrol:Start() + +end diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/Moose.lua b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/Moose.lua new file mode 100644 index 000000000..8faec6fc4 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/Moose.lua @@ -0,0 +1,31 @@ +env.info( '*** MOOSE DYNAMIC INCLUDE START *** ' ) +env.info( 'Moose Generation Timestamp: 20170116_2116' ) + +local base = _G + +Include = {} + +Include.File = function( IncludeFile ) + if not Include.Files[ IncludeFile ] then + Include.Files[IncludeFile] = IncludeFile + env.info( "Include:" .. IncludeFile .. " from " .. Include.ProgramPath ) + local f = assert( base.loadfile( Include.ProgramPath .. IncludeFile .. ".lua" ) ) + if f == nil then + error ("Could not load MOOSE file " .. IncludeFile .. ".lua" ) + else + env.info( "Include:" .. IncludeFile .. " loaded from " .. Include.ProgramPath ) + return f() + end + end +end + +Include.ProgramPath = "Scripts/Moose/" + +env.info( "Include.ProgramPath = " .. Include.ProgramPath) + +Include.Files = {} + +Include.File( "Moose" ) + +BASE:TraceOnOff( true ) +env.info( '*** MOOSE INCLUDE END *** ' ) diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/dictionary b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/dictionary new file mode 100644 index 000000000..c29347756 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/dictionary @@ -0,0 +1,416 @@ +dictionary = +{ + ["DictKey_UnitName_89"] = "", + ["DictKey_UnitName_67"] = "AI US 1", + ["DictKey_UnitName_156"] = "RU Client #020", + ["DictKey_UnitName_297"] = "US Client #023", + ["DictKey_WptName_310"] = "", + ["DictKey_GroupName_125"] = "RU Client #010", + ["DictKey_UnitName_135"] = "RU Client #013", + ["DictKey_UnitName_374"] = "RU Client #004", + ["DictKey_WptName_292"] = "", + ["DictKey_WptName_48"] = "", + ["DictKey_GroupName_137"] = "RU Client #014", + ["DictKey_WptName_70"] = "", + ["DictKey_WptName_295"] = "", + ["DictKey_UnitName_25"] = "AI RU", + ["DictKey_GroupName_113"] = "RU Client #006", + ["DictKey_GroupName_284"] = "US Client #019", + ["DictKey_UnitName_312"] = "US Client #028", + ["DictKey_WptName_13"] = "", + ["DictKey_WptName_124"] = "", + ["DictKey_WptName_217"] = "", + ["DictKey_GroupName_10"] = "Client Group 2", + ["DictKey_GroupName_302"] = "US Client #025", + ["DictKey_UnitName_258"] = "US Client #010", + ["DictKey_WptName_181"] = "", + ["DictKey_WptName_109"] = "", + ["DictKey_WptName_336"] = "", + ["DictKey_GroupName_311"] = "US Client #028", + ["DictKey_GroupName_242"] = "US Client #005", + ["DictKey_UnitName_74"] = "Pilot #004", + ["DictKey_WptName_136"] = "", + ["DictKey_WptName_99"] = "", + ["DictKey_UnitName_315"] = "US Client #029", + ["DictKey_UnitName_43"] = "Client 5", + ["DictKey_GroupName_331"] = "PatrolZone2", + ["DictKey_WptName_178"] = "", + ["DictKey_GroupName_30"] = "AI RU", + ["DictKey_UnitName_249"] = "US Client #007", + ["DictKey_WptName_53"] = "", + ["DictKey_UnitName_171"] = "RU Client #025", + ["DictKey_WptName_289"] = "", + ["DictKey_GroupName_352"] = "RU Client #008", + ["DictKey_GroupName_260"] = "US Client #011", + ["DictKey_descriptionRedTask_2"] = "", + ["DictKey_WptName_55"] = "", + ["DictKey_GroupName_33"] = "AI RU", + ["DictKey_UnitName_183"] = "RU Client #029", + ["DictKey_WptName_190"] = "", + ["DictKey_UnitName_216"] = "RU Client #040", + ["DictKey_WptName_286"] = "", + ["DictKey_UnitName_153"] = "RU Client #019", + ["DictKey_WptName_75"] = "", + ["DictKey_UnitName_105"] = "RU Client #003", + ["DictKey_GroupName_382"] = "RU Client #007", + ["DictKey_UnitName_270"] = "US Client #014", + ["DictKey_WptName_47"] = "", + ["DictKey_GroupName_170"] = "RU Client #025", + ["DictKey_UnitName_46"] = "Client 7", + ["DictKey_WptName_92"] = "", + ["DictKey_UnitName_380"] = "RU Client #006", + ["DictKey_GroupName_191"] = "RU Client #032", + ["DictKey_UnitName_40"] = "Client 6", + ["DictKey_UnitName_95"] = "Pilot #002", + ["DictKey_GroupName_296"] = "US Client #023", + ["DictKey_WptName_244"] = "", + ["DictKey_UnitName_377"] = "RU Client #005", + ["DictKey_WptName_9"] = "", + ["DictKey_UnitName_11"] = "Client 2", + ["DictKey_GroupName_308"] = "US Client #027", + ["DictKey_GroupName_27"] = "AI RU", + ["DictKey_UnitName_22"] = "Client 4", + ["DictKey_WptName_62"] = "", + ["DictKey_GroupName_367"] = "RU Client #002", + ["DictKey_sortie_4"] = "", + ["DictKey_WptName_333"] = "", + ["DictKey_UnitName_356"] = "RU Client #009", + ["DictKey_GroupName_152"] = "RU Client #019", + ["DictKey_GroupName_281"] = "US Client #018", + ["DictKey_WptName_235"] = "", + ["DictKey_UnitName_362"] = "RU Client #011", + ["DictKey_WptName_375"] = "", + ["DictKey_GroupName_379"] = "RU Client #006", + ["DictKey_UnitName_267"] = "US Client #013", + ["DictKey_GroupName_173"] = "RU Client #026", + ["DictKey_GroupName_248"] = "US Client #007", + ["DictKey_WptName_369"] = "", + ["DictKey_UnitName_58"] = "Pilot #003", + ["DictKey_WptName_160"] = "", + ["DictKey_UnitName_246"] = "US Client #006", + ["DictKey_WptName_163"] = "", + ["DictKey_WptName_98"] = "", + ["DictKey_GroupName_340"] = "RU Client #004", + ["DictKey_UnitName_365"] = "RU Client #012", + ["DictKey_GroupName_221"] = "RU Client #042", + ["DictKey_UnitName_318"] = "US Client #030", + ["DictKey_GroupName_158"] = "RU Client #021", + ["DictKey_GroupName_320"] = "US Client #031", + ["DictKey_UnitName_34"] = "AI RU", + ["DictKey_WptName_208"] = "", + ["DictKey_WptName_334"] = "", + ["DictKey_WptName_54"] = "", + ["DictKey_WptName_82"] = "", + ["DictKey_UnitName_383"] = "RU Client #007", + ["DictKey_UnitName_234"] = "US Client #002", + ["DictKey_GroupName_104"] = "RU Client #003", + ["DictKey_UnitName_368"] = "RU Client #002", + ["DictKey_WptName_366"] = "", + ["DictKey_GroupName_206"] = "RU Client #037", + ["DictKey_GroupName_24"] = "AI RU", + ["DictKey_GroupName_325"] = "PatrolZone1", + ["DictKey_UnitName_225"] = "RU Client #043", + ["DictKey_WptName_328"] = "", + ["DictKey_WptName_193"] = "", + ["DictKey_UnitName_219"] = "RU Client #041", + ["DictKey_WptName_68"] = "", + ["DictKey_GroupName_122"] = "RU Client #009", + ["DictKey_GroupName_266"] = "US Client #013", + ["DictKey_UnitName_350"] = "RU Client #007", + ["DictKey_UnitName_341"] = "RU Client #004", + ["DictKey_UnitName_228"] = "RU Client #044", + ["DictKey_UnitName_204"] = "RU Client #036", + ["DictKey_WptName_49"] = "", + ["DictKey_UnitName_303"] = "US Client #025", + ["DictKey_GroupName_245"] = "US Client #006", + ["DictKey_GroupName_275"] = "US Client #016", + ["DictKey_WptName_90"] = "", + ["DictKey_UnitName_222"] = "RU Client #042", + ["DictKey_GroupName_110"] = "RU Client #005", + ["DictKey_UnitName_120"] = "RU Client #008", + ["DictKey_WptName_280"] = "", + ["DictKey_UnitName_144"] = "RU Client #016", + ["DictKey_UnitName_306"] = "US Client #026", + ["DictKey_WptName_118"] = "", + ["DictKey_WptName_307"] = "", + ["DictKey_UnitName_129"] = "RU Client #011", + ["DictKey_GroupName_59"] = "Client Group Range 1", + ["DictKey_GroupName_164"] = "RU Client #023", + ["DictKey_UnitName_252"] = "US Client #008", + ["DictKey_WptName_61"] = "", + ["DictKey_WptName_184"] = "", + ["DictKey_GroupName_361"] = "RU Client #011", + ["DictKey_WptName_80"] = "", + ["DictKey_GroupName_299"] = "US Client #024", + ["DictKey_GroupName_314"] = "US Client #029", + ["DictKey_WptName_86"] = "", + ["DictKey_GroupName_346"] = "RU Client #006", + ["DictKey_WptName_205"] = "", + ["DictKey_WptName_390"] = "", + ["DictKey_WptName_196"] = "", + ["DictKey_GroupName_263"] = "US Client #012", + ["DictKey_WptName_238"] = "", + ["DictKey_WptName_51"] = "", + ["DictKey_UnitName_150"] = "RU Client #018", + ["DictKey_WptName_76"] = "", + ["DictKey_UnitName_291"] = "US Client #021", + ["DictKey_WptName_127"] = "", + ["DictKey_GroupName_21"] = "Client Group 4", + ["DictKey_GroupName_364"] = "RU Client #012", + ["DictKey_GroupName_278"] = "US Client #017", + ["DictKey_WptName_44"] = "", + ["DictKey_WptName_335"] = "", + ["DictKey_WptName_100"] = "", + ["DictKey_GroupName_185"] = "RU Client #030", + ["DictKey_UnitName_321"] = "US Client #031", + ["DictKey_WptName_112"] = "", + ["DictKey_GroupName_230"] = "RU Client #045", + ["DictKey_UnitName_201"] = "RU Client #035", + ["DictKey_WptName_145"] = "", + ["DictKey_GroupName_128"] = "RU Client #011", + ["DictKey_descriptionBlueTask_3"] = "", + ["DictKey_WptName_241"] = "", + ["DictKey_descriptionText_1"] = "-- Name: AIB-005 - Patrol AI and Randomize Zones\ +-- Author: FlightControl\ +-- Date Created: 10 Jan 2016\ +--\ +-- # Situation:\ +--\ +-- For the red coalition, 2 client slots are foreseen.\ +-- For those players that have not joined the mission, red AI is spawned.\ +-- The red AI should start patrolling an area until fuel is empty and return to the home base.\ +-- For each AI being spawned, ensure that they fly to a random zone defined within the mission editor.\ +-- Right now there are two patrol zones defined, so the AI should start patrolliing in one of these zones.\ +-- \ +-- # Test cases:\ +-- \ +-- 1. If no player is logging into the red slots, 2 red AI planes should be alive.\ +-- 2. If a player joins one red slot, one red AI plane should return to the nearest home base.\ +-- 3. If two players join the red slots, no AI plane should be spawned, and all airborne AI planes should return to the nearest home base.\ +-- 4. Spawned AI should take-off from the airbase, and start patrolling the area around Anapa.\ +-- 5. When the AI is out-of-fuel, it should report it is returning to the home base, and land at Anapa.\ +-- 6. Ensure that you see the AI patrol in one of the two zones ...\ +", + ["DictKey_GroupName_134"] = "RU Client #013", + ["DictKey_UnitName_102"] = "RU Client #002", + ["DictKey_WptName_378"] = "", + ["DictKey_GroupName_224"] = "RU Client #043", + ["DictKey_UnitName_371"] = "RU Client #003", + ["DictKey_UnitName_392"] = "RU Client #010", + ["DictKey_UnitName_108"] = "RU Client #004", + ["DictKey_UnitName_132"] = "RU Client #012", + ["DictKey_UnitName_174"] = "RU Client #026", + ["DictKey_WptName_274"] = "", + ["DictKey_GroupName_176"] = "RU Client #027", + ["DictKey_WptName_339"] = "", + ["DictKey_WptName_199"] = "", + ["DictKey_UnitName_123"] = "RU Client #009", + ["DictKey_WptName_81"] = "", + ["DictKey_UnitName_213"] = "RU Client #039", + ["DictKey_WptName_211"] = "", + ["DictKey_GroupName_227"] = "RU Client #044", + ["DictKey_WptName_77"] = "", + ["DictKey_WptName_29"] = "", + ["DictKey_WptName_166"] = "", + ["DictKey_WptName_396"] = "", + ["DictKey_UnitName_168"] = "RU Client #024", + ["DictKey_UnitName_210"] = "RU Client #038", + ["DictKey_WptName_169"] = "", + ["DictKey_GroupName_7"] = "US Client #001", + ["DictKey_WptName_384"] = "", + ["DictKey_WptName_354"] = "", + ["DictKey_GroupName_143"] = "RU Client #016", + ["DictKey_UnitName_288"] = "US Client #020", + ["DictKey_GroupName_155"] = "RU Client #020", + ["DictKey_GroupName_236"] = "US Client #003", + ["DictKey_ActionText_17"] = "", + ["DictKey_WptName_157"] = "", + ["DictKey_UnitName_114"] = "RU Client #006", + ["DictKey_WptName_298"] = "", + ["DictKey_WptName_142"] = "", + ["DictKey_GroupName_254"] = "US Client #009", + ["DictKey_WptName_91"] = "", + ["DictKey_WptName_259"] = "", + ["DictKey_WptName_23"] = "", + ["DictKey_WptName_172"] = "", + ["DictKey_WptName_214"] = "", + ["DictKey_UnitName_264"] = "US Client #012", + ["DictKey_WptName_151"] = "", + ["DictKey_UnitName_15"] = "AI US 2", + ["DictKey_GroupName_45"] = "Client Group 7", + ["DictKey_WptName_71"] = "", + ["DictKey_WptName_26"] = "", + ["DictKey_UnitName_57"] = "Pilot #002", + ["DictKey_UnitName_31"] = "AI RU", + ["DictKey_UnitName_111"] = "RU Client #005", + ["DictKey_WptName_12"] = "", + ["DictKey_GroupName_39"] = "Client Group 6", + ["DictKey_WptName_52"] = "", + ["DictKey_UnitName_159"] = "RU Client #021", + ["DictKey_WptName_38"] = "", + ["DictKey_UnitName_138"] = "RU Client #014", + ["DictKey_WptName_330"] = "", + ["DictKey_UnitName_309"] = "US Client #027", + ["DictKey_WptName_85"] = "", + ["DictKey_GroupName_290"] = "US Client #021", + ["DictKey_GroupName_373"] = "RU Client #004", + ["DictKey_UnitName_240"] = "US Client #004", + ["DictKey_GroupName_358"] = "RU Client #010", + ["DictKey_WptName_247"] = "", + ["DictKey_WptName_223"] = "", + ["DictKey_WptName_324"] = "", + ["DictKey_GroupName_18"] = "RU Client #001", + ["DictKey_WptName_148"] = "", + ["DictKey_GroupName_349"] = "RU Client #007", + ["DictKey_GroupName_36"] = "AI RU", + ["DictKey_WptName_130"] = "", + ["DictKey_WptName_381"] = "", + ["DictKey_UnitName_180"] = "RU Client #028", + ["DictKey_UnitName_117"] = "RU Client #007", + ["DictKey_WptName_329"] = "", + ["DictKey_GroupName_73"] = "Patrol Zone Blue", + ["DictKey_WptName_121"] = "", + ["DictKey_WptName_78"] = "", + ["DictKey_UnitName_147"] = "RU Client #017", + ["DictKey_UnitName_56"] = "Pilot #001", + ["DictKey_GroupName_203"] = "RU Client #036", + ["DictKey_GroupName_337"] = "RU Client #003", + ["DictKey_WptName_304"] = "", + ["DictKey_WptName_103"] = "", + ["DictKey_WptName_265"] = "", + ["DictKey_GroupName_14"] = "AI US 2", + ["DictKey_UnitName_282"] = "US Client #018", + ["DictKey_WptName_357"] = "", + ["DictKey_WptName_175"] = "", + ["DictKey_WptName_327"] = "", + ["DictKey_WptName_342"] = "", + ["DictKey_WptName_154"] = "", + ["DictKey_GroupName_391"] = "RU Client #010", + ["DictKey_UnitName_359"] = "RU Client #010", + ["DictKey_GroupName_197"] = "RU Client #034", + ["DictKey_GroupName_42"] = "Client Group 5", + ["DictKey_WptName_283"] = "", + ["DictKey_GroupName_161"] = "RU Client #022", + ["DictKey_UnitName_19"] = "RU Client #001", + ["DictKey_UnitName_237"] = "US Client #003", + ["DictKey_WptName_65"] = "", + ["DictKey_WptName_372"] = "", + ["DictKey_WptName_322"] = "", + ["DictKey_WptName_97"] = "", + ["DictKey_WptName_360"] = "", + ["DictKey_GroupName_131"] = "RU Client #012", + ["DictKey_WptName_16"] = "", + ["DictKey_GroupName_101"] = "RU Client #002", + ["DictKey_WptName_202"] = "", + ["DictKey_UnitName_198"] = "RU Client #034", + ["DictKey_WptName_253"] = "", + ["DictKey_GroupName_394"] = "RU Client #011", + ["DictKey_WptName_32"] = "", + ["DictKey_UnitName_279"] = "US Client #017", + ["DictKey_GroupName_305"] = "US Client #026", + ["DictKey_UnitName_141"] = "RU Client #015", + ["DictKey_WptName_79"] = "", + ["DictKey_UnitName_207"] = "RU Client #037", + ["DictKey_WptName_250"] = "", + ["DictKey_GroupName_116"] = "RU Client #007", + ["DictKey_GroupName_94"] = "Patrol Zone Red", + ["DictKey_GroupName_212"] = "RU Client #039", + ["DictKey_GroupName_233"] = "US Client #002", + ["DictKey_GroupName_200"] = "RU Client #035", + ["DictKey_WptName_96"] = "", + ["DictKey_WptName_50"] = "", + ["DictKey_WptName_115"] = "", + ["DictKey_WptName_226"] = "", + ["DictKey_UnitName_126"] = "RU Client #010", + ["DictKey_UnitName_243"] = "US Client #005", + ["DictKey_WptName_316"] = "", + ["DictKey_WptName_69"] = "", + ["DictKey_UnitName_347"] = "RU Client #006", + ["DictKey_GroupName_209"] = "RU Client #038", + ["DictKey_UnitName_28"] = "AI RU", + ["DictKey_GroupName_215"] = "RU Client #040", + ["DictKey_WptName_64"] = "", + ["DictKey_UnitName_192"] = "RU Client #032", + ["DictKey_UnitName_338"] = "RU Client #003", + ["DictKey_GroupName_257"] = "US Client #010", + ["DictKey_GroupName_188"] = "RU Client #031", + ["DictKey_GroupName_107"] = "RU Client #004", + ["DictKey_UnitName_255"] = "US Client #009", + ["DictKey_UnitName_231"] = "RU Client #045", + ["DictKey_UnitName_88"] = "Pilot #001", + ["DictKey_WptName_232"] = "", + ["DictKey_UnitName_195"] = "RU Client #033", + ["DictKey_GroupName_370"] = "RU Client #003", + ["DictKey_WptName_229"] = "", + ["DictKey_WptName_256"] = "", + ["DictKey_WptName_345"] = "", + ["DictKey_WptName_277"] = "", + ["DictKey_WptName_63"] = "", + ["DictKey_WptName_363"] = "", + ["DictKey_GroupName_167"] = "RU Client #024", + ["DictKey_GroupName_385"] = "RU Client #008", + ["DictKey_GroupName_376"] = "RU Client #005", + ["DictKey_UnitName_60"] = "Client Range 1", + ["DictKey_UnitName_326"] = "Pilot #001", + ["DictKey_GroupName_388"] = "RU Client #009", + ["DictKey_GroupName_251"] = "US Client #008", + ["DictKey_WptName_41"] = "", + ["DictKey_UnitName_273"] = "US Client #015", + ["DictKey_GroupName_66"] = "AI US", + ["DictKey_WptName_87"] = "", + ["DictKey_GroupName_343"] = "RU Client #005", + ["DictKey_GroupName_119"] = "RU Client #008", + ["DictKey_WptName_268"] = "", + ["DictKey_WptName_220"] = "", + ["DictKey_WptName_262"] = "", + ["DictKey_WptName_83"] = "", + ["DictKey_WptName_72"] = "", + ["DictKey_UnitName_276"] = "US Client #016", + ["DictKey_WptName_387"] = "", + ["DictKey_GroupName_272"] = "US Client #015", + ["DictKey_WptName_187"] = "", + ["DictKey_UnitName_189"] = "RU Client #031", + ["DictKey_UnitName_162"] = "RU Client #022", + ["DictKey_GroupName_146"] = "RU Client #017", + ["DictKey_GroupName_140"] = "RU Client #015", + ["DictKey_GroupName_239"] = "US Client #004", + ["DictKey_UnitName_353"] = "RU Client #008", + ["DictKey_UnitName_386"] = "RU Client #008", + ["DictKey_WptName_351"] = "", + ["DictKey_WptName_313"] = "", + ["DictKey_UnitName_93"] = "Pilot #001", + ["DictKey_GroupName_287"] = "US Client #020", + ["DictKey_UnitName_395"] = "RU Client #011", + ["DictKey_UnitName_332"] = "Pilot #002", + ["DictKey_WptName_133"] = "", + ["DictKey_UnitName_186"] = "RU Client #030", + ["DictKey_GroupName_194"] = "RU Client #033", + ["DictKey_GroupName_179"] = "RU Client #028", + ["DictKey_GroupName_269"] = "US Client #014", + ["DictKey_WptName_20"] = "", + ["DictKey_WptName_348"] = "", + ["DictKey_WptName_301"] = "", + ["DictKey_UnitName_285"] = "US Client #019", + ["DictKey_UnitName_344"] = "RU Client #005", + ["DictKey_WptName_393"] = "", + ["DictKey_WptName_84"] = "", + ["DictKey_GroupName_355"] = "RU Client #009", + ["DictKey_UnitName_177"] = "RU Client #027", + ["DictKey_UnitName_37"] = "AI RU", + ["DictKey_WptName_319"] = "", + ["DictKey_WptName_106"] = "", + ["DictKey_UnitName_294"] = "US Client #022", + ["DictKey_UnitName_165"] = "RU Client #023", + ["DictKey_WptName_35"] = "", + ["DictKey_UnitName_261"] = "US Client #011", + ["DictKey_GroupName_293"] = "US Client #022", + ["DictKey_UnitName_389"] = "RU Client #009", + ["DictKey_GroupName_182"] = "RU Client #029", + ["DictKey_UnitName_300"] = "US Client #024", + ["DictKey_GroupName_317"] = "US Client #030", + ["DictKey_WptName_271"] = "", + ["DictKey_WptName_139"] = "", + ["DictKey_GroupName_149"] = "RU Client #018", + ["DictKey_GroupName_218"] = "RU Client #041", + ["DictKey_UnitName_8"] = "US Client #001", +} -- end of dictionary diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/mapResource b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/mapResource new file mode 100644 index 000000000..dc130cd07 --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/l10n/DEFAULT/mapResource @@ -0,0 +1,5 @@ +mapResource = +{ + ["ResKey_Action_323"] = "Moose.lua", + ["ResKey_Action_6"] = "AIB-005 - Patrol AI and Randomize Zones.lua", +} -- end of mapResource diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/mission b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/mission new file mode 100644 index 000000000..d243c5ada --- /dev/null +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/mission @@ -0,0 +1,5000 @@ +mission = +{ + ["trig"] = + { + ["actions"] = + { + [1] = "a_do_script_file(getValueResourceByKey(\"ResKey_Action_323\"));", + [2] = "a_do_script(getValueDictByKey(\"DictKey_ActionText_17\"));", + [3] = "a_do_script_file(getValueResourceByKey(\"ResKey_Action_6\"));", + }, -- end of ["actions"] + ["events"] = + { + }, -- end of ["events"] + ["custom"] = + { + }, -- end of ["custom"] + ["func"] = + { + }, -- end of ["func"] + ["flag"] = + { + [1] = true, + [2] = true, + [3] = true, + }, -- end of ["flag"] + ["conditions"] = + { + [1] = "return(true)", + [2] = "return(true)", + [3] = "return(true)", + }, -- end of ["conditions"] + ["customStartup"] = + { + }, -- end of ["customStartup"] + ["funcStartup"] = + { + [1] = "if mission.trig.conditions[1]() then mission.trig.actions[1]() end", + [2] = "if mission.trig.conditions[2]() then mission.trig.actions[2]() end", + [3] = "if mission.trig.conditions[3]() then mission.trig.actions[3]() end", + }, -- end of ["funcStartup"] + }, -- end of ["trig"] + ["date"] = + { + ["Day"] = 1, + ["Year"] = 2011, + ["Month"] = 6, + }, -- end of ["date"] + ["maxDictId"] = 396, + ["result"] = + { + ["offline"] = + { + ["conditions"] = + { + }, -- end of ["conditions"] + ["actions"] = + { + }, -- end of ["actions"] + ["func"] = + { + }, -- end of ["func"] + }, -- end of ["offline"] + ["total"] = 0, + ["blue"] = + { + ["conditions"] = + { + }, -- end of ["conditions"] + ["actions"] = + { + }, -- end of ["actions"] + ["func"] = + { + }, -- end of ["func"] + }, -- end of ["blue"] + ["red"] = + { + ["conditions"] = + { + }, -- end of ["conditions"] + ["actions"] = + { + }, -- end of ["actions"] + ["func"] = + { + }, -- end of ["func"] + }, -- end of ["red"] + }, -- end of ["result"] + ["groundControl"] = + { + ["isPilotControlVehicles"] = false, + ["roles"] = + { + ["artillery_commander"] = + { + ["blue"] = 0, + ["red"] = 0, + }, -- end of ["artillery_commander"] + ["instructor"] = + { + ["blue"] = 0, + ["red"] = 0, + }, -- end of ["instructor"] + ["observer"] = + { + ["blue"] = 0, + ["red"] = 0, + }, -- end of ["observer"] + ["forward_observer"] = + { + ["blue"] = 0, + ["red"] = 0, + }, -- end of ["forward_observer"] + }, -- end of ["roles"] + }, -- end of ["groundControl"] + ["triggers"] = + { + ["zones"] = + { + }, -- end of ["zones"] + }, -- end of ["triggers"] + ["weather"] = + { + ["atmosphere_type"] = 0, + ["wind"] = + { + ["at8000"] = + { + ["speed"] = 0, + ["dir"] = 0, + }, -- end of ["at8000"] + ["atGround"] = + { + ["speed"] = 0, + ["dir"] = 0, + }, -- end of ["atGround"] + ["at2000"] = + { + ["speed"] = 0, + ["dir"] = 0, + }, -- end of ["at2000"] + }, -- end of ["wind"] + ["enable_fog"] = false, + ["season"] = + { + ["temperature"] = 20, + }, -- end of ["season"] + ["type_weather"] = 0, + ["qnh"] = 760, + ["cyclones"] = + { + }, -- end of ["cyclones"] + ["name"] = "Winter, clean sky", + ["fog"] = + { + ["thickness"] = 0, + ["visibility"] = 25, + ["density"] = 7, + }, -- end of ["fog"] + ["groundTurbulence"] = 0, + ["visibility"] = + { + ["distance"] = 80000, + }, -- end of ["visibility"] + ["clouds"] = + { + ["thickness"] = 200, + ["density"] = 0, + ["base"] = 300, + ["iprecptns"] = 0, + }, -- end of ["clouds"] + }, -- end of ["weather"] + ["theatre"] = "Caucasus", + ["needModules"] = + { + }, -- end of ["needModules"] + ["map"] = + { + ["centerY"] = 295177.98214286, + ["zoom"] = 25000, + ["centerX"] = -8598.8505859375, + }, -- end of ["map"] + ["coalitions"] = + { + ["blue"] = + { + [1] = 11, + [2] = 4, + [3] = 6, + [4] = 16, + [5] = 13, + [6] = 15, + [7] = 9, + [8] = 8, + [9] = 12, + [10] = 2, + [11] = 3, + [12] = 5, + [13] = 10, + [14] = 20, + [15] = 21, + [16] = 40, + [17] = 26, + [18] = 45, + [19] = 28, + }, -- end of ["blue"] + ["neutrals"] = + { + [1] = 7, + [2] = 17, + [3] = 22, + [4] = 23, + [5] = 25, + [6] = 29, + [7] = 30, + [8] = 31, + [9] = 32, + [10] = 33, + [11] = 35, + [12] = 36, + [13] = 39, + [14] = 41, + [15] = 42, + [16] = 44, + [17] = 46, + }, -- end of ["neutrals"] + ["red"] = + { + [1] = 0, + [2] = 1, + [3] = 18, + [4] = 19, + [5] = 37, + [6] = 24, + [7] = 27, + [8] = 43, + [9] = 47, + [10] = 34, + [11] = 38, + }, -- end of ["red"] + }, -- end of ["coalitions"] + ["descriptionText"] = "DictKey_descriptionText_1", + ["pictureFileNameR"] = + { + }, -- end of ["pictureFileNameR"] + ["descriptionBlueTask"] = "DictKey_descriptionBlueTask_3", + ["descriptionRedTask"] = "DictKey_descriptionRedTask_2", + ["pictureFileNameB"] = + { + }, -- end of ["pictureFileNameB"] + ["trigrules"] = + { + [1] = + { + ["rules"] = + { + }, -- end of ["rules"] + ["eventlist"] = "", + ["actions"] = + { + [1] = + { + ["file"] = "ResKey_Action_323", + ["predicate"] = "a_do_script_file", + ["ai_task"] = + { + [1] = "", + [2] = "", + }, -- end of ["ai_task"] + }, -- end of [1] + }, -- end of ["actions"] + ["predicate"] = "triggerStart", + ["comment"] = "Load Moose", + }, -- end of [1] + [2] = + { + ["rules"] = + { + }, -- end of ["rules"] + ["eventlist"] = "", + ["actions"] = + { + [1] = + { + ["KeyDict_text"] = "DictKey_ActionText_17", + ["text"] = "DictKey_ActionText_17", + ["predicate"] = "a_do_script", + ["ai_task"] = + { + [1] = "", + [2] = "", + }, -- end of ["ai_task"] + }, -- end of [1] + }, -- end of ["actions"] + ["predicate"] = "triggerStart", + ["comment"] = "Trace", + }, -- end of [2] + [3] = + { + ["rules"] = + { + }, -- end of ["rules"] + ["eventlist"] = "", + ["actions"] = + { + [1] = + { + ["file"] = "ResKey_Action_6", + ["predicate"] = "a_do_script_file", + ["ai_task"] = + { + [1] = "", + [2] = "", + }, -- end of ["ai_task"] + }, -- end of [1] + }, -- end of ["actions"] + ["predicate"] = "triggerStart", + ["comment"] = "Load Mission", + }, -- end of [3] + }, -- end of ["trigrules"] + ["coalition"] = + { + ["blue"] = + { + ["bullseye"] = + { + ["y"] = 617414, + ["x"] = -291014, + }, -- end of ["bullseye"] + ["nav_points"] = + { + }, -- end of ["nav_points"] + ["name"] = "blue", + ["country"] = + { + [1] = + { + ["id"] = 11, + ["name"] = "Belgium", + }, -- end of [1] + [2] = + { + ["id"] = 4, + ["name"] = "UK", + }, -- end of [2] + [3] = + { + ["id"] = 6, + ["name"] = "Germany", + }, -- end of [3] + [4] = + { + ["id"] = 16, + ["name"] = "Georgia", + }, -- end of [4] + [5] = + { + ["id"] = 13, + ["name"] = "Denmark", + }, -- end of [5] + [6] = + { + ["id"] = 15, + ["name"] = "Israel", + }, -- end of [6] + [7] = + { + ["id"] = 9, + ["name"] = "Spain", + }, -- end of [7] + [8] = + { + ["id"] = 8, + ["name"] = "Canada", + }, -- end of [8] + [9] = + { + ["id"] = 12, + ["name"] = "Norway", + }, -- end of [9] + [10] = + { + ["id"] = 2, + ["name"] = "USA", + }, -- end of [10] + [11] = + { + ["id"] = 3, + ["name"] = "Turkey", + }, -- end of [11] + [12] = + { + ["id"] = 5, + ["name"] = "France", + }, -- end of [12] + [13] = + { + ["id"] = 10, + ["name"] = "The Netherlands", + }, -- end of [13] + [14] = + { + ["id"] = 20, + ["name"] = "Italy", + }, -- end of [14] + [15] = + { + ["id"] = 21, + ["name"] = "Australia", + }, -- end of [15] + [16] = + { + ["id"] = 40, + ["name"] = "Poland", + }, -- end of [16] + [17] = + { + ["id"] = 26, + ["name"] = "Czech Republic", + }, -- end of [17] + [18] = + { + ["id"] = 45, + ["name"] = "South Korea", + }, -- end of [18] + [19] = + { + ["id"] = 28, + ["name"] = "Croatia", + }, -- end of [19] + }, -- end of ["country"] + }, -- end of ["blue"] + ["red"] = + { + ["bullseye"] = + { + ["y"] = 371700, + ["x"] = 11557, + }, -- end of ["bullseye"] + ["nav_points"] = + { + }, -- end of ["nav_points"] + ["name"] = "red", + ["country"] = + { + [1] = + { + ["helicopter"] = + { + ["group"] = + { + [1] = + { + ["lateActivation"] = true, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAS", + ["uncontrolled"] = false, + ["route"] = + { + ["routeRelativeTOT"] = true, + ["points"] = + { + [1] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["number"] = 1, + ["key"] = "CAS", + ["id"] = "EngageTargets", + ["enabled"] = true, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Helicopters", + [2] = "Ground Units", + [3] = "Light armed ships", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 325834.45982144, + ["x"] = 7740.8543526806, + ["name"] = "DictKey_WptName_327", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [1] + [2] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 614.57680810556, + ["ETA_locked"] = false, + ["y"] = 325977.31696429, + ["x"] = 41883.711495538, + ["name"] = "DictKey_WptName_328", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [2] + [3] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 903.60812481849, + ["ETA_locked"] = false, + ["y"] = 311263.03125001, + ["x"] = 48312.282924109, + ["name"] = "DictKey_WptName_329", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [3] + [4] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 1667.3397263538, + ["ETA_locked"] = false, + ["y"] = 310977.31696429, + ["x"] = 5883.7114955378, + ["name"] = "DictKey_WptName_330", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [4] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 19, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 500, + ["alt_type"] = "BARO", + ["livery_id"] = "Russia Standard Army", + ["skill"] = "High", + ["ropeLength"] = 15, + ["speed"] = 55.555555555556, + ["type"] = "Ka-50", + ["unitId"] = 24, + ["psi"] = -0.0041840760018655, + ["y"] = 325834.45982144, + ["x"] = 7740.8543526806, + ["name"] = "DictKey_UnitName_326", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = "1450", + ["flare"] = 128, + ["chaff"] = 0, + ["gun"] = 100, + }, -- end of ["payload"] + ["heading"] = 0.0041840760018655, + ["callsign"] = 105, + ["onboard_num"] = "050", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 325834.45982144, + ["x"] = 7740.8543526806, + ["name"] = "DictKey_GroupName_325", + ["communication"] = true, + ["start_time"] = 0, + ["modulation"] = 0, + ["frequency"] = 124, + }, -- end of [1] + [2] = + { + ["lateActivation"] = true, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAS", + ["uncontrolled"] = false, + ["route"] = + { + ["routeRelativeTOT"] = true, + ["points"] = + { + [1] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["number"] = 1, + ["key"] = "CAS", + ["id"] = "EngageTargets", + ["enabled"] = true, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Helicopters", + [2] = "Ground Units", + [3] = "Light armed ships", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 323894.45982144, + ["x"] = -71460.574218749, + ["name"] = "DictKey_WptName_333", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [1] + [2] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 829.44018494895, + ["ETA_locked"] = false, + ["y"] = 321608.74553573, + ["x"] = -7603.4313616057, + ["name"] = "DictKey_WptName_334", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [2] + [3] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 581.44512129878, + ["ETA_locked"] = false, + ["y"] = 309465.88839287, + ["x"] = -8174.8599330343, + ["name"] = "DictKey_WptName_335", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [3] + [4] = + { + ["alt"] = 500, + ["action"] = "Turning Point", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 55.555555555556, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "Turning Point", + ["ETA"] = 2541.8313343196, + ["ETA_locked"] = false, + ["y"] = 310894.45982144, + ["x"] = -73317.717075891, + ["name"] = "DictKey_WptName_336", + ["formation_template"] = "", + ["speed_locked"] = true, + }, -- end of [4] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 20, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 500, + ["alt_type"] = "BARO", + ["livery_id"] = "Russia Standard Army", + ["skill"] = "High", + ["ropeLength"] = 15, + ["speed"] = 55.555555555556, + ["type"] = "Ka-50", + ["unitId"] = 25, + ["psi"] = 0.035778908402037, + ["y"] = 323894.45982144, + ["x"] = -71460.574218749, + ["name"] = "DictKey_UnitName_332", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = "1450", + ["flare"] = 128, + ["chaff"] = 0, + ["gun"] = 100, + }, -- end of ["payload"] + ["heading"] = -0.035778908402037, + ["callsign"] = 105, + ["onboard_num"] = "050", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 323894.45982144, + ["x"] = -71460.574218749, + ["name"] = "DictKey_GroupName_331", + ["communication"] = true, + ["start_time"] = 0, + ["modulation"] = 0, + ["frequency"] = 124, + }, -- end of [2] + }, -- end of ["group"] + }, -- end of ["helicopter"] + ["name"] = "Russia", + ["id"] = 0, + ["plane"] = + { + ["group"] = + { + [1] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 293785.125, + ["x"] = -7523.8505859375, + ["name"] = "DictKey_WptName_20", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 4, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = 2, + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 4, + ["psi"] = 0, + ["parking_id"] = "04", + ["x"] = -7523.8505859375, + ["name"] = "DictKey_UnitName_19", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 293785.125, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 293785.125, + ["x"] = -7523.8505859375, + ["name"] = "DictKey_GroupName_18", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [1] + [2] = + { + ["lateActivation"] = true, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["routeRelativeTOT"] = true, + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area Hot", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 250, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParkingHot", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 294155.125, + ["x"] = -7498.103515625, + ["name"] = "DictKey_WptName_26", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 6, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["hardpoint_racks"] = true, + ["alt_type"] = "BARO", + ["livery_id"] = "`snow` test paint scheme", + ["skill"] = "High", + ["parking"] = 91, + ["speed"] = 250, + ["type"] = "Su-30", + ["unitId"] = 6, + ["psi"] = 1.7036072745551, + ["parking_id"] = "29", + ["x"] = -7498.103515625, + ["name"] = "DictKey_UnitName_25", + ["payload"] = + { + ["pylons"] = + { + [1] = + { + ["CLSID"] = "{44EE8698-89F9-48EE-AF36-5FD31896A82F}", + }, -- end of [1] + [2] = + { + ["CLSID"] = "{FBC29BFE-3D24-4C64-B81D-941239D12249}", + }, -- end of [2] + [3] = + { + ["CLSID"] = "{88DAC840-9F75-4531-8689-B46E64E42E53}", + }, -- end of [3] + [4] = + { + ["CLSID"] = "{B79C379A-9E87-4E50-A1EE-7F7E29C2E87A}", + }, -- end of [4] + [5] = + { + ["CLSID"] = "{E8069896-8435-4B90-95C0-01A03AE6E400}", + }, -- end of [5] + [6] = + { + ["CLSID"] = "{E8069896-8435-4B90-95C0-01A03AE6E400}", + }, -- end of [6] + [7] = + { + ["CLSID"] = "{B79C379A-9E87-4E50-A1EE-7F7E29C2E87A}", + }, -- end of [7] + [8] = + { + ["CLSID"] = "{88DAC840-9F75-4531-8689-B46E64E42E53}", + }, -- end of [8] + [9] = + { + ["CLSID"] = "{FBC29BFE-3D24-4C64-B81D-941239D12249}", + }, -- end of [9] + [10] = + { + ["CLSID"] = "{44EE8698-89F9-48EE-AF36-5FD31896A82A}", + }, -- end of [10] + }, -- end of ["pylons"] + ["fuel"] = "9400", + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 294155.125, + ["heading"] = 0, + ["callsign"] = 104, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 294155.125, + ["x"] = -7498.103515625, + ["name"] = "DictKey_GroupName_24", + ["communication"] = true, + ["start_time"] = 0, + ["modulation"] = 0, + ["frequency"] = 251, + }, -- end of [2] + [3] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 294994.1875, + ["x"] = -6702.66796875, + ["name"] = "DictKey_WptName_369", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 21, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "75", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 26, + ["psi"] = 0, + ["parking_id"] = "44", + ["x"] = -6702.66796875, + ["name"] = "DictKey_UnitName_368", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 294994.1875, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 294994.1875, + ["x"] = -6702.66796875, + ["name"] = "DictKey_GroupName_367", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [3] + [4] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 295139.9375, + ["x"] = -6351.4077148438, + ["name"] = "DictKey_WptName_372", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 22, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "107", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 27, + ["psi"] = 0, + ["parking_id"] = "48", + ["x"] = -6351.4077148438, + ["name"] = "DictKey_UnitName_371", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 295139.9375, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 295139.9375, + ["x"] = -6351.4077148438, + ["name"] = "DictKey_GroupName_370", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [4] + [5] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 295287.09375, + ["x"] = -6172.1333007813, + ["name"] = "DictKey_WptName_375", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 23, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "62", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 28, + ["psi"] = 0, + ["parking_id"] = "51", + ["x"] = -6172.1333007813, + ["name"] = "DictKey_UnitName_374", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 295287.09375, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 295287.09375, + ["x"] = -6172.1333007813, + ["name"] = "DictKey_GroupName_373", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [5] + [6] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 295051.375, + ["x"] = -6629.2661132813, + ["name"] = "DictKey_WptName_378", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 24, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "76", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 29, + ["psi"] = 0, + ["parking_id"] = "43", + ["x"] = -6629.2661132813, + ["name"] = "DictKey_UnitName_377", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 295051.375, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 295051.375, + ["x"] = -6629.2661132813, + ["name"] = "DictKey_GroupName_376", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [6] + [7] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 293769.75, + ["x"] = -7511.0883789063, + ["name"] = "DictKey_WptName_381", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 25, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "6", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 30, + ["psi"] = 0, + ["parking_id"] = "03", + ["x"] = -7511.0883789063, + ["name"] = "DictKey_UnitName_380", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 293769.75, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 293769.75, + ["x"] = -7511.0883789063, + ["name"] = "DictKey_GroupName_379", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [7] + [8] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 295124.0625, + ["x"] = -6280.3999023438, + ["name"] = "DictKey_WptName_384", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 26, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "108", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 31, + ["psi"] = 0, + ["parking_id"] = "49", + ["x"] = -6280.3999023438, + ["name"] = "DictKey_UnitName_383", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 295124.0625, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 295124.0625, + ["x"] = -6280.3999023438, + ["name"] = "DictKey_GroupName_382", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [8] + [9] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 293890.4375, + ["x"] = -7713.9541015625, + ["name"] = "DictKey_WptName_387", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 27, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "124", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 32, + ["psi"] = 0, + ["parking_id"] = "09", + ["x"] = -7713.9541015625, + ["name"] = "DictKey_UnitName_386", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 293890.4375, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 293890.4375, + ["x"] = -7713.9541015625, + ["name"] = "DictKey_GroupName_385", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [9] + [10] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 295106.59375, + ["x"] = -6693.9848632813, + ["name"] = "DictKey_WptName_390", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 28, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "77", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 33, + ["psi"] = 0, + ["parking_id"] = "42", + ["x"] = -6693.9848632813, + ["name"] = "DictKey_UnitName_389", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 295106.59375, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 295106.59375, + ["x"] = -6693.9848632813, + ["name"] = "DictKey_GroupName_388", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [10] + [11] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 293815.90625, + ["x"] = -7549.3779296875, + ["name"] = "DictKey_WptName_393", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 29, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "12", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 34, + ["psi"] = 0, + ["parking_id"] = "06", + ["x"] = -7549.3779296875, + ["name"] = "DictKey_UnitName_392", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 293815.90625, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 293815.90625, + ["x"] = -7549.3779296875, + ["name"] = "DictKey_GroupName_391", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [11] + [12] = + { + ["modulation"] = 0, + ["tasks"] = + { + }, -- end of ["tasks"] + ["radioSet"] = false, + ["task"] = "CAP", + ["uncontrolled"] = false, + ["route"] = + { + ["points"] = + { + [1] = + { + ["alt"] = 88, + ["action"] = "From Parking Area", + ["alt_type"] = "BARO", + ["properties"] = + { + ["vnav"] = 1, + ["scale"] = 0, + ["angle"] = 0, + ["vangle"] = 0, + ["steer"] = 2, + }, -- end of ["properties"] + ["speed"] = 138.88888888889, + ["task"] = + { + ["id"] = "ComboTask", + ["params"] = + { + ["tasks"] = + { + [1] = + { + ["enabled"] = true, + ["key"] = "CAP", + ["id"] = "EngageTargets", + ["number"] = 1, + ["auto"] = true, + ["params"] = + { + ["targetTypes"] = + { + [1] = "Air", + }, -- end of ["targetTypes"] + ["priority"] = 0, + }, -- end of ["params"] + }, -- end of [1] + }, -- end of ["tasks"] + }, -- end of ["params"] + }, -- end of ["task"] + ["type"] = "TakeOffParking", + ["ETA"] = 0, + ["ETA_locked"] = true, + ["y"] = 293831.25, + ["x"] = -7562.1723632813, + ["name"] = "DictKey_WptName_396", + ["formation_template"] = "", + ["airdromeId"] = 15, + ["speed_locked"] = true, + }, -- end of [1] + }, -- end of ["points"] + }, -- end of ["route"] + ["groupId"] = 30, + ["hidden"] = false, + ["units"] = + { + [1] = + { + ["alt"] = 88, + ["alt_type"] = "BARO", + ["livery_id"] = "Air Force Standard", + ["skill"] = "Client", + ["parking"] = "14", + ["speed"] = 138.88888888889, + ["type"] = "Su-27", + ["unitId"] = 35, + ["psi"] = 0, + ["parking_id"] = "07", + ["x"] = -7562.1723632813, + ["name"] = "DictKey_UnitName_395", + ["payload"] = + { + ["pylons"] = + { + }, -- end of ["pylons"] + ["fuel"] = 5217, + ["flare"] = 96, + ["chaff"] = 96, + ["gun"] = 100, + }, -- end of ["payload"] + ["y"] = 293831.25, + ["heading"] = 0, + ["callsign"] = 103, + ["onboard_num"] = "013", + }, -- end of [1] + }, -- end of ["units"] + ["y"] = 293831.25, + ["x"] = -7562.1723632813, + ["name"] = "DictKey_GroupName_394", + ["communication"] = true, + ["start_time"] = 0, + ["frequency"] = 127.5, + }, -- end of [12] + }, -- end of ["group"] + }, -- end of ["plane"] + }, -- end of [1] + [2] = + { + ["id"] = 1, + ["name"] = "Ukraine", + }, -- end of [2] + [3] = + { + ["id"] = 18, + ["name"] = "Abkhazia", + }, -- end of [3] + [4] = + { + ["id"] = 19, + ["name"] = "South Ossetia", + }, -- end of [4] + [5] = + { + ["id"] = 37, + ["name"] = "Kazakhstan", + }, -- end of [5] + [6] = + { + ["id"] = 24, + ["name"] = "Belarus", + }, -- end of [6] + [7] = + { + ["id"] = 27, + ["name"] = "China", + }, -- end of [7] + [8] = + { + ["id"] = 43, + ["name"] = "Serbia", + }, -- end of [8] + [9] = + { + ["id"] = 47, + ["name"] = "Syria", + }, -- end of [9] + [10] = + { + ["id"] = 34, + ["name"] = "Iran", + }, -- end of [10] + [11] = + { + ["id"] = 38, + ["name"] = "North Korea", + }, -- end of [11] + }, -- end of ["country"] + }, -- end of ["red"] + }, -- end of ["coalition"] + ["sortie"] = "DictKey_sortie_4", + ["version"] = 12, + ["goals"] = + { + }, -- end of ["goals"] + ["currentKey"] = 12213, + ["start_time"] = 43200, + ["forcedOptions"] = + { + }, -- end of ["forcedOptions"] + ["failures"] = + { + ["OIL_RADIATOR_SENSOR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "OIL_RADIATOR_SENSOR", + ["mm"] = 0, + }, -- end of ["OIL_RADIATOR_SENSOR"] + ["TURNIND_POINTER_FAILS_NO_VACUUM"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_POINTER_FAILS_NO_VACUUM", + ["mm"] = 0, + }, -- end of ["TURNIND_POINTER_FAILS_NO_VACUUM"] + ["helmet"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "helmet", + ["mm"] = 0, + }, -- end of ["helmet"] + ["GUN_LEFT_IN_MOUNT_LOOSE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_IN_MOUNT_LOOSE", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_IN_MOUNT_LOOSE"] + ["es_damage_MainInverter"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_MainInverter", + ["mm"] = 0, + }, -- end of ["es_damage_MainInverter"] + ["rws"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "rws", + ["mm"] = 0, + }, -- end of ["rws"] + ["AN_ALR69V_FAILURE_SENSOR_TAIL_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALR69V_FAILURE_SENSOR_TAIL_RIGHT", + ["mm"] = 0, + }, -- end of ["AN_ALR69V_FAILURE_SENSOR_TAIL_RIGHT"] + ["MainReductor_ShaveInOil"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MainReductor_ShaveInOil", + ["mm"] = 0, + }, -- end of ["MainReductor_ShaveInOil"] + ["asc_y"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "asc_y", + ["mm"] = 0, + }, -- end of ["asc_y"] + ["MAIN_L_GEAR_D_LOCK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MAIN_L_GEAR_D_LOCK", + ["mm"] = 0, + }, -- end of ["MAIN_L_GEAR_D_LOCK"] + ["AAR_47_FAILURE_SENSOR_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AAR_47_FAILURE_SENSOR_LEFT", + ["mm"] = 0, + }, -- end of ["AAR_47_FAILURE_SENSOR_LEFT"] + ["tail_reductor_chip"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "tail_reductor_chip", + ["mm"] = 0, + }, -- end of ["tail_reductor_chip"] + ["TACAN_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACAN_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["TACAN_FAILURE_TOTAL"] + ["OIL_RADIATOR_MOTOR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "OIL_RADIATOR_MOTOR", + ["mm"] = 0, + }, -- end of ["OIL_RADIATOR_MOTOR"] + ["SUPERCHARGER_WIRE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SUPERCHARGER_WIRE", + ["mm"] = 0, + }, -- end of ["SUPERCHARGER_WIRE"] + ["CADC_FAILURE_TEMPERATURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_TEMPERATURE", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_TEMPERATURE"] + ["FUSELAGE_TANK_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FUSELAGE_TANK_LEAK", + ["mm"] = 0, + }, -- end of ["FUSELAGE_TANK_LEAK"] + ["AN_ALE_40V_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALE_40V_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["AN_ALE_40V_FAILURE_TOTAL"] + ["HORIZON_BAR_NOT_SETTLE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "HORIZON_BAR_NOT_SETTLE", + ["mm"] = 0, + }, -- end of ["HORIZON_BAR_NOT_SETTLE"] + ["AN_ALE_40V_FAILURE_CONTAINER_LEFT_WING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALE_40V_FAILURE_CONTAINER_LEFT_WING", + ["mm"] = 0, + }, -- end of ["AN_ALE_40V_FAILURE_CONTAINER_LEFT_WING"] + ["OIL_DILUTION_WIRE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "OIL_DILUTION_WIRE", + ["mm"] = 0, + }, -- end of ["OIL_DILUTION_WIRE"] + ["FLEX_S_BKP_LAMP_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FLEX_S_BKP_LAMP_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["FLEX_S_BKP_LAMP_DEFECTIVE"] + ["TAIL_GEAR_FAIL_GO_DOWN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TAIL_GEAR_FAIL_GO_DOWN", + ["mm"] = 0, + }, -- end of ["TAIL_GEAR_FAIL_GO_DOWN"] + ["GUN_FAIL_RIGHT_CENTER_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_FAIL_RIGHT_CENTER_GUN", + ["mm"] = 0, + }, -- end of ["GUN_FAIL_RIGHT_CENTER_GUN"] + ["LeftEngine_ShaveInOil"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "LeftEngine_ShaveInOil", + ["mm"] = 0, + }, -- end of ["LeftEngine_ShaveInOil"] + ["MAIN_R_GEAR_D_LOCK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MAIN_R_GEAR_D_LOCK", + ["mm"] = 0, + }, -- end of ["MAIN_R_GEAR_D_LOCK"] + ["R_GEAR_DLK_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "R_GEAR_DLK_FAULT", + ["mm"] = 0, + }, -- end of ["R_GEAR_DLK_FAULT"] + ["GMC_GYRO_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GMC_GYRO_FAILURE", + ["mm"] = 0, + }, -- end of ["GMC_GYRO_FAILURE"] + ["L_GEAR_DLK_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "L_GEAR_DLK_FAULT", + ["mm"] = 0, + }, -- end of ["L_GEAR_DLK_FAULT"] + ["K14_FIXED_LAMP_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "K14_FIXED_LAMP_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["K14_FIXED_LAMP_DEFECTIVE"] + ["GUN_FAIL_LEFT_CENTER_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_FAIL_LEFT_CENTER_GUN", + ["mm"] = 0, + }, -- end of ["GUN_FAIL_LEFT_CENTER_GUN"] + ["engine_droop_failure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "engine_droop_failure", + ["mm"] = 0, + }, -- end of ["engine_droop_failure"] + ["IGNITION_TERM_CONNECT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "IGNITION_TERM_CONNECT", + ["mm"] = 0, + }, -- end of ["IGNITION_TERM_CONNECT"] + ["CADC_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_TOTAL"] + ["COOLANT_POOR_CONNTECT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_POOR_CONNTECT", + ["mm"] = 0, + }, -- end of ["COOLANT_POOR_CONNTECT"] + ["TURNIND_POINTER_FAILS_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_POINTER_FAILS_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["TURNIND_POINTER_FAILS_DEFECTIVE"] + ["GUN_FAIL_RIGHT_OUT_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_FAIL_RIGHT_OUT_GUN", + ["mm"] = 0, + }, -- end of ["GUN_FAIL_RIGHT_OUT_GUN"] + ["BOMBS_DAMAGE_LINKAGE_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_DAMAGE_LINKAGE_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_DAMAGE_LINKAGE_LEFT"] + ["FUSELAGE_TANK_PUMP_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FUSELAGE_TANK_PUMP_FAULT", + ["mm"] = 0, + }, -- end of ["FUSELAGE_TANK_PUMP_FAULT"] + ["hydro_main"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hydro_main", + ["mm"] = 0, + }, -- end of ["hydro_main"] + ["CICU_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CICU_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["CICU_FAILURE_TOTAL"] + ["GUN_LEFT_OUT_MOUNT_LOOSE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_OUT_MOUNT_LOOSE", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_OUT_MOUNT_LOOSE"] + ["TAIL_GEAR_U_LOCK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TAIL_GEAR_U_LOCK", + ["mm"] = 0, + }, -- end of ["TAIL_GEAR_U_LOCK"] + ["RADAR_ALT_TOTAL_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RADAR_ALT_TOTAL_FAILURE", + ["mm"] = 0, + }, -- end of ["RADAR_ALT_TOTAL_FAILURE"] + ["GUN_RIGHT_CENTER_MOUNT_LOOSE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_CENTER_MOUNT_LOOSE", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_CENTER_MOUNT_LOOSE"] + ["TAIL_GEAR_FAIL_GO_UP"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TAIL_GEAR_FAIL_GO_UP", + ["mm"] = 0, + }, -- end of ["TAIL_GEAR_FAIL_GO_UP"] + ["asc_r"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "asc_r", + ["mm"] = 0, + }, -- end of ["asc_r"] + ["BOMBS_SOLENOID_FAULT_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_SOLENOID_FAULT_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_SOLENOID_FAULT_LEFT"] + ["sas_yaw_left"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "sas_yaw_left", + ["mm"] = 0, + }, -- end of ["sas_yaw_left"] + ["BOMBS_ARMING_NO_VOLATAGE_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_NO_VOLATAGE_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_NO_VOLATAGE_LEFT"] + ["PITOT_HEAT_ELEMENT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PITOT_HEAT_ELEMENT", + ["mm"] = 0, + }, -- end of ["PITOT_HEAT_ELEMENT"] + ["ILS_FAILURE_ANT_LOCALIZER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ILS_FAILURE_ANT_LOCALIZER", + ["mm"] = 0, + }, -- end of ["ILS_FAILURE_ANT_LOCALIZER"] + ["AN_ALE_40V_FAILURE_CONTAINER_LEFT_GEAR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALE_40V_FAILURE_CONTAINER_LEFT_GEAR", + ["mm"] = 0, + }, -- end of ["AN_ALE_40V_FAILURE_CONTAINER_LEFT_GEAR"] + ["CARBAIR_SHORT_CIRCUIT_BLB"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CARBAIR_SHORT_CIRCUIT_BLB", + ["mm"] = 0, + }, -- end of ["CARBAIR_SHORT_CIRCUIT_BLB"] + ["LEFT_TANK_PUMP_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "LEFT_TANK_PUMP_FAULT", + ["mm"] = 0, + }, -- end of ["LEFT_TANK_PUMP_FAULT"] + ["Surge_RightEngine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "Surge_RightEngine", + ["mm"] = 0, + }, -- end of ["Surge_RightEngine"] + ["RightEngine_Fire"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["mm"] = 0, + }, -- end of ["RightEngine_Fire"] + ["GUN_FAIL_LEFT_IN_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_FAIL_LEFT_IN_GUN", + ["mm"] = 0, + }, -- end of ["GUN_FAIL_LEFT_IN_GUN"] + ["CADC_FAILURE_TAS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_TAS", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_TAS"] + ["STARTER_SOL_SHORT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "STARTER_SOL_SHORT", + ["mm"] = 0, + }, -- end of ["STARTER_SOL_SHORT"] + ["asc_p"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "asc_p", + ["mm"] = 0, + }, -- end of ["asc_p"] + ["COOLANT_SHORT_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_SHORT_CIRCUIT", + ["mm"] = 0, + }, -- end of ["COOLANT_SHORT_CIRCUIT"] + ["GUN_LEFT_IN_AMMUN_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_IN_AMMUN_FAULT", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_IN_AMMUN_FAULT"] + ["PUMP_RELIEF_VALVE_SCREEN_CLOGGED"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PUMP_RELIEF_VALVE_SCREEN_CLOGGED", + ["mm"] = 0, + }, -- end of ["PUMP_RELIEF_VALVE_SCREEN_CLOGGED"] + ["abris_hardware"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "abris_hardware", + ["mm"] = 0, + }, -- end of ["abris_hardware"] + ["EEC_Failure_LeftEngine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "EEC_Failure_LeftEngine", + ["mm"] = 0, + }, -- end of ["EEC_Failure_LeftEngine"] + ["COMPASS_POINTER_PULLS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COMPASS_POINTER_PULLS", + ["mm"] = 0, + }, -- end of ["COMPASS_POINTER_PULLS"] + ["GUN_RIGHT_OUT_OPEN_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_OUT_OPEN_CIRCUIT", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_OUT_OPEN_CIRCUIT"] + ["VHF_SHORTED_CTL_BOX"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_SHORTED_CTL_BOX", + ["mm"] = 0, + }, -- end of ["VHF_SHORTED_CTL_BOX"] + ["CLOCK_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CLOCK_FAILURE", + ["mm"] = 0, + }, -- end of ["CLOCK_FAILURE"] + ["TURNIND_INCORRECT_SENS_VAC_HIGH"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_INCORRECT_SENS_VAC_HIGH", + ["mm"] = 0, + }, -- end of ["TURNIND_INCORRECT_SENS_VAC_HIGH"] + ["OIL_RADIATOR_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "OIL_RADIATOR_WIRING", + ["mm"] = 0, + }, -- end of ["OIL_RADIATOR_WIRING"] + ["IGNITION_NO_OUTPUT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "IGNITION_NO_OUTPUT", + ["mm"] = 0, + }, -- end of ["IGNITION_NO_OUTPUT"] + ["AAR_47_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AAR_47_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["AAR_47_FAILURE_TOTAL"] + ["PILOT_KILLED_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PILOT_KILLED_FAILURE", + ["mm"] = 0, + }, -- end of ["PILOT_KILLED_FAILURE"] + ["GUN_LEFT_CENTER_MOUNT_LOOSE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_CENTER_MOUNT_LOOSE", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_CENTER_MOUNT_LOOSE"] + ["GUN_LEFT_OUT_AMMUN_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_OUT_AMMUN_FAULT", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_OUT_AMMUN_FAULT"] + ["COMPASS_ERRATIC_OPERATION"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COMPASS_ERRATIC_OPERATION", + ["mm"] = 0, + }, -- end of ["COMPASS_ERRATIC_OPERATION"] + ["asc_a"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "asc_a", + ["mm"] = 0, + }, -- end of ["asc_a"] + ["AIRSPEED_INDICATOR_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AIRSPEED_INDICATOR_FAILURE", + ["mm"] = 0, + }, -- end of ["AIRSPEED_INDICATOR_FAILURE"] + ["GUN_LEFT_CENTER_BARREL_WORN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_CENTER_BARREL_WORN", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_CENTER_BARREL_WORN"] + ["abris_software"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "abris_software", + ["mm"] = 0, + }, -- end of ["abris_software"] + ["GUN_FAIL_LEFT_OUT_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_FAIL_LEFT_OUT_GUN", + ["mm"] = 0, + }, -- end of ["GUN_FAIL_LEFT_OUT_GUN"] + ["SAR_1_101"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SAR_1_101", + ["mm"] = 0, + }, -- end of ["SAR_1_101"] + ["ROCKETS_INTERVALOMETER_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ROCKETS_INTERVALOMETER_WIRING", + ["mm"] = 0, + }, -- end of ["ROCKETS_INTERVALOMETER_WIRING"] + ["MainReductor_LowOilPressure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MainReductor_LowOilPressure", + ["mm"] = 0, + }, -- end of ["MainReductor_LowOilPressure"] + ["GUN_RIGHT_IN_AMMUN_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_IN_AMMUN_FAULT", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_IN_AMMUN_FAULT"] + ["D2_LEFT_CYLINDER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "D2_LEFT_CYLINDER", + ["mm"] = 0, + }, -- end of ["D2_LEFT_CYLINDER"] + ["Surge_LeftEngine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "Surge_LeftEngine", + ["mm"] = 0, + }, -- end of ["Surge_LeftEngine"] + ["BOMBS_RUST_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_RUST_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_RUST_LEFT"] + ["GUN_RIGHT_CENTER_BARREL_WORN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_CENTER_BARREL_WORN", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_CENTER_BARREL_WORN"] + ["asc"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "asc", + ["mm"] = 0, + }, -- end of ["asc"] + ["COMPASS_NO_TORQUE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COMPASS_NO_TORQUE", + ["mm"] = 0, + }, -- end of ["COMPASS_NO_TORQUE"] + ["COOLANT_BREAK_BULB"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_BREAK_BULB", + ["mm"] = 0, + }, -- end of ["COOLANT_BREAK_BULB"] + ["PROP_GOVERNOR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PROP_GOVERNOR", + ["mm"] = 0, + }, -- end of ["PROP_GOVERNOR"] + ["MANIFOLD_SHIFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MANIFOLD_SHIFT", + ["mm"] = 0, + }, -- end of ["MANIFOLD_SHIFT"] + ["RIGHT_GUNNER_KILLED_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RIGHT_GUNNER_KILLED_FAILURE", + ["mm"] = 0, + }, -- end of ["RIGHT_GUNNER_KILLED_FAILURE"] + ["UNLOAD_VALVE_NOT_UNLOAD"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "UNLOAD_VALVE_NOT_UNLOAD", + ["mm"] = 0, + }, -- end of ["UNLOAD_VALVE_NOT_UNLOAD"] + ["STARTER_BURNOUT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "STARTER_BURNOUT", + ["mm"] = 0, + }, -- end of ["STARTER_BURNOUT"] + ["UNLOAD_VALVE_NOT_LOAD"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "UNLOAD_VALVE_NOT_LOAD", + ["mm"] = 0, + }, -- end of ["UNLOAD_VALVE_NOT_LOAD"] + ["TURNIND_INCORRECT_SENS_VAC_LOW"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_INCORRECT_SENS_VAC_LOW", + ["mm"] = 0, + }, -- end of ["TURNIND_INCORRECT_SENS_VAC_LOW"] + ["Failure_LeftEngine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "Failure_LeftEngine", + ["mm"] = 0, + }, -- end of ["Failure_LeftEngine"] + ["GUN_RIGHT_IN_BARREL_WORN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_IN_BARREL_WORN", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_IN_BARREL_WORN"] + ["K14_MOV_LAMP_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "K14_MOV_LAMP_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["K14_MOV_LAMP_DEFECTIVE"] + ["ILS_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ILS_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["ILS_FAILURE_TOTAL"] + ["GUN_RIGHT_OUT_BARREL_WORN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_OUT_BARREL_WORN", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_OUT_BARREL_WORN"] + ["fuel_sys_transfer_pumps"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "fuel_sys_transfer_pumps", + ["mm"] = 0, + }, -- end of ["fuel_sys_transfer_pumps"] + ["PITOT_HEAT_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PITOT_HEAT_WIRING", + ["mm"] = 0, + }, -- end of ["PITOT_HEAT_WIRING"] + ["TURNIND_POINTER_NOT_SET_ZERO"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_POINTER_NOT_SET_ZERO", + ["mm"] = 0, + }, -- end of ["TURNIND_POINTER_NOT_SET_ZERO"] + ["MD1_GYRO_TOTAL_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MD1_GYRO_TOTAL_FAILURE", + ["mm"] = 0, + }, -- end of ["MD1_GYRO_TOTAL_FAILURE"] + ["VHF_FM_RADIO_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_FM_RADIO_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["VHF_FM_RADIO_FAILURE_TOTAL"] + ["RIGHT_MFCD_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RIGHT_MFCD_FAILURE", + ["mm"] = 0, + }, -- end of ["RIGHT_MFCD_FAILURE"] + ["F2_BOTTOM_CYLINDER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "F2_BOTTOM_CYLINDER", + ["mm"] = 0, + }, -- end of ["F2_BOTTOM_CYLINDER"] + ["LEFT_WING_TANK_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "LEFT_WING_TANK_LEAK", + ["mm"] = 0, + }, -- end of ["LEFT_WING_TANK_LEAK"] + ["CARBAIR_BREAK_LEADS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CARBAIR_BREAK_LEADS", + ["mm"] = 0, + }, -- end of ["CARBAIR_BREAK_LEADS"] + ["GUN_LEFT_IN_OPEN_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_IN_OPEN_CIRCUIT", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_IN_OPEN_CIRCUIT"] + ["EGI_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "EGI_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["EGI_FAILURE_TOTAL"] + ["UHF_RADIO_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "UHF_RADIO_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["UHF_RADIO_FAILURE_TOTAL"] + ["GUN_RIGHT_CENTER_AMMUN_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_CENTER_AMMUN_FAULT", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_CENTER_AMMUN_FAULT"] + ["LEFT_GUNNER_KILLED_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "LEFT_GUNNER_KILLED_FAILURE", + ["mm"] = 0, + }, -- end of ["LEFT_GUNNER_KILLED_FAILURE"] + ["VHF_VT207_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_VT207_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["VHF_VT207_DEFECTIVE"] + ["RightEngine_LowOilPressure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RightEngine_LowOilPressure", + ["mm"] = 0, + }, -- end of ["RightEngine_LowOilPressure"] + ["radar"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "radar", + ["mm"] = 0, + }, -- end of ["radar"] + ["RIGHT_TANK_PUMP_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RIGHT_TANK_PUMP_FAULT", + ["mm"] = 0, + }, -- end of ["RIGHT_TANK_PUMP_FAULT"] + ["COOLANT_UNPRES"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_UNPRES", + ["mm"] = 0, + }, -- end of ["COOLANT_UNPRES"] + ["ARN_82_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ARN_82_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["ARN_82_FAILURE_TOTAL"] + ["FLEX_S_NO_POWER_SUPPLY"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FLEX_S_NO_POWER_SUPPLY", + ["mm"] = 0, + }, -- end of ["FLEX_S_NO_POWER_SUPPLY"] + ["eos"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "eos", + ["mm"] = 0, + }, -- end of ["eos"] + ["HYDRO_LOW_AIR_PRESSURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "HYDRO_LOW_AIR_PRESSURE", + ["mm"] = 0, + }, -- end of ["HYDRO_LOW_AIR_PRESSURE"] + ["K14_MOTOR_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "K14_MOTOR_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["K14_MOTOR_DEFECTIVE"] + ["GENERATOR_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GENERATOR_FAULT", + ["mm"] = 0, + }, -- end of ["GENERATOR_FAULT"] + ["FUEL_PUMP_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FUEL_PUMP_FAILURE", + ["mm"] = 0, + }, -- end of ["FUEL_PUMP_FAILURE"] + ["RADAR_ALTIMETR_LEFT_ANT_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RADAR_ALTIMETR_LEFT_ANT_FAILURE", + ["mm"] = 0, + }, -- end of ["RADAR_ALTIMETR_LEFT_ANT_FAILURE"] + ["hydro"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hydro", + ["mm"] = 0, + }, -- end of ["hydro"] + ["BAT_SOLENOID_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BAT_SOLENOID_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["BAT_SOLENOID_DEFECTIVE"] + ["LeftEngine_Fire"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["mm"] = 0, + }, -- end of ["LeftEngine_Fire"] + ["SUPERCHARGER_LIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SUPERCHARGER_LIGHT", + ["mm"] = 0, + }, -- end of ["SUPERCHARGER_LIGHT"] + ["L_GEAR_UPL_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "L_GEAR_UPL_FAULT", + ["mm"] = 0, + }, -- end of ["L_GEAR_UPL_FAULT"] + ["fs_damage_right_cell_boost_pump"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "fs_damage_right_cell_boost_pump", + ["mm"] = 0, + }, -- end of ["fs_damage_right_cell_boost_pump"] + ["TACH_RESISTANCE_ADJ"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACH_RESISTANCE_ADJ", + ["mm"] = 0, + }, -- end of ["TACH_RESISTANCE_ADJ"] + ["MAGNETO_1"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MAGNETO_1", + ["mm"] = 0, + }, -- end of ["MAGNETO_1"] + ["BOMBS_NO_VOLATAGE_AT_RACK_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_NO_VOLATAGE_AT_RACK_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_NO_VOLATAGE_AT_RACK_RIGHT"] + ["GUN_RIGHT_OUT_MOUNT_LOOSE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_OUT_MOUNT_LOOSE", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_OUT_MOUNT_LOOSE"] + ["TailReductor_ShaveInOil"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TailReductor_ShaveInOil", + ["mm"] = 0, + }, -- end of ["TailReductor_ShaveInOil"] + ["R_GEAR_UPL_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "R_GEAR_UPL_FAULT", + ["mm"] = 0, + }, -- end of ["R_GEAR_UPL_FAULT"] + ["BOMBS_TRAIN_DEFECTIVE_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_TRAIN_DEFECTIVE_WIRING", + ["mm"] = 0, + }, -- end of ["BOMBS_TRAIN_DEFECTIVE_WIRING"] + ["autopilot"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "autopilot", + ["mm"] = 0, + }, -- end of ["autopilot"] + ["BOMBS_TRAIN_DEFECTIVE_SWITCH"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_TRAIN_DEFECTIVE_SWITCH", + ["mm"] = 0, + }, -- end of ["BOMBS_TRAIN_DEFECTIVE_SWITCH"] + ["CARBAIR_SHORT_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CARBAIR_SHORT_CIRCUIT", + ["mm"] = 0, + }, -- end of ["CARBAIR_SHORT_CIRCUIT"] + ["STARTER_RELAY"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "STARTER_RELAY", + ["mm"] = 0, + }, -- end of ["STARTER_RELAY"] + ["AN_ALE_40V_FAILURE_CONTAINER_RIGHT_WING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALE_40V_FAILURE_CONTAINER_RIGHT_WING", + ["mm"] = 0, + }, -- end of ["AN_ALE_40V_FAILURE_CONTAINER_RIGHT_WING"] + ["TACH_POOR_CONNECTION"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACH_POOR_CONNECTION", + ["mm"] = 0, + }, -- end of ["TACH_POOR_CONNECTION"] + ["GUN_RIGHT_IN_MOUNT_LOOSE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_IN_MOUNT_LOOSE", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_IN_MOUNT_LOOSE"] + ["LEFT_MFCD_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "LEFT_MFCD_FAILURE", + ["mm"] = 0, + }, -- end of ["LEFT_MFCD_FAILURE"] + ["sas_yaw_right"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "sas_yaw_right", + ["mm"] = 0, + }, -- end of ["sas_yaw_right"] + ["DOORS_TVC_BROKEN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "DOORS_TVC_BROKEN", + ["mm"] = 0, + }, -- end of ["DOORS_TVC_BROKEN"] + ["SADL_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SADL_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["SADL_FAILURE_TOTAL"] + ["fs_damage_left_cell_boost_pump"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "fs_damage_left_cell_boost_pump", + ["mm"] = 0, + }, -- end of ["fs_damage_left_cell_boost_pump"] + ["BOOST_REG"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOOST_REG", + ["mm"] = 0, + }, -- end of ["BOOST_REG"] + ["r_conv"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "r_conv", + ["mm"] = 0, + }, -- end of ["r_conv"] + ["ENGINE_JAM"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ENGINE_JAM", + ["mm"] = 0, + }, -- end of ["ENGINE_JAM"] + ["MAGNETO_2"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MAGNETO_2", + ["mm"] = 0, + }, -- end of ["MAGNETO_2"] + ["SAR_1_95"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SAR_1_95", + ["mm"] = 0, + }, -- end of ["SAR_1_95"] + ["BOMBS_SOLENOID_FAULT_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_SOLENOID_FAULT_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_SOLENOID_FAULT_RIGHT"] + ["CDU_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CDU_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["CDU_FAILURE_TOTAL"] + ["AN_ALR69V_FAILURE_SENSOR_NOSE_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALR69V_FAILURE_SENSOR_NOSE_RIGHT", + ["mm"] = 0, + }, -- end of ["AN_ALR69V_FAILURE_SENSOR_NOSE_RIGHT"] + ["TAIL_GEAR_C_CABLE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TAIL_GEAR_C_CABLE", + ["mm"] = 0, + }, -- end of ["TAIL_GEAR_C_CABLE"] + ["STARTER_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "STARTER_WIRING", + ["mm"] = 0, + }, -- end of ["STARTER_WIRING"] + ["engine_driveshaft_failure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "engine_driveshaft_failure", + ["mm"] = 0, + }, -- end of ["engine_driveshaft_failure"] + ["PUMP_RELIEF_VALVE_LEAKS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PUMP_RELIEF_VALVE_LEAKS", + ["mm"] = 0, + }, -- end of ["PUMP_RELIEF_VALVE_LEAKS"] + ["HUD_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "HUD_FAILURE", + ["mm"] = 0, + }, -- end of ["HUD_FAILURE"] + ["mfd"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "mfd", + ["mm"] = 0, + }, -- end of ["mfd"] + ["CARBAIR_GND_LEAD"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CARBAIR_GND_LEAD", + ["mm"] = 0, + }, -- end of ["CARBAIR_GND_LEAD"] + ["GMC_MAGN_COMP_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GMC_MAGN_COMP_FAILURE", + ["mm"] = 0, + }, -- end of ["GMC_MAGN_COMP_FAILURE"] + ["es_damage_GeneratorLeft"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_GeneratorLeft", + ["mm"] = 0, + }, -- end of ["es_damage_GeneratorLeft"] + ["ILS_FAILURE_ANT_GLIDESLOPE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ILS_FAILURE_ANT_GLIDESLOPE", + ["mm"] = 0, + }, -- end of ["ILS_FAILURE_ANT_GLIDESLOPE"] + ["engine_chip"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "engine_chip", + ["mm"] = 0, + }, -- end of ["engine_chip"] + ["ARN_83_TOTAL_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ARN_83_TOTAL_FAILURE", + ["mm"] = 0, + }, -- end of ["ARN_83_TOTAL_FAILURE"] + ["CADC_FAILURE_MACH"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_MACH", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_MACH"] + ["ROCKETS_DEFECTIVE_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ROCKETS_DEFECTIVE_WIRING", + ["mm"] = 0, + }, -- end of ["ROCKETS_DEFECTIVE_WIRING"] + ["COPILOT_GYRO_TOTAL_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COPILOT_GYRO_TOTAL_FAILURE", + ["mm"] = 0, + }, -- end of ["COPILOT_GYRO_TOTAL_FAILURE"] + ["RightEngine_ShaveInOil"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RightEngine_ShaveInOil", + ["mm"] = 0, + }, -- end of ["RightEngine_ShaveInOil"] + ["EEC_Failure_RightEngine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "EEC_Failure_RightEngine", + ["mm"] = 0, + }, -- end of ["EEC_Failure_RightEngine"] + ["laser_failure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "laser_failure", + ["mm"] = 0, + }, -- end of ["laser_failure"] + ["ARN_83_ADF_DAMAGE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ARN_83_ADF_DAMAGE", + ["mm"] = 0, + }, -- end of ["ARN_83_ADF_DAMAGE"] + ["BOMBS_NO_VOLATAGE_BOTH"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_NO_VOLATAGE_BOTH", + ["mm"] = 0, + }, -- end of ["BOMBS_NO_VOLATAGE_BOTH"] + ["es_damage_SpareInverter"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_SpareInverter", + ["mm"] = 0, + }, -- end of ["es_damage_SpareInverter"] + ["AAR_47_FAILURE_SENSOR_BOTTOM"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AAR_47_FAILURE_SENSOR_BOTTOM", + ["mm"] = 0, + }, -- end of ["AAR_47_FAILURE_SENSOR_BOTTOM"] + ["CARBAIR_SHORT_CIRCUIT_LEADS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CARBAIR_SHORT_CIRCUIT_LEADS", + ["mm"] = 0, + }, -- end of ["CARBAIR_SHORT_CIRCUIT_LEADS"] + ["sas_pitch_left"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "sas_pitch_left", + ["mm"] = 0, + }, -- end of ["sas_pitch_left"] + ["BATTERY_OVERHEAT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BATTERY_OVERHEAT", + ["mm"] = 0, + }, -- end of ["BATTERY_OVERHEAT"] + ["NOSE_AIRSPEED_INDICATOR_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "NOSE_AIRSPEED_INDICATOR_FAILURE", + ["mm"] = 0, + }, -- end of ["NOSE_AIRSPEED_INDICATOR_FAILURE"] + ["CADC_FAILURE_DYNAMIC"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_DYNAMIC", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_DYNAMIC"] + ["INSUF_FUEL_PRES"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "INSUF_FUEL_PRES", + ["mm"] = 0, + }, -- end of ["INSUF_FUEL_PRES"] + ["GUN_LEFT_CENTER_OPEN_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_CENTER_OPEN_CIRCUIT", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_CENTER_OPEN_CIRCUIT"] + ["AN_ALR69V_FAILURE_SENSOR_TAIL_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALR69V_FAILURE_SENSOR_TAIL_LEFT", + ["mm"] = 0, + }, -- end of ["AN_ALR69V_FAILURE_SENSOR_TAIL_LEFT"] + ["CADC_FAILURE_IAS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_IAS", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_IAS"] + ["GUN_LEFT_CENTER_AMMUN_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_CENTER_AMMUN_FAULT", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_CENTER_AMMUN_FAULT"] + ["GMC_TOTAL_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GMC_TOTAL_FAILURE", + ["mm"] = 0, + }, -- end of ["GMC_TOTAL_FAILURE"] + ["DEFECTIVE_MECHANISM"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "DEFECTIVE_MECHANISM", + ["mm"] = 0, + }, -- end of ["DEFECTIVE_MECHANISM"] + ["INT_HYDRO_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "INT_HYDRO_LEAK", + ["mm"] = 0, + }, -- end of ["INT_HYDRO_LEAK"] + ["TACH_BREAK_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACH_BREAK_CIRCUIT", + ["mm"] = 0, + }, -- end of ["TACH_BREAK_CIRCUIT"] + ["hydro_main_irreversible_valve"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hydro_main_irreversible_valve", + ["mm"] = 0, + }, -- end of ["hydro_main_irreversible_valve"] + ["COOLANT_DEFECTIVE_IND"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_DEFECTIVE_IND", + ["mm"] = 0, + }, -- end of ["COOLANT_DEFECTIVE_IND"] + ["hud"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hud", + ["mm"] = 0, + }, -- end of ["hud"] + ["STARTER_SOLENOID"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "STARTER_SOLENOID", + ["mm"] = 0, + }, -- end of ["STARTER_SOLENOID"] + ["hydro_left"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hydro_left", + ["mm"] = 0, + }, -- end of ["hydro_left"] + ["SAR_1_2_95"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SAR_1_2_95", + ["mm"] = 0, + }, -- end of ["SAR_1_2_95"] + ["fuel_sys_left_transfer_pump"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "fuel_sys_left_transfer_pump", + ["mm"] = 0, + }, -- end of ["fuel_sys_left_transfer_pump"] + ["LeftEngine_LowOilPressure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "LeftEngine_LowOilPressure", + ["mm"] = 0, + }, -- end of ["LeftEngine_LowOilPressure"] + ["BOMBS_ARMING_BROKEN_SOLENOID_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_BROKEN_SOLENOID_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_BROKEN_SOLENOID_LEFT"] + ["FAULTY_ROCKET_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FAULTY_ROCKET_LEFT", + ["mm"] = 0, + }, -- end of ["FAULTY_ROCKET_LEFT"] + ["l_conv"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "l_conv", + ["mm"] = 0, + }, -- end of ["l_conv"] + ["hydro_right"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hydro_right", + ["mm"] = 0, + }, -- end of ["hydro_right"] + ["es_damage_StarterGenerator"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_StarterGenerator", + ["mm"] = 0, + }, -- end of ["es_damage_StarterGenerator"] + ["es_damage_Battery"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_Battery", + ["mm"] = 0, + }, -- end of ["es_damage_Battery"] + ["ILS_FAILURE_ANT_MARKER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ILS_FAILURE_ANT_MARKER", + ["mm"] = 0, + }, -- end of ["ILS_FAILURE_ANT_MARKER"] + ["TGP_FAILURE_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TGP_FAILURE_LEFT", + ["mm"] = 0, + }, -- end of ["TGP_FAILURE_LEFT"] + ["VHF_CRYSTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_CRYSTAL", + ["mm"] = 0, + }, -- end of ["VHF_CRYSTAL"] + ["VHF_VT_BURNED_OUT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_VT_BURNED_OUT", + ["mm"] = 0, + }, -- end of ["VHF_VT_BURNED_OUT"] + ["sas_pitch_right"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "sas_pitch_right", + ["mm"] = 0, + }, -- end of ["sas_pitch_right"] + ["BOMBS_NO_VOLATAGE_AT_RACK_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_NO_VOLATAGE_AT_RACK_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_NO_VOLATAGE_AT_RACK_LEFT"] + ["TGP_FAILURE_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TGP_FAILURE_RIGHT", + ["mm"] = 0, + }, -- end of ["TGP_FAILURE_RIGHT"] + ["TACAN_FAILURE_RECEIVER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACAN_FAILURE_RECEIVER", + ["mm"] = 0, + }, -- end of ["TACAN_FAILURE_RECEIVER"] + ["VHF_AM_RADIO_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_AM_RADIO_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["VHF_AM_RADIO_FAILURE_TOTAL"] + ["main_reductor_chip"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "main_reductor_chip", + ["mm"] = 0, + }, -- end of ["main_reductor_chip"] + ["VHF_SQUELCH_RELAY"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "VHF_SQUELCH_RELAY", + ["mm"] = 0, + }, -- end of ["VHF_SQUELCH_RELAY"] + ["COOLANT_RADIATOR_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_RADIATOR_WIRING", + ["mm"] = 0, + }, -- end of ["COOLANT_RADIATOR_WIRING"] + ["RADAR_ALTIMETR_RIGHT_ANT_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RADAR_ALTIMETR_RIGHT_ANT_FAILURE", + ["mm"] = 0, + }, -- end of ["RADAR_ALTIMETR_RIGHT_ANT_FAILURE"] + ["F2_TOP_CYLINDER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "F2_TOP_CYLINDER", + ["mm"] = 0, + }, -- end of ["F2_TOP_CYLINDER"] + ["FLEX_S_MAIN_LAMP_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FLEX_S_MAIN_LAMP_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["FLEX_S_MAIN_LAMP_DEFECTIVE"] + ["MANIFOLD_LINE_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "MANIFOLD_LINE_LEAK", + ["mm"] = 0, + }, -- end of ["MANIFOLD_LINE_LEAK"] + ["engine_surge_failure"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "engine_surge_failure", + ["mm"] = 0, + }, -- end of ["engine_surge_failure"] + ["CADC_FAILURE_PRESSURE_ALT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_PRESSURE_ALT", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_PRESSURE_ALT"] + ["K14_NO_POWER_SUPPLY"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "K14_NO_POWER_SUPPLY", + ["mm"] = 0, + }, -- end of ["K14_NO_POWER_SUPPLY"] + ["PUMP_FAILS"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PUMP_FAILS", + ["mm"] = 0, + }, -- end of ["PUMP_FAILS"] + ["RIGHT_WING_TANK_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "RIGHT_WING_TANK_LEAK", + ["mm"] = 0, + }, -- end of ["RIGHT_WING_TANK_LEAK"] + ["BOMBS_DAMAGE_LINKAGE_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_DAMAGE_LINKAGE_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_DAMAGE_LINKAGE_RIGHT"] + ["fs_damage_engine_pump"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "fs_damage_engine_pump", + ["mm"] = 0, + }, -- end of ["fs_damage_engine_pump"] + ["ROOF_AIRSPEED_INDICATOR_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ROOF_AIRSPEED_INDICATOR_FAILURE", + ["mm"] = 0, + }, -- end of ["ROOF_AIRSPEED_INDICATOR_FAILURE"] + ["CADC_FAILURE_STATIC"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_STATIC", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_STATIC"] + ["CADC_FAILURE_BARO_ALT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CADC_FAILURE_BARO_ALT", + ["mm"] = 0, + }, -- end of ["CADC_FAILURE_BARO_ALT"] + ["GUN_RIGHT_CENTER_OPEN_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_CENTER_OPEN_CIRCUIT", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_CENTER_OPEN_CIRCUIT"] + ["IFFCC_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "IFFCC_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["IFFCC_FAILURE_TOTAL"] + ["GUN_FAIL_RIGHT_IN_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_FAIL_RIGHT_IN_GUN", + ["mm"] = 0, + }, -- end of ["GUN_FAIL_RIGHT_IN_GUN"] + ["BOMBS_ARMING_BROKEN_WIRING_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_BROKEN_WIRING_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_BROKEN_WIRING_LEFT"] + ["Failure_RightEngine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "Failure_RightEngine", + ["mm"] = 0, + }, -- end of ["Failure_RightEngine"] + ["ecf"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["mm"] = 0, + }, -- end of ["ecf"] + ["GUN_LEFT_OUT_BARREL_WORN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_OUT_BARREL_WORN", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_OUT_BARREL_WORN"] + ["EXT_HYDRO_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "EXT_HYDRO_LEAK", + ["mm"] = 0, + }, -- end of ["EXT_HYDRO_LEAK"] + ["BOMBS_ARMING_BROKEN_SOLENOID_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_BROKEN_SOLENOID_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_BROKEN_SOLENOID_RIGHT"] + ["DEFECTIVE_INSTRUMENT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "DEFECTIVE_INSTRUMENT", + ["mm"] = 0, + }, -- end of ["DEFECTIVE_INSTRUMENT"] + ["AN_ALR69V_FAILURE_SENSOR_NOSE_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALR69V_FAILURE_SENSOR_NOSE_LEFT", + ["mm"] = 0, + }, -- end of ["AN_ALR69V_FAILURE_SENSOR_NOSE_LEFT"] + ["mlws"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "mlws", + ["mm"] = 0, + }, -- end of ["mlws"] + ["BOMBS_ARMING_NO_VOLATAGE_BOTH"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_NO_VOLATAGE_BOTH", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_NO_VOLATAGE_BOTH"] + ["BAT_SOLENOID_WIRING"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BAT_SOLENOID_WIRING", + ["mm"] = 0, + }, -- end of ["BAT_SOLENOID_WIRING"] + ["STARTER_LOSE_CON"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "STARTER_LOSE_CON", + ["mm"] = 0, + }, -- end of ["STARTER_LOSE_CON"] + ["FUEL_VALVE_LEAK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FUEL_VALVE_LEAK", + ["mm"] = 0, + }, -- end of ["FUEL_VALVE_LEAK"] + ["FLEX_S_NO_GUN_SIGN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FLEX_S_NO_GUN_SIGN", + ["mm"] = 0, + }, -- end of ["FLEX_S_NO_GUN_SIGN"] + ["fuel_sys_right_transfer_pump"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "fuel_sys_right_transfer_pump", + ["mm"] = 0, + }, -- end of ["fuel_sys_right_transfer_pump"] + ["COOLANT_RADIATOR_MOTOR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_RADIATOR_MOTOR", + ["mm"] = 0, + }, -- end of ["COOLANT_RADIATOR_MOTOR"] + ["CARBAIR_OPEN_CIRCUIT_BLB"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CARBAIR_OPEN_CIRCUIT_BLB", + ["mm"] = 0, + }, -- end of ["CARBAIR_OPEN_CIRCUIT_BLB"] + ["AAR_47_FAILURE_SENSOR_TAIL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AAR_47_FAILURE_SENSOR_TAIL", + ["mm"] = 0, + }, -- end of ["AAR_47_FAILURE_SENSOR_TAIL"] + ["GUN_LEFT_OUT_OPEN_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_OUT_OPEN_CIRCUIT", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_OUT_OPEN_CIRCUIT"] + ["TACAN_FAILURE_TRANSMITTER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACAN_FAILURE_TRANSMITTER", + ["mm"] = 0, + }, -- end of ["TACAN_FAILURE_TRANSMITTER"] + ["BOMBS_ARMING_BROKEN_WIRING_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_BROKEN_WIRING_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_BROKEN_WIRING_RIGHT"] + ["l_gen"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "l_gen", + ["mm"] = 0, + }, -- end of ["l_gen"] + ["TURNIND_POINTER_VIBRATES"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_POINTER_VIBRATES", + ["mm"] = 0, + }, -- end of ["TURNIND_POINTER_VIBRATES"] + ["GUN_LEFT_IN_BARREL_WORN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_LEFT_IN_BARREL_WORN", + ["mm"] = 0, + }, -- end of ["GUN_LEFT_IN_BARREL_WORN"] + ["r_gen"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "r_gen", + ["mm"] = 0, + }, -- end of ["r_gen"] + ["COOLANT_RADIATOR_SENSOR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COOLANT_RADIATOR_SENSOR", + ["mm"] = 0, + }, -- end of ["COOLANT_RADIATOR_SENSOR"] + ["AAR_47_FAILURE_SENSOR_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AAR_47_FAILURE_SENSOR_RIGHT", + ["mm"] = 0, + }, -- end of ["AAR_47_FAILURE_SENSOR_RIGHT"] + ["ROCKETS_INTERVALOMETER_SEQ"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ROCKETS_INTERVALOMETER_SEQ", + ["mm"] = 0, + }, -- end of ["ROCKETS_INTERVALOMETER_SEQ"] + ["hydro_common"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "hydro_common", + ["mm"] = 0, + }, -- end of ["hydro_common"] + ["SAR_2_95"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SAR_2_95", + ["mm"] = 0, + }, -- end of ["SAR_2_95"] + ["SAR_2_101"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SAR_2_101", + ["mm"] = 0, + }, -- end of ["SAR_2_101"] + ["BOOSTER_COIL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOOSTER_COIL", + ["mm"] = 0, + }, -- end of ["BOOSTER_COIL"] + ["BOMBS_DAMAGE_ELINKAGE_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_DAMAGE_ELINKAGE_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_DAMAGE_ELINKAGE_RIGHT"] + ["FAULTY_ROCKET_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "FAULTY_ROCKET_RIGHT", + ["mm"] = 0, + }, -- end of ["FAULTY_ROCKET_RIGHT"] + ["GUN_RIGHT_IN_OPEN_CIRCUIT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_IN_OPEN_CIRCUIT", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_IN_OPEN_CIRCUIT"] + ["COMPASS_ERRATIC_INDIACATON"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COMPASS_ERRATIC_INDIACATON", + ["mm"] = 0, + }, -- end of ["COMPASS_ERRATIC_INDIACATON"] + ["OIL_DILUTION_SOLENOID"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "OIL_DILUTION_SOLENOID", + ["mm"] = 0, + }, -- end of ["OIL_DILUTION_SOLENOID"] + ["PUMP_SEPARATOR_CLOGGED"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "PUMP_SEPARATOR_CLOGGED", + ["mm"] = 0, + }, -- end of ["PUMP_SEPARATOR_CLOGGED"] + ["es_damage_MainGenerator"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_MainGenerator", + ["mm"] = 0, + }, -- end of ["es_damage_MainGenerator"] + ["BOMBS_RUST_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_RUST_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_RUST_RIGHT"] + ["CLOGGED_FUEL_STRAINER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "CLOGGED_FUEL_STRAINER", + ["mm"] = 0, + }, -- end of ["CLOGGED_FUEL_STRAINER"] + ["BOMBS_DAMAGE_ELINKAGE_LEFT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_DAMAGE_ELINKAGE_LEFT", + ["mm"] = 0, + }, -- end of ["BOMBS_DAMAGE_ELINKAGE_LEFT"] + ["r_engine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "r_engine", + ["mm"] = 0, + }, -- end of ["r_engine"] + ["TACH_BREAK_IN_INDICATOR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TACH_BREAK_IN_INDICATOR", + ["mm"] = 0, + }, -- end of ["TACH_BREAK_IN_INDICATOR"] + ["A11_CLOCK_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "A11_CLOCK_FAILURE", + ["mm"] = 0, + }, -- end of ["A11_CLOCK_FAILURE"] + ["DOORS_TV_JAMMED"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "DOORS_TV_JAMMED", + ["mm"] = 0, + }, -- end of ["DOORS_TV_JAMMED"] + ["D2_RIGHT_CYLINDER"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "D2_RIGHT_CYLINDER", + ["mm"] = 0, + }, -- end of ["D2_RIGHT_CYLINDER"] + ["ecm"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "ecm", + ["mm"] = 0, + }, -- end of ["ecm"] + ["AN_ALR69V_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALR69V_FAILURE_TOTAL", + ["mm"] = 0, + }, -- end of ["AN_ALR69V_FAILURE_TOTAL"] + ["es_damage_GeneratorRight"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "es_damage_GeneratorRight", + ["mm"] = 0, + }, -- end of ["es_damage_GeneratorRight"] + ["SUPERCHARGER_SOLENOID"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "SUPERCHARGER_SOLENOID", + ["mm"] = 0, + }, -- end of ["SUPERCHARGER_SOLENOID"] + ["GUN_RIGHT_OUT_AMMUN_FAULT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "GUN_RIGHT_OUT_AMMUN_FAULT", + ["mm"] = 0, + }, -- end of ["GUN_RIGHT_OUT_AMMUN_FAULT"] + ["l_engine"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "l_engine", + ["mm"] = 0, + }, -- end of ["l_engine"] + ["AN_ALE_40V_FAILURE_CONTAINER_RIGHT_GEAR"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "AN_ALE_40V_FAILURE_CONTAINER_RIGHT_GEAR", + ["mm"] = 0, + }, -- end of ["AN_ALE_40V_FAILURE_CONTAINER_RIGHT_GEAR"] + ["TransitionalReductor_ShaveInOil"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TransitionalReductor_ShaveInOil", + ["mm"] = 0, + }, -- end of ["TransitionalReductor_ShaveInOil"] + ["COPILOT_KILLED_FAILURE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "COPILOT_KILLED_FAILURE", + ["mm"] = 0, + }, -- end of ["COPILOT_KILLED_FAILURE"] + ["TAIL_GEAR_D_LOCK"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TAIL_GEAR_D_LOCK", + ["mm"] = 0, + }, -- end of ["TAIL_GEAR_D_LOCK"] + ["JADRO_1A_FAILURE_TOTAL"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["mm"] = 0, + }, -- end of ["JADRO_1A_FAILURE_TOTAL"] + ["BOMBS_ARMING_NO_VOLATAGE_RIGHT"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "BOMBS_ARMING_NO_VOLATAGE_RIGHT", + ["mm"] = 0, + }, -- end of ["BOMBS_ARMING_NO_VOLATAGE_RIGHT"] + ["IFFCC_FAILURE_GUN"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "IFFCC_FAILURE_GUN", + ["mm"] = 0, + }, -- end of ["IFFCC_FAILURE_GUN"] + ["APU_Fire"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["mm"] = 0, + }, -- end of ["APU_Fire"] + ["TURNIND_INCORRECT_SENS_DEFECTIVE"] = + { + ["hh"] = 0, + ["prob"] = 100, + ["enable"] = false, + ["mmint"] = 1, + ["id"] = "TURNIND_INCORRECT_SENS_DEFECTIVE", + ["mm"] = 0, + }, -- end of ["TURNIND_INCORRECT_SENS_DEFECTIVE"] + }, -- end of ["failures"] +} -- end of mission diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/options b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/options similarity index 100% rename from Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/options rename to Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/options diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/warehouses b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/warehouses similarity index 99% rename from Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/warehouses rename to Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/warehouses index 68ca70eb9..52b43d127 100644 --- a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/warehouses +++ b/Moose Test Missions/AIB - AI Balancing/AIB-005 - Patrol AI and Randomize Zones/AIB-005 - Patrol AI and Randomize Zones/warehouses @@ -24,7 +24,7 @@ warehouses = ["suppliers"] = { }, -- end of ["suppliers"] - ["coalition"] = "NEUTRAL", + ["coalition"] = "RED", ["jet_fuel"] = { ["InitFuel"] = 100, @@ -62,7 +62,7 @@ warehouses = ["suppliers"] = { }, -- end of ["suppliers"] - ["coalition"] = "NEUTRAL", + ["coalition"] = "BLUE", ["jet_fuel"] = { ["InitFuel"] = 100, @@ -100,7 +100,7 @@ warehouses = ["suppliers"] = { }, -- end of ["suppliers"] - ["coalition"] = "NEUTRAL", + ["coalition"] = "RED", ["jet_fuel"] = { ["InitFuel"] = 100, @@ -138,7 +138,7 @@ warehouses = ["suppliers"] = { }, -- end of ["suppliers"] - ["coalition"] = "NEUTRAL", + ["coalition"] = "RED", ["jet_fuel"] = { ["InitFuel"] = 100, @@ -176,7 +176,7 @@ warehouses = ["suppliers"] = { }, -- end of ["suppliers"] - ["coalition"] = "NEUTRAL", + ["coalition"] = "BLUE", ["jet_fuel"] = { ["InitFuel"] = 100, diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.lua b/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.lua index 650aca254..1b604a94f 100644 --- a/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.lua +++ b/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.lua @@ -35,7 +35,7 @@ local PatrolZone1 = ZONE_POLYGON:New( "PatrolZone1", PatrolZoneGroup1 ) function RU_AI_Balancer:OnAfterSpawned( SetGroup, From, Event, To, AIGroup ) - local Patrol = AI_PATROLZONE:New( PatrolZone1, 3000, 6000, 400, 600 ) + local Patrol = AI_PATROL_ZONE:New( PatrolZone1, 3000, 6000, 400, 600 ) Patrol:ManageFuel( 0.2, 60 ) Patrol:SetControllable( AIGroup ) Patrol:__Start( 5 ) diff --git a/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.miz b/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.miz index 6ab88b384..13541bd70 100644 Binary files a/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.miz and b/Moose Test Missions/AIB - AI Balancing/AIB-006 - Declutter AI at Airbases/AIB-006 - Declutter AI at Airbases.miz differ diff --git a/Moose Test Missions/CAP - Combat Air Patrol/CAP-001 - Combat Air Patrol/CAP-001 - Combat Air Patrol.lua b/Moose Test Missions/CAP - Combat Air Patrol/CAP-001 - Combat Air Patrol/CAP-001 - Combat Air Patrol.lua new file mode 100644 index 000000000..92d27b1b2 --- /dev/null +++ b/Moose Test Missions/CAP - Combat Air Patrol/CAP-001 - Combat Air Patrol/CAP-001 - Combat Air Patrol.lua @@ -0,0 +1,18 @@ +-- Name: CAP-001 - Combat Air Patrol +-- Author: FlightControl +-- Date Created: 16 January 2017 +-- +-- # Situation: +-- +-- # Test cases: +-- + +local CapPlane = GROUP:FindByName( "Plane" ) + +local PatrolZone = ZONE:New( "Patrol Zone" ) + +local AICapZone = AI_CAP_ZONE:New( PatrolZone, 500, 1000, 500, 600 ) + +AICapZone:SetControllable( CapPlane ) + +AICapZone:__Start( 1 ) -- They should statup, and start patrolling in the PatrolZone. diff --git a/Moose Test Missions/CAP - Combat Air Patrol/CAP-001 - Combat Air Patrol/CAP-001 - Combat Air Patrol.miz b/Moose Test Missions/CAP - Combat Air Patrol/CAP-001 - Combat Air Patrol/CAP-001 - Combat Air Patrol.miz new file mode 100644 index 000000000..dc4ceadc4 Binary files /dev/null and b/Moose Test Missions/CAP - Combat Air Patrol/CAP-001 - Combat Air Patrol/CAP-001 - Combat Air Patrol.miz differ diff --git a/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Range/CAP-010 - CAP and Engage within Range.lua b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Range/CAP-010 - CAP and Engage within Range.lua new file mode 100644 index 000000000..283396d73 --- /dev/null +++ b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Range/CAP-010 - CAP and Engage within Range.lua @@ -0,0 +1,19 @@ +-- Name: CAP-001 - Combat Air Patrol +-- Author: FlightControl +-- Date Created: 16 January 2017 +-- +-- # Situation: +-- +-- # Test cases: +-- + +local CapPlane = GROUP:FindByName( "Plane" ) + +local PatrolZone = ZONE:New( "Patrol Zone" ) + +local AICapZone = AI_CAP_ZONE:New( PatrolZone, 500, 1000, 500, 600 ) + +AICapZone:SetControllable( CapPlane ) +AICapZone:SetEngageRange( 20000 ) -- Set the Engage Range to 20.000 meters. The AI won't engage when the enemy is beyond 20.000 meters. + +AICapZone:__Start( 1 ) -- They should statup, and start patrolling in the PatrolZone. diff --git a/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Range/CAP-010 - CAP and Engage within Range.miz b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Range/CAP-010 - CAP and Engage within Range.miz new file mode 100644 index 000000000..936a6cda6 Binary files /dev/null and b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Range/CAP-010 - CAP and Engage within Range.miz differ diff --git a/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Zone/CAP-010 - CAP and Engage within Zone.lua b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Zone/CAP-010 - CAP and Engage within Zone.lua new file mode 100644 index 000000000..5e911a096 --- /dev/null +++ b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Zone/CAP-010 - CAP and Engage within Zone.lua @@ -0,0 +1,23 @@ +-- Name: CAP-001 - Combat Air Patrol +-- Author: FlightControl +-- Date Created: 16 January 2017 +-- +-- # Situation: +-- +-- # Test cases: +-- + +local CapPlane = GROUP:FindByName( "Plane" ) + +local PatrolZone = ZONE:New( "Patrol Zone" ) + +local AICapZone = AI_CAP_ZONE:New( PatrolZone, 500, 1000, 500, 600 ) + +local EngageZoneGroup = GROUP:FindByName( "Engage Zone" ) + +local CapEngageZone = ZONE_POLYGON:New( "Engage Zone", EngageZoneGroup ) + +AICapZone:SetControllable( CapPlane ) +AICapZone:SetEngageZone( CapEngageZone ) -- Set the Engage Zone. The AI will only engage when the bogeys are within the CapEngageZone. + +AICapZone:__Start( 1 ) -- They should statup, and start patrolling in the PatrolZone. diff --git a/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Zone/CAP-010 - CAP and Engage within Zone.miz b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Zone/CAP-010 - CAP and Engage within Zone.miz new file mode 100644 index 000000000..705139400 Binary files /dev/null and b/Moose Test Missions/CAP - Combat Air Patrol/CAP-010 - CAP and Engage within Zone/CAP-010 - CAP and Engage within Zone.miz differ diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.lua b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.lua index 30c25eb7e..f5f267f69 100644 --- a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.lua +++ b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.lua @@ -6,32 +6,54 @@ -- -- # Test cases: -- - +-- Create a local variable (in this case called CASEngagementZone) and +-- using the ZONE function find the pre-defined zone called "Engagement Zone" +-- currently on the map and assign it to this variable local CASEngagementZone = ZONE:New( "Engagement Zone" ) +-- Create a local variable (in this case called CASPlane) and +-- using the GROUP function find the aircraft group called "Plane" and assign to this variable local CASPlane = GROUP:FindByName( "Plane" ) +-- Create a local Variable (in this cased called PatrolZone and +-- using the ZONE function find the pre-defined zone called "Patrol Zone" and assign it to this variable local PatrolZone = ZONE:New( "Patrol Zone" ) -local AICasZone = AI_CAS_ZONE:New( PatrolZone, 500, 1000, 350, 600, CASEngagementZone ) +-- Create and object (in this case called AICasZone) and +-- using the functions AI_CAS_ZONE assign the parameters that define this object +-- (in this case PatrolZone, 500, 1000, 500, 600, CASEngagementZone) +local AICasZone = AI_CAS_ZONE:New( PatrolZone, 500, 1000, 500, 600, CASEngagementZone ) + +-- Create an object (in this case called Targets) and +-- using the GROUP function find the group labeled "Targets" and assign it to this object local Targets = GROUP:FindByName("Targets") -AICasZone:SetControllable(CASPlane) -AICasZone:__Start(1) -AICasZone:__Engage(10) + +-- Tell the program to use the object (in this case called CASPlane) as the group to use in the CAS function +AICasZone:SetControllable( CASPlane ) + +-- Tell the group CASPlane to start the mission in 1 second. +AICasZone:__Start( 1 ) -- They should statup, and start patrolling in the PatrolZone. + +-- After 10 minutes, tell the group CASPlane to engage the targets located in the engagement zone called CASEngagement Zone. (600 is 600 seconds) +AICasZone:__Engage( 600 ) -- Check every 60 seconds whether the Targets have been eliminated. -- When the trigger completed has been fired, the Plane will go back to the Patrol Zone. -Check = SCHEDULER:New(nil, +Check, CheckScheduleID = SCHEDULER:New(nil, function() BASE:E( { "In Scheduler: ", Targets:GetSize() } ) - if Targets:IsAlive() and Targets:GetSize() ~= 0 then + if Targets:IsAlive() and Targets:GetSize() > 5 then BASE:E("Still alive") else BASE:E("Destroyed") - AICasZone:__Completed(1) + AICasZone:__Accomplish( 1 ) -- Now they should fly back to teh patrolzone and patrol. + Check:Stop(CheckScheduleID) end end, {}, 20, 60, 0.2 ) - - + +-- When the targets in the zone are destroyed, (see scheduled function), the planes will return home ... +function AICasZone:OnAfterAccomplish( Controllable, From, Event, To ) + AICasZone:__RTB( 1 ) +end diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.miz b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.miz index 75784d5da..b9a4b9a0a 100644 Binary files a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.miz and b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - CAS in a ZONE.miz differ diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test.miz b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test.miz index 37b9b2e56..a1f6b5ca8 100644 Binary files a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test.miz and b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test.miz differ diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/l10n/DEFAULT/dictionary b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/l10n/DEFAULT/dictionary deleted file mode 100644 index b956754dd..000000000 --- a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/l10n/DEFAULT/dictionary +++ /dev/null @@ -1,18 +0,0 @@ -dictionary = -{ - ["DictKey_WptName_7"] = "", - ["DictKey_WptName_11"] = "", - ["DictKey_descriptionText_1"] = "", - ["DictKey_descriptionBlueTask_3"] = "", - ["DictKey_WptName_10"] = "", - ["DictKey_UnitName_9"] = "Unit #1", - ["DictKey_sortie_4"] = "", - ["DictKey_UnitName_13"] = "Unit #002", - ["DictKey_GroupName_8"] = "New Vehicle Group", - ["DictKey_UnitName_14"] = "Unit #003", - ["DictKey_UnitName_15"] = "Unit #004", - ["DictKey_GroupName_5"] = "RU25T", - ["DictKey_UnitName_6"] = "Pilot #001", - ["DictKey_UnitName_12"] = "Unit #001", - ["DictKey_descriptionRedTask_2"] = "", -} -- end of dictionary diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/l10n/DEFAULT/mapResource b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/l10n/DEFAULT/mapResource deleted file mode 100644 index d3e154afa..000000000 --- a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/l10n/DEFAULT/mapResource +++ /dev/null @@ -1,3 +0,0 @@ -mapResource = -{ -} -- end of mapResource diff --git a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/mission b/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/mission deleted file mode 100644 index 79afaaeb1..000000000 --- a/Moose Test Missions/CAS - Close Air Support/CAS-001 - CAS in a ZONE/CAS-001 - Manual Test/mission +++ /dev/null @@ -1,878 +0,0 @@ -mission = -{ - ["trig"] = - { - ["actions"] = - { - }, -- end of ["actions"] - ["events"] = - { - }, -- end of ["events"] - ["custom"] = - { - }, -- end of ["custom"] - ["func"] = - { - }, -- end of ["func"] - ["flag"] = - { - }, -- end of ["flag"] - ["conditions"] = - { - }, -- end of ["conditions"] - ["customStartup"] = - { - }, -- end of ["customStartup"] - ["funcStartup"] = - { - }, -- end of ["funcStartup"] - }, -- end of ["trig"] - ["date"] = - { - ["Day"] = 1, - ["Year"] = 2011, - ["Month"] = 6, - }, -- end of ["date"] - ["maxDictId"] = 15, - ["result"] = - { - ["offline"] = - { - ["conditions"] = - { - }, -- end of ["conditions"] - ["actions"] = - { - }, -- end of ["actions"] - ["func"] = - { - }, -- end of ["func"] - }, -- end of ["offline"] - ["total"] = 0, - ["blue"] = - { - ["conditions"] = - { - }, -- end of ["conditions"] - ["actions"] = - { - }, -- end of ["actions"] - ["func"] = - { - }, -- end of ["func"] - }, -- end of ["blue"] - ["red"] = - { - ["conditions"] = - { - }, -- end of ["conditions"] - ["actions"] = - { - }, -- end of ["actions"] - ["func"] = - { - }, -- end of ["func"] - }, -- end of ["red"] - }, -- end of ["result"] - ["groundControl"] = - { - ["isPilotControlVehicles"] = false, - ["roles"] = - { - ["artillery_commander"] = - { - ["blue"] = 0, - ["red"] = 0, - }, -- end of ["artillery_commander"] - ["instructor"] = - { - ["blue"] = 0, - ["red"] = 0, - }, -- end of ["instructor"] - ["observer"] = - { - ["blue"] = 0, - ["red"] = 0, - }, -- end of ["observer"] - ["forward_observer"] = - { - ["blue"] = 0, - ["red"] = 0, - }, -- end of ["forward_observer"] - }, -- end of ["roles"] - }, -- end of ["groundControl"] - ["triggers"] = - { - ["zones"] = - { - }, -- end of ["zones"] - }, -- end of ["triggers"] - ["weather"] = - { - ["atmosphere_type"] = 0, - ["wind"] = - { - ["at8000"] = - { - ["speed"] = 0, - ["dir"] = 0, - }, -- end of ["at8000"] - ["at2000"] = - { - ["speed"] = 0, - ["dir"] = 0, - }, -- end of ["at2000"] - ["atGround"] = - { - ["speed"] = 0, - ["dir"] = 0, - }, -- end of ["atGround"] - }, -- end of ["wind"] - ["enable_fog"] = false, - ["season"] = - { - ["temperature"] = 20, - }, -- end of ["season"] - ["type_weather"] = 0, - ["qnh"] = 760, - ["cyclones"] = - { - }, -- end of ["cyclones"] - ["name"] = "Winter, clean sky", - ["fog"] = - { - ["thickness"] = 0, - ["visibility"] = 25, - ["density"] = 7, - }, -- end of ["fog"] - ["groundTurbulence"] = 0, - ["visibility"] = - { - ["distance"] = 80000, - }, -- end of ["visibility"] - ["clouds"] = - { - ["thickness"] = 200, - ["density"] = 0, - ["base"] = 300, - ["iprecptns"] = 0, - }, -- end of ["clouds"] - }, -- end of ["weather"] - ["theatre"] = "Caucasus", - ["needModules"] = - { - }, -- end of ["needModules"] - ["map"] = - { - ["centerY"] = 627628.57142857, - ["zoom"] = 100000, - ["centerX"] = -293371.42857143, - }, -- end of ["map"] - ["coalitions"] = - { - ["neutrals"] = - { - [1] = 7, - [2] = 17, - [3] = 22, - [4] = 23, - [5] = 25, - [6] = 29, - [7] = 30, - [8] = 31, - [9] = 32, - [10] = 33, - [11] = 35, - [12] = 36, - [13] = 39, - [14] = 41, - [15] = 42, - [16] = 44, - [17] = 46, - [18] = 48, - [19] = 49, - [20] = 50, - [21] = 51, - [22] = 52, - [23] = 53, - [24] = 54, - [25] = 55, - [26] = 56, - [27] = 57, - [28] = 58, - [29] = 59, - [30] = 60, - [31] = 61, - [32] = 62, - [33] = 63, - [34] = 64, - [35] = 65, - }, -- end of ["neutrals"] - ["blue"] = - { - [1] = 11, - [2] = 4, - [3] = 6, - [4] = 16, - [5] = 13, - [6] = 15, - [7] = 9, - [8] = 8, - [9] = 12, - [10] = 2, - [11] = 3, - [12] = 5, - [13] = 10, - [14] = 20, - [15] = 21, - [16] = 40, - [17] = 26, - [18] = 45, - [19] = 28, - }, -- end of ["blue"] - ["red"] = - { - [1] = 0, - [2] = 1, - [3] = 18, - [4] = 19, - [5] = 37, - [6] = 24, - [7] = 27, - [8] = 43, - [9] = 47, - [10] = 34, - [11] = 38, - }, -- end of ["red"] - }, -- end of ["coalitions"] - ["descriptionText"] = "DictKey_descriptionText_1", - ["pictureFileNameR"] = - { - }, -- end of ["pictureFileNameR"] - ["descriptionBlueTask"] = "DictKey_descriptionBlueTask_3", - ["descriptionRedTask"] = "DictKey_descriptionRedTask_2", - ["pictureFileNameB"] = - { - }, -- end of ["pictureFileNameB"] - ["trigrules"] = - { - }, -- end of ["trigrules"] - ["coalition"] = - { - ["blue"] = - { - ["bullseye"] = - { - ["y"] = 617414, - ["x"] = -291014, - }, -- end of ["bullseye"] - ["nav_points"] = - { - }, -- end of ["nav_points"] - ["name"] = "blue", - ["country"] = - { - [1] = - { - ["id"] = 11, - ["name"] = "Belgium", - }, -- end of [1] - [2] = - { - ["id"] = 4, - ["name"] = "UK", - }, -- end of [2] - [3] = - { - ["id"] = 6, - ["name"] = "Germany", - }, -- end of [3] - [4] = - { - ["id"] = 16, - ["name"] = "Georgia", - }, -- end of [4] - [5] = - { - ["id"] = 13, - ["name"] = "Denmark", - }, -- end of [5] - [6] = - { - ["id"] = 15, - ["name"] = "Israel", - }, -- end of [6] - [7] = - { - ["id"] = 9, - ["name"] = "Spain", - }, -- end of [7] - [8] = - { - ["id"] = 8, - ["name"] = "Canada", - }, -- end of [8] - [9] = - { - ["id"] = 12, - ["name"] = "Norway", - }, -- end of [9] - [10] = - { - ["id"] = 2, - ["vehicle"] = - { - ["group"] = - { - [1] = - { - ["visible"] = false, - ["taskSelected"] = true, - ["route"] = - { - ["spans"] = - { - [1] = - { - [1] = - { - ["y"] = 622200, - ["x"] = -288542.85714286, - }, -- end of [1] - [2] = - { - ["y"] = 625342.85714286, - ["x"] = -286257.14285714, - }, -- end of [2] - }, -- end of [1] - }, -- end of ["spans"] - ["points"] = - { - [1] = - { - ["alt"] = 3, - ["type"] = "Turning Point", - ["ETA"] = 0, - ["alt_type"] = "BARO", - ["formation_template"] = "", - ["y"] = 622978.57142857, - ["x"] = -287792.85714286, - ["name"] = "DictKey_WptName_10", - ["ETA_locked"] = true, - ["speed"] = 5.5555555555556, - ["action"] = "Off Road", - ["task"] = - { - ["id"] = "ComboTask", - ["params"] = - { - ["tasks"] = - { - }, -- end of ["tasks"] - }, -- end of ["params"] - }, -- end of ["task"] - ["speed_locked"] = true, - }, -- end of [1] - }, -- end of ["points"] - }, -- end of ["route"] - ["groupId"] = 2, - ["tasks"] = - { - }, -- end of ["tasks"] - ["hidden"] = false, - ["units"] = - { - [1] = - { - ["type"] = "AAV7", - ["transportable"] = - { - ["randomTransportable"] = false, - }, -- end of ["transportable"] - ["unitId"] = 2, - ["skill"] = "Average", - ["y"] = 622978.57142857, - ["x"] = -287792.85714286, - ["name"] = "DictKey_UnitName_9", - ["playerCanDrive"] = true, - ["heading"] = 0.94200004037947, - }, -- end of [1] - [2] = - { - ["type"] = "AAV7", - ["transportable"] = - { - ["randomTransportable"] = false, - }, -- end of ["transportable"] - ["unitId"] = 3, - ["skill"] = "Average", - ["y"] = 622457.14285714, - ["x"] = -288121.42857143, - ["name"] = "DictKey_UnitName_12", - ["playerCanDrive"] = true, - ["heading"] = 0.94200004037947, - }, -- end of [2] - [3] = - { - ["type"] = "AAV7", - ["transportable"] = - { - ["randomTransportable"] = false, - }, -- end of ["transportable"] - ["unitId"] = 4, - ["skill"] = "Average", - ["y"] = 621935.71428571, - ["x"] = -288892.85714286, - ["name"] = "DictKey_UnitName_13", - ["playerCanDrive"] = true, - ["heading"] = 0.94200004037947, - }, -- end of [3] - [4] = - { - ["type"] = "M1043 HMMWV Armament", - ["transportable"] = - { - ["randomTransportable"] = false, - }, -- end of ["transportable"] - ["unitId"] = 5, - ["skill"] = "Average", - ["y"] = 620992.85714286, - ["x"] = -287100, - ["name"] = "DictKey_UnitName_14", - ["playerCanDrive"] = true, - ["heading"] = 0.94200004037947, - }, -- end of [4] - [5] = - { - ["type"] = "AAV7", - ["transportable"] = - { - ["randomTransportable"] = false, - }, -- end of ["transportable"] - ["unitId"] = 6, - ["skill"] = "Average", - ["y"] = 623271.42857143, - ["x"] = -286535.71428571, - ["name"] = "DictKey_UnitName_15", - ["playerCanDrive"] = true, - ["heading"] = 0.94200004037947, - }, -- end of [5] - }, -- end of ["units"] - ["y"] = 622978.57142857, - ["x"] = -287792.85714286, - ["name"] = "DictKey_GroupName_8", - ["start_time"] = 0, - ["task"] = "Ground Nothing", - }, -- end of [1] - }, -- end of ["group"] - }, -- end of ["vehicle"] - ["name"] = "USA", - }, -- end of [10] - [11] = - { - ["id"] = 3, - ["name"] = "Turkey", - }, -- end of [11] - [12] = - { - ["id"] = 5, - ["name"] = "France", - }, -- end of [12] - [13] = - { - ["id"] = 10, - ["name"] = "The Netherlands", - }, -- end of [13] - [14] = - { - ["id"] = 20, - ["name"] = "Italy", - }, -- end of [14] - [15] = - { - ["id"] = 21, - ["name"] = "Australia", - }, -- end of [15] - [16] = - { - ["id"] = 40, - ["name"] = "Poland", - }, -- end of [16] - [17] = - { - ["id"] = 26, - ["name"] = "Czech Republic", - }, -- end of [17] - [18] = - { - ["id"] = 45, - ["name"] = "South Korea", - }, -- end of [18] - [19] = - { - ["id"] = 28, - ["name"] = "Croatia", - }, -- end of [19] - }, -- end of ["country"] - }, -- end of ["blue"] - ["red"] = - { - ["bullseye"] = - { - ["y"] = 371700, - ["x"] = 11557, - }, -- end of ["bullseye"] - ["nav_points"] = - { - }, -- end of ["nav_points"] - ["name"] = "red", - ["country"] = - { - [1] = - { - ["id"] = 0, - ["name"] = "Russia", - ["plane"] = - { - ["group"] = - { - [1] = - { - ["modulation"] = 0, - ["tasks"] = - { - }, -- end of ["tasks"] - ["radioSet"] = false, - ["task"] = "CAS", - ["uncontrolled"] = false, - ["route"] = - { - ["points"] = - { - [1] = - { - ["alt"] = 2000, - ["action"] = "Turning Point", - ["alt_type"] = "BARO", - ["properties"] = - { - ["vnav"] = 1, - ["scale"] = 0, - ["angle"] = 0, - ["vangle"] = 0, - ["steer"] = 2, - }, -- end of ["properties"] - ["speed"] = 138.88888888889, - ["task"] = - { - ["id"] = "ComboTask", - ["params"] = - { - ["tasks"] = - { - [1] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "WrappedAction", - ["number"] = 1, - ["params"] = - { - ["action"] = - { - ["id"] = "Option", - ["params"] = - { - ["value"] = 2, - ["name"] = 0, - }, -- end of ["params"] - }, -- end of ["action"] - }, -- end of ["params"] - }, -- end of [1] - [2] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "WrappedAction", - ["number"] = 2, - ["params"] = - { - ["action"] = - { - ["id"] = "Option", - ["params"] = - { - ["value"] = 1, - ["name"] = 1, - }, -- end of ["params"] - }, -- end of ["action"] - }, -- end of ["params"] - }, -- end of [2] - [3] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "AttackUnit", - ["number"] = 3, - ["params"] = - { - ["altitudeEnabled"] = false, - ["unitId"] = 2, - ["attackQtyLimit"] = false, - ["attackQty"] = 1, - ["expend"] = "Auto", - ["altitude"] = 2000, - ["directionEnabled"] = false, - ["groupAttack"] = false, - ["weaponType"] = 1073741822, - ["direction"] = 0, - }, -- end of ["params"] - }, -- end of [3] - [4] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "AttackUnit", - ["number"] = 4, - ["params"] = - { - ["altitudeEnabled"] = false, - ["unitId"] = 3, - ["attackQtyLimit"] = false, - ["attackQty"] = 1, - ["expend"] = "Auto", - ["altitude"] = 2000, - ["directionEnabled"] = false, - ["groupAttack"] = false, - ["weaponType"] = 1073741822, - ["direction"] = 0, - }, -- end of ["params"] - }, -- end of [4] - [5] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "AttackUnit", - ["number"] = 5, - ["params"] = - { - ["altitudeEnabled"] = false, - ["unitId"] = 4, - ["attackQtyLimit"] = false, - ["attackQty"] = 1, - ["expend"] = "Auto", - ["altitude"] = 2000, - ["directionEnabled"] = false, - ["groupAttack"] = false, - ["weaponType"] = 1073741822, - ["direction"] = 0, - }, -- end of ["params"] - }, -- end of [5] - [6] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "AttackUnit", - ["number"] = 6, - ["params"] = - { - ["altitudeEnabled"] = false, - ["unitId"] = 5, - ["attackQtyLimit"] = false, - ["attackQty"] = 1, - ["expend"] = "Auto", - ["altitude"] = 2000, - ["directionEnabled"] = false, - ["groupAttack"] = false, - ["weaponType"] = 1073741822, - ["direction"] = 0, - }, -- end of ["params"] - }, -- end of [6] - [7] = - { - ["enabled"] = true, - ["auto"] = false, - ["id"] = "AttackUnit", - ["number"] = 7, - ["params"] = - { - ["altitudeEnabled"] = false, - ["unitId"] = 6, - ["attackQtyLimit"] = false, - ["attackQty"] = 1, - ["expend"] = "Auto", - ["altitude"] = 2000, - ["directionEnabled"] = false, - ["groupAttack"] = false, - ["weaponType"] = 1073741822, - ["direction"] = 0, - }, -- end of ["params"] - }, -- end of [7] - }, -- end of ["tasks"] - }, -- end of ["params"] - }, -- end of ["task"] - ["type"] = "Turning Point", - ["ETA"] = 0, - ["ETA_locked"] = true, - ["y"] = 619400, - ["x"] = -285628.57142857, - ["name"] = "DictKey_WptName_7", - ["formation_template"] = "", - ["speed_locked"] = true, - }, -- end of [1] - }, -- end of ["points"] - }, -- end of ["route"] - ["groupId"] = 1, - ["hidden"] = false, - ["units"] = - { - [1] = - { - ["alt"] = 2000, - ["hardpoint_racks"] = true, - ["alt_type"] = "BARO", - ["livery_id"] = "af standard 1", - ["skill"] = "Excellent", - ["speed"] = 138.88888888889, - ["type"] = "Su-25T", - ["unitId"] = 1, - ["psi"] = 0, - ["y"] = 619400, - ["x"] = -285628.57142857, - ["name"] = "DictKey_UnitName_6", - ["payload"] = - { - ["pylons"] = - { - [1] = - { - ["CLSID"] = "{44EE8698-89F9-48EE-AF36-5FD31896A82D}", - }, -- end of [1] - [2] = - { - ["CLSID"] = "{CBC29BFE-3D24-4C64-B81D-941239D12249}", - }, -- end of [2] - [3] = - { - ["CLSID"] = "{0180F983-C14A-11d8-9897-000476191836}", - }, -- end of [3] - [4] = - { - ["CLSID"] = "{F789E86A-EE2E-4E6B-B81E-D5E5F903B6ED}", - }, -- end of [4] - [5] = - { - ["CLSID"] = "{E92CBFE5-C153-11d8-9897-000476191836}", - }, -- end of [5] - [6] = - { - ["CLSID"] = "{B1EF6B0E-3D91-4047-A7A5-A99E7D8B4A8B}", - }, -- end of [6] - [7] = - { - ["CLSID"] = "{E92CBFE5-C153-11d8-9897-000476191836}", - }, -- end of [7] - [8] = - { - ["CLSID"] = "{F789E86A-EE2E-4E6B-B81E-D5E5F903B6ED}", - }, -- end of [8] - [9] = - { - ["CLSID"] = "{0180F983-C14A-11d8-9897-000476191836}", - }, -- end of [9] - [10] = - { - ["CLSID"] = "{CBC29BFE-3D24-4C64-B81D-941239D12249}", - }, -- end of [10] - [11] = - { - ["CLSID"] = "{44EE8698-89F9-48EE-AF36-5FD31896A82C}", - }, -- end of [11] - }, -- end of ["pylons"] - ["fuel"] = "3790", - ["flare"] = 128, - ["chaff"] = 128, - ["gun"] = 100, - }, -- end of ["payload"] - ["heading"] = 0, - ["callsign"] = 101, - ["onboard_num"] = "010", - }, -- end of [1] - }, -- end of ["units"] - ["y"] = 619400, - ["x"] = -285628.57142857, - ["name"] = "DictKey_GroupName_5", - ["communication"] = true, - ["start_time"] = 0, - ["frequency"] = 124, - }, -- end of [1] - }, -- end of ["group"] - }, -- end of ["plane"] - }, -- end of [1] - [2] = - { - ["id"] = 1, - ["name"] = "Ukraine", - }, -- end of [2] - [3] = - { - ["id"] = 18, - ["name"] = "Abkhazia", - }, -- end of [3] - [4] = - { - ["id"] = 19, - ["name"] = "South Ossetia", - }, -- end of [4] - [5] = - { - ["id"] = 37, - ["name"] = "Kazakhstan", - }, -- end of [5] - [6] = - { - ["id"] = 24, - ["name"] = "Belarus", - }, -- end of [6] - [7] = - { - ["id"] = 27, - ["name"] = "China", - }, -- end of [7] - [8] = - { - ["id"] = 43, - ["name"] = "Serbia", - }, -- end of [8] - [9] = - { - ["id"] = 47, - ["name"] = "Syria", - }, -- end of [9] - [10] = - { - ["id"] = 34, - ["name"] = "Iran", - }, -- end of [10] - [11] = - { - ["id"] = 38, - ["name"] = "North Korea", - }, -- end of [11] - }, -- end of ["country"] - }, -- end of ["red"] - }, -- end of ["coalition"] - ["sortie"] = "DictKey_sortie_4", - ["version"] = 12, - ["goals"] = - { - }, -- end of ["goals"] - ["currentKey"] = 175, - ["start_time"] = 43200, - ["forcedOptions"] = - { - }, -- end of ["forcedOptions"] - ["failures"] = - { - }, -- end of ["failures"] -} -- end of mission diff --git a/Moose Test Missions/CGO - Cargo/CGO-001 - Unit Boarding/CGO-001 - Unit Boarding.miz b/Moose Test Missions/CGO - Cargo/CGO-001 - Unit Boarding/CGO-001 - Unit Boarding.miz index 33473c24a..7f0505c7f 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-001 - Unit Boarding/CGO-001 - Unit Boarding.miz and b/Moose Test Missions/CGO - Cargo/CGO-001 - Unit Boarding/CGO-001 - Unit Boarding.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-002 - Unit Unboarding/CGO-002 - Unit Unboarding.miz b/Moose Test Missions/CGO - Cargo/CGO-002 - Unit Unboarding/CGO-002 - Unit Unboarding.miz index 7e015c9dd..304357caf 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-002 - Unit Unboarding/CGO-002 - Unit Unboarding.miz and b/Moose Test Missions/CGO - Cargo/CGO-002 - Unit Unboarding/CGO-002 - Unit Unboarding.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-003 - Unit Transferring/CGO-003 - Unit Transferring.miz b/Moose Test Missions/CGO - Cargo/CGO-003 - Unit Transferring/CGO-003 - Unit Transferring.miz index e459b9335..4ef50a887 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-003 - Unit Transferring/CGO-003 - Unit Transferring.miz and b/Moose Test Missions/CGO - Cargo/CGO-003 - Unit Transferring/CGO-003 - Unit Transferring.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-101 - Group Boarding/CGO-101 - Group Boarding.miz b/Moose Test Missions/CGO - Cargo/CGO-101 - Group Boarding/CGO-101 - Group Boarding.miz index cf671a7af..f81573419 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-101 - Group Boarding/CGO-101 - Group Boarding.miz and b/Moose Test Missions/CGO - Cargo/CGO-101 - Group Boarding/CGO-101 - Group Boarding.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-102 - Group Unboarding/CGO-102 - Group Unboarding.miz b/Moose Test Missions/CGO - Cargo/CGO-102 - Group Unboarding/CGO-102 - Group Unboarding.miz index ccf573840..91bcabb31 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-102 - Group Unboarding/CGO-102 - Group Unboarding.miz and b/Moose Test Missions/CGO - Cargo/CGO-102 - Group Unboarding/CGO-102 - Group Unboarding.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-103 - Group Transferring/CGO-103 - Group Transferring.miz b/Moose Test Missions/CGO - Cargo/CGO-103 - Group Transferring/CGO-103 - Group Transferring.miz index f3b12e987..3ca7000e7 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-103 - Group Transferring/CGO-103 - Group Transferring.miz and b/Moose Test Missions/CGO - Cargo/CGO-103 - Group Transferring/CGO-103 - Group Transferring.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-201 - Package Boarding/CGO-201 - Package Boarding.miz b/Moose Test Missions/CGO - Cargo/CGO-201 - Package Boarding/CGO-201 - Package Boarding.miz index 0408bebed..b6d70f09d 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-201 - Package Boarding/CGO-201 - Package Boarding.miz and b/Moose Test Missions/CGO - Cargo/CGO-201 - Package Boarding/CGO-201 - Package Boarding.miz differ diff --git a/Moose Test Missions/CGO - Cargo/CGO-202 - Package Unboarding/CGO-202 - Package Unboarding.miz b/Moose Test Missions/CGO - Cargo/CGO-202 - Package Unboarding/CGO-202 - Package Unboarding.miz index 89bc3900b..2c3a99429 100644 Binary files a/Moose Test Missions/CGO - Cargo/CGO-202 - Package Unboarding/CGO-202 - Package Unboarding.miz and b/Moose Test Missions/CGO - Cargo/CGO-202 - Package Unboarding/CGO-202 - Package Unboarding.miz differ diff --git a/Moose Test Missions/DET - Detection/DET-001 - Detection Areas/DET-001 - Detection Areas.miz b/Moose Test Missions/DET - Detection/DET-001 - Detection Areas/DET-001 - Detection Areas.miz index 5dba8db0f..1b32d1b58 100644 Binary files a/Moose Test Missions/DET - Detection/DET-001 - Detection Areas/DET-001 - Detection Areas.miz and b/Moose Test Missions/DET - Detection/DET-001 - Detection Areas/DET-001 - Detection Areas.miz differ diff --git a/Moose Test Missions/DET - Detection/DET-101 - Detection Reporting/DET-101 - Detection Reporting.miz b/Moose Test Missions/DET - Detection/DET-101 - Detection Reporting/DET-101 - Detection Reporting.miz index efdd04d6d..d445f5128 100644 Binary files a/Moose Test Missions/DET - Detection/DET-101 - Detection Reporting/DET-101 - Detection Reporting.miz and b/Moose Test Missions/DET - Detection/DET-101 - Detection Reporting/DET-101 - Detection Reporting.miz differ diff --git a/Moose Test Missions/ESC - Escorting/ESC-001 - Escorting Helicopters/ESC-001 - Escorting Helicopters.miz b/Moose Test Missions/ESC - Escorting/ESC-001 - Escorting Helicopters/ESC-001 - Escorting Helicopters.miz index 0b9cebf31..23d06b8c9 100644 Binary files a/Moose Test Missions/ESC - Escorting/ESC-001 - Escorting Helicopters/ESC-001 - Escorting Helicopters.miz and b/Moose Test Missions/ESC - Escorting/ESC-001 - Escorting Helicopters/ESC-001 - Escorting Helicopters.miz differ diff --git a/Moose Test Missions/FSM - Finite State Machine/FSM-100 - Transition Explanation/FSM-100 - Transition Explanation.miz b/Moose Test Missions/FSM - Finite State Machine/FSM-100 - Transition Explanation/FSM-100 - Transition Explanation.miz index 3e19b3727..7c69b1ae9 100644 Binary files a/Moose Test Missions/FSM - Finite State Machine/FSM-100 - Transition Explanation/FSM-100 - Transition Explanation.miz and b/Moose Test Missions/FSM - Finite State Machine/FSM-100 - Transition Explanation/FSM-100 - Transition Explanation.miz differ diff --git a/Moose Test Missions/GRP - Group Commands/GRP-200 - Follow Group/GRP-200 - Follow Group.miz b/Moose Test Missions/GRP - Group Commands/GRP-200 - Follow Group/GRP-200 - Follow Group.miz index e9a596a8e..abe076c97 100644 Binary files a/Moose Test Missions/GRP - Group Commands/GRP-200 - Follow Group/GRP-200 - Follow Group.miz and b/Moose Test Missions/GRP - Group Commands/GRP-200 - Follow Group/GRP-200 - Follow Group.miz differ diff --git a/Moose Test Missions/GRP - Group Commands/GRP-300 - Switch WayPoints/GRP-300 - Switch WayPoints.miz b/Moose Test Missions/GRP - Group Commands/GRP-300 - Switch WayPoints/GRP-300 - Switch WayPoints.miz index 0ac6bdec6..2a7df90f6 100644 Binary files a/Moose Test Missions/GRP - Group Commands/GRP-300 - Switch WayPoints/GRP-300 - Switch WayPoints.miz and b/Moose Test Missions/GRP - Group Commands/GRP-300 - Switch WayPoints/GRP-300 - Switch WayPoints.miz differ diff --git a/Moose Test Missions/GRP - Group Commands/Moose_Test_WRAPPER.miz b/Moose Test Missions/GRP - Group Commands/Moose_Test_WRAPPER.miz index 26aa5a2bd..c8430de80 100644 Binary files a/Moose Test Missions/GRP - Group Commands/Moose_Test_WRAPPER.miz and b/Moose Test Missions/GRP - Group Commands/Moose_Test_WRAPPER.miz differ diff --git a/Moose Test Missions/MEN - Menu Options/MEN-001 - Menu Client/MEN-001 - Menu Client.miz b/Moose Test Missions/MEN - Menu Options/MEN-001 - Menu Client/MEN-001 - Menu Client.miz index 02a22eddf..5a7c87f98 100644 Binary files a/Moose Test Missions/MEN - Menu Options/MEN-001 - Menu Client/MEN-001 - Menu Client.miz and b/Moose Test Missions/MEN - Menu Options/MEN-001 - Menu Client/MEN-001 - Menu Client.miz differ diff --git a/Moose Test Missions/MEN - Menu Options/MEN-002 - Menu Coalition/MEN-002 - Menu Coalition.miz b/Moose Test Missions/MEN - Menu Options/MEN-002 - Menu Coalition/MEN-002 - Menu Coalition.miz index 990df79d0..a428c9c86 100644 Binary files a/Moose Test Missions/MEN - Menu Options/MEN-002 - Menu Coalition/MEN-002 - Menu Coalition.miz and b/Moose Test Missions/MEN - Menu Options/MEN-002 - Menu Coalition/MEN-002 - Menu Coalition.miz differ diff --git a/Moose Test Missions/MEN - Menu Options/MEN-003 - Menu Group/MEN-003 - Menu Group.miz b/Moose Test Missions/MEN - Menu Options/MEN-003 - Menu Group/MEN-003 - Menu Group.miz index 3dfe63edb..8322e8f62 100644 Binary files a/Moose Test Missions/MEN - Menu Options/MEN-003 - Menu Group/MEN-003 - Menu Group.miz and b/Moose Test Missions/MEN - Menu Options/MEN-003 - Menu Group/MEN-003 - Menu Group.miz differ diff --git a/Moose Test Missions/MIT - Missile Trainer/MIT-001 - Missile Trainer/MIT-001 - Missile Trainer.miz b/Moose Test Missions/MIT - Missile Trainer/MIT-001 - Missile Trainer/MIT-001 - Missile Trainer.miz index 4799b33f3..592dd05da 100644 Binary files a/Moose Test Missions/MIT - Missile Trainer/MIT-001 - Missile Trainer/MIT-001 - Missile Trainer.miz and b/Moose Test Missions/MIT - Missile Trainer/MIT-001 - Missile Trainer/MIT-001 - Missile Trainer.miz differ diff --git a/Moose Test Missions/MOOSE_Test_Template.miz b/Moose Test Missions/MOOSE_Test_Template.miz index c70a7fa0c..31b824c41 100644 Binary files a/Moose Test Missions/MOOSE_Test_Template.miz and b/Moose Test Missions/MOOSE_Test_Template.miz differ diff --git a/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.lua b/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.lua index 5d96265c3..0cbc54bdc 100644 --- a/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.lua +++ b/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.lua @@ -1,6 +1,6 @@ --- This test mission models the behaviour of the AI_PATROLZONE class. +-- This test mission models the behaviour of the AI_PATROL_ZONE class. -- --- It creates a 2 AI_PATROLZONE objects with the name Patrol1 and Patrol2. +-- It creates a 2 AI_PATROL_ZONE objects with the name Patrol1 and Patrol2. -- Patrol1 will govern a GROUP object to patrol the zone defined by PatrolZone1, within 3000 meters and 6000 meters, within a speed of 400 and 600 km/h. -- When the GROUP object that is assigned to Patrol has fuel below 20%, the GROUP object will orbit for 60 secondes, before returning to base. -- @@ -23,16 +23,16 @@ local PatrolZone2 = ZONE_POLYGON:New( "Patrol Zone 2", PatrolZoneGroup2 ) local PatrolSpawn = SPAWN:New( "Patrol Group" ) local PatrolGroup = PatrolSpawn:Spawn() -local Patrol1 = AI_PATROLZONE:New( PatrolZone1, 3000, 6000, 400, 600 ) +local Patrol1 = AI_PATROL_ZONE:New( PatrolZone1, 3000, 6000, 400, 600 ) Patrol1:ManageFuel( 0.2, 60 ) Patrol1:SetControllable( PatrolGroup ) Patrol1:__Start( 5 ) -local Patrol2 = AI_PATROLZONE:New( PatrolZone2, 600, 1000, 300, 400 ) +local Patrol2 = AI_PATROL_ZONE:New( PatrolZone2, 600, 1000, 300, 400 ) Patrol2:ManageFuel( 0.2, 0 ) --- State transition function for the PROCESS\_PATROLZONE **Patrol1** object --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Wrapper.Group#GROUP AIGroup -- @return #boolean If false is returned, then the OnAfter state transition function will not be called. function Patrol1:OnLeaveRTB( AIGroup ) @@ -40,7 +40,7 @@ function Patrol1:OnLeaveRTB( AIGroup ) end --- State transition function for the PROCESS\_PATROLZONE **Patrol1** object --- @param Process_PatrolCore.Zone#AI_PATROLZONE self +-- @param Process_PatrolCore.Zone#AI_PATROL_ZONE self -- @param Wrapper.Group#GROUP AIGroup function Patrol1:OnAfterRTB( AIGroup ) local NewGroup = PatrolSpawn:Spawn() @@ -49,14 +49,14 @@ function Patrol1:OnAfterRTB( AIGroup ) end --- State transition function for the PROCESS\_PATROLZONE **Patrol1** object --- @param Process_PatrolCore.Zone#AI_PATROLZONE self +-- @param Process_PatrolCore.Zone#AI_PATROL_ZONE self -- @param Wrapper.Group#GROUP AIGroup function Patrol1:OnEnterPatrol( AIGroup ) AIGroup:MessageToRed( "Patrolling in zone " .. PatrolZone1:GetName() , 20 ) end --- State transition function for the PROCESS\_PATROLZONE **Patrol2** object --- @param #AI_PATROLZONE self +-- @param #AI_PATROL_ZONE self -- @param Wrapper.Group#GROUP AIGroup -- @return #boolean If false is returned, then the OnEnter state transition function will not be called. function Patrol2:OnBeforeRTB( AIGroup ) @@ -64,7 +64,7 @@ function Patrol2:OnBeforeRTB( AIGroup ) end --- State transition function for the PROCESS\_PATROLZONE **Patrol2** object --- @param Process_PatrolCore.Zone#AI_PATROLZONE self +-- @param Process_PatrolCore.Zone#AI_PATROL_ZONE self -- @param Wrapper.Group#GROUP AIGroup function Patrol2:OnEnterRTB( AIGroup ) local NewGroup = PatrolSpawn:Spawn() @@ -73,7 +73,7 @@ function Patrol2:OnEnterRTB( AIGroup ) end --- State transition function for the PROCESS\_PATROLZONE **Patrol2** object --- @param Process_PatrolCore.Zone#AI_PATROLZONE self +-- @param Process_PatrolCore.Zone#AI_PATROL_ZONE self -- @param Wrapper.Group#GROUP AIGroup function Patrol2:OnEnterPatrol( AIGroup ) AIGroup:MessageToRed( "Patrolling in zone " .. PatrolZone2:GetName() , 20 ) diff --git a/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.miz b/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.miz index 7b16880de..7ce81baab 100644 Binary files a/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.miz and b/Moose Test Missions/PAT - Patrolling/PAT-001 - Switching Patrol Zones/PAT-001 - Switching Patrol Zones.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-000 - Simple Scheduling/SCH-000 - Simple Scheduling.miz b/Moose Test Missions/SCH - Scheduler/SCH-000 - Simple Scheduling/SCH-000 - Simple Scheduling.miz index f0ab4a64a..3ad072a39 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-000 - Simple Scheduling/SCH-000 - Simple Scheduling.miz and b/Moose Test Missions/SCH - Scheduler/SCH-000 - Simple Scheduling/SCH-000 - Simple Scheduling.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-001 - Simple Object Scheduling/SCH-001 - Simple Object Scheduling.miz b/Moose Test Missions/SCH - Scheduler/SCH-001 - Simple Object Scheduling/SCH-001 - Simple Object Scheduling.miz index 94f6aa9f3..c0d7d9922 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-001 - Simple Object Scheduling/SCH-001 - Simple Object Scheduling.miz and b/Moose Test Missions/SCH - Scheduler/SCH-001 - Simple Object Scheduling/SCH-001 - Simple Object Scheduling.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-100 - Simple Repeat Scheduling/SCH-100 - Simple Repeat Scheduling.miz b/Moose Test Missions/SCH - Scheduler/SCH-100 - Simple Repeat Scheduling/SCH-100 - Simple Repeat Scheduling.miz index 17bc5c039..08f643cb9 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-100 - Simple Repeat Scheduling/SCH-100 - Simple Repeat Scheduling.miz and b/Moose Test Missions/SCH - Scheduler/SCH-100 - Simple Repeat Scheduling/SCH-100 - Simple Repeat Scheduling.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-110 - Object Repeat Scheduling/SCH-110 - Object Repeat Scheduling.miz b/Moose Test Missions/SCH - Scheduler/SCH-110 - Object Repeat Scheduling/SCH-110 - Object Repeat Scheduling.miz index 85e09a0be..34db8ea48 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-110 - Object Repeat Scheduling/SCH-110 - Object Repeat Scheduling.miz and b/Moose Test Missions/SCH - Scheduler/SCH-110 - Object Repeat Scheduling/SCH-110 - Object Repeat Scheduling.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-200 - Simple Repeat Scheduling Stop and Start/SCH-200 - Simple Repeat Scheduling Stop and Start.miz b/Moose Test Missions/SCH - Scheduler/SCH-200 - Simple Repeat Scheduling Stop and Start/SCH-200 - Simple Repeat Scheduling Stop and Start.miz index e7206cfa0..1db4a1df9 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-200 - Simple Repeat Scheduling Stop and Start/SCH-200 - Simple Repeat Scheduling Stop and Start.miz and b/Moose Test Missions/SCH - Scheduler/SCH-200 - Simple Repeat Scheduling Stop and Start/SCH-200 - Simple Repeat Scheduling Stop and Start.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-300 - GC Simple Object Scheduling/SCH-300 - GC Simple Object Scheduling.miz b/Moose Test Missions/SCH - Scheduler/SCH-300 - GC Simple Object Scheduling/SCH-300 - GC Simple Object Scheduling.miz index d390ec35e..a3236fccc 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-300 - GC Simple Object Scheduling/SCH-300 - GC Simple Object Scheduling.miz and b/Moose Test Missions/SCH - Scheduler/SCH-300 - GC Simple Object Scheduling/SCH-300 - GC Simple Object Scheduling.miz differ diff --git a/Moose Test Missions/SCH - Scheduler/SCH-310 - GC Object Repeat Scheduling/SCH-310 - GC Object Repeat Scheduling.miz b/Moose Test Missions/SCH - Scheduler/SCH-310 - GC Object Repeat Scheduling/SCH-310 - GC Object Repeat Scheduling.miz index 6efefaefe..3bb2eaee7 100644 Binary files a/Moose Test Missions/SCH - Scheduler/SCH-310 - GC Object Repeat Scheduling/SCH-310 - GC Object Repeat Scheduling.miz and b/Moose Test Missions/SCH - Scheduler/SCH-310 - GC Object Repeat Scheduling/SCH-310 - GC Object Repeat Scheduling.miz differ diff --git a/Moose Test Missions/SET - Data Sets/SET-001 - Airbase Sets/SET-001 - Airbase Sets.miz b/Moose Test Missions/SET - Data Sets/SET-001 - Airbase Sets/SET-001 - Airbase Sets.miz index f8345655b..f4f865d13 100644 Binary files a/Moose Test Missions/SET - Data Sets/SET-001 - Airbase Sets/SET-001 - Airbase Sets.miz and b/Moose Test Missions/SET - Data Sets/SET-001 - Airbase Sets/SET-001 - Airbase Sets.miz differ diff --git a/Moose Test Missions/SET - Data Sets/SET-101 - Group Sets/SET-101 - Group Sets.miz b/Moose Test Missions/SET - Data Sets/SET-101 - Group Sets/SET-101 - Group Sets.miz index a7df8cc87..aa98512c0 100644 Binary files a/Moose Test Missions/SET - Data Sets/SET-101 - Group Sets/SET-101 - Group Sets.miz and b/Moose Test Missions/SET - Data Sets/SET-101 - Group Sets/SET-101 - Group Sets.miz differ diff --git a/Moose Test Missions/SET - Data Sets/SET-201 - Client Sets/SET-201 - Client Sets.miz b/Moose Test Missions/SET - Data Sets/SET-201 - Client Sets/SET-201 - Client Sets.miz index fc1fe90c5..5b70c77fd 100644 Binary files a/Moose Test Missions/SET - Data Sets/SET-201 - Client Sets/SET-201 - Client Sets.miz and b/Moose Test Missions/SET - Data Sets/SET-201 - Client Sets/SET-201 - Client Sets.miz differ diff --git a/Moose Test Missions/SEV - SEAD Evasion/SEV-001 - SEAD Evasion/SEV-001 - SEAD Evasion.miz b/Moose Test Missions/SEV - SEAD Evasion/SEV-001 - SEAD Evasion/SEV-001 - SEAD Evasion.miz index f73026097..3a5c951bb 100644 Binary files a/Moose Test Missions/SEV - SEAD Evasion/SEV-001 - SEAD Evasion/SEV-001 - SEAD Evasion.miz and b/Moose Test Missions/SEV - SEAD Evasion/SEV-001 - SEAD Evasion/SEV-001 - SEAD Evasion.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-010 - Spawn Demo/SPA-010 - Spawn Demo.miz b/Moose Test Missions/SPA - Spawning/SPA-010 - Spawn Demo/SPA-010 - Spawn Demo.miz index 44d150a21..f1a2bed6c 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-010 - Spawn Demo/SPA-010 - Spawn Demo.miz and b/Moose Test Missions/SPA - Spawning/SPA-010 - Spawn Demo/SPA-010 - Spawn Demo.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-011 - Ground Ops - Simple Spawning/SPA-011 - Ground Ops - Simple Spawning.miz b/Moose Test Missions/SPA - Spawning/SPA-011 - Ground Ops - Simple Spawning/SPA-011 - Ground Ops - Simple Spawning.miz index 2ca0aeb1a..77d59f731 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-011 - Ground Ops - Simple Spawning/SPA-011 - Ground Ops - Simple Spawning.miz and b/Moose Test Missions/SPA - Spawning/SPA-011 - Ground Ops - Simple Spawning/SPA-011 - Ground Ops - Simple Spawning.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-012 - Ground Ops - Multiple Spawns/SPA-012 - Ground Ops - Multiple Spawns.miz b/Moose Test Missions/SPA - Spawning/SPA-012 - Ground Ops - Multiple Spawns/SPA-012 - Ground Ops - Multiple Spawns.miz index 0053000a5..110dceb8f 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-012 - Ground Ops - Multiple Spawns/SPA-012 - Ground Ops - Multiple Spawns.miz and b/Moose Test Missions/SPA - Spawning/SPA-012 - Ground Ops - Multiple Spawns/SPA-012 - Ground Ops - Multiple Spawns.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-013 - Ground Ops - Scheduled Spawns/SPA-013 - Ground Ops - Scheduled Spawns.miz b/Moose Test Missions/SPA - Spawning/SPA-013 - Ground Ops - Scheduled Spawns/SPA-013 - Ground Ops - Scheduled Spawns.miz index 3586ae155..cf3bc2187 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-013 - Ground Ops - Scheduled Spawns/SPA-013 - Ground Ops - Scheduled Spawns.miz and b/Moose Test Missions/SPA - Spawning/SPA-013 - Ground Ops - Scheduled Spawns/SPA-013 - Ground Ops - Scheduled Spawns.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-014 - Ground Ops - Scheduled Spawns Limited/SPA-014 - Ground Ops - Scheduled Spawns Limited.miz b/Moose Test Missions/SPA - Spawning/SPA-014 - Ground Ops - Scheduled Spawns Limited/SPA-014 - Ground Ops - Scheduled Spawns Limited.miz index 2c3bda068..3f5f562b9 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-014 - Ground Ops - Scheduled Spawns Limited/SPA-014 - Ground Ops - Scheduled Spawns Limited.miz and b/Moose Test Missions/SPA - Spawning/SPA-014 - Ground Ops - Scheduled Spawns Limited/SPA-014 - Ground Ops - Scheduled Spawns Limited.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-015 - Ground Ops - Randomize Route/SPA-015 - Ground Ops - Randomize Route.miz b/Moose Test Missions/SPA - Spawning/SPA-015 - Ground Ops - Randomize Route/SPA-015 - Ground Ops - Randomize Route.miz index 457bca34b..2c4fe1adb 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-015 - Ground Ops - Randomize Route/SPA-015 - Ground Ops - Randomize Route.miz and b/Moose Test Missions/SPA - Spawning/SPA-015 - Ground Ops - Randomize Route/SPA-015 - Ground Ops - Randomize Route.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-016 - Ground Ops - Randomize Zones/SPA-016 - Ground Ops - Randomize Zones.miz b/Moose Test Missions/SPA - Spawning/SPA-016 - Ground Ops - Randomize Zones/SPA-016 - Ground Ops - Randomize Zones.miz index 5f91970d9..37f984464 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-016 - Ground Ops - Randomize Zones/SPA-016 - Ground Ops - Randomize Zones.miz and b/Moose Test Missions/SPA - Spawning/SPA-016 - Ground Ops - Randomize Zones/SPA-016 - Ground Ops - Randomize Zones.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-100 - CleanUp Inactive Units/SPA-100 - CleanUp Inactive Units.miz b/Moose Test Missions/SPA - Spawning/SPA-100 - CleanUp Inactive Units/SPA-100 - CleanUp Inactive Units.miz index 7f8eeada9..14b5c1234 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-100 - CleanUp Inactive Units/SPA-100 - CleanUp Inactive Units.miz and b/Moose Test Missions/SPA - Spawning/SPA-100 - CleanUp Inactive Units/SPA-100 - CleanUp Inactive Units.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-110 - Limit Spawning/SPA-110 - Limit Spawning.miz b/Moose Test Missions/SPA - Spawning/SPA-110 - Limit Spawning/SPA-110 - Limit Spawning.miz index ae52d0673..7ab9d16f5 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-110 - Limit Spawning/SPA-110 - Limit Spawning.miz and b/Moose Test Missions/SPA - Spawning/SPA-110 - Limit Spawning/SPA-110 - Limit Spawning.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-120 - Repeat Spawning/SPA-120 - Repeat Spawning.miz b/Moose Test Missions/SPA - Spawning/SPA-120 - Repeat Spawning/SPA-120 - Repeat Spawning.miz index e6761b5f3..bc6fcb145 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-120 - Repeat Spawning/SPA-120 - Repeat Spawning.miz and b/Moose Test Missions/SPA - Spawning/SPA-120 - Repeat Spawning/SPA-120 - Repeat Spawning.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-200 - Randomize Unit Types/SPA-200 - Randomize Unit Types.miz b/Moose Test Missions/SPA - Spawning/SPA-200 - Randomize Unit Types/SPA-200 - Randomize Unit Types.miz index 7dd75bfd9..6e5d59d14 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-200 - Randomize Unit Types/SPA-200 - Randomize Unit Types.miz and b/Moose Test Missions/SPA - Spawning/SPA-200 - Randomize Unit Types/SPA-200 - Randomize Unit Types.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-220 - Randomize Zones/SPA-220 - Randomize Zones.miz b/Moose Test Missions/SPA - Spawning/SPA-220 - Randomize Zones/SPA-220 - Randomize Zones.miz index 5b1afc834..62e0518c5 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-220 - Randomize Zones/SPA-220 - Randomize Zones.miz and b/Moose Test Missions/SPA - Spawning/SPA-220 - Randomize Zones/SPA-220 - Randomize Zones.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-310 - Spawn at Static position/SPA-310 - Spawn at Static position.miz b/Moose Test Missions/SPA - Spawning/SPA-310 - Spawn at Static position/SPA-310 - Spawn at Static position.miz index 54fab0006..16b472608 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-310 - Spawn at Static position/SPA-310 - Spawn at Static position.miz and b/Moose Test Missions/SPA - Spawning/SPA-310 - Spawn at Static position/SPA-310 - Spawn at Static position.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-320 - Spawn at Unit position/SPA-320 - Spawn at Unit position.miz b/Moose Test Missions/SPA - Spawning/SPA-320 - Spawn at Unit position/SPA-320 - Spawn at Unit position.miz index fddfe282f..b30e871b9 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-320 - Spawn at Unit position/SPA-320 - Spawn at Unit position.miz and b/Moose Test Missions/SPA - Spawning/SPA-320 - Spawn at Unit position/SPA-320 - Spawn at Unit position.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-330 - Spawn at Vec2 position/SPA-330 - Spawn at Vec2 position.miz b/Moose Test Missions/SPA - Spawning/SPA-330 - Spawn at Vec2 position/SPA-330 - Spawn at Vec2 position.miz index e267ab44d..a25aa52cc 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-330 - Spawn at Vec2 position/SPA-330 - Spawn at Vec2 position.miz and b/Moose Test Missions/SPA - Spawning/SPA-330 - Spawn at Vec2 position/SPA-330 - Spawn at Vec2 position.miz differ diff --git a/Moose Test Missions/SPA - Spawning/SPA-340 - Spawn at Vec3 position/SPA-340 - Spawn at Vec3 position.miz b/Moose Test Missions/SPA - Spawning/SPA-340 - Spawn at Vec3 position/SPA-340 - Spawn at Vec3 position.miz index 37ae077ae..de64be70e 100644 Binary files a/Moose Test Missions/SPA - Spawning/SPA-340 - Spawn at Vec3 position/SPA-340 - Spawn at Vec3 position.miz and b/Moose Test Missions/SPA - Spawning/SPA-340 - Spawn at Vec3 position/SPA-340 - Spawn at Vec3 position.miz differ diff --git a/Moose Test Missions/TAD - Task Dispatching/TAD-010 - Task Dispatching Demo/TAD-010 - Task Dispatching Demo.miz b/Moose Test Missions/TAD - Task Dispatching/TAD-010 - Task Dispatching Demo/TAD-010 - Task Dispatching Demo.miz index 9558f3d5d..91669ff65 100644 Binary files a/Moose Test Missions/TAD - Task Dispatching/TAD-010 - Task Dispatching Demo/TAD-010 - Task Dispatching Demo.miz and b/Moose Test Missions/TAD - Task Dispatching/TAD-010 - Task Dispatching Demo/TAD-010 - Task Dispatching Demo.miz differ diff --git a/Moose Test Missions/TSK - Task Modelling/TSK-010 - Task Modelling - SEAD/TSK-010 - Task Modelling - SEAD.miz b/Moose Test Missions/TSK - Task Modelling/TSK-010 - Task Modelling - SEAD/TSK-010 - Task Modelling - SEAD.miz index 3e5b66dc0..1b3d36c4a 100644 Binary files a/Moose Test Missions/TSK - Task Modelling/TSK-010 - Task Modelling - SEAD/TSK-010 - Task Modelling - SEAD.miz and b/Moose Test Missions/TSK - Task Modelling/TSK-010 - Task Modelling - SEAD/TSK-010 - Task Modelling - SEAD.miz differ diff --git a/Moose Test Missions/TSK - Task Modelling/TSK-020 - Task Modelling - Pickup/TSK-020 - Task Modelling - Pickup.miz b/Moose Test Missions/TSK - Task Modelling/TSK-020 - Task Modelling - Pickup/TSK-020 - Task Modelling - Pickup.miz index e1b5c53db..7a8b7692d 100644 Binary files a/Moose Test Missions/TSK - Task Modelling/TSK-020 - Task Modelling - Pickup/TSK-020 - Task Modelling - Pickup.miz and b/Moose Test Missions/TSK - Task Modelling/TSK-020 - Task Modelling - Pickup/TSK-020 - Task Modelling - Pickup.miz differ diff --git a/Moose Test Missions/ZON - Zones/ZON-100 - Normal Zone/ZON-100 - Normal Zone.miz b/Moose Test Missions/ZON - Zones/ZON-100 - Normal Zone/ZON-100 - Normal Zone.miz index 21465089e..e1e737483 100644 Binary files a/Moose Test Missions/ZON - Zones/ZON-100 - Normal Zone/ZON-100 - Normal Zone.miz and b/Moose Test Missions/ZON - Zones/ZON-100 - Normal Zone/ZON-100 - Normal Zone.miz differ diff --git a/Moose Test Missions/ZON - Zones/ZON-200 - Group Zone/ZON-200 - Group Zone.miz b/Moose Test Missions/ZON - Zones/ZON-200 - Group Zone/ZON-200 - Group Zone.miz index 29570cbc7..ee13b09d3 100644 Binary files a/Moose Test Missions/ZON - Zones/ZON-200 - Group Zone/ZON-200 - Group Zone.miz and b/Moose Test Missions/ZON - Zones/ZON-200 - Group Zone/ZON-200 - Group Zone.miz differ diff --git a/Moose Test Missions/ZON - Zones/ZON-300 - Unit Zone/ZON-300 - Unit Zone.miz b/Moose Test Missions/ZON - Zones/ZON-300 - Unit Zone/ZON-300 - Unit Zone.miz index 88b92cf1e..92133f436 100644 Binary files a/Moose Test Missions/ZON - Zones/ZON-300 - Unit Zone/ZON-300 - Unit Zone.miz and b/Moose Test Missions/ZON - Zones/ZON-300 - Unit Zone/ZON-300 - Unit Zone.miz differ diff --git a/Moose Test Missions/ZON - Zones/ZON-400 - Radius Zone/ZON-400 - Radius Zone.miz b/Moose Test Missions/ZON - Zones/ZON-400 - Radius Zone/ZON-400 - Radius Zone.miz index c8dc303e0..614c1b017 100644 Binary files a/Moose Test Missions/ZON - Zones/ZON-400 - Radius Zone/ZON-400 - Radius Zone.miz and b/Moose Test Missions/ZON - Zones/ZON-400 - Radius Zone/ZON-400 - Radius Zone.miz differ diff --git a/Moose Test Missions/ZON - Zones/ZON-500 - Polygon Zone/ZON-500 - Polygon Zone.miz b/Moose Test Missions/ZON - Zones/ZON-500 - Polygon Zone/ZON-500 - Polygon Zone.miz index 80994f343..ff9359079 100644 Binary files a/Moose Test Missions/ZON - Zones/ZON-500 - Polygon Zone/ZON-500 - Polygon Zone.miz and b/Moose Test Missions/ZON - Zones/ZON-500 - Polygon Zone/ZON-500 - Polygon Zone.miz differ diff --git a/docs/Documentation/AI_Balancer.html b/docs/Documentation/AI_Balancer.html index 048dbfbc2..02a4952eb 100644 --- a/docs/Documentation/AI_Balancer.html +++ b/docs/Documentation/AI_Balancer.html @@ -18,6 +18,9 @@
  • AI_Balancer
  • +
  • AI_Cap
  • +
  • AI_Cas
  • +
  • AI_Patrol
  • Account
  • Airbase
  • AirbasePolice
  • @@ -41,7 +44,6 @@
  • MissileTrainer
  • Mission
  • Object
  • -
  • Patrol
  • Point
  • Positionable
  • Process_JTAC
  • @@ -541,6 +543,12 @@ In order to keep the credibility of the the author, I want to emphasize that the

    Type POINT_VEC3.RoutePointAction

    + + + +
    POINT_VEC3.RoutePointAction.FromParkingArea +

    "From Parking Area"

    +
    POINT_VEC3.RoutePointAction.TurningPoint

    "Turning Point"

    @@ -561,6 +569,12 @@ In order to keep the credibility of the the author, I want to emphasize that the

    Type POINT_VEC3.RoutePointType

    + + + + + + + + @@ -425,6 +433,34 @@ The POSITIONABLE is not existing or alive.

    + +POSITIONABLE:GetPointVec3() + +
    +
    + +

    Returns a POINT_VEC3 object indicating the point in 3D of the POSITIONABLE within the mission.

    + +

    Return values

    +
      +
    1. + +

      Core.Point#POINT_VEC3: +The 3D point vector of the POSITIONABLE.

      + +
    2. +
    3. + +

      #nil: +The POSITIONABLE is not existing or alive.

      + +
    4. +
    +
    +
    +
    +
    + POSITIONABLE:GetPositionVec3() @@ -609,6 +645,9 @@ The POSITIONABLE is not existing or alive.

    Returns true if the POSITIONABLE is in the air.

    + +

    Polymorphic, is overridden in GROUP and UNIT.

    +

    Return values

    1. diff --git a/docs/Documentation/Process_JTAC.html b/docs/Documentation/Process_JTAC.html index b838cdfb0..194cee4de 100644 --- a/docs/Documentation/Process_JTAC.html +++ b/docs/Documentation/Process_JTAC.html @@ -18,6 +18,9 @@
    diff --git a/docs/Documentation/Static.html b/docs/Documentation/Static.html index a59aa4a26..4be12f0c8 100644 --- a/docs/Documentation/Static.html +++ b/docs/Documentation/Static.html @@ -18,6 +18,9 @@
    + + + + @@ -292,6 +300,12 @@ If you want to obtain the complete 3D position including ori� + + + + @@ -996,6 +1010,24 @@ The DCS Unit is not existing or alive.

    + +UNIT:GetUnits() + +
    +
    + +

    Returns the UNIT in a UNIT list of one element.

    + +

    Return value

    + +

    #list: +Wrapper.Unit#UNIT> The UNITs wrappers.

    + +
    +
    +
    +
    + UNIT:HasSEAD() @@ -1060,6 +1092,34 @@ The DCS Unit is not existing or alive.

    + +UNIT:InAir() + +
    +
    + +

    Returns true if the UNIT is in the air.

    + +

    Return values

    +
      +
    1. + +

      #boolean: +true if in the air.

      + +
    2. +
    3. + +

      #nil: +The UNIT is not existing or alive.

      + +
    4. +
    +
    +
    +
    +
    + UNIT:IsActive() @@ -1505,6 +1565,8 @@ The name of the DCS unit.

    +

    Type list

    + diff --git a/docs/Documentation/Utils.html b/docs/Documentation/Utils.html index 257221207..e0be30322 100644 --- a/docs/Documentation/Utils.html +++ b/docs/Documentation/Utils.html @@ -18,6 +18,9 @@
    + + + + + + + + + + + + @@ -107,7 +167,7 @@ @@ -210,12 +270,6 @@ - - - - diff --git a/docs/Documentation/routines.html b/docs/Documentation/routines.html index 01e4bbccc..f59f1eb4f 100644 --- a/docs/Documentation/routines.html +++ b/docs/Documentation/routines.html @@ -18,6 +18,9 @@
    • AI_Balancer
    • +
    • AI_Cap
    • +
    • AI_Cas
    • +
    • AI_Patrol
    • Account
    • Airbase
    • AirbasePolice
    • @@ -41,7 +44,6 @@
    • MissileTrainer
    • Mission
    • Object
    • -
    • Patrol
    • Point
    • Positionable
    • Process_JTAC
    • diff --git a/docs/Presentations/AI_CAP.pptx b/docs/Presentations/AI_CAP.pptx new file mode 100644 index 000000000..17395cd37 Binary files /dev/null and b/docs/Presentations/AI_CAP.pptx differ diff --git a/docs/Presentations/AI_CAP/Dia1.JPG b/docs/Presentations/AI_CAP/Dia1.JPG new file mode 100644 index 000000000..7b1c0d8dc Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia1.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia10.JPG b/docs/Presentations/AI_CAP/Dia10.JPG new file mode 100644 index 000000000..c49f26545 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia10.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia11.JPG b/docs/Presentations/AI_CAP/Dia11.JPG new file mode 100644 index 000000000..0e7e53142 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia11.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia12.JPG b/docs/Presentations/AI_CAP/Dia12.JPG new file mode 100644 index 000000000..b9c42741b Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia12.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia13.JPG b/docs/Presentations/AI_CAP/Dia13.JPG new file mode 100644 index 000000000..efedca7b0 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia13.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia14.JPG b/docs/Presentations/AI_CAP/Dia14.JPG new file mode 100644 index 000000000..2913091b7 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia14.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia2.JPG b/docs/Presentations/AI_CAP/Dia2.JPG new file mode 100644 index 000000000..1b1492d6c Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia2.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia3.JPG b/docs/Presentations/AI_CAP/Dia3.JPG new file mode 100644 index 000000000..f32e036c0 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia3.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia4.JPG b/docs/Presentations/AI_CAP/Dia4.JPG new file mode 100644 index 000000000..f3015fbeb Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia4.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia5.JPG b/docs/Presentations/AI_CAP/Dia5.JPG new file mode 100644 index 000000000..1fd33de78 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia5.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia6.JPG b/docs/Presentations/AI_CAP/Dia6.JPG new file mode 100644 index 000000000..c5024ddbf Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia6.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia7.JPG b/docs/Presentations/AI_CAP/Dia7.JPG new file mode 100644 index 000000000..fbf9987ad Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia7.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia8.JPG b/docs/Presentations/AI_CAP/Dia8.JPG new file mode 100644 index 000000000..ee0b36aba Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia8.JPG differ diff --git a/docs/Presentations/AI_CAP/Dia9.JPG b/docs/Presentations/AI_CAP/Dia9.JPG new file mode 100644 index 000000000..0c4760538 Binary files /dev/null and b/docs/Presentations/AI_CAP/Dia9.JPG differ diff --git a/docs/Presentations/AI_CAS.pptx b/docs/Presentations/AI_CAS.pptx new file mode 100644 index 000000000..07e718c00 Binary files /dev/null and b/docs/Presentations/AI_CAS.pptx differ diff --git a/docs/Presentations/AI_CAS/Dia1.JPG b/docs/Presentations/AI_CAS/Dia1.JPG new file mode 100644 index 000000000..0bf4c1e92 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia1.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia10.JPG b/docs/Presentations/AI_CAS/Dia10.JPG new file mode 100644 index 000000000..6e5096863 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia10.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia11.JPG b/docs/Presentations/AI_CAS/Dia11.JPG new file mode 100644 index 000000000..a236d65e2 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia11.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia12.JPG b/docs/Presentations/AI_CAS/Dia12.JPG new file mode 100644 index 000000000..bcf6d85ff Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia12.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia13.JPG b/docs/Presentations/AI_CAS/Dia13.JPG new file mode 100644 index 000000000..797dcbaf8 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia13.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia2.JPG b/docs/Presentations/AI_CAS/Dia2.JPG new file mode 100644 index 000000000..574ed5b9b Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia2.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia3.JPG b/docs/Presentations/AI_CAS/Dia3.JPG new file mode 100644 index 000000000..9bcc78a57 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia3.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia4.JPG b/docs/Presentations/AI_CAS/Dia4.JPG new file mode 100644 index 000000000..2cd22e14a Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia4.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia5.JPG b/docs/Presentations/AI_CAS/Dia5.JPG new file mode 100644 index 000000000..22f923f5c Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia5.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia6.JPG b/docs/Presentations/AI_CAS/Dia6.JPG new file mode 100644 index 000000000..668413e95 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia6.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia7.JPG b/docs/Presentations/AI_CAS/Dia7.JPG new file mode 100644 index 000000000..04d4abd9a Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia7.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia8.JPG b/docs/Presentations/AI_CAS/Dia8.JPG new file mode 100644 index 000000000..c1aebf592 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia8.JPG differ diff --git a/docs/Presentations/AI_CAS/Dia9.JPG b/docs/Presentations/AI_CAS/Dia9.JPG new file mode 100644 index 000000000..47845f382 Binary files /dev/null and b/docs/Presentations/AI_CAS/Dia9.JPG differ diff --git a/docs/Presentations/AI_PATROL.pptx b/docs/Presentations/AI_PATROL.pptx new file mode 100644 index 000000000..bf425bd57 Binary files /dev/null and b/docs/Presentations/AI_PATROL.pptx differ diff --git a/docs/Presentations/AI_PATROL/Dia1.JPG b/docs/Presentations/AI_PATROL/Dia1.JPG new file mode 100644 index 000000000..26bc14fe0 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia1.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia10.JPG b/docs/Presentations/AI_PATROL/Dia10.JPG new file mode 100644 index 000000000..63cee3a04 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia10.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia11.JPG b/docs/Presentations/AI_PATROL/Dia11.JPG new file mode 100644 index 000000000..cae7f2722 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia11.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia12.JPG b/docs/Presentations/AI_PATROL/Dia12.JPG new file mode 100644 index 000000000..851e5f161 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia12.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia2.JPG b/docs/Presentations/AI_PATROL/Dia2.JPG new file mode 100644 index 000000000..0227de5ed Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia2.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia3.JPG b/docs/Presentations/AI_PATROL/Dia3.JPG new file mode 100644 index 000000000..f32e036c0 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia3.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia4.JPG b/docs/Presentations/AI_PATROL/Dia4.JPG new file mode 100644 index 000000000..f3015fbeb Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia4.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia5.JPG b/docs/Presentations/AI_PATROL/Dia5.JPG new file mode 100644 index 000000000..1fd33de78 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia5.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia6.JPG b/docs/Presentations/AI_PATROL/Dia6.JPG new file mode 100644 index 000000000..a41920d1c Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia6.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia7.JPG b/docs/Presentations/AI_PATROL/Dia7.JPG new file mode 100644 index 000000000..55ee1a64b Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia7.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia8.JPG b/docs/Presentations/AI_PATROL/Dia8.JPG new file mode 100644 index 000000000..8c9155db4 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia8.JPG differ diff --git a/docs/Presentations/AI_PATROL/Dia9.JPG b/docs/Presentations/AI_PATROL/Dia9.JPG new file mode 100644 index 000000000..0c4760538 Binary files /dev/null and b/docs/Presentations/AI_PATROL/Dia9.JPG differ diff --git a/docs/Presentations/MOOSE.pptx b/docs/Presentations/MOOSE.pptx index bae85cf51..b9c40c706 100644 Binary files a/docs/Presentations/MOOSE.pptx and b/docs/Presentations/MOOSE.pptx differ
    POINT_VEC3.RoutePointType.TakeOffParking +

    "TakeOffParking"

    +
    POINT_VEC3.RoutePointType.TurningPoint

    "Turning Point"

    @@ -2097,6 +2111,19 @@ The new calculated POINT_VEC3.

    + +POINT_VEC3.RoutePointAction.FromParkingArea + +
    +
    + +

    "From Parking Area"

    + +
    +
    +
    +
    + POINT_VEC3.RoutePointAction.TurningPoint @@ -2135,6 +2162,19 @@ The new calculated POINT_VEC3.

    + +POINT_VEC3.RoutePointType.TakeOffParking + +
    +
    + +

    "TakeOffParking"

    + +
    +
    +
    +
    + POINT_VEC3.RoutePointType.TurningPoint diff --git a/docs/Documentation/Positionable.html b/docs/Documentation/Positionable.html index 64e64762c..a45df76af 100644 --- a/docs/Documentation/Positionable.html +++ b/docs/Documentation/Positionable.html @@ -18,6 +18,9 @@
    POSITIONABLE:GetPointVec2()

    Returns a POINT_VEC2 object indicating the point in 2D of the POSITIONABLE within the mission.

    +
    POSITIONABLE:GetPointVec3() +

    Returns a POINT_VEC3 object indicating the point in 3D of the POSITIONABLE within the mission.

    UNIT:GetThreatLevel()

    Returns the Unit's A2G threat level on a scale from 1 to 10 ...

    +
    UNIT:GetUnits() +

    Returns the UNIT in a UNIT list of one element.

    UNIT:HasSensors(...)

    Returns if the unit has sensors of a certain type.

    +
    UNIT:InAir() +

    Returns true if the UNIT is in the air.

    AI_Balancer -

    SP:N MP:Y AI:Y HU:N TYP:A -- This module contains the AI_BALANCER class.

    +

    Single-Player:No / Mulit-Player:Yes / AI:Yes / Human:No / Types:All -- AI Balancing will replace in multi player missions +non-occupied human slots with AI groups, in order to provide an engaging simulation environment, +even when there are hardly any players in the mission.

    + +

    Banner Image

    + + +
    + +

    1) AI.AIBalancer#AIBALANCER class, extends Core.Fsm#FSM_SET

    + +

    The AI.AIBalancer#AIBALANCER class monitors and manages as many replacement AI groups as there are +CLIENTS in a SET_CLIENT collection, which are not occupied by human players.

    +
    AI_Cap +

    Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Air -- Execute Combat Air Patrol (CAP).

    + +

    Banner Image

    + + +
    + +

    1) #AICAPZONE class, extends AI.AICap#AIPATROL_ZONE

    + +

    The #AICAPZONE class implements the core functions to patrol a Zone by an AI Controllable or Group +and automatically engage any airborne enemies that are within a certain range or within a certain zone.

    +
    AI_Cas +

    Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Air -- Provide Close Air Support to friendly ground troops.

    + +

    Banner Image

    + + +
    + +

    1) #AICASZONE class, extends AI.AIPatrol#AIPATROL_ZONE

    + +

    #AICASZONE derives from the AI.AIPatrol#AIPATROL_ZONE, inheriting its methods and behaviour.

    +
    AI_Patrol +

    Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Air -- Air Patrolling or Staging.

    + +

    Banner Image

    + + +
    + +

    1) #AIPATROLZONE class, extends Core.Fsm#FSM_CONTROLLABLE

    + +

    The #AIPATROLZONE class implements the core functions to patrol a Zone by an AI Controllable or Group.

    Cargo -

    Management of logical cargo objects, that can be transported from and to transportation carriers.

    +

    Single-Player:Yes / Mulit-Player:Yes / AI:Yes / Human:No / Types:Ground -- Management of logical cargo objects, that can be transported from and to transportation carriers.

    Object

    This module contains the OBJECT class.

    -
    Patrol -

    (AI) (FSM) Make AI patrol routes or zones.