Compare commits

...

59 Commits

Author SHA1 Message Date
Frank
28ae63bd8d Update Airboss.lua 2025-06-23 22:39:52 +02:00
Frank
42e7e3f94f Update Airboss.lua 2025-06-23 22:28:48 +02:00
Frank
24b47b02e0 AIRBOSS
- Essex
- Corsair
2025-06-22 22:29:52 +02:00
Applevangelist
cbcc893ce5 #CTLD - avoid smoking runways on airbase zones 2025-06-15 17:01:58 +02:00
Applevangelist
382b049c5f #AIRBASE - Syria and Sinai few names corrected 2025-06-15 15:38:12 +02:00
Thomas
a53763221c Update Airbase.lua
Correct afb name gor Borg al arab on Sinai
2025-06-15 13:14:05 +02:00
Thomas
b7bac28113 Merge pull request #2313 from FlightControl-Master/Applevangelist-patch-1
Update CSAR.lua
2025-06-15 10:18:01 +02:00
Thomas
a9edb16554 Update CSAR.lua
Make static and zone mash SETs dynamic
2025-06-15 10:17:32 +02:00
Applevangelist
0aeb1fc6af #UTILS - Small fix for GetReportingName to distinguish Shark from Mainstay 2025-06-10 18:05:02 +02:00
Applevangelist
eeeeda4e5e #POINT - Offset options for smoke 2025-06-08 18:43:01 +02:00
Applevangelist
f5881eda53 AIRBOSS - Remove useless E Messages for non-debug 2025-06-01 12:19:42 +02:00
Thomas
c1997d9f70 Merge pull request #2311 from FlightControl-Master/Applevangelist-patch-1
Update CSAR.lua
2025-05-30 18:37:50 +02:00
Thomas
bb1caa6642 Update CSAR.lua 2025-05-30 18:37:38 +02:00
Applevangelist
dd5ca93f26 CSAR Small addition 2025-05-30 11:13:50 +02:00
Thomas
1889df4952 Merge pull request #2308 from shaji-Dev/master
[FIXED] Velocity is taking into account dead units for GROUP
2025-05-25 09:12:04 +02:00
shaji
7ca219748d [FIXED] Velocity is taking into account dead units for GROUP 2025-05-24 19:46:20 +02:00
Applevangelist
2fc16ba694 Runway text duplication 2025-05-24 15:53:43 +02:00
Applevangelist
a4feafab8e #POINT - improved IsDay() for Kola 2025-05-21 10:21:48 +02:00
Applevangelist
997baf21a0 #CSAR fix for ADF beacons 2025-05-21 10:04:58 +02:00
Applevangelist
b126cc00d0 xx 2025-05-16 13:43:03 +02:00
Applevangelist
09b7922b84 Small fixes 2025-05-16 11:58:40 +02:00
Applevangelist
7a5b9a75f3 #AIRBASE - added Syria Marka AFB 2025-05-15 17:07:55 +02:00
Applevangelist
4bab2ee1de Add deprecated banner 2025-05-15 13:19:42 +02:00
Applevangelist
d7defe6f7f xx 2025-05-15 11:42:05 +02:00
Applevangelist
db869bcb6d #MANTIS - Make DLINK caching (DEV version) configureable 2025-05-15 08:51:30 +02:00
Thomas
ea4a1f9ff9 Merge pull request #2305 from shaji-Dev/master
[FIXED] Kola Airbase name "Alakourtti" to "Alakurtti"
2025-05-15 06:42:07 +02:00
shaji
20406e40ca [FIXED] Kola Airbase name "Alakourtti" to "Alakurtti" 2025-05-15 01:17:55 +02:00
Applevangelist
3b50fee5a0 #CTLD - extract troops, check for groupname in task properties of PLAYERTASKs, so the right people rescue the correct group 2025-05-12 17:50:37 +02:00
Applevangelist
804004198b #MANTIS - Update docu 2025-05-12 17:49:25 +02:00
Thomas
5b8b8a5566 Merge pull request #2303 from leka1986/master
Fix Line 77390: attempt to index local 'zonecoord' (a nil value)
2025-05-12 07:00:19 +02:00
leka1986
0468bacc0b Fix Line 77390: attempt to index local 'zonecoord' (a nil value) 2025-05-11 21:15:31 +02:00
Thomas
7eba1349ae Merge pull request #2301 from leka1986/master
VS Code pointed out some errors, like duplicated values in tables. This is first time I do changes through VS Code, Hope for the best
2025-05-04 10:47:28 +02:00
leka1986
b6074a4795 VS Code pointed out some errors, like duplicated values in tables. This is first time I do changes through VS Code, Hope for the best 2025-05-04 10:38:44 +02:00
Thomas
36c9f551d9 Merge pull request #2299 from leka1986/patch-3
Update CTLD.lua
2025-05-03 20:32:40 +02:00
leka1986
89c3f7310b Update CTLD.lua
Changed the naming from Get only to Get

and the order is Get, Get and load
Instead of Get and load, and Get only.

Changed the order on Pack and load, Pack and remove, pack only to 
Pack, Pack and load, Pack and remove.

Same goes for Drop and build, Drop only to Drop, Drop and build.

It purely subjective what one would like, so I leave it up to you. If you like it this way or the first version, you decide, then disregard this change.
2025-05-03 19:22:59 +02:00
Applevangelist
a6b622ed31 #CTLD - Additional features by Lekaa to drop and build one/many in one go and pack/load or get/load in one go 2025-05-03 17:01:02 +02:00
Frank
f1af3a50b8 Update Unit.lua
- GetAmmo HE shells can also be named "HESH"
2025-05-02 21:36:03 +02:00
Applevangelist
0c90e90c18 #CSAR - fixed design issue that prevented usage of ZONE objects as MASHes 2025-05-02 10:53:02 +02:00
Frank
f97ef25104 Update Unit.lua 2025-05-01 22:11:43 +02:00
Thomas
069c0aa03f Merge pull request #2297 from FlightControl-Master/Applevangelist-patch-1
Update CTLD.lua
2025-04-28 09:20:58 +02:00
Thomas
b145588ed5 Update CTLD.lua
Fix an issue when a ship is used as loading zone and the ship is destroyed
2025-04-28 09:20:04 +02:00
Applevangelist
3ad60a95ce #MANTIS - Adde Gepard data, made Roland Short 2025-04-27 11:25:46 +02:00
Frank
ac4b620f16 COORDINATE
- Improved Smoke and Fire and Smoke functions by adding delay and duration parameters
2025-04-26 23:39:22 +02:00
Thomas
ccada18a6a Merge pull request #2295 from leka1986/patch-2
Update CTLD.lua
2025-04-26 07:52:01 +02:00
leka1986
1547d66327 Update CTLD.lua
Getting rid of this error,
bad argument #1 to 'find' (string expected, got nil)
2025-04-26 03:28:16 +02:00
Thomas
8042e8bfaf Merge pull request #2293 from shaji-Dev/master
[ADDED] AIRBOSS:SetMaxSectionDistance
2025-04-23 14:21:31 +02:00
shaji
dd7b87e9cd [ADDED] AIRBOSS:SetMaxSectionDistance 2025-04-23 13:39:55 +02:00
Thomas
460d2768ff Merge pull request #2291 from FlightControl-Master/Applevangelist-patch-1
Update Range.lua
2025-04-23 09:03:54 +02:00
Thomas
3c74272749 Update Range.lua
#RANGE log an error if os/os.date() are not available
2025-04-23 09:00:05 +02:00
Thomas
82c409d77a Merge pull request #2289 from shaji-Dev/master
[ADDED] IsAlive condition for Unit and Group out message
2025-04-23 06:28:13 +02:00
shaji
195aac4504 [ADDED] IsAlive condition for Unit and Group out message 2025-04-22 20:57:06 +02:00
Thomas
08d8f3e25f Merge pull request #2285 from shaji-Dev/master
[ADDED] New Kola airbases
2025-04-21 19:37:22 +02:00
shaji
6f72697e26 [ADDED] New Kola airbases
-- * AIRBASE.Kola.Alta
-- * AIRBASE.Kola.Sodankyla
-- * AIRBASE.Kola.Enontekio
-- * AIRBASE.Kola.Evenes
-- * AIRBASE.Kola.Hosio
2025-04-21 19:11:22 +02:00
Applevangelist
0f6439cf9f #MANTIS - added C-RAM Point Defense 2025-04-20 17:49:25 +02:00
Frank
2c10943cb1 Update Airbase.lua
Germany map Umlaute
2025-04-18 17:50:01 +02:00
Frank
544db963ea Update Airbase.lua 2025-04-18 17:45:43 +02:00
Frank
207698a2dd Update Airbase.lua
- Germany map readded Umlaute in keys
2025-04-18 17:40:55 +02:00
Applevangelist
d1ae2c0f5e xx 2025-04-18 16:01:55 +02:00
Applevangelist
0392417189 Germany CW Bases 2025-04-18 14:46:13 +02:00
77 changed files with 1517 additions and 787 deletions

View File

@@ -1953,7 +1953,7 @@ local function refct_from_id(id) -- refct = refct_from_id(CTypeID)
unsigned = refct.unsigned, unsigned = refct.unsigned,
size = bit.band(bit.rshift(ctype.info, 16), 127), size = bit.band(bit.rshift(ctype.info, 16), 127),
} }
refct.bool, refct.const, refct.volatile, refct.unsigned = nil refct.bool, refct.const, refct.volatile, refct.unsigned = nil, nil, nil, nil
end end
if CT[4] then -- Merge sibling attributes onto this type. if CT[4] then -- Merge sibling attributes onto this type.

View File

@@ -18,6 +18,8 @@
--- The AI_A2A_CAP class implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Group} or @{Wrapper.Group} --- The AI_A2A_CAP class implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Group} or @{Wrapper.Group}
-- and automatically engage any airborne enemies that are within a certain range or within a certain zone. -- and automatically engage any airborne enemies that are within a certain range or within a certain zone.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ![Process](..\Presentations\AI_CAP\Dia3.JPG) -- ![Process](..\Presentations\AI_CAP\Dia3.JPG)
-- --
-- The AI_A2A_CAP is assigned a @{Wrapper.Group} and this must be done before the AI_A2A_CAP process can be started using the **Start** event. -- The AI_A2A_CAP is assigned a @{Wrapper.Group} and this must be done before the AI_A2A_CAP process can be started using the **Start** event.

View File

@@ -33,6 +33,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # QUICK START GUIDE -- # QUICK START GUIDE
-- --
-- There are basically two classes available to model an A2A defense system. -- There are basically two classes available to model an A2A defense system.

View File

@@ -19,6 +19,8 @@
--- Implements the core functions to intercept intruders. Use the Engage trigger to intercept intruders. --- Implements the core functions to intercept intruders. Use the Engage trigger to intercept intruders.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The AI_A2A_GCI is assigned a @{Wrapper.Group} and this must be done before the AI_A2A_GCI process can be started using the **Start** event. -- The AI_A2A_GCI is assigned a @{Wrapper.Group} and this must be done before the AI_A2A_GCI process can be started using the **Start** event.
-- --
-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. -- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits.

View File

@@ -15,6 +15,8 @@
--- Implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Group} or @{Wrapper.Group}. --- Implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Group} or @{Wrapper.Group}.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ![Process](..\Presentations\AI_PATROL\Dia3.JPG) -- ![Process](..\Presentations\AI_PATROL\Dia3.JPG)
-- --
-- The AI_A2A_PATROL is assigned a @{Wrapper.Group} and this must be done before the AI_A2A_PATROL process can be started using the **Start** event. -- The AI_A2A_PATROL is assigned a @{Wrapper.Group} and this must be done before the AI_A2A_PATROL process can be started using the **Start** event.

View File

@@ -17,6 +17,8 @@
--- Implements the core functions to intercept intruders. Use the Engage trigger to intercept intruders. --- Implements the core functions to intercept intruders. Use the Engage trigger to intercept intruders.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # Developer Note -- # Developer Note
-- --
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE

View File

@@ -19,6 +19,8 @@
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE
-- Therefore, this class is considered to be deprecated -- Therefore, this class is considered to be deprecated
-- --

View File

@@ -36,6 +36,8 @@
-- --
-- # QUICK START GUIDE -- # QUICK START GUIDE
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The following class is available to model an A2G defense system. -- The following class is available to model an A2G defense system.
-- --
-- AI_A2G_DISPATCHER is the main A2G defense class that models the A2G defense system. -- AI_A2G_DISPATCHER is the main A2G defense class that models the A2G defense system.

View File

@@ -20,6 +20,8 @@
--- Implements the core functions to SEAD intruders. Use the Engage trigger to intercept intruders. --- Implements the core functions to SEAD intruders. Use the Engage trigger to intercept intruders.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The AI_A2G_SEAD is assigned a @{Wrapper.Group} and this must be done before the AI_A2G_SEAD process can be started using the **Start** event. -- The AI_A2G_SEAD is assigned a @{Wrapper.Group} and this must be done before the AI_A2G_SEAD process can be started using the **Start** event.
-- --
-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. -- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits.

View File

@@ -15,6 +15,7 @@
--- The AI_AIR class implements the core functions to operate an AI @{Wrapper.Group}. --- The AI_AIR class implements the core functions to operate an AI @{Wrapper.Group}.
-- --
-- ![Banner Image](..\Images\deprecated.png)
-- --
-- # 1) AI_AIR constructor -- # 1) AI_AIR constructor
-- --

View File

@@ -36,6 +36,8 @@
-- --
-- # QUICK START GUIDE -- # QUICK START GUIDE
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The following class is available to model an AIR defense system. -- The following class is available to model an AIR defense system.
-- --
-- AI_AIR_DISPATCHER is the main AIR defense class that models the AIR defense system. -- AI_AIR_DISPATCHER is the main AIR defense class that models the AIR defense system.

View File

@@ -13,12 +13,14 @@
-- @type AI_AIR_ENGAGE --- @type AI_AIR_ENGAGE
-- @extends AI.AI_AIR#AI_AIR -- @extends AI.AI_AIR#AI_AIR
--- Implements the core functions to intercept intruders. Use the Engage trigger to intercept intruders. --- Implements the core functions to intercept intruders. Use the Engage trigger to intercept intruders.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The AI_AIR_ENGAGE is assigned a @{Wrapper.Group} and this must be done before the AI_AIR_ENGAGE process can be started using the **Start** event. -- The AI_AIR_ENGAGE is assigned a @{Wrapper.Group} and this must be done before the AI_AIR_ENGAGE process can be started using the **Start** event.
-- --
-- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits. -- The AI will fly towards the random 3D point within the patrol zone, using a random speed within the given altitude and speed limits.

View File

@@ -15,6 +15,8 @@
--- The AI_AIR_PATROL class implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Group} --- The AI_AIR_PATROL class implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Group}
-- and automatically engage any airborne enemies that are within a certain range or within a certain zone. -- and automatically engage any airborne enemies that are within a certain range or within a certain zone.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ![Process](..\Presentations\AI_CAP\Dia3.JPG) -- ![Process](..\Presentations\AI_CAP\Dia3.JPG)
-- --
-- The AI_AIR_PATROL is assigned a @{Wrapper.Group} and this must be done before the AI_AIR_PATROL process can be started using the **Start** event. -- The AI_AIR_PATROL is assigned a @{Wrapper.Group} and this must be done before the AI_AIR_PATROL process can be started using the **Start** event.

View File

@@ -13,7 +13,7 @@
-- @type AI_AIR_SQUADRON --- @type AI_AIR_SQUADRON
-- @extends Core.Base#BASE -- @extends Core.Base#BASE
@@ -21,6 +21,8 @@
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE
-- Therefore, this class is considered to be deprecated -- Therefore, this class is considered to be deprecated
-- --

View File

@@ -38,6 +38,8 @@
--- Implements the core functions to provide BattleGround Air Interdiction in an Engage @{Core.Zone} by an AIR @{Wrapper.Controllable} or @{Wrapper.Group}. --- Implements the core functions to provide BattleGround Air Interdiction in an Engage @{Core.Zone} by an AIR @{Wrapper.Controllable} or @{Wrapper.Group}.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The AI_BAI_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. -- The AI_BAI_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_BAI\Dia3.JPG) -- ![HoldAndEngage](..\Presentations\AI_BAI\Dia3.JPG)

View File

@@ -33,8 +33,9 @@
-- @field Wrapper.Group#GROUP Test -- @field Wrapper.Group#GROUP Test
-- @extends Core.Fsm#FSM_SET -- @extends Core.Fsm#FSM_SET
--- ![Banner Image](..\Images\deprecated.png)
--- Monitors and manages as many replacement AI groups as there are --
-- Monitors and manages as many replacement AI groups as there are
-- CLIENTS in a SET\_CLIENT collection, which are not occupied by human players. -- CLIENTS in a SET\_CLIENT collection, which are not occupied by human players.
-- In other words, use AI_BALANCER to simulate human behaviour by spawning in replacement AI in multi player missions. -- In other words, use AI_BALANCER to simulate human behaviour by spawning in replacement AI in multi player missions.
-- --

View File

@@ -39,6 +39,8 @@
--- Implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Controllable} or @{Wrapper.Group} --- Implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Controllable} or @{Wrapper.Group}
-- and automatically engage any airborne enemies that are within a certain range or within a certain zone. -- and automatically engage any airborne enemies that are within a certain range or within a certain zone.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ![Process](..\Presentations\AI_CAP\Dia3.JPG) -- ![Process](..\Presentations\AI_CAP\Dia3.JPG)
-- --
-- The AI_CAP_ZONE is assigned a @{Wrapper.Group} and this must be done before the AI_CAP_ZONE process can be started using the **Start** event. -- The AI_CAP_ZONE is assigned a @{Wrapper.Group} and this must be done before the AI_CAP_ZONE process can be started using the **Start** event.

View File

@@ -38,6 +38,9 @@
-- @extends AI.AI_Patrol#AI_PATROL_ZONE -- @extends AI.AI_Patrol#AI_PATROL_ZONE
--- Implements the core functions to provide Close Air Support in an Engage @{Core.Zone} by an AIR @{Wrapper.Controllable} or @{Wrapper.Group}. --- Implements the core functions to provide Close Air Support in an Engage @{Core.Zone} by an AIR @{Wrapper.Controllable} or @{Wrapper.Group}.
--
-- ![Banner Image](..\Images\deprecated.png)
--
-- 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. -- 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) -- ![HoldAndEngage](..\Presentations\AI_CAS\Dia3.JPG)

View File

@@ -9,12 +9,14 @@
-- @module AI.AI_Cargo -- @module AI.AI_Cargo
-- @image Cargo.JPG -- @image Cargo.JPG
-- @type AI_CARGO --- @type AI_CARGO
-- @extends Core.Fsm#FSM_CONTROLLABLE -- @extends Core.Fsm#FSM_CONTROLLABLE
--- Base class for the dynamic cargo handling capability for AI groups. --- Base class for the dynamic cargo handling capability for AI groups.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Carriers can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Carriers can be mobilized to intelligently transport infantry and other cargo within the simulation.
-- The AI_CARGO module uses the @{Cargo.Cargo} capabilities within the MOOSE framework. -- The AI_CARGO module uses the @{Cargo.Cargo} capabilities within the MOOSE framework.
-- CARGO derived objects must be declared within the mission to make the AI_CARGO object recognize the cargo. -- CARGO derived objects must be declared within the mission to make the AI_CARGO object recognize the cargo.

View File

@@ -15,6 +15,8 @@
--- Brings a dynamic cargo handling capability for an AI vehicle group. --- Brings a dynamic cargo handling capability for an AI vehicle group.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Armoured Personnel Carriers (APC), Trucks, Jeeps and other ground based carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Armoured Personnel Carriers (APC), Trucks, Jeeps and other ground based carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation.
-- --
-- The AI_CARGO_APC class uses the @{Cargo.Cargo} capabilities within the MOOSE framework. -- The AI_CARGO_APC class uses the @{Cargo.Cargo} capabilities within the MOOSE framework.

View File

@@ -15,6 +15,8 @@
--- Brings a dynamic cargo handling capability for an AI airplane group. --- Brings a dynamic cargo handling capability for an AI airplane group.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Airplane carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation between airbases. -- Airplane carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation between airbases.
-- --
-- The AI_CARGO_AIRPLANE module uses the @{Cargo.Cargo} capabilities within the MOOSE framework. -- The AI_CARGO_AIRPLANE module uses the @{Cargo.Cargo} capabilities within the MOOSE framework.

View File

@@ -22,6 +22,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # The dispatcher concept. -- # The dispatcher concept.
-- --
-- Carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation.

View File

@@ -36,6 +36,8 @@
--- A dynamic cargo transportation capability for AI groups. --- A dynamic cargo transportation capability for AI groups.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Armoured Personnel APCs (APC), Trucks, Jeeps and other carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Armoured Personnel APCs (APC), Trucks, Jeeps and other carrier equipment can be mobilized to intelligently transport infantry and other cargo within the simulation.
-- --
-- The AI_CARGO_DISPATCHER_APC module is derived from the AI_CARGO_DISPATCHER module. -- The AI_CARGO_DISPATCHER_APC module is derived from the AI_CARGO_DISPATCHER module.

View File

@@ -30,6 +30,8 @@
--- Brings a dynamic cargo handling capability for AI groups. --- Brings a dynamic cargo handling capability for AI groups.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Airplanes can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Airplanes can be mobilized to intelligently transport infantry and other cargo within the simulation.
-- --
-- The AI_CARGO_DISPATCHER_AIRPLANE module is derived from the AI_CARGO_DISPATCHER module. -- The AI_CARGO_DISPATCHER_AIRPLANE module is derived from the AI_CARGO_DISPATCHER module.

View File

@@ -31,6 +31,8 @@
--- A dynamic cargo handling capability for AI helicopter groups. --- A dynamic cargo handling capability for AI helicopter groups.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Helicopters can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Helicopters can be mobilized to intelligently transport infantry and other cargo within the simulation.
-- --
-- --

View File

@@ -29,6 +29,8 @@
--- A dynamic cargo transportation capability for AI groups. --- A dynamic cargo transportation capability for AI groups.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Naval vessels can be mobilized to semi-intelligently transport cargo within the simulation. -- Naval vessels can be mobilized to semi-intelligently transport cargo within the simulation.
-- --
-- The AI_CARGO_DISPATCHER_SHIP module is derived from the AI_CARGO_DISPATCHER module. -- The AI_CARGO_DISPATCHER_SHIP module is derived from the AI_CARGO_DISPATCHER module.

View File

@@ -15,6 +15,8 @@
--- Brings a dynamic cargo handling capability for an AI helicopter group. --- Brings a dynamic cargo handling capability for an AI helicopter group.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Helicopter carriers can be mobilized to intelligently transport infantry and other cargo within the simulation. -- Helicopter carriers can be mobilized to intelligently transport infantry and other cargo within the simulation.
-- --
-- The AI_CARGO_HELICOPTER class uses the @{Cargo.Cargo} capabilities within the MOOSE framework. -- The AI_CARGO_HELICOPTER class uses the @{Cargo.Cargo} capabilities within the MOOSE framework.

View File

@@ -14,6 +14,8 @@
--- Brings a dynamic cargo handling capability for an AI naval group. --- Brings a dynamic cargo handling capability for an AI naval group.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Naval ships can be utilized to transport cargo around the map following naval shipping lanes. -- Naval ships can be utilized to transport cargo around the map following naval shipping lanes.
-- The AI_CARGO_SHIP class uses the @{Cargo.Cargo} capabilities within the MOOSE framework. -- The AI_CARGO_SHIP class uses the @{Cargo.Cargo} capabilities within the MOOSE framework.
-- @{Cargo.Cargo} must be declared within the mission or warehouse to make the AI_CARGO_SHIP recognize the cargo. -- @{Cargo.Cargo} must be declared within the mission or warehouse to make the AI_CARGO_SHIP recognize the cargo.

View File

@@ -25,6 +25,8 @@
-- --
-- Allows you to interact with escorting AI on your flight and take the lead. -- Allows you to interact with escorting AI on your flight and take the lead.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Each escorting group can be commanded with a complete set of radio commands (radio menu in your flight, and then F10). -- Each escorting group can be commanded with a complete set of radio commands (radio menu in your flight, and then F10).
-- --
-- The radio commands will vary according the category of the group. The richest set of commands are with helicopters and airPlanes. -- The radio commands will vary according the category of the group. The richest set of commands are with helicopters and airPlanes.

View File

@@ -23,6 +23,8 @@
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE
-- Therefore, this class is considered to be deprecated -- Therefore, this class is considered to be deprecated
-- --

View File

@@ -21,6 +21,8 @@
--- Models the assignment of AI escorts to player flights upon request using the radio menu. --- Models the assignment of AI escorts to player flights upon request using the radio menu.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # Developer Note -- # Developer Note
-- --
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE

View File

@@ -25,6 +25,8 @@
-- --
-- Allows you to interact with escorting AI on your flight and take the lead. -- Allows you to interact with escorting AI on your flight and take the lead.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Each escorting group can be commanded with a complete set of radio commands (radio menu in your flight, and then F10). -- Each escorting group can be commanded with a complete set of radio commands (radio menu in your flight, and then F10).
-- --
-- The radio commands will vary according the category of the group. The richest set of commands are with helicopters and airPlanes. -- The radio commands will vary according the category of the group. The richest set of commands are with helicopters and airPlanes.

View File

@@ -41,6 +41,8 @@
--- Build large formations, make AI follow a @{Wrapper.Client#CLIENT} (player) leader or a @{Wrapper.Unit#UNIT} (AI) leader. --- Build large formations, make AI follow a @{Wrapper.Client#CLIENT} (player) leader or a @{Wrapper.Unit#UNIT} (AI) leader.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- AI_FORMATION makes AI @{Wrapper.Group#GROUP}s fly in formation of various compositions. -- AI_FORMATION makes AI @{Wrapper.Group#GROUP}s fly in formation of various compositions.
-- The AI_FORMATION class models formations in a different manner than the internal DCS formation logic!!! -- The AI_FORMATION class models formations in a different manner than the internal DCS formation logic!!!
-- The purpose of the class is to: -- The purpose of the class is to:
@@ -158,7 +160,6 @@ AI_FORMATION.__Enum.Mode = {
-- @field #number GroundRadar -- @field #number GroundRadar
-- @field #number Ground -- @field #number Ground
AI_FORMATION.__Enum.ReportType = { AI_FORMATION.__Enum.ReportType = {
Airborne = "*",
Airborne = "A", Airborne = "A",
GroundRadar = "R", GroundRadar = "R",
Ground = "G", Ground = "G",
@@ -1222,7 +1223,6 @@ function AI_FORMATION:FollowMe(FollowGroup, ClientUnit, CT1, CV1, CT2, CV2)
local CVI = { local CVI = {
x = CV2.x + CS * 10 * math.sin(Ca), x = CV2.x + CS * 10 * math.sin(Ca),
y = GH2.y + Inclination, -- + FollowFormation.y, y = GH2.y + Inclination, -- + FollowFormation.y,
y = GH2.y,
z = CV2.z + CS * 10 * math.cos(Ca), z = CV2.z + CS * 10 * math.cos(Ca),
} }

View File

@@ -48,6 +48,8 @@
--- Implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Controllable} or @{Wrapper.Group}. --- Implements the core functions to patrol a @{Core.Zone} by an AI @{Wrapper.Controllable} or @{Wrapper.Group}.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ![Process](..\Presentations\AI_PATROL\Dia3.JPG) -- ![Process](..\Presentations\AI_PATROL\Dia3.JPG)
-- --
-- The AI_PATROL_ZONE is assigned a @{Wrapper.Group} and this must be done before the AI_PATROL_ZONE process can be started using the **Start** event. -- The AI_PATROL_ZONE is assigned a @{Wrapper.Group} and this must be done before the AI_PATROL_ZONE process can be started using the **Start** event.

View File

@@ -1,6 +1,6 @@
--- **Actions** - ACT_ACCOUNT_ classes **account for** (detect, count & report) various DCS events occurring on UNITs. --- **Actions** - ACT_ACCOUNT_ classes **account for** (detect, count & report) various DCS events occurring on UNITs.
-- --
-- ![Banner Image](..\Presentations\ACT_ACCOUNT\Dia1.JPG) -- ![Banner Image](..\Images\deprecated.png)
-- --
-- === -- ===
-- --
@@ -11,6 +11,8 @@ do -- ACT_ACCOUNT
--- # @{#ACT_ACCOUNT} FSM class, extends @{Core.Fsm#FSM_PROCESS} --- # @{#ACT_ACCOUNT} FSM class, extends @{Core.Fsm#FSM_PROCESS}
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ## ACT_ACCOUNT state machine: -- ## ACT_ACCOUNT state machine:
-- --
-- This class is a state machine: it manages a process that is triggered by events causing state transitions to occur. -- This class is a state machine: it manages a process that is triggered by events causing state transitions to occur.
@@ -133,7 +135,7 @@ do -- ACT_ACCOUNT
-- @param #string Event -- @param #string Event
-- @param #string From -- @param #string From
-- @param #string To -- @param #string To
function ACT_ACCOUNT:onafterEvent( ProcessUnit, From, Event, To, Event ) function ACT_ACCOUNT:onafterEvent( ProcessUnit, From, Event, To )
self:__NoMore( 1 ) self:__NoMore( 1 )
end end

View File

@@ -2,6 +2,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # @{#ACT_ASSIGN} FSM template class, extends @{Core.Fsm#FSM_PROCESS} -- # @{#ACT_ASSIGN} FSM template class, extends @{Core.Fsm#FSM_PROCESS}
-- --
-- ## ACT_ASSIGN state machine: -- ## ACT_ASSIGN state machine:

View File

@@ -1,5 +1,6 @@
--- (SP) (MP) (FSM) Route AI or players through waypoints or to zones. --- (SP) (MP) (FSM) Route AI or players through waypoints or to zones.
-- --
-- ![Banner Image](..\Images\deprecated.png)
-- ## ACT_ASSIST state machine: -- ## ACT_ASSIST state machine:
-- --
-- This class is a state machine: it manages a process that is triggered by events causing state transitions to occur. -- This class is a state machine: it manages a process that is triggered by events causing state transitions to occur.

View File

@@ -2,6 +2,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # @{#ACT_ROUTE} FSM class, extends @{Core.Fsm#FSM_PROCESS} -- # @{#ACT_ROUTE} FSM class, extends @{Core.Fsm#FSM_PROCESS}
-- --
-- ## ACT_ROUTE state machine: -- ## ACT_ROUTE state machine:

View File

@@ -2,6 +2,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # 1) MOOSE Cargo System. -- # 1) MOOSE Cargo System.
-- --
-- #### Those who have used the mission editor, know that the DCS mission editor provides cargo facilities. -- #### Those who have used the mission editor, know that the DCS mission editor provides cargo facilities.

View File

@@ -22,6 +22,9 @@ do -- CARGO_CRATE
-- @type CARGO_CRATE -- @type CARGO_CRATE
-- @extends Cargo.Cargo#CARGO_REPRESENTABLE -- @extends Cargo.Cargo#CARGO_REPRESENTABLE
---
-- ![Banner Image](..\Images\deprecated.png)
--
--- Defines a cargo that is represented by a UNIT object within the simulator, and can be transported by a carrier. --- Defines a cargo that is represented by a UNIT object within the simulator, and can be transported by a carrier.
-- Use the event functions as described above to Load, UnLoad, Board, UnBoard the CARGO\_CRATE objects to and from carriers. -- Use the event functions as described above to Load, UnLoad, Board, UnBoard the CARGO\_CRATE objects to and from carriers.
-- --

View File

@@ -26,6 +26,8 @@ do -- CARGO_GROUP
-- @extends Cargo.Cargo#CARGO_REPORTABLE -- @extends Cargo.Cargo#CARGO_REPORTABLE
--- Defines a cargo that is represented by a @{Wrapper.Group} object within the simulator. --- Defines a cargo that is represented by a @{Wrapper.Group} object within the simulator.
--
-- ![Banner Image](..\Images\deprecated.png)
-- The cargo can be Loaded, UnLoaded, Boarded, UnBoarded to and from Carriers. -- The cargo can be Loaded, UnLoaded, Boarded, UnBoarded to and from Carriers.
-- --
-- The above cargo classes are used by the following AI_CARGO_ classes to allow AI groups to transport cargo: -- The above cargo classes are used by the following AI_CARGO_ classes to allow AI groups to transport cargo:

View File

@@ -32,6 +32,8 @@ do -- CARGO_SLINGLOAD
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE
-- Therefore, this class is considered to be deprecated -- Therefore, this class is considered to be deprecated
-- --

View File

@@ -30,6 +30,8 @@ do -- CARGO_UNIT
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE
-- Therefore, this class is considered to be deprecated -- Therefore, this class is considered to be deprecated
-- --

View File

@@ -974,7 +974,7 @@ do -- Scheduling
-- @param #BASE self -- @param #BASE self
-- @param #number Start Specifies the amount of seconds that will be waited before the scheduling is started, and the event function is called. -- @param #number Start Specifies the amount of seconds that will be waited before the scheduling is started, and the event function is called.
-- @param #function SchedulerFunction The event function to be called when a timer event occurs. The event function needs to accept the parameters specified in SchedulerArguments. -- @param #function SchedulerFunction The event function to be called when a timer event occurs. The event function needs to accept the parameters specified in SchedulerArguments.
-- @param #table ... Optional arguments that can be given as part of scheduler. The arguments need to be given as a table { param1, param 2, ... }. -- @param ... Optional arguments that can be given as part of scheduler. The arguments need to be given as a table { param1, param 2, ... }.
-- @return #string The Schedule ID of the planned schedule. -- @return #string The Schedule ID of the planned schedule.
function BASE:ScheduleOnce( Start, SchedulerFunction, ... ) function BASE:ScheduleOnce( Start, SchedulerFunction, ... )

View File

@@ -872,6 +872,8 @@ end
-- @return Wrapper.Group#GROUP The found GROUP. -- @return Wrapper.Group#GROUP The found GROUP.
function DATABASE:FindGroup( GroupName ) function DATABASE:FindGroup( GroupName )
if type(GroupName) ~= "string" or GroupName == "" then return end
local GroupFound = self.GROUPS[GroupName] local GroupFound = self.GROUPS[GroupName]
if GroupFound == nil and GroupName ~= nil and self.Templates.Groups[GroupName] == nil then if GroupFound == nil and GroupName ~= nil and self.Templates.Groups[GroupName] == nil then
@@ -1697,7 +1699,7 @@ function DATABASE:_EventOnBirth( Event )
if PlayerName then if PlayerName then
-- Debug info. -- Debug info.
self:I(string.format("Player '%s' joined unit '%s' of group '%s'", tostring(PlayerName), tostring(Event.IniDCSUnitName), tostring(Event.IniDCSGroupName))) self:I(string.format("Player '%s' joined unit '%s' (%s) of group '%s'", tostring(PlayerName), tostring(Event.IniDCSUnitName), tostring(Event.IniTypeName), tostring(Event.IniDCSGroupName)))
-- Add client in case it does not exist already. -- Add client in case it does not exist already.
if client == nil or (client and client:CountPlayers() == 0) then if client == nil or (client and client:CountPlayers() == 0) then

View File

@@ -206,7 +206,7 @@ end
function MESSAGE:ToGroup( Group, Settings ) function MESSAGE:ToGroup( Group, Settings )
self:F( Group.GroupName ) self:F( Group.GroupName )
if Group then if Group and Group:IsAlive() then
if self.MessageType then if self.MessageType then
local Settings = Settings or (Group and _DATABASE:GetPlayerSettings( Group:GetPlayerName() )) or _SETTINGS -- Core.Settings#SETTINGS local Settings = Settings or (Group and _DATABASE:GetPlayerSettings( Group:GetPlayerName() )) or _SETTINGS -- Core.Settings#SETTINGS
@@ -231,7 +231,7 @@ end
function MESSAGE:ToUnit( Unit, Settings ) function MESSAGE:ToUnit( Unit, Settings )
self:F( Unit.IdentifiableName ) self:F( Unit.IdentifiableName )
if Unit then if Unit and Unit:IsAlive() then
if self.MessageType then if self.MessageType then
local Settings = Settings or ( Unit and _DATABASE:GetPlayerSettings( Unit:GetPlayerName() ) ) or _SETTINGS -- Core.Settings#SETTINGS local Settings = Settings or ( Unit and _DATABASE:GetPlayerSettings( Unit:GetPlayerName() ) ) or _SETTINGS -- Core.Settings#SETTINGS

View File

@@ -25,7 +25,7 @@
do -- COORDINATE do -- COORDINATE
--- --- Coordinate class
-- @type COORDINATE -- @type COORDINATE
-- @field #string ClassName Name of the class -- @field #string ClassName Name of the class
-- @field #number x Component of the 3D vector. -- @field #number x Component of the 3D vector.
@@ -59,6 +59,10 @@ do -- COORDINATE
-- * @{#COORDINATE.SmokeOrange}(): To smoke the point in orange. -- * @{#COORDINATE.SmokeOrange}(): To smoke the point in orange.
-- * @{#COORDINATE.SmokeWhite}(): To smoke the point in white. -- * @{#COORDINATE.SmokeWhite}(): To smoke the point in white.
-- * @{#COORDINATE.SmokeGreen}(): To smoke the point in green. -- * @{#COORDINATE.SmokeGreen}(): To smoke the point in green.
-- * @{#COORDINATE.SetSmokeOffsetDirection}(): To set an offset point direction for smoke.
-- * @{#COORDINATE.SetSmokeOffsetDistance}(): To set an offset point distance for smoke.
-- * @{#COORDINATE.SwitchSmokeOffsetOn}(): To set an offset point for smoke to on.
-- * @{#COORDINATE.SwitchSmokeOffsetOff}(): To set an offset point for smoke to off.
-- --
-- ## 2.2) Flare -- ## 2.2) Flare
-- --
@@ -2118,16 +2122,114 @@ do -- COORDINATE
end end
--- Smokes the point in a color. --- Create colored smoke the point. The smoke we last up to 5 min (DCS limitation) but you can optionally specify a shorter duration or stop it manually.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param Utilities.Utils#SMOKECOLOR SmokeColor -- @param #number SmokeColor Color of smoke, e.g. `SMOKECOLOR.Green` for green smoke.
-- @param #string name (Optional) Name if you want to stop the smoke early (normal duration: 5mins) -- @param #number Duration (Optional) Duration of the smoke in seconds. DCS stopps the smoke automatically after 5 min.
function COORDINATE:Smoke( SmokeColor, name ) -- @param #number Delay (Optional) Delay before the smoke is started in seconds.
self:F2( { SmokeColor } ) -- @param #string Name (Optional) Name if you want to stop the smoke early (normal duration: 5mins)
self.firename = name or "Smoke-"..math.random(1,100000) -- @param #boolean Offset (Optional) If true, offset the smokle a bit.
-- @param #number Direction (Optional) If Offset is true this is the direction of the offset, 1-359 (degrees). Default random.
-- @param #number Distance (Optional) If Offset is true this is the distance of the offset in meters. Default random 10-20.
-- @return #COORDINATE self
function COORDINATE:Smoke( SmokeColor, Duration, Delay, Name, Offset,Direction,Distance)
self:F2( { SmokeColor, Name, Duration, Delay, Offset } )
SmokeColor=SmokeColor or SMOKECOLOR.Green
if Delay and Delay>0 then
self:ScheduleOnce(Delay, COORDINATE.Smoke, self, SmokeColor, Duration, 0, Name, Direction,Distance)
else
-- Create a name which is used to stop the smoke manually
self.firename = Name or "Smoke-"..math.random(1,100000)
-- Create smoke
if Offset or self.SmokeOffset then
local Angle = Direction or self:GetSmokeOffsetDirection()
local Distance = Distance or self:GetSmokeOffsetDistance()
local newpos = self:Translate(Distance,Angle,true,false)
local newvec3 = newpos:GetVec3()
trigger.action.smoke( newvec3, SmokeColor, self.firename )
else
trigger.action.smoke( self:GetVec3(), SmokeColor, self.firename ) trigger.action.smoke( self:GetVec3(), SmokeColor, self.firename )
end end
-- Stop smoke
if Duration and Duration>0 then
self:ScheduleOnce(Duration, COORDINATE.StopSmoke, self, self.firename )
end
end
return self
end
--- Get the offset direction when using `COORDINATE:Smoke()`.
-- @param #COORDINATE self
-- @return #number Direction in degrees.
function COORDINATE:GetSmokeOffsetDirection()
local direction = self.SmokeOffsetDirection or math.random(1,359)
return direction
end
--- Set the offset direction when using `COORDINATE:Smoke()`.
-- @param #COORDINATE self
-- @param #number Direction (Optional) This is the direction of the offset, 1-359 (degrees). Default random.
-- @return #COORDINATE self
function COORDINATE:SetSmokeOffsetDirection(Direction)
if self then
self.SmokeOffsetDirection = Direction or math.random(1,359)
return self
else
COORDINATE.SmokeOffsetDirection = Direction or math.random(1,359)
end
end
--- Get the offset distance when using `COORDINATE:Smoke()`.
-- @param #COORDINATE self
-- @return #number Distance Distance in meters.
function COORDINATE:GetSmokeOffsetDistance()
local distance = self.SmokeOffsetDistance or math.random(10,20)
return distance
end
--- Set the offset distance when using `COORDINATE:Smoke()`.
-- @param #COORDINATE self
-- @param #number Distance (Optional) This is the distance of the offset in meters. Default random 10-20.
-- @return #COORDINATE self
function COORDINATE:SetSmokeOffsetDistance(Distance)
if self then
self.SmokeOffsetDistance = Distance or math.random(10,20)
return self
else
COORDINATE.SmokeOffsetDistance = Distance or math.random(10,20)
end
end
--- Set the offset on when using `COORDINATE:Smoke()`.
-- @param #COORDINATE self
-- @return #COORDINATE self
function COORDINATE:SwitchSmokeOffsetOn()
if self then
self.SmokeOffset = true
return self
else
COORDINATE.SmokeOffset = true
end
end
--- Set the offset off when using `COORDINATE:Smoke()`.
-- @param #COORDINATE self
-- @return #COORDINATE self
function COORDINATE:SwitchSmokeOffsetOff()
if self then
self.SmokeOffset = false
return self
else
COORDINATE.SmokeOffset = false
end
end
--- Stops smoking the point in a color. --- Stops smoking the point in a color.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #string name (Optional) Name if you want to stop the smoke early (normal duration: 5mins) -- @param #string name (Optional) Name if you want to stop the smoke early (normal duration: 5mins)
@@ -2137,49 +2239,83 @@ do -- COORDINATE
--- Smoke the COORDINATE Green. --- Smoke the COORDINATE Green.
-- @param #COORDINATE self -- @param #COORDINATE self
function COORDINATE:SmokeGreen() -- @param #number Duration (Optional) Duration of the smoke in seconds. DCS stopps the smoke automatically after 5 min.
self:F2() -- @param #number Delay (Optional) Delay before the smoke is started in seconds.
self:Smoke( SMOKECOLOR.Green ) -- @return #COORDINATE self
function COORDINATE:SmokeGreen(Duration, Delay)
self:Smoke( SMOKECOLOR.Green, Duration, Delay )
return self
end end
--- Smoke the COORDINATE Red. --- Smoke the COORDINATE Red.
-- @param #COORDINATE self -- @param #COORDINATE self
function COORDINATE:SmokeRed() -- @param #number Duration (Optional) Duration of the smoke in seconds. DCS stopps the smoke automatically after 5 min.
self:F2() -- @param #number Delay (Optional) Delay before the smoke is started in seconds.
self:Smoke( SMOKECOLOR.Red ) -- @return #COORDINATE self
function COORDINATE:SmokeRed(Duration, Delay)
self:Smoke( SMOKECOLOR.Red, Duration, Delay )
return self
end end
--- Smoke the COORDINATE White. --- Smoke the COORDINATE White.
-- @param #COORDINATE self -- @param #COORDINATE self
function COORDINATE:SmokeWhite() -- @param #number Duration (Optional) Duration of the smoke in seconds. DCS stopps the smoke automatically after 5 min.
self:F2() -- @param #number Delay (Optional) Delay before the smoke is started in seconds.
self:Smoke( SMOKECOLOR.White ) -- @return #COORDINATE self
function COORDINATE:SmokeWhite(Duration, Delay)
self:Smoke( SMOKECOLOR.White, Duration, Delay )
return self
end end
--- Smoke the COORDINATE Orange. --- Smoke the COORDINATE Orange.
-- @param #COORDINATE self -- @param #COORDINATE self
function COORDINATE:SmokeOrange() -- @param #number Duration (Optional) Duration of the smoke in seconds. DCS stopps the smoke automatically after 5 min.
self:F2() -- @param #number Delay (Optional) Delay before the smoke is started in seconds.
self:Smoke( SMOKECOLOR.Orange ) -- @return #COORDINATE self
function COORDINATE:SmokeOrange(Duration, Delay)
self:Smoke( SMOKECOLOR.Orange, Duration, Delay )
return self
end end
--- Smoke the COORDINATE Blue. --- Smoke the COORDINATE Blue.
-- @param #COORDINATE self -- @param #COORDINATE self
function COORDINATE:SmokeBlue() -- @param #number Duration (Optional) Duration of the smoke in seconds. DCS stopps the smoke automatically after 5 min.
self:F2() -- @param #number Delay (Optional) Delay before the smoke is started in seconds.
self:Smoke( SMOKECOLOR.Blue ) -- @return #COORDINATE self
function COORDINATE:SmokeBlue(Duration, Delay)
self:Smoke( SMOKECOLOR.Blue, Duration, Delay )
return self
end end
--- Big smoke and fire at the coordinate. --- Big smoke and fire at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param Utilities.Utils#BIGSMOKEPRESET preset Smoke preset (1=small smoke and fire, 2=medium smoke and fire, 3=large smoke and fire, 4=huge smoke and fire, 5=small smoke, 6=medium smoke, 7=large smoke, 8=huge smoke). -- @param #number Preset Smoke preset (1=small smoke and fire, 2=medium smoke and fire, 3=large smoke and fire, 4=huge smoke and fire, 5=small smoke, 6=medium smoke, 7=large smoke, 8=huge smoke).
-- @param #number density (Optional) Smoke density. Number in [0,...,1]. Default 0.5. -- @param #number Density (Optional) Smoke density. Number in [0,...,1]. Default 0.5.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
function COORDINATE:BigSmokeAndFire( preset, density, name ) -- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
self:F2( { preset=preset, density=density } ) -- @param #string Name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
density=density or 0.5 -- @return #COORDINATE self
self.firename = name or "Fire-"..math.random(1,10000) function COORDINATE:BigSmokeAndFire( Preset, Density, Duration, Delay, Name )
trigger.action.effectSmokeBig( self:GetVec3(), preset, density, self.firename ) self:F2( { preset=Preset, density=Density } )
Preset=Preset or BIGSMOKEPRESET.SmallSmokeAndFire
Density=Density or 0.5
if Delay and Delay>0 then
self:ScheduleOnce(Delay, COORDINATE.BigSmokeAndFire, self, Preset, Density, Duration, 0, Name)
else
self.firename = Name or "Fire-"..math.random(1,10000)
trigger.action.effectSmokeBig( self:GetVec3(), Preset, Density, self.firename )
-- Stop smoke
if Duration and Duration>0 then
self:ScheduleOnce(Duration, COORDINATE.StopBigSmokeAndFire, self, self.firename )
end
end
return self
end end
--- Stop big smoke and fire at the coordinate. --- Stop big smoke and fire at the coordinate.
@@ -2192,82 +2328,98 @@ do -- COORDINATE
--- Small smoke and fire at the coordinate. --- Small smoke and fire at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number Density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
function COORDINATE:BigSmokeAndFireSmall( density, name ) -- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
self:F2( { density=density } ) -- @param #string Name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
density=density or 0.5 -- @return #COORDINATE self
self:BigSmokeAndFire(BIGSMOKEPRESET.SmallSmokeAndFire, density, name) function COORDINATE:BigSmokeAndFireSmall( Density, Duration, Delay, Name )
self:BigSmokeAndFire(BIGSMOKEPRESET.SmallSmokeAndFire, Density, Duration, Delay, Name)
return self
end end
--- Medium smoke and fire at the coordinate. --- Medium smoke and fire at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeAndFireMedium( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeAndFireMedium( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.MediumSmokeAndFire, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.MediumSmokeAndFire, density, name) return self
end end
--- Large smoke and fire at the coordinate. --- Large smoke and fire at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeAndFireLarge( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeAndFireLarge( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.LargeSmokeAndFire, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.LargeSmokeAndFire, density, name) return self
end end
--- Huge smoke and fire at the coordinate. --- Huge smoke and fire at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeAndFireHuge( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeAndFireHuge( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.HugeSmokeAndFire, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.HugeSmokeAndFire, density, name) return self
end end
--- Small smoke at the coordinate. --- Small smoke at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeSmall( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeSmall( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.SmallSmoke, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.SmallSmoke, density, name) return self
end end
--- Medium smoke at the coordinate. --- Medium smoke at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeMedium( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeMedium( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.MediumSmoke, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.MediumSmoke, density, name) return self
end end
--- Large smoke at the coordinate. --- Large smoke at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeLarge( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeLarge( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.LargeSmoke, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.LargeSmoke, density,name) return self
end end
--- Huge smoke at the coordinate. --- Huge smoke at the coordinate.
-- @param #COORDINATE self -- @param #COORDINATE self
-- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5. -- @param #number density (Optional) Smoke density. Number between 0 and 1. Default 0.5.
-- @param #number Duration (Optional) Duration of the smoke and fire in seconds.
-- @param #number Delay (Optional) Delay before the smoke and fire is started in seconds.
-- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number. -- @param #string name (Optional) Name of the fire to stop it later again if not using the same COORDINATE object. Defaults to "Fire-" plus a random 5-digit-number.
function COORDINATE:BigSmokeHuge( density, name ) -- @return #COORDINATE self
self:F2( { density=density } ) function COORDINATE:BigSmokeHuge( Density, Duration, Delay, Name )
density=density or 0.5 self:BigSmokeAndFire(BIGSMOKEPRESET.HugeSmoke, Density, Duration, Delay, Name)
self:BigSmokeAndFire(BIGSMOKEPRESET.HugeSmoke, density,name) return self
end end
--- Flares the point in a color. --- Flares the point in a color.
@@ -2921,8 +3073,10 @@ do -- COORDINATE
local sunrise=UTILS.GetSunRiseAndSet(DayOfYear, Latitude, Longitude, true, Tdiff) local sunrise=UTILS.GetSunRiseAndSet(DayOfYear, Latitude, Longitude, true, Tdiff)
local sunset=UTILS.GetSunRiseAndSet(DayOfYear, Latitude, Longitude, false, Tdiff) local sunset=UTILS.GetSunRiseAndSet(DayOfYear, Latitude, Longitude, false, Tdiff)
if type(sunrise) == "string" or type(sunset) == "string" then
if sunrise == "N/R" then return false end if sunrise == "N/R" then return false end
if sunrise == "N/S" then return true end if sunset == "N/S" then return true end
end
local time=UTILS.ClockToSeconds(clock) local time=UTILS.ClockToSeconds(clock)
@@ -2941,6 +3095,11 @@ do -- COORDINATE
-- Todays sun set in sec. -- Todays sun set in sec.
local sunset=self:GetSunset(true) local sunset=self:GetSunset(true)
if type(sunrise) == "string" or type(sunset) == "string" then
if sunrise == "N/R" then return false end
if sunset == "N/S" then return true end
end
-- Seconds passed since midnight. -- Seconds passed since midnight.
local time=UTILS.SecondsOfToday() local time=UTILS.SecondsOfToday()

View File

@@ -198,7 +198,7 @@ end -- env
do -- radio do -- radio
---@type radio --@type radio
-- @field #radio.modulation modulation -- @field #radio.modulation modulation
--- ---

View File

@@ -141,7 +141,6 @@ FOX = {
explosiondist = 200, explosiondist = 200,
explosiondist2 = 500, explosiondist2 = 500,
bigmissilemass = 50, bigmissilemass = 50,
destroy = nil,
dt50 = 5, dt50 = 5,
dt10 = 1, dt10 = 1,
dt05 = 0.5, dt05 = 0.5,

View File

@@ -22,7 +22,7 @@
-- @module Functional.Mantis -- @module Functional.Mantis
-- @image Functional.Mantis.jpg -- @image Functional.Mantis.jpg
-- --
-- Last Update: Mar 2025 -- Last Update: May 2025
------------------------------------------------------------------------- -------------------------------------------------------------------------
--- **MANTIS** class, extends Core.Base#BASE --- **MANTIS** class, extends Core.Base#BASE
@@ -62,7 +62,9 @@
-- @field #table FilterZones Table of Core.Zone#ZONE Zones Consider SAM groups in this zone(s) only for this MANTIS instance, must be handed as #table of Zone objects. -- @field #table FilterZones Table of Core.Zone#ZONE Zones Consider SAM groups in this zone(s) only for this MANTIS instance, must be handed as #table of Zone objects.
-- @field #boolean SmokeDecoy If true, smoke short range SAM units as decoy if a plane is in firing range. -- @field #boolean SmokeDecoy If true, smoke short range SAM units as decoy if a plane is in firing range.
-- @field #number SmokeDecoyColor Color to use, defaults to SMOKECOLOR.White -- @field #number SmokeDecoyColor Color to use, defaults to SMOKECOLOR.White
-- @field #number checkcounter Counter for SAM Table refreshes -- @field #number checkcounter Counter for SAM Table refreshes.
-- @field #number DLinkCacheTime Seconds after which cached contacts in DLink will decay.
-- @field #boolean logsamstatus Log SAM status in dcs.log every cycle if true
-- @extends Core.Base#BASE -- @extends Core.Base#BASE
@@ -74,10 +76,9 @@
-- --
-- * Moose derived Modular, Automatic and Network capable Targeting and Interception System. -- * Moose derived Modular, Automatic and Network capable Targeting and Interception System.
-- * Controls a network of SAM sites. Uses detection to switch on the SAM site closest to the enemy. -- * Controls a network of SAM sites. Uses detection to switch on the SAM site closest to the enemy.
-- * **Automatic mode** (default since 0.8) will set-up your SAM site network automatically for you -- * **Automatic mode** (default) will set-up your SAM site network automatically for you.
-- * **Classic mode** behaves like before -- * Leverage evasiveness from SEAD, leverage attack range setting.
-- * Leverage evasiveness from SEAD, leverage attack range setting -- * Automatic setup of SHORAD based on groups of the class "short-range".
-- * Automatic setup of SHORAD based on groups of the class "short-range"
-- --
-- # 0. Base considerations and naming conventions -- # 0. Base considerations and naming conventions
-- --
@@ -133,10 +134,10 @@
-- --
-- # 0.1 Set-up in the mission editor -- # 0.1 Set-up in the mission editor
-- --
-- Set up your SAM sites in the mission editor. Name the groups using a systematic approach like above. -- Set up your SAM sites in the mission editor. Name the groups using a systematic approach like above.Can be e.g. AWACS or a combination of AWACS and Search Radars like e.g. EWR 1L13 etc.
-- Set up your EWR system in the mission editor. Name the groups using a systematic approach like above. Can be e.g. AWACS or a combination of AWACS and Search Radars like e.g. EWR 1L13 etc.
-- Search Radars usually have "SR" or "STR" in their names. Use the encyclopedia in the mission editor to inform yourself. -- Search Radars usually have "SR" or "STR" in their names. Use the encyclopedia in the mission editor to inform yourself.
-- Set up your SHORAD systems. They need to be **close** to (i.e. around) the SAM sites to be effective. Use **one** group per SAM location. SA-15 TOR systems offer a good missile defense. -- Set up your SHORAD systems. They need to be **close** to (i.e. around) the SAM sites to be effective. Use **one unit ** per group (multiple groups) for the SAM location.
-- Else, evasive manoevers might club up all defenders in one place. Red SA-15 TOR systems offer a good missile defense.
-- --
-- [optional] Set up your HQ. Can be any group, e.g. a command vehicle. -- [optional] Set up your HQ. Can be any group, e.g. a command vehicle.
-- --
@@ -188,7 +189,7 @@
-- --
-- ## 2.1 Auto mode features -- ## 2.1 Auto mode features
-- --
-- ### 2.1.1 You can now add Accept-, Reject- and Conflict-Zones to your setup, e.g. to consider borders or de-militarized zones: -- ### 2.1.1 You can add Accept-, Reject- and Conflict-Zones to your setup, e.g. to consider borders or de-militarized zones:
-- --
-- -- Parameters are tables of Core.Zone#ZONE objects! -- -- Parameters are tables of Core.Zone#ZONE objects!
-- -- This is effectively a 3-stage filter allowing for zone overlap. A coordinate is accepted first when -- -- This is effectively a 3-stage filter allowing for zone overlap. A coordinate is accepted first when
@@ -206,9 +207,6 @@
-- --
-- ### 2.1.4 Advanced features -- ### 2.1.4 Advanced features
-- --
-- -- Option to switch off auto mode **before** you start MANTIS (not recommended)
-- mybluemantis.automode = false
--
-- -- Option to set the scale of the activation range, i.e. don't activate at the fringes of max range, defaults below. -- -- Option to set the scale of the activation range, i.e. don't activate at the fringes of max range, defaults below.
-- -- also see engagerange below. -- -- also see engagerange below.
-- self.radiusscale[MANTIS.SamType.LONG] = 1.1 -- self.radiusscale[MANTIS.SamType.LONG] = 1.1
@@ -221,6 +219,12 @@
-- -- For some scenarios, like Cold War, it might be useful not to activate SAMs if friendly aircraft are around to avoid death by friendly fire. -- -- For some scenarios, like Cold War, it might be useful not to activate SAMs if friendly aircraft are around to avoid death by friendly fire.
-- mybluemantis.checkforfriendlies = true -- mybluemantis.checkforfriendlies = true
-- --
-- ### 2.1.6 Shoot & Scoot
--
-- -- Option to make the (driveable) SHORAD units drive around and shuffle positions
-- -- We use a SET_ZONE for that, number of zones to consider defaults to three, Random is true for random coordinates and Formation is e.g. "Vee".
-- mybluemantis:AddScootZones(ZoneSet, Number, Random, Formation)
--
-- # 3. Default settings [both modes unless stated otherwise] -- # 3. Default settings [both modes unless stated otherwise]
-- --
-- By default, the following settings are active: -- By default, the following settings are active:
@@ -243,25 +247,7 @@
-- --
-- Use this option if you want to make use of or allow advanced SEAD tactics. -- Use this option if you want to make use of or allow advanced SEAD tactics.
-- --
-- # 5. Integrate SHORAD [classic mode, not necessary in automode, not recommended for manual setup] -- # 5. Integrated SEAD
--
-- You can also choose to integrate Mantis with @{Functional.Shorad#SHORAD} for protection against HARMs and AGMs manually. When SHORAD detects a missile fired at one of MANTIS' SAM sites, it will activate SHORAD systems in
-- the given defense checkradius around that SAM site. Create a SHORAD object first, then integrate with MANTIS like so:
--
-- local SamSet = SET_GROUP:New():FilterPrefixes("Blue SAM"):FilterCoalitions("blue"):FilterStart()
-- myshorad = SHORAD:New("BlueShorad", "Blue SHORAD", SamSet, 22000, 600, "blue")
-- -- now set up MANTIS
-- mymantis = MANTIS:New("BlueMantis","Blue SAM","Blue EWR",nil,"blue",false,"Blue Awacs")
-- mymantis:AddShorad(myshorad,720)
-- mymantis:Start()
--
-- If you systematically name your SHORAD groups starting with "Blue SHORAD" you'll need exactly **one** SHORAD instance to manage all SHORAD groups.
--
-- (Optionally) you can remove the link later on with
--
-- mymantis:RemoveShorad()
--
-- # 6. Integrated SEAD
-- --
-- MANTIS is using @{Functional.Sead#SEAD} internally to both detect and evade HARM attacks. No extra efforts needed to set this up! -- MANTIS is using @{Functional.Sead#SEAD} internally to both detect and evade HARM attacks. No extra efforts needed to set this up!
-- Once a HARM attack is detected, MANTIS (via SEAD) will shut down the radars of the attacked SAM site and take evasive action by moving the SAM -- Once a HARM attack is detected, MANTIS (via SEAD) will shut down the radars of the attacked SAM site and take evasive action by moving the SAM
@@ -336,6 +322,8 @@ MANTIS = {
SmokeDecoy = false, SmokeDecoy = false,
SmokeDecoyColor = SMOKECOLOR.White, SmokeDecoyColor = SMOKECOLOR.White,
checkcounter = 1, checkcounter = 1,
DLinkCacheTime = 120,
logsamstatus = false,
} }
--- Advanced state enumerator --- Advanced state enumerator
@@ -374,7 +362,7 @@ MANTIS.radiusscale[MANTIS.SamType.POINT] = 3
MANTIS.SamData = { MANTIS.SamData = {
["Hawk"] = { Range=35, Blindspot=0, Height=12, Type="Medium", Radar="Hawk" }, -- measures in km ["Hawk"] = { Range=35, Blindspot=0, Height=12, Type="Medium", Radar="Hawk" }, -- measures in km
["NASAMS"] = { Range=14, Blindspot=0, Height=7, Type="Short", Radar="NSAMS" }, -- AIM 120B ["NASAMS"] = { Range=14, Blindspot=0, Height=7, Type="Short", Radar="NSAMS" }, -- AIM 120B
["Patriot"] = { Range=99, Blindspot=0, Height=25, Type="Long", Radar="Patriot" }, ["Patriot"] = { Range=99, Blindspot=0, Height=25, Type="Long", Radar="Patriot str" },
["Rapier"] = { Range=10, Blindspot=0, Height=3, Type="Short", Radar="rapier" }, ["Rapier"] = { Range=10, Blindspot=0, Height=3, Type="Short", Radar="rapier" },
["SA-2"] = { Range=40, Blindspot=7, Height=25, Type="Medium", Radar="S_75M_Volhov" }, ["SA-2"] = { Range=40, Blindspot=7, Height=25, Type="Medium", Radar="S_75M_Volhov" },
["SA-3"] = { Range=18, Blindspot=6, Height=18, Type="Short", Radar="5p73 s-125 ln" }, ["SA-3"] = { Range=18, Blindspot=6, Height=18, Type="Short", Radar="5p73 s-125 ln" },
@@ -382,7 +370,8 @@ MANTIS.SamData = {
["SA-6"] = { Range=25, Blindspot=0, Height=8, Type="Medium", Radar="1S91" }, ["SA-6"] = { Range=25, Blindspot=0, Height=8, Type="Medium", Radar="1S91" },
["SA-10"] = { Range=119, Blindspot=0, Height=18, Type="Long" , Radar="S-300PS 4"}, ["SA-10"] = { Range=119, Blindspot=0, Height=18, Type="Long" , Radar="S-300PS 4"},
["SA-11"] = { Range=35, Blindspot=0, Height=20, Type="Medium", Radar="SA-11" }, ["SA-11"] = { Range=35, Blindspot=0, Height=20, Type="Medium", Radar="SA-11" },
["Roland"] = { Range=5, Blindspot=0, Height=5, Type="Point", Radar="Roland" }, ["Roland"] = { Range=6, Blindspot=0, Height=5, Type="Short", Radar="Roland" },
["Gepard"] = { Range=5, Blindspot=0, Height=4, Type="Point", Radar="Gepard" },
["HQ-7"] = { Range=12, Blindspot=0, Height=3, Type="Short", Radar="HQ-7" }, ["HQ-7"] = { Range=12, Blindspot=0, Height=3, Type="Short", Radar="HQ-7" },
["SA-9"] = { Range=4, Blindspot=0, Height=3, Type="Point", Radar="Strela", Point="true" }, ["SA-9"] = { Range=4, Blindspot=0, Height=3, Type="Point", Radar="Strela", Point="true" },
["SA-8"] = { Range=10, Blindspot=0, Height=5, Type="Short", Radar="Osa 9A33" }, ["SA-8"] = { Range=10, Blindspot=0, Height=5, Type="Short", Radar="Osa 9A33" },
@@ -393,6 +382,7 @@ MANTIS.SamData = {
["Chaparral"] = { Range=8, Blindspot=0, Height=3, Type="Short", Radar="Chaparral" }, ["Chaparral"] = { Range=8, Blindspot=0, Height=3, Type="Short", Radar="Chaparral" },
["Linebacker"] = { Range=4, Blindspot=0, Height=3, Type="Point", Radar="Linebacker", Point="true" }, ["Linebacker"] = { Range=4, Blindspot=0, Height=3, Type="Point", Radar="Linebacker", Point="true" },
["Silkworm"] = { Range=90, Blindspot=1, Height=0.2, Type="Long", Radar="Silkworm" }, ["Silkworm"] = { Range=90, Blindspot=1, Height=0.2, Type="Long", Radar="Silkworm" },
["HEMTT_C-RAM_Phalanx"] = { Range=2, Blindspot=0, Height=2, Type="Point", Radar="HEMTT_C-RAM_Phalanx", Point="true" },
-- units from HDS Mod, multi launcher options is tricky -- units from HDS Mod, multi launcher options is tricky
["SA-10B"] = { Range=75, Blindspot=0, Height=18, Type="Medium" , Radar="SA-10B"}, ["SA-10B"] = { Range=75, Blindspot=0, Height=18, Type="Medium" , Radar="SA-10B"},
["SA-17"] = { Range=50, Blindspot=3, Height=30, Type="Medium", Radar="SA-17" }, ["SA-17"] = { Range=50, Blindspot=3, Height=30, Type="Medium", Radar="SA-17" },
@@ -625,6 +615,7 @@ do
self.advAwacs = false self.advAwacs = false
end end
self:SetDLinkCacheTime()
-- Set the string id for output to DCS.log file. -- Set the string id for output to DCS.log file.
self.lid=string.format("MANTIS %s | ", self.name) self.lid=string.format("MANTIS %s | ", self.name)
@@ -658,6 +649,8 @@ do
table.insert(self.ewr_templates,awacs) table.insert(self.ewr_templates,awacs)
end end
self.logsamstatus = false
self:T({self.ewr_templates}) self:T({self.ewr_templates})
self.SAM_Group = SET_GROUP:New():FilterPrefixes(self.SAM_Templates_Prefix):FilterCoalitions(self.Coalition) self.SAM_Group = SET_GROUP:New():FilterPrefixes(self.SAM_Templates_Prefix):FilterCoalitions(self.Coalition)
@@ -689,7 +682,7 @@ do
-- TODO Version -- TODO Version
-- @field #string version -- @field #string version
self.version="0.9.27" self.version="0.9.30"
self:I(string.format("***** Starting MANTIS Version %s *****", self.version)) self:I(string.format("***** Starting MANTIS Version %s *****", self.version))
--- FSM Functions --- --- FSM Functions ---
@@ -1040,6 +1033,16 @@ do
return self return self
end end
--- Function to set how long INTEL DLINK remembers contacts.
-- @param #MANTIS self
-- @param #number seconds Remember this many seconds, at least 5 seconds.
-- @return #MANTIS self
function MANTIS:SetDLinkCacheTime(seconds)
self.DLinkCacheTime = math.abs(seconds or 120)
if self.DLinkCacheTime < 5 then self.DLinkCacheTime = 5 end
return self
end
--- Function to set the detection interval --- Function to set the detection interval
-- @param #MANTIS self -- @param #MANTIS self
-- @param #number interval The interval in seconds -- @param #number interval The interval in seconds
@@ -1431,7 +1434,9 @@ do
--IntelTwo:SetClusterRadius(5000) --IntelTwo:SetClusterRadius(5000)
IntelTwo:Start() IntelTwo:Start()
local IntelDlink = INTEL_DLINK:New({IntelOne,IntelTwo},self.name.." DLINK",22,300) local CacheTime = self.DLinkCacheTime or 120
local IntelDlink = INTEL_DLINK:New({IntelOne,IntelTwo},self.name.." DLINK",22,CacheTime)
IntelDlink:__Start(1) IntelDlink:__Start(1)
self:SetUsingDLink(IntelDlink) self:SetUsingDLink(IntelDlink)
@@ -1493,7 +1498,7 @@ do
elseif chm then elseif chm then
SAMData = self.SamDataCH SAMData = self.SamDataCH
end end
--self:T("Looking to auto-match for "..grpname) --self:I("Looking to auto-match for "..grpname)
for _,_unit in pairs(units) do for _,_unit in pairs(units) do
local unit = _unit -- Wrapper.Unit#UNIT local unit = _unit -- Wrapper.Unit#UNIT
local type = string.lower(unit:GetTypeName()) local type = string.lower(unit:GetTypeName())
@@ -1694,7 +1699,9 @@ do
local grpname = group:GetName() local grpname = group:GetName()
local grpcoord = group:GetCoordinate() local grpcoord = group:GetCoordinate()
local grprange, grpheight,type,blind = self:_GetSAMRange(grpname) local grprange, grpheight,type,blind = self:_GetSAMRange(grpname)
local radaralive = group:IsSAM() -- TODO the below might stop working at some point after some hours, needs testing
--local radaralive = group:IsSAM()
local radaralive = true
table.insert( SAM_Tbl, {grpname, grpcoord, grprange, grpheight, blind, type}) -- make the table lighter, as I don't really use the zone here table.insert( SAM_Tbl, {grpname, grpcoord, grprange, grpheight, blind, type}) -- make the table lighter, as I don't really use the zone here
table.insert( SEAD_Grps, grpname ) table.insert( SEAD_Grps, grpname )
if type == MANTIS.SamType.LONG and radaralive then if type == MANTIS.SamType.LONG and radaralive then
@@ -1856,7 +1863,7 @@ do
end --end alive end --end alive
end --end check end --end check
end --for loop end --for loop
if self.debug or self.verbose then if self.debug or self.verbose or self.logsamstatus then
for _,_status in pairs(self.SamStateTracker) do for _,_status in pairs(self.SamStateTracker) do
if _status == "GREEN" then if _status == "GREEN" then
instatusgreen=instatusgreen+1 instatusgreen=instatusgreen+1
@@ -1877,8 +1884,9 @@ do
-- @param #MANTIS self -- @param #MANTIS self
-- @param Functional.Detection#DETECTION_AREAS detection Detection object -- @param Functional.Detection#DETECTION_AREAS detection Detection object
-- @param #boolean dlink -- @param #boolean dlink
-- @param #boolean reporttolog
-- @return #MANTIS self -- @return #MANTIS self
function MANTIS:_Check(detection,dlink) function MANTIS:_Check(detection,dlink,reporttolog)
self:T(self.lid .. "Check") self:T(self.lid .. "Check")
--get detected set --get detected set
local detset = detection:GetDetectedItemCoordinates() local detset = detection:GetDetectedItemCoordinates()
@@ -1905,7 +1913,8 @@ do
local samset = self:_GetSAMTable() -- table of i.1=names, i.2=coordinates, i.3=firing range, i.4=firing height local samset = self:_GetSAMTable() -- table of i.1=names, i.2=coordinates, i.3=firing range, i.4=firing height
instatusred, instatusgreen, activeshorads = self:_CheckLoop(samset,detset,dlink,self.maxclassic) instatusred, instatusgreen, activeshorads = self:_CheckLoop(samset,detset,dlink,self.maxclassic)
end end
if self.debug or self.verbose then
local function GetReport()
local statusreport = REPORT:New("\nMANTIS Status "..self.name) local statusreport = REPORT:New("\nMANTIS Status "..self.name)
statusreport:Add("+-----------------------------+") statusreport:Add("+-----------------------------+")
statusreport:Add(string.format("+ SAM in RED State: %2d",instatusred)) statusreport:Add(string.format("+ SAM in RED State: %2d",instatusred))
@@ -1914,7 +1923,15 @@ do
statusreport:Add(string.format("+ SHORAD active: %2d",activeshorads)) statusreport:Add(string.format("+ SHORAD active: %2d",activeshorads))
end end
statusreport:Add("+-----------------------------+") statusreport:Add("+-----------------------------+")
return statusreport
end
if self.debug or self.verbose then
local statusreport = GetReport()
MESSAGE:New(statusreport:Text(),10):ToAll():ToLog() MESSAGE:New(statusreport:Text(),10):ToAll():ToLog()
elseif reporttolog == true then
local statusreport = GetReport()
MESSAGE:New(statusreport:Text(),10):ToLog()
end end
return self return self
end end
@@ -2022,7 +2039,7 @@ do
self:T({From, Event, To}) self:T({From, Event, To})
-- check detection -- check detection
if not self.state2flag then if not self.state2flag then
self:_Check(self.Detection,self.DLink) self:_Check(self.Detection,self.DLink,self.logsamstatus)
end end
local EWRAlive = self:_CheckAnyEWRAlive() local EWRAlive = self:_CheckAnyEWRAlive()

View File

@@ -53,6 +53,8 @@
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE. -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE.
-- Therefore, this class is considered to be deprecated and superseded by the [Functional.Fox](https://flightcontrol-master.github.io/MOOSE_DOCS_DEVELOP/Documentation/Functional.Fox.html) class, which provides the same functionality. -- Therefore, this class is considered to be deprecated and superseded by the [Functional.Fox](https://flightcontrol-master.github.io/MOOSE_DOCS_DEVELOP/Documentation/Functional.Fox.html) class, which provides the same functionality.
-- --

View File

@@ -2102,7 +2102,12 @@ function RANGE._OnImpact(weapon, self, playerData, attackHdg, attackAlt, attackV
result.attackHdg = attackHdg result.attackHdg = attackHdg
result.attackVel = attackVel result.attackVel = attackVel
result.attackAlt = attackAlt result.attackAlt = attackAlt
result.date=os and os.date() or "n/a" if os and os.date then
result.date=os.date()
else
self:E(self.lid.."os or os.date() not available")
result.date = "n/a"
end
-- Add to table. -- Add to table.
table.insert( _results, result ) table.insert( _results, result )

View File

@@ -7,6 +7,8 @@
-- --
-- # Developer Note -- # Developer Note
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE -- Note while this class still works, it is no longer supported as the original author stopped active development of MOOSE
-- Therefore, this class is considered to be deprecated -- Therefore, this class is considered to be deprecated
-- --

View File

@@ -2798,7 +2798,7 @@ function ATIS:onafterBroadcast( From, Event, To )
end end
_RUNACT = subtitle _RUNACT = subtitle
alltext = alltext .. ";\n" .. subtitle --alltext = alltext .. ";\n" .. subtitle
-- Runway length. -- Runway length.
if self.rwylength then if self.rwylength then

View File

@@ -32,6 +32,7 @@
-- * [USS George Washington](https://en.wikipedia.org/wiki/USS_George_Washington_\(CVN-73\)) (CVN-73) [Super Carrier Module] -- * [USS George Washington](https://en.wikipedia.org/wiki/USS_George_Washington_\(CVN-73\)) (CVN-73) [Super Carrier Module]
-- * [USS Harry S. Truman](https://en.wikipedia.org/wiki/USS_Harry_S._Truman) (CVN-75) [Super Carrier Module] -- * [USS Harry S. Truman](https://en.wikipedia.org/wiki/USS_Harry_S._Truman) (CVN-75) [Super Carrier Module]
-- * [USS Forrestal](https://en.wikipedia.org/wiki/USS_Forrestal_\(CV-59\)) (CV-59) [Heatblur Carrier Module] -- * [USS Forrestal](https://en.wikipedia.org/wiki/USS_Forrestal_\(CV-59\)) (CV-59) [Heatblur Carrier Module]
-- * [Essex Class](https://en.wikipedia.org/wiki/Essex-class_aircraft_carrier) (CV-11) [Magnitude 3 Carrier Module]
-- * [HMS Hermes](https://en.wikipedia.org/wiki/HMS_Hermes_\(R12\)) (R12) -- * [HMS Hermes](https://en.wikipedia.org/wiki/HMS_Hermes_\(R12\)) (R12)
-- * [HMS Invincible](https://en.wikipedia.org/wiki/HMS_Invincible_\(R05\)) (R05) -- * [HMS Invincible](https://en.wikipedia.org/wiki/HMS_Invincible_\(R05\)) (R05)
-- * [USS Tarawa](https://en.wikipedia.org/wiki/USS_Tarawa_\(LHA-1\)) (LHA-1) -- * [USS Tarawa](https://en.wikipedia.org/wiki/USS_Tarawa_\(LHA-1\)) (LHA-1)
@@ -47,6 +48,7 @@
-- * [AV-8B N/A Harrier](https://forums.eagle.ru/forumdisplay.php?f=555) (Player & AI) -- * [AV-8B N/A Harrier](https://forums.eagle.ru/forumdisplay.php?f=555) (Player & AI)
-- * [T-45C Goshawk](https://forum.dcs.world/topic/203816-vnao-t-45-goshawk/) (VNAO mod) (Player & AI) -- * [T-45C Goshawk](https://forum.dcs.world/topic/203816-vnao-t-45-goshawk/) (VNAO mod) (Player & AI)
-- * [FE/A-18E/F/G Superhornet](https://forum.dcs.world/topic/316971-cjs-super-hornet-community-mod-v20-official-thread/) (CJS mod) (Player & AI) -- * [FE/A-18E/F/G Superhornet](https://forum.dcs.world/topic/316971-cjs-super-hornet-community-mod-v20-official-thread/) (CJS mod) (Player & AI)
-- * [F4U-1D Corsair](https://forum.dcs.world/forum/781-f4u-1d/) (Player & AI)
-- * F/A-18C Hornet (AI) -- * F/A-18C Hornet (AI)
-- * F-14A Tomcat (AI) -- * F-14A Tomcat (AI)
-- * E-2D Hawkeye (AI) -- * E-2D Hawkeye (AI)
@@ -1283,6 +1285,8 @@ AIRBOSS = {
-- @field #string RHINOE F/A-18E Superhornet (mod). -- @field #string RHINOE F/A-18E Superhornet (mod).
-- @field #string RHINOF F/A-18F Superhornet (mod). -- @field #string RHINOF F/A-18F Superhornet (mod).
-- @field #string GROWLER FEA-18G Superhornet (mod). -- @field #string GROWLER FEA-18G Superhornet (mod).
-- @field #string CORSAIR F4U-1D Corsair.
-- @field #string CORSAIR_CW F4U-1D Corsair Mk.4 (clipped wing).
AIRBOSS.AircraftCarrier={ AIRBOSS.AircraftCarrier={
AV8B="AV8BNA", AV8B="AV8BNA",
HORNET="FA-18C_hornet", HORNET="FA-18C_hornet",
@@ -1299,6 +1303,8 @@ AIRBOSS.AircraftCarrier={
RHINOE="FA-18E", RHINOE="FA-18E",
RHINOF="FA-18F", RHINOF="FA-18F",
GROWLER="EA-18G", GROWLER="EA-18G",
CORSAIR="F4U-1D",
CORSAIR_CW="F4U-1D CW",
} }
--- Carrier types. --- Carrier types.
@@ -1310,6 +1316,7 @@ AIRBOSS.AircraftCarrier={
-- @field #string TRUMAN USS Harry S. Truman (CVN-75) [Super Carrier Module] -- @field #string TRUMAN USS Harry S. Truman (CVN-75) [Super Carrier Module]
-- @field #string FORRESTAL USS Forrestal (CV-59) [Heatblur Carrier Module] -- @field #string FORRESTAL USS Forrestal (CV-59) [Heatblur Carrier Module]
-- @field #string VINSON USS Carl Vinson (CVN-70) [Deprecated!] -- @field #string VINSON USS Carl Vinson (CVN-70) [Deprecated!]
-- @field #string ESSEX Essex class carrier (e.g. USS Yorktown (CV-10)) [Magnitude 3 Carrier Module]
-- @field #string HERMES HMS Hermes (R12) [V/STOL Carrier] -- @field #string HERMES HMS Hermes (R12) [V/STOL Carrier]
-- @field #string INVINCIBLE HMS Invincible (R05) [V/STOL Carrier] -- @field #string INVINCIBLE HMS Invincible (R05) [V/STOL Carrier]
-- @field #string TARAWA USS Tarawa (LHA-1) [V/STOL Carrier] -- @field #string TARAWA USS Tarawa (LHA-1) [V/STOL Carrier]
@@ -1325,6 +1332,7 @@ AIRBOSS.CarrierType = {
STENNIS = "Stennis", STENNIS = "Stennis",
FORRESTAL = "Forrestal", FORRESTAL = "Forrestal",
VINSON = "VINSON", VINSON = "VINSON",
ESSEX = "Essex",
HERMES = "HERMES81", HERMES = "HERMES81",
INVINCIBLE = "hms_invincible", INVINCIBLE = "hms_invincible",
TARAWA = "LHA_Tarawa", TARAWA = "LHA_Tarawa",
@@ -1747,7 +1755,7 @@ AIRBOSS.MenuF10Root = nil
--- Airboss class version. --- Airboss class version.
-- @field #string version -- @field #string version
AIRBOSS.version = "1.3.3" AIRBOSS.version = "1.4.0"
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
-- TODO list -- TODO list
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
@@ -1912,6 +1920,9 @@ function AIRBOSS:New( carriername, alias )
-- Set max section members. Default 2. -- Set max section members. Default 2.
self:SetMaxSectionSize() self:SetMaxSectionSize()
-- Set max section distance. Default 100 meters.
self:SetMaxSectionDistance()
-- Set max flights per stack. Default is 2. -- Set max flights per stack. Default is 2.
self:SetMaxFlightsPerStack() self:SetMaxFlightsPerStack()
@@ -2010,6 +2021,8 @@ function AIRBOSS:New( carriername, alias )
elseif self.carriertype == AIRBOSS.CarrierType.VINSON then elseif self.carriertype == AIRBOSS.CarrierType.VINSON then
-- Carl Vinson is legacy now. -- Carl Vinson is legacy now.
self:_InitStennis() self:_InitStennis()
elseif self.carriertype == AIRBOSS.CarrierType.ESSEX then
self:_InitEssex()
elseif self.carriertype == AIRBOSS.CarrierType.HERMES then elseif self.carriertype == AIRBOSS.CarrierType.HERMES then
-- Hermes parameters. -- Hermes parameters.
self:_InitHermes() self:_InitHermes()
@@ -2863,7 +2876,12 @@ end
function AIRBOSS:SetGlideslopeErrorThresholds(_max,_min, High, HIGH, Low, LOW) function AIRBOSS:SetGlideslopeErrorThresholds(_max,_min, High, HIGH, Low, LOW)
--Check if V/STOL Carrier --Check if V/STOL Carrier
if self.carriertype == AIRBOSS.CarrierType.INVINCIBLE or self.carriertype == AIRBOSS.CarrierType.HERMES or self.carriertype == AIRBOSS.CarrierType.TARAWA or self.carriertype == AIRBOSS.CarrierType.AMERICA or self.carriertype == AIRBOSS.CarrierType.JCARLOS or self.carriertype == AIRBOSS.CarrierType.CANBERRA then if self.carriertype == AIRBOSS.CarrierType.INVINCIBLE or
self.carriertype == AIRBOSS.CarrierType.HERMES or
self.carriertype == AIRBOSS.CarrierType.TARAWA or
self.carriertype == AIRBOSS.CarrierType.AMERICA or
self.carriertype == AIRBOSS.CarrierType.JCARLOS or
self.carriertype == AIRBOSS.CarrierType.CANBERRA then
-- allow a larger GSE for V/STOL operations --Pene Testing -- allow a larger GSE for V/STOL operations --Pene Testing
self.gle._max=_max or 0.7 self.gle._max=_max or 0.7
@@ -2872,8 +2890,8 @@ function AIRBOSS:SetGlideslopeErrorThresholds(_max,_min, High, HIGH, Low, LOW)
self.gle._min=_min or -0.5 self.gle._min=_min or -0.5
self.gle.Low=Low or -1.2 self.gle.Low=Low or -1.2
self.gle.LOW=LOW or -1.5 self.gle.LOW=LOW or -1.5
-- CVN values
else else
-- CVN values
self.gle._max=_max or 0.4 self.gle._max=_max or 0.4
self.gle.High=High or 0.8 self.gle.High=High or 0.8
self.gle.HIGH=HIGH or 1.5 self.gle.HIGH=HIGH or 1.5
@@ -3343,6 +3361,22 @@ function AIRBOSS:SetMaxSectionSize( nmax )
return self return self
end end
--- Set maximum distance up to which section members are allowed (default: 100 meters).
-- @param #AIRBOSS self
-- @param #number dmax Max distance in meters (default 100 m). Minimum is 10 m, maximum is 5000 m.
-- @return #AIRBOSS self
function AIRBOSS:SetMaxSectionDistance( dmax )
if dmax then
if dmax < 10 then
dmax = 10
elseif dmax > 5000 then
dmax = 5000
end
end
self.maxsectiondistance = dmax or 100
return self
end
--- Set max number of flights per stack. All members of a section count as one "flight". --- Set max number of flights per stack. All members of a section count as one "flight".
-- @param #AIRBOSS self -- @param #AIRBOSS self
-- @param #number nmax Number of max allowed flights per stack. Default is two. Minimum is one, maximum is 4. -- @param #number nmax Number of max allowed flights per stack. Default is two. Minimum is one, maximum is 4.
@@ -4608,6 +4642,51 @@ function AIRBOSS:_InitForrestal()
end end
--- Init parameters for Essec class carriers.
-- @param #AIRBOSS self
function AIRBOSS:_InitEssex()
-- Init Nimitz as default.
self:_InitNimitz()
-- Carrier Parameters.
self.carrierparam.sterndist = -126
self.carrierparam.deckheight = 19.27 --DCS World\CoreMods\tech\M3 WWII PTO units\Database\Essex_Class_Carrier_1944.lua
-- Total size of the carrier (approx as rectangle).
self.carrierparam.totlength = 268
self.carrierparam.totwidthport = 23
self.carrierparam.totwidthstarboard = 23
-- Landing runway.
self.carrierparam.rwyangle = 0.0
self.carrierparam.rwylength = 265
self.carrierparam.rwywidth = 20
-- Wires.
self.carrierparam.wire1 = 21.9
self.carrierparam.wire2 = 28.3
self.carrierparam.wire3 = 34.7
self.carrierparam.wire4 = 41.1
self.carrierparam.wire5 = 47.4
self.carrierparam.wire6 = 53.7
self.carrierparam.wire7 = 59.0
self.carrierparam.wire8 = 64.1
self.carrierparam.wire9 = 72.7
self.carrierparam.wire10 = 78.0
self.carrierparam.wire11 = 85.5
self.carrierparam.wire12 = 105.9
self.carrierparam.wire13 = 113.3
self.carrierparam.wire14 = 121.0
self.carrierparam.wire15 = 128.5
-- Landing distance.
self.carrierparam.landingdist = self.carrierparam.sterndist+self.carrierparam.wire3
end
--- Init parameters for R12 HMS Hermes carrier. --- Init parameters for R12 HMS Hermes carrier.
-- @param #AIRBOSS self -- @param #AIRBOSS self
function AIRBOSS:_InitHermes() function AIRBOSS:_InitHermes()
@@ -5311,6 +5390,7 @@ function AIRBOSS:_GetAircraftAoA( playerData )
local skyhawk = playerData.actype == AIRBOSS.AircraftCarrier.A4EC local skyhawk = playerData.actype == AIRBOSS.AircraftCarrier.A4EC
local harrier = playerData.actype == AIRBOSS.AircraftCarrier.AV8B local harrier = playerData.actype == AIRBOSS.AircraftCarrier.AV8B
local tomcat = playerData.actype == AIRBOSS.AircraftCarrier.F14A or playerData.actype == AIRBOSS.AircraftCarrier.F14B local tomcat = playerData.actype == AIRBOSS.AircraftCarrier.F14A or playerData.actype == AIRBOSS.AircraftCarrier.F14B
local corsair = playerData.actype == AIRBOSS.AircraftCarrier.CORSAIR or playerData.actype == AIRBOSS.AircraftCarrier.CORSAIR_CW
-- Table with AoA values. -- Table with AoA values.
local aoa = {} -- #AIRBOSS.AircraftAoA local aoa = {} -- #AIRBOSS.AircraftAoA
@@ -5355,7 +5435,6 @@ function AIRBOSS:_GetAircraftAoA( playerData )
aoa.Fast = 8.25 -- =17.5/2 aoa.Fast = 8.25 -- =17.5/2
aoa.FAST = 8.00 -- =16.5/2 aoa.FAST = 8.00 -- =16.5/2
elseif harrier then elseif harrier then
-- AV-8B Harrier parameters. Tuning done on the Fast AoA to allow for abeam and ninety at Nozzles 55. Pene testing -- AV-8B Harrier parameters. Tuning done on the Fast AoA to allow for abeam and ninety at Nozzles 55. Pene testing
aoa.SLOW = 16.0 aoa.SLOW = 16.0
aoa.Slow = 13.5 aoa.Slow = 13.5
@@ -5364,7 +5443,15 @@ function AIRBOSS:_GetAircraftAoA( playerData )
aoa.OnSpeedMin = 9.5 aoa.OnSpeedMin = 9.5
aoa.Fast = 8.0 aoa.Fast = 8.0
aoa.FAST = 7.5 aoa.FAST = 7.5
elseif corsair then
-- F4U-1D Corsair parameters.
aoa.SLOW = 16.0
aoa.Slow = 13.5
aoa.OnSpeedMax = 12.5
aoa.OnSpeed = 10.0
aoa.OnSpeedMin = 9.5
aoa.Fast = 8.0
aoa.FAST = 7.5
end end
return aoa return aoa
@@ -5477,6 +5564,7 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
local tomcat = playerData.actype == AIRBOSS.AircraftCarrier.F14A or playerData.actype == AIRBOSS.AircraftCarrier.F14B local tomcat = playerData.actype == AIRBOSS.AircraftCarrier.F14A or playerData.actype == AIRBOSS.AircraftCarrier.F14B
local harrier = playerData.actype == AIRBOSS.AircraftCarrier.AV8B local harrier = playerData.actype == AIRBOSS.AircraftCarrier.AV8B
local goshawk = playerData.actype == AIRBOSS.AircraftCarrier.T45C local goshawk = playerData.actype == AIRBOSS.AircraftCarrier.T45C
local corsair = playerData.actype == AIRBOSS.AircraftCarrier.CORSAIR or playerData.actype == AIRBOSS.AircraftCarrier.CORSAIR_CW
-- Return values. -- Return values.
local alt local alt
@@ -5536,6 +5624,9 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
elseif goshawk then elseif goshawk then
alt = UTILS.FeetToMeters( 800 ) alt = UTILS.FeetToMeters( 800 )
speed = UTILS.KnotsToMps( 300 ) speed = UTILS.KnotsToMps( 300 )
elseif corsair then
alt = UTILS.FeetToMeters( 300 )
speed = UTILS.KnotsToMps( 120 )
end end
elseif step == AIRBOSS.PatternStep.BREAKENTRY then elseif step == AIRBOSS.PatternStep.BREAKENTRY then
@@ -5549,6 +5640,9 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
elseif goshawk then elseif goshawk then
alt = UTILS.FeetToMeters( 800 ) alt = UTILS.FeetToMeters( 800 )
speed = UTILS.KnotsToMps( 300 ) speed = UTILS.KnotsToMps( 300 )
elseif corsair then
alt = UTILS.FeetToMeters( 200 )
speed = UTILS.KnotsToMps( 110 )
end end
elseif step == AIRBOSS.PatternStep.EARLYBREAK then elseif step == AIRBOSS.PatternStep.EARLYBREAK then
@@ -5557,6 +5651,9 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
alt = UTILS.FeetToMeters( 800 ) alt = UTILS.FeetToMeters( 800 )
elseif skyhawk then elseif skyhawk then
alt = UTILS.FeetToMeters( 600 ) alt = UTILS.FeetToMeters( 600 )
elseif corsair then
alt = UTILS.FeetToMeters( 200 )
speed = UTILS.KnotsToMps( 100 )
end end
elseif step == AIRBOSS.PatternStep.LATEBREAK then elseif step == AIRBOSS.PatternStep.LATEBREAK then
@@ -5565,6 +5662,9 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
alt = UTILS.FeetToMeters( 800 ) alt = UTILS.FeetToMeters( 800 )
elseif skyhawk then elseif skyhawk then
alt = UTILS.FeetToMeters( 600 ) alt = UTILS.FeetToMeters( 600 )
elseif corsair then
alt = UTILS.FeetToMeters( 150 )
speed = UTILS.KnotsToMps( 100 )
end end
elseif step == AIRBOSS.PatternStep.ABEAM then elseif step == AIRBOSS.PatternStep.ABEAM then
@@ -5573,6 +5673,9 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
alt = UTILS.FeetToMeters( 600 ) alt = UTILS.FeetToMeters( 600 )
elseif skyhawk then elseif skyhawk then
alt = UTILS.FeetToMeters( 500 ) alt = UTILS.FeetToMeters( 500 )
elseif corsair then
alt = UTILS.FeetToMeters( 150 )
speed = UTILS.KnotsToMps( 90 )
end end
aoa = aoaac.OnSpeed aoa = aoaac.OnSpeed
@@ -5597,6 +5700,9 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
alt = UTILS.FeetToMeters( 500 ) alt = UTILS.FeetToMeters( 500 )
elseif harrier then elseif harrier then
alt = UTILS.FeetToMeters( 425 ) alt = UTILS.FeetToMeters( 425 )
elseif corsair then
alt = UTILS.FeetToMeters( 90 )
speed = UTILS.KnotsToMps( 90 )
end end
aoa = aoaac.OnSpeed aoa = aoaac.OnSpeed
@@ -5609,6 +5715,8 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
alt = UTILS.FeetToMeters( 430 ) -- Tomcat should be a bit higher as it intercepts the GS a bit higher. alt = UTILS.FeetToMeters( 430 ) -- Tomcat should be a bit higher as it intercepts the GS a bit higher.
elseif skyhawk then elseif skyhawk then
alt = UTILS.FeetToMeters( 370 ) -- ? alt = UTILS.FeetToMeters( 370 ) -- ?
elseif corsair then
alt = UTILS.FeetToMeters( 80 )
end end
-- Harrier wont get into wake pos. Runway is not angled and it stays port. -- Harrier wont get into wake pos. Runway is not angled and it stays port.
@@ -5624,6 +5732,8 @@ function AIRBOSS:_GetAircraftParameters( playerData, step )
alt = UTILS.FeetToMeters( 300 ) -- ? alt = UTILS.FeetToMeters( 300 ) -- ?
elseif harrier then elseif harrier then
alt=UTILS.FeetToMeters(312)-- 300-325 ft alt=UTILS.FeetToMeters(312)-- 300-325 ft
elseif corsair then
alt = UTILS.FeetToMeters( 80 )
end end
aoa = aoaac.OnSpeed aoa = aoaac.OnSpeed
@@ -6500,6 +6610,8 @@ function AIRBOSS:_LandAI( flight )
Speed = UTILS.KnotsToKmph( 175 ) Speed = UTILS.KnotsToKmph( 175 )
elseif flight.actype == AIRBOSS.AircraftCarrier.S3B or flight.actype == AIRBOSS.AircraftCarrier.S3BTANKER then elseif flight.actype == AIRBOSS.AircraftCarrier.S3B or flight.actype == AIRBOSS.AircraftCarrier.S3BTANKER then
Speed = UTILS.KnotsToKmph( 140 ) Speed = UTILS.KnotsToKmph( 140 )
elseif flight.actype == AIRBOSS.AircraftCarrier.CORSAIR or flight.actype == AIRBOSS.AircraftCarrier.CORSAIR_CW then
Speed = UTILS.KnotsToKmph( 100 )
end end
-- Carrier position. -- Carrier position.
@@ -8722,13 +8834,13 @@ function AIRBOSS:OnEventRemoveUnit( EventData )
-- Nil checks. -- Nil checks.
if EventData == nil then if EventData == nil then
self:E( self.lid .. "ERROR: EventData=nil in event REMOVEUNIT!" ) self:T( self.lid .. "ERROR: EventData=nil in event REMOVEUNIT!" )
self:E( EventData ) self:T( EventData )
return return
end end
if EventData.IniUnit == nil then if EventData.IniUnit == nil then
self:E( self.lid .. "ERROR: EventData.IniUnit=nil in event REMOVEUNIT!" ) self:T( self.lid .. "ERROR: EventData.IniUnit=nil in event REMOVEUNIT!" )
self:E( EventData ) self:T( EventData )
return return
end end
@@ -10295,6 +10407,9 @@ function AIRBOSS:_GetSternCoord()
elseif self.carriertype == AIRBOSS.CarrierType.FORRESTAL then elseif self.carriertype == AIRBOSS.CarrierType.FORRESTAL then
-- Forrestal -- Forrestal
self.sterncoord:Translate( self.carrierparam.sterndist, hdg, true, true ):Translate( 7.5, FB + 90, true, true ) self.sterncoord:Translate( self.carrierparam.sterndist, hdg, true, true ):Translate( 7.5, FB + 90, true, true )
elseif self.carriertype == AIRBOSS.CarrierType.ESSEX then
-- Forrestal
self.sterncoord:Translate( self.carrierparam.sterndist, hdg, true, true ):Translate( -1, FB + 90, true, true )
else else
-- Nimitz SC: translate 8 meters starboard wrt Final bearing. -- Nimitz SC: translate 8 meters starboard wrt Final bearing.
self.sterncoord:Translate( self.carrierparam.sterndist, hdg, true, true ):Translate( 9.5, FB + 90, true, true ) self.sterncoord:Translate( self.carrierparam.sterndist, hdg, true, true ):Translate( 9.5, FB + 90, true, true )
@@ -17047,7 +17162,7 @@ function AIRBOSS:_RemoveSectionMember( playerData, sectionmember )
return false return false
end end
--- Set all flights within 100 meters to be part of my section. --- Set all flights within maxsectiondistance meters to be part of my section (default: 100 meters).
-- @param #AIRBOSS self -- @param #AIRBOSS self
-- @param #string _unitName Name of the player unit. -- @param #string _unitName Name of the player unit.
function AIRBOSS:_SetSection( _unitName ) function AIRBOSS:_SetSection( _unitName )
@@ -17065,7 +17180,7 @@ function AIRBOSS:_SetSection( _unitName )
local mycoord = _unit:GetCoordinate() local mycoord = _unit:GetCoordinate()
-- Max distance up to which section members are allowed. -- Max distance up to which section members are allowed.
local dmax = 100 local dmax = self.maxsectiondistance
-- Check if player is in Marshal or pattern queue already. -- Check if player is in Marshal or pattern queue already.
local text local text

View File

@@ -31,7 +31,7 @@
-- @image OPS_CSAR.jpg -- @image OPS_CSAR.jpg
--- ---
-- Last Update Jan 2025 -- Last Update May 2025
------------------------------------------------------------------------- -------------------------------------------------------------------------
--- **CSAR** class, extends Core.Base#BASE, Core.Fsm#FSM --- **CSAR** class, extends Core.Base#BASE, Core.Fsm#FSM
@@ -263,6 +263,7 @@ CSAR = {
rescuedpilots = 0, rescuedpilots = 0,
limitmaxdownedpilots = true, limitmaxdownedpilots = true,
maxdownedpilots = 10, maxdownedpilots = 10,
useFIFOLimitReplacement = false, -- If true, it will remove the oldest downed pilot when a new one is added, if the limit is reached.
allheligroupset = nil, allheligroupset = nil,
topmenuname = "CSAR", topmenuname = "CSAR",
ADFRadioPwr = 1000, ADFRadioPwr = 1000,
@@ -313,7 +314,7 @@ CSAR.AircraftType["CH-47Fbl1"] = 31
--- CSAR class version. --- CSAR class version.
-- @field #string version -- @field #string version
CSAR.version="1.0.30" CSAR.version="1.0.33"
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
-- ToDo list -- ToDo list
@@ -468,7 +469,7 @@ function CSAR:New(Coalition, Template, Alias)
-- added 1.0.15 -- added 1.0.15
self.allowbronco = false -- set to true to use the Bronco mod as a CSAR plane self.allowbronco = false -- set to true to use the Bronco mod as a CSAR plane
self.ADFRadioPwr = 1000 self.ADFRadioPwr = 500
-- added 1.0.16 -- added 1.0.16
self.PilotWeight = 80 self.PilotWeight = 80
@@ -1145,17 +1146,6 @@ function CSAR:_EventHandler(EventData)
return self return self
end end
-- limit no of pilots in the field.
if self.limitmaxdownedpilots and self:_ReachedPilotLimit() then
self:T("Maxed Downed Pilot!")
return self
end
-- TODO: Over water check --- EVENTS.LandingAfterEjection NOT triggered by DCS, so handle csarUsePara = true case
-- might create dual pilots in edge cases
local wetfeet = false
local initdcscoord = nil local initdcscoord = nil
local initcoord = nil local initcoord = nil
@@ -1169,6 +1159,36 @@ function CSAR:_EventHandler(EventData)
self:T({initdcscoord}) self:T({initdcscoord})
end end
-- Remove downed pilot if already exists to replace with new one.
if _event.IniPlayerName then
local PilotTable = self.downedPilots --#CSAR.DownedPilot
local _foundPilot = nil
for _,_pilot in pairs(PilotTable) do
if _pilot.player == _event.IniPlayerName and _pilot.alive == true then
_foundPilot = _pilot
break
end
end
if _foundPilot then
self:T("Downed pilot already exists!")
_foundPilot.group:Destroy(false)
self:_RemoveNameFromDownedPilots(_foundPilot.name)
self:_CheckDownedPilotTable()
end
end
-- limit no of pilots in the field.
if self.limitmaxdownedpilots and self:_ReachedPilotLimit() then
self:T("Maxed Downed Pilot!")
return self
end
-- TODO: Over water check --- EVENTS.LandingAfterEjection NOT triggered by DCS, so handle csarUsePara = true case
-- might create dual pilots in edge cases
local wetfeet = false
--local surface = _unit:GetCoordinate():GetSurfaceType() --local surface = _unit:GetCoordinate():GetSurfaceType()
local surface = initcoord:GetSurfaceType() local surface = initcoord:GetSurfaceType()
@@ -2116,56 +2136,50 @@ end
--- (Internal) Determine distance to closest MASH. --- (Internal) Determine distance to closest MASH.
-- @param #CSAR self -- @param #CSAR self
-- @param Wrapper.Unit#UNIT _heli Helicopter #UNIT -- @param Wrapper.Unit#UNIT _heli Helicopter #UNIT
-- @return #CSAR self -- @return #number Distance in meters
-- @return #string MASH Name as string
function CSAR:_GetClosestMASH(_heli) function CSAR:_GetClosestMASH(_heli)
self:T(self.lid .. " _GetClosestMASH") self:T(self.lid .. " _GetClosestMASH")
local _mashset = self.mash -- Core.Set#SET_GROUP local _mashset = self.mash -- Core.Set#SET_GROUP
local _mashes = _mashset:GetSetObjects() -- #table local MashSets = {}
--local _mashes = _mashset.Set-- #table
table.insert(MashSets,_mashset.Set)
table.insert(MashSets,self.zonemashes.Set)
table.insert(MashSets,self.staticmashes.Set)
local _shortestDistance = -1 local _shortestDistance = -1
local _distance = 0 local _distance = 0
local _helicoord = _heli:GetCoordinate() local _helicoord = _heli:GetCoordinate()
local MashName = nil
local function GetCloseAirbase(coordinate,Coalition,Category)
local a=coordinate:GetVec3()
local distmin=math.huge
local airbase=nil
for DCSairbaseID, DCSairbase in pairs(world.getAirbases(Coalition)) do
local b=DCSairbase:getPoint()
local c=UTILS.VecSubstract(a,b)
local dist=UTILS.VecNorm(c)
if dist<distmin and (Category==nil or Category==DCSairbase:getDesc().category) then
distmin=dist
airbase=DCSairbase
end
end
return distmin
end
if self.allowFARPRescue then if self.allowFARPRescue then
local position = _heli:GetCoordinate() local position = _heli:GetCoordinate()
local afb,distance = position:GetClosestAirbase(nil,self.coalition) local afb,distance = position:GetClosestAirbase(nil,self.coalition)
_shortestDistance = distance _shortestDistance = distance
MashName = (afb ~= nil) and afb:GetName() or "Unknown"
end end
for _, _mashUnit in pairs(_mashes) do for _,_mashes in pairs(MashSets) do
if _mashUnit and _mashUnit:IsAlive() then for _, _mashUnit in pairs(_mashes or {}) do
local _mashcoord = _mashUnit:GetCoordinate() local _mashcoord
if _mashUnit and (not _mashUnit:IsInstanceOf("ZONE_BASE")) and _mashUnit:IsAlive() then
_mashcoord = _mashUnit:GetCoordinate()
elseif _mashUnit and _mashUnit:IsInstanceOf("ZONE_BASE") then
_mashcoord = _mashUnit:GetCoordinate()
end
_distance = self:_GetDistance(_helicoord, _mashcoord) _distance = self:_GetDistance(_helicoord, _mashcoord)
if _distance ~= nil and (_shortestDistance == -1 or _distance < _shortestDistance) then if _distance ~= nil and (_shortestDistance == -1 or _distance < _shortestDistance) then
_shortestDistance = _distance _shortestDistance = _distance
MashName = _mashUnit:GetName() or "Unknown"
end end
end end
end end
if _shortestDistance ~= -1 then if _shortestDistance ~= -1 then
return _shortestDistance return _shortestDistance, MashName
else else
return -1 return -1
end end
end end
--- (Internal) Display onboarded rescued pilots. --- (Internal) Display onboarded rescued pilots.
@@ -2323,9 +2337,9 @@ end
-- @param #CSAR self -- @param #CSAR self
-- @param Wrapper.Group#GROUP _group Group #GROUP object. -- @param Wrapper.Group#GROUP _group Group #GROUP object.
-- @param #number _freq Frequency to use -- @param #number _freq Frequency to use
-- @param #string _name Beacon Name to use -- @param #string BeaconName Beacon Name to use
-- @return #CSAR self -- @return #CSAR self
function CSAR:_AddBeaconToGroup(_group, _freq, _name) function CSAR:_AddBeaconToGroup(_group, _freq, BeaconName)
self:T(self.lid .. " _AddBeaconToGroup") self:T(self.lid .. " _AddBeaconToGroup")
if self.CreateRadioBeacons == false then return end if self.CreateRadioBeacons == false then return end
local _group = _group local _group = _group
@@ -2346,10 +2360,11 @@ function CSAR:_AddBeaconToGroup(_group, _freq, _name)
if _radioUnit then if _radioUnit then
local name = _radioUnit:GetName() local name = _radioUnit:GetName()
local Frequency = _freq -- Freq in Hertz local Frequency = _freq -- Freq in Hertz
local name = _radioUnit:GetName() --local name = _radioUnit:GetName()
local Sound = "l10n/DEFAULT/"..self.radioSound local Sound = "l10n/DEFAULT/"..self.radioSound
local vec3 = _radioUnit:GetVec3() or _radioUnit:GetPositionVec3() or {x=0,y=0,z=0} local vec3 = _radioUnit:GetVec3() or _radioUnit:GetPositionVec3() or {x=0,y=0,z=0}
trigger.action.radioTransmission(Sound, vec3, 0, false, Frequency, self.ADFRadioPwr or 1000,_name) -- Beacon in MP only runs for exactly 30secs straight self:I(self.lid..string.format("Added Radio Beacon %d Hertz | Name %s | Position {%d,%d,%d}",Frequency,BeaconName,vec3.x,vec3.y,vec3.z))
trigger.action.radioTransmission(Sound, vec3, 0, true, Frequency, self.ADFRadioPwr or 500,BeaconName) -- Beacon in MP only runs for exactly 30secs straight
end end
end end
@@ -2370,9 +2385,13 @@ function CSAR:_RefreshRadioBeacons()
local group = pilot.group local group = pilot.group
local frequency = pilot.frequency or 0 -- thanks to @Thrud local frequency = pilot.frequency or 0 -- thanks to @Thrud
local bname = pilot.BeaconName or pilot.name..math.random(1,100000) local bname = pilot.BeaconName or pilot.name..math.random(1,100000)
trigger.action.stopRadioTransmission(bname) --trigger.action.stopRadioTransmission(bname)
if group and group:IsAlive() and frequency > 0 then if group and group:IsAlive() and frequency > 0 then
self:_AddBeaconToGroup(group,frequency,bname) --self:_AddBeaconToGroup(group,frequency,bname)
else
if frequency > 0 then
trigger.action.stopRadioTransmission(bname)
end
end end
end end
end end
@@ -2403,6 +2422,21 @@ function CSAR:_ReachedPilotLimit()
local islimited = self.limitmaxdownedpilots local islimited = self.limitmaxdownedpilots
local count = self:_CountActiveDownedPilots() local count = self:_CountActiveDownedPilots()
if islimited and (count >= limit) then if islimited and (count >= limit) then
if self.useFIFOLimitReplacement then
local oldIndex = -1
local oldDownedPilot = nil
for _index, _downedpilot in pairs(self.downedPilots) do
oldIndex = _index
oldDownedPilot = _downedpilot
break
end
if oldDownedPilot then
oldDownedPilot.group:Destroy(false)
oldDownedPilot.alive = false
self:_CheckDownedPilotTable()
return false
end
end
return true return true
else else
return false return false
@@ -2454,9 +2488,10 @@ function CSAR:onafterStart(From, Event, To)
self.mash = SET_GROUP:New():FilterCoalitions(self.coalitiontxt):FilterPrefixes(self.mashprefix):FilterStart() self.mash = SET_GROUP:New():FilterCoalitions(self.coalitiontxt):FilterPrefixes(self.mashprefix):FilterStart()
local staticmashes = SET_STATIC:New():FilterCoalitions(self.coalitiontxt):FilterPrefixes(self.mashprefix):FilterOnce() self.staticmashes = SET_STATIC:New():FilterCoalitions(self.coalitiontxt):FilterPrefixes(self.mashprefix):FilterStart()
local zonemashes = SET_ZONE:New():FilterPrefixes(self.mashprefix):FilterOnce() self.zonemashes = SET_ZONE:New():FilterPrefixes(self.mashprefix):FilterStart()
--[[
if staticmashes:Count() > 0 then if staticmashes:Count() > 0 then
for _,_mash in pairs(staticmashes.Set) do for _,_mash in pairs(staticmashes.Set) do
self.mash:AddObject(_mash) self.mash:AddObject(_mash)
@@ -2464,10 +2499,13 @@ function CSAR:onafterStart(From, Event, To)
end end
if zonemashes:Count() > 0 then if zonemashes:Count() > 0 then
self:T("Adding zones to self.mash SET")
for _,_mash in pairs(zonemashes.Set) do for _,_mash in pairs(zonemashes.Set) do
self.mash:AddObject(_mash) self.mash:AddObject(_mash)
end end
self:T("Objects in SET: "..self.mash:Count())
end end
--]]
if not self.coordinate then if not self.coordinate then
local csarhq = self.mash:GetRandom() local csarhq = self.mash:GetRandom()

View File

@@ -20,11 +20,12 @@
-- --
-- ### Author: **Applevangelist** (Moose Version), ***Ciribob*** (original), Thanks to: Shadowze, Cammel (testing), bbirchnz (additional code!!) -- ### Author: **Applevangelist** (Moose Version), ***Ciribob*** (original), Thanks to: Shadowze, Cammel (testing), bbirchnz (additional code!!)
-- ### Repack addition for crates: **Raiden** -- ### Repack addition for crates: **Raiden**
-- ### Additional cool features: **Lekaa**
-- --
-- @module Ops.CTLD -- @module Ops.CTLD
-- @image OPS_CTLD.jpg -- @image OPS_CTLD.jpg
-- Last Update April 2025 -- Last Update May 2025
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
@@ -865,6 +866,7 @@ do
-- my_ctld.TroopUnloadDistGroundHook = 15 -- On the ground, unload troops this far behind the Chinook -- my_ctld.TroopUnloadDistGroundHook = 15 -- On the ground, unload troops this far behind the Chinook
-- my_ctld.TroopUnloadDistHoverHook = 5 -- When hovering, unload troops this far behind the Chinook -- my_ctld.TroopUnloadDistHoverHook = 5 -- When hovering, unload troops this far behind the Chinook
-- my_ctld.showstockinmenuitems = false -- When set to true, the menu lines will also show the remaining items in stock (that is, if you set any), downside is that the menu for all will be build every 30 seconds anew. -- my_ctld.showstockinmenuitems = false -- When set to true, the menu lines will also show the remaining items in stock (that is, if you set any), downside is that the menu for all will be build every 30 seconds anew.
-- my_ctld.onestepmenu = false -- When set to true, the menu will create Drop and build, Get and load, Pack and remove, Pack and load, Pack. it will be a 1 step solution.
-- --
-- ## 2.1 CH-47 Chinook support -- ## 2.1 CH-47 Chinook support
-- --
@@ -1412,7 +1414,7 @@ CTLD.FixedWingTypes = {
--- CTLD class version. --- CTLD class version.
-- @field #string version -- @field #string version
CTLD.version="1.2.33" CTLD.version="1.3.35"
--- Instantiate a new CTLD. --- Instantiate a new CTLD.
-- @param #CTLD self -- @param #CTLD self
@@ -1591,6 +1593,7 @@ function CTLD:New(Coalition, Prefixes, Alias)
self.subcats = {} self.subcats = {}
self.subcatsTroop = {} self.subcatsTroop = {}
self.showstockinmenuitems = false self.showstockinmenuitems = false
self.onestepmenu = false
-- disallow building in loadzones -- disallow building in loadzones
self.nobuildinloadzones = true self.nobuildinloadzones = true
@@ -2913,10 +2916,10 @@ function CTLD:_GetCrates(Group, Unit, Cargo, number, drop, pack)
if drop then if drop then
text = string.format("Crates for %s have been dropped!",cratename) text = string.format("Crates for %s have been dropped!",cratename)
self:__CratesDropped(1, Group, Unit, droppedcargo) self:__CratesDropped(1, Group, Unit, droppedcargo)
end else
self:_SendMessage(text, 10, false, Group) self:_SendMessage(text, 10, false, Group)
end
self:_RefreshLoadCratesMenu(Group, Unit) self:_RefreshLoadCratesMenu(Group, Unit)
return self return self
end end
@@ -3564,7 +3567,7 @@ end
function CTLD:IsFixedWing(Unit) function CTLD:IsFixedWing(Unit)
local typename = Unit:GetTypeName() or "none" local typename = Unit:GetTypeName() or "none"
for _,_name in pairs(self.FixedWingTypes or {}) do for _,_name in pairs(self.FixedWingTypes or {}) do
if typename == _name or string.find(typename,_name,1,true) then if _name and (typename==_name or string.find(typename,_name,1,true))then
return true return true
end end
end end
@@ -3576,7 +3579,10 @@ end
-- @param Wrapper.Unit#UNIT Unit -- @param Wrapper.Unit#UNIT Unit
-- @return #boolean Outcome -- @return #boolean Outcome
function CTLD:IsHook(Unit) function CTLD:IsHook(Unit)
if Unit and string.find(Unit:GetTypeName(),"CH.47") then if not Unit then return false end
local typeName = Unit:GetTypeName()
if not typeName then return false end
if string.find(typeName, "CH.47") then
return true return true
else else
return false return false
@@ -3766,7 +3772,6 @@ function CTLD:_UnloadCrates(Group, Unit)
self:T(self.lid .. " _UnloadCrates") self:T(self.lid .. " _UnloadCrates")
if not self.dropcratesanywhere then -- #1570 if not self.dropcratesanywhere then -- #1570
-- check if we are in DROP zone
local inzone, zonename, zone, distance = self:IsUnitInZone(Unit,CTLD.CargoZoneType.DROP) local inzone, zonename, zone, distance = self:IsUnitInZone(Unit,CTLD.CargoZoneType.DROP)
if not inzone then if not inzone then
self:_SendMessage("You are not close enough to a drop zone!", 10, false, Group) self:_SendMessage("You are not close enough to a drop zone!", 10, false, Group)
@@ -3775,46 +3780,60 @@ function CTLD:_UnloadCrates(Group, Unit)
end end
end end
end end
-- Door check
if self.pilotmustopendoors and not UTILS.IsLoadingDoorOpen(Unit:GetName()) then if self.pilotmustopendoors and not UTILS.IsLoadingDoorOpen(Unit:GetName()) then
self:_SendMessage("You need to open the door(s) to drop cargo!", 10, false, Group) self:_SendMessage("You need to open the door(s) to drop cargo!", 10, false, Group)
if not self.debug then return self end if not self.debug then return self end
end end
-- check for hover unload local hoverunload = self:IsCorrectHover(Unit)
local hoverunload = self:IsCorrectHover(Unit) --if true we\'re hovering in parameters
local IsHerc = self:IsFixedWing(Unit) local IsHerc = self:IsFixedWing(Unit)
local IsHook = self:IsHook(Unit) local IsHook = self:IsHook(Unit)
if IsHerc and (not IsHook) then if IsHerc and (not IsHook) then
-- no hover but airdrop here
hoverunload = self:IsCorrectFlightParameters(Unit) hoverunload = self:IsCorrectFlightParameters(Unit)
end end
-- check if we\'re landed
local grounded = not self:IsUnitInAir(Unit) local grounded = not self:IsUnitInAir(Unit)
-- Get what we have loaded
local unitname = Unit:GetName() local unitname = Unit:GetName()
if self.Loaded_Cargo[unitname] and (grounded or hoverunload) then if self.Loaded_Cargo[unitname] and (grounded or hoverunload) then
local loadedcargo = self.Loaded_Cargo[unitname] or {} -- #CTLD.LoadedCargo local loadedcargo = self.Loaded_Cargo[unitname] or {}
-- looking for crate
local cargotable = loadedcargo.Cargo local cargotable = loadedcargo.Cargo
local droppedCount = {}
local neededMap = {}
for _,_cargo in pairs (cargotable) do for _,_cargo in pairs (cargotable) do
local cargo = _cargo -- #CTLD_CARGO local cargo = _cargo
local type = cargo:GetType() -- #CTLD_CARGO.Enum local type = cargo:GetType()
if type ~= CTLD_CARGO.Enum.TROOPS and type ~= CTLD_CARGO.Enum.ENGINEERS and type ~= CTLD_CARGO.Enum.GCLOADABLE and (not cargo:WasDropped() or self.allowcratepickupagain) then if type ~= CTLD_CARGO.Enum.TROOPS and type ~= CTLD_CARGO.Enum.ENGINEERS and type ~= CTLD_CARGO.Enum.GCLOADABLE and (not cargo:WasDropped() or self.allowcratepickupagain) then
-- unload crates
self:_GetCrates(Group, Unit, cargo, 1, true) self:_GetCrates(Group, Unit, cargo, 1, true)
cargo:SetWasDropped(true) cargo:SetWasDropped(true)
cargo:SetHasMoved(true) cargo:SetHasMoved(true)
local cname = cargo:GetName() or "Unknown"
droppedCount[cname] = (droppedCount[cname] or 0) + 1
if not neededMap[cname] then
neededMap[cname] = cargo:GetCratesNeeded() or 1
end end
end end
-- cleanup load list end
local loaded = {} -- #CTLD.LoadedCargo for cname,count in pairs(droppedCount) do
local needed = neededMap[cname] or 1
if needed > 1 then
local full = math.floor(count/needed)
local left = count % needed
if full > 0 and left == 0 then
self:_SendMessage(string.format("Dropped %d %s.",full,cname),10,false,Group)
elseif full > 0 and left > 0 then
self:_SendMessage(string.format("Dropped %d %s(s), with %d leftover crate(s).",full,cname,left),10,false,Group)
else
self:_SendMessage(string.format("Dropped %d/%d crate(s) of %s.",count,needed,cname),15,false,Group)
end
else
self:_SendMessage(string.format("Dropped %d %s(s).",count,cname),10,false,Group)
end
end
local loaded = {}
loaded.Troopsloaded = 0 loaded.Troopsloaded = 0
loaded.Cratesloaded = 0 loaded.Cratesloaded = 0
loaded.Cargo = {} loaded.Cargo = {}
for _,_cargo in pairs (cargotable) do for _,_cargo in pairs (cargotable) do
local cargo = _cargo -- #CTLD_CARGO local cargo = _cargo
local type = cargo:GetType() -- #CTLD_CARGO.Enum local type = cargo:GetType()
local size = cargo:GetCratesNeeded() local size = cargo:GetCratesNeeded()
if type == CTLD_CARGO.Enum.TROOPS or type == CTLD_CARGO.Enum.ENGINEERS then if type == CTLD_CARGO.Enum.TROOPS or type == CTLD_CARGO.Enum.ENGINEERS then
table.insert(loaded.Cargo,_cargo) table.insert(loaded.Cargo,_cargo)
@@ -3838,14 +3857,15 @@ function CTLD:_UnloadCrates(Group, Unit)
end end
end end
return self return self
end end
--- (Internal) Function to build nearby crates. --- (Internal) Function to build nearby crates.
-- @param #CTLD self -- @param #CTLD self
-- @param Wrapper.Group#GROUP Group -- @param Wrapper.Group#GROUP Group
-- @param Wrapper.Unit#UNIT Unit -- @param Wrapper.Unit#UNIT Unit
-- @param #boolean Engineering If true build is by an engineering team. -- @param #boolean Engineering If true build is by an engineering team.
function CTLD:_BuildCrates(Group, Unit,Engineering) -- @param #boolean MultiDrop If true and not engineering or FOB, vary position a bit.
function CTLD:_BuildCrates(Group, Unit,Engineering,MultiDrop)
self:T(self.lid .. " _BuildCrates") self:T(self.lid .. " _BuildCrates")
-- avoid users trying to build from flying Hercs -- avoid users trying to build from flying Hercs
if self:IsFixedWing(Unit) and self.enableFixedWing and not Engineering then if self:IsFixedWing(Unit) and self.enableFixedWing and not Engineering then
@@ -3939,12 +3959,13 @@ function CTLD:_BuildCrates(Group, Unit,Engineering)
if build.CanBuild then if build.CanBuild then
self:_CleanUpCrates(crates,build,number) self:_CleanUpCrates(crates,build,number)
if self.buildtime and self.buildtime > 0 then if self.buildtime and self.buildtime > 0 then
local buildtimer = TIMER:New(self._BuildObjectFromCrates,self,Group,Unit,build,false,Group:GetCoordinate()) local buildtimer = TIMER:New(self._BuildObjectFromCrates,self,Group,Unit,build,false,Group:GetCoordinate(),MultiDrop)
buildtimer:Start(self.buildtime) buildtimer:Start(self.buildtime)
self:_SendMessage(string.format("Build started, ready in %d seconds!",self.buildtime),15,false,Group) self:_SendMessage(string.format("Build started, ready in %d seconds!",self.buildtime),15,false,Group)
self:__CratesBuildStarted(1,Group,Unit) self:__CratesBuildStarted(1,Group,Unit)
self:_RefreshDropTroopsMenu(Group,Unit)
else else
self:_BuildObjectFromCrates(Group,Unit,build) self:_BuildObjectFromCrates(Group,Unit,build,false,nil,MultiDrop)
end end
end end
end end
@@ -3983,13 +4004,14 @@ function CTLD:_PackCratesNearby(Group, Unit)
_Group:Destroy() -- if a match is found destroy the Wrapper.Group#GROUP near the player _Group:Destroy() -- if a match is found destroy the Wrapper.Group#GROUP near the player
self:_GetCrates(Group, Unit, _entry, nil, false, true) -- spawn the appropriate crates near the player self:_GetCrates(Group, Unit, _entry, nil, false, true) -- spawn the appropriate crates near the player
self:_RefreshLoadCratesMenu(Group,Unit) -- call the refresher to show the crates in the menu self:_RefreshLoadCratesMenu(Group,Unit) -- call the refresher to show the crates in the menu
return self return true
end end
end end
end end
end end
end end
return self self:_SendMessage("Nothing to pack at this distance pilot!",10,false,Group)
return false
end end
--- (Internal) Function to repair nearby vehicles / FOBs --- (Internal) Function to repair nearby vehicles / FOBs
@@ -4082,7 +4104,8 @@ end
-- @param #CTLD.Buildable Build -- @param #CTLD.Buildable Build
-- @param #boolean Repair If true this is a repair and not a new build -- @param #boolean Repair If true this is a repair and not a new build
-- @param Core.Point#COORDINATE RepairLocation Location for repair (e.g. where the destroyed unit was) -- @param Core.Point#COORDINATE RepairLocation Location for repair (e.g. where the destroyed unit was)
function CTLD:_BuildObjectFromCrates(Group,Unit,Build,Repair,RepairLocation) -- @param #boolean MultiDrop if true and not a repair, vary location a bit if not a FOB
function CTLD:_BuildObjectFromCrates(Group,Unit,Build,Repair,RepairLocation,MultiDrop)
self:T(self.lid .. " _BuildObjectFromCrates") self:T(self.lid .. " _BuildObjectFromCrates")
-- Spawn-a-crate-content -- Spawn-a-crate-content
if Group and Group:IsAlive() or (RepairLocation and not Repair) then if Group and Group:IsAlive() or (RepairLocation and not Repair) then
@@ -4099,7 +4122,7 @@ function CTLD:_BuildObjectFromCrates(Group,Unit,Build,Repair,RepairLocation)
if type(temptable) == "string" then if type(temptable) == "string" then
temptable = {temptable} temptable = {temptable}
end end
local zone = nil local zone = nil -- Core.Zone#ZONE_RADIUS
if RepairLocation and not Repair then if RepairLocation and not Repair then
-- timed build -- timed build
zone = ZONE_RADIUS:New(string.format("Build zone-%d",math.random(1,10000)),RepairLocation:GetVec2(),100) zone = ZONE_RADIUS:New(string.format("Build zone-%d",math.random(1,10000)),RepairLocation:GetVec2(),100)
@@ -4108,6 +4131,10 @@ function CTLD:_BuildObjectFromCrates(Group,Unit,Build,Repair,RepairLocation)
end end
--local randomcoord = zone:GetRandomCoordinate(35):GetVec2() --local randomcoord = zone:GetRandomCoordinate(35):GetVec2()
local randomcoord = Build.Coord or zone:GetRandomCoordinate(35):GetVec2() local randomcoord = Build.Coord or zone:GetRandomCoordinate(35):GetVec2()
if MultiDrop and (not Repair) and canmove then
-- coordinate may be the same, avoid
local randomcoord = zone:GetRandomCoordinate(35):GetVec2()
end
if Repair then if Repair then
randomcoord = RepairLocation:GetVec2() randomcoord = RepairLocation:GetVec2()
end end
@@ -4199,11 +4226,91 @@ function CTLD:_CleanUpCrates(Crates,Build,Number)
return self return self
end end
--- (Internal) Helper - Drop **all** loaded crates nearby and build them.
-- @param Wrapper.Group#GROUP Group The calling group
-- @param Wrapper.Unit#UNIT Unit The calling unit
function CTLD:_DropAndBuild(Group,Unit)
if self.nobuildinloadzones then
if self:IsUnitInZone(Unit,CTLD.CargoZoneType.LOAD) then
self:_SendMessage("You cannot build in a loading area, Pilot!",10,false,Group)
return self
end
end
self:_UnloadCrates(Group,Unit)
timer.scheduleFunction(function() self:_BuildCrates(Group,Unit,false,true) end,{},timer.getTime()+1)
end
--- (Internal) Helper - Drop a **single** crate set and build it.
-- @param Wrapper.Group#GROUP Group The calling group
-- @param Wrapper.Unit#UNIT Unit The calling unit
-- @param number setIndex Index of the crate-set to drop
function CTLD:_DropSingleAndBuild(Group,Unit,setIndex)
if self.nobuildinloadzones then
if self:IsUnitInZone(Unit,CTLD.CargoZoneType.LOAD) then
self:_SendMessage("You cannot build in a loading area, Pilot!",10,false,Group)
return self
end
end
self:_UnloadSingleCrateSet(Group,Unit,setIndex)
timer.scheduleFunction(function() self:_BuildCrates(Group,Unit,false) end,{},timer.getTime()+1)
end
--- (Internal) Helper - Pack crates near the unit and load them.
-- @param Wrapper.Group#GROUP Group The calling group
-- @param Wrapper.Unit#UNIT Unit The calling unit
function CTLD:_PackAndLoad(Group,Unit)
if self.pilotmustopendoors and not UTILS.IsLoadingDoorOpen(Unit:GetName()) then
self:_SendMessage("You need to open the door(s) to load cargo!",10,false,Group)
return self
end
if not self:_PackCratesNearby(Group,Unit) then
return self
end
timer.scheduleFunction(function() self:_LoadCratesNearby(Group,Unit) end,{},timer.getTime()+1)
return self
end
--- (Internal) Helper - Pack crates near the unit and then remove them.
-- @param Wrapper.Group#GROUP Group The calling group
-- @param Wrapper.Unit#UNIT Unit The calling unit
function CTLD:_PackAndRemove(Group,Unit)
if not self:_PackCratesNearby(Group,Unit) then
return self
end
timer.scheduleFunction(function() self:_RemoveCratesNearby(Group,Unit) end,{},timer.getTime()+1)
return self
end
--- (Internal) Helper - get and load in one step
-- @param Wrapper.Group#GROUP Group The calling group
-- @param Wrapper.Unit#UNIT Unit The calling unit
function CTLD:_GetAndLoad(Group,Unit,cargoObj)
if self.pilotmustopendoors and not UTILS.IsLoadingDoorOpen(Unit:GetName()) then
self:_SendMessage("You need to open the door(s) to load cargo!",10,false,Group)
return self
end
self:_GetCrates(Group,Unit,cargoObj)
timer.scheduleFunction(function() self:_LoadSingleCrateSet(Group,Unit,cargoObj.Name) end,{},timer.getTime()+1)
end
-- @param Wrapper.Group#GROUP Group The players group that triggered the action
-- @param Wrapper.Unit#UNIT Unit The unit performing the pack-and-load
function CTLD:_GetAllAndLoad(Group,Unit)
if self.pilotmustopendoors and not UTILS.IsLoadingDoorOpen(Unit:GetName()) then
self:_SendMessage("You need to open the door(s) to load cargo!",10,false,Group)
return self
end
timer.scheduleFunction(function() self:_LoadCratesNearby(Group,Unit) end,{},timer.getTime()+1)
end
--- (Internal) Housekeeping - Function to refresh F10 menus. --- (Internal) Housekeeping - Function to refresh F10 menus.
-- @param #CTLD self -- @param #CTLD self
-- @return #CTLD self -- @return #CTLD self
function CTLD:_RefreshF10Menus() function CTLD:_RefreshF10Menus()
self:T(self.lid .. " _RefreshF10Menus") self:T(self.lid .. " _RefreshF10Menus")
self.onestepmenu = self.onestepmenu or false -- hybrid toggle (default = false)
-- 1) Gather all the pilot groups from our Set -- 1) Gather all the pilot groups from our Set
local PlayerSet = self.PilotGroups local PlayerSet = self.PilotGroups
@@ -4314,7 +4421,6 @@ function CTLD:_RefreshF10Menus()
local menutext = cargoObj.Name local menutext = cargoObj.Name
if (stock >= 0) and (self.showstockinmenuitems == true) then menutext = menutext.." ["..stock.."]" end if (stock >= 0) and (self.showstockinmenuitems == true) then menutext = menutext.." ["..stock.."]" end
MENU_GROUP_COMMAND:New(_group, menutext, troopsmenu, self._LoadTroops, self, _group, _unit, cargoObj) MENU_GROUP_COMMAND:New(_group, menutext, troopsmenu, self._LoadTroops, self, _group, _unit, cargoObj)
end end
end end
end end
@@ -4340,11 +4446,66 @@ function CTLD:_RefreshF10Menus()
_group.MyTopCratesMenu = topcrates _group.MyTopCratesMenu = topcrates
-- Build the “Get Crates” sub-menu items -- Build the “Get Crates” sub-menu items
local cratesmenu = MENU_GROUP:New(_group, "Get Crates", topcrates) local cratesmenu = MENU_GROUP:New(_group,"Get Crates",topcrates)
if self.onestepmenu then
if self.usesubcats then
local subcatmenus = {}
for catName,_ in pairs(self.subcats) do
subcatmenus[catName] = MENU_GROUP:New(_group,catName,cratesmenu)
end
for _,cargoObj in pairs(self.Cargo_Crates) do
if not cargoObj.DontShowInMenu then
local txt = string.format("Crate %s (%dkg)",cargoObj.Name,cargoObj.PerCrateMass or 0)
if cargoObj.Location then txt = txt.."[R]" end
local stock = cargoObj:GetStock()
if stock>=0 and self.showstockinmenuitems then txt = txt.."["..stock.."]" end
local mSet = MENU_GROUP:New(_group,txt,subcatmenus[cargoObj.Subcategory])
MENU_GROUP_COMMAND:New(_group,"Get",mSet,self._GetCrates,self,_group,_unit,cargoObj)
MENU_GROUP_COMMAND:New(_group,"Get and Load",mSet,self._GetAndLoad,self,_group,_unit,cargoObj)
end
end
for _,cargoObj in pairs(self.Cargo_Statics) do
if not cargoObj.DontShowInMenu then
local txt = string.format("Crate %s (%dkg)",cargoObj.Name,cargoObj.PerCrateMass or 0)
if cargoObj.Location then txt = txt.."[R]" end
local stock = cargoObj:GetStock()
if stock>=0 and self.showstockinmenuitems then txt = txt.."["..stock.."]" end
local mSet = MENU_GROUP:New(_group,txt,subcatmenus[cargoObj.Subcategory])
MENU_GROUP_COMMAND:New(_group,"Get",mSet,self._GetCrates,self,_group,_unit,cargoObj)
MENU_GROUP_COMMAND:New(_group,"Get and Load",mSet,self._GetAndLoad,self,_group,_unit,cargoObj)
end
end
else
for _,cargoObj in pairs(self.Cargo_Crates) do
if not cargoObj.DontShowInMenu then
local txt = string.format("Crate %s (%dkg)",cargoObj.Name,cargoObj.PerCrateMass or 0)
if cargoObj.Location then txt = txt.."[R]" end
local stock = cargoObj:GetStock()
if stock>=0 and self.showstockinmenuitems then txt = txt.."["..stock.."]" end
local mSet = MENU_GROUP:New(_group,txt,cratesmenu)
MENU_GROUP_COMMAND:New(_group,"Get",mSet,self._GetCrates,self,_group,_unit,cargoObj)
MENU_GROUP_COMMAND:New(_group,"Get and Load",mSet,self._GetAndLoad,self,_group,_unit,cargoObj)
end
end
for _,cargoObj in pairs(self.Cargo_Statics) do
if not cargoObj.DontShowInMenu then
local txt = string.format("Crate %s (%dkg)",cargoObj.Name,cargoObj.PerCrateMass or 0)
if cargoObj.Location then txt = txt.."[R]" end
local stock = cargoObj:GetStock()
if stock>=0 and self.showstockinmenuitems then txt = txt.."["..stock.."]" end
local mSet = MENU_GROUP:New(_group,txt,cratesmenu)
MENU_GROUP_COMMAND:New(_group,"Get",mSet,self._GetCrates,self,_group,_unit,cargoObj)
MENU_GROUP_COMMAND:New(_group,"Get and Load",mSet,self._GetAndLoad,self,_group,_unit,cargoObj)
end
end
end
else
if self.usesubcats then if self.usesubcats then
local subcatmenus = {} local subcatmenus = {}
for catName, _ in pairs(self.subcats) do for catName, _ in pairs(self.subcats) do
subcatmenus[catName] = MENU_GROUP:New(_group, catName, cratesmenu) subcatmenus[catName] = MENU_GROUP:New(_group, catName, cratesmenu) -- fixed variable case
end end
for _, cargoObj in pairs(self.Cargo_Crates) do for _, cargoObj in pairs(self.Cargo_Crates) do
if not cargoObj.DontShowInMenu then if not cargoObj.DontShowInMenu then
@@ -4384,14 +4545,15 @@ function CTLD:_RefreshF10Menus()
end end
end end
end end
end
local loadCratesMenu=MENU_GROUP:New(_group,"Load Crates",topcrates) local loadCratesMenu=MENU_GROUP:New(_group,"Load Crates",topcrates)
_group.MyLoadCratesMenu=loadCratesMenu _group.MyLoadCratesMenu=loadCratesMenu
MENU_GROUP_COMMAND:New(_group,"Load ALL",loadCratesMenu,self._LoadCratesNearby,self,_group,_unit) MENU_GROUP_COMMAND:New(_group,"Load ALL",loadCratesMenu,self._LoadCratesNearby,self,_group,_unit)
MENU_GROUP_COMMAND:New(_group,"Show loadable crates",loadCratesMenu,self._RefreshLoadCratesMenu,self,_group,_unit) MENU_GROUP_COMMAND:New(_group,"Show loadable crates",loadCratesMenu,self._RefreshLoadCratesMenu,self,_group,_unit)
local dropCratesMenu=MENU_GROUP:New(_group,"Drop Crates",topcrates) local dropCratesMenu = MENU_GROUP:New(_group,"Drop Crates",topcrates)
topcrates.DropCratesMenu=dropCratesMenu topcrates.DropCratesMenu = dropCratesMenu
if not self.nobuildmenu then if not self.nobuildmenu then
MENU_GROUP_COMMAND:New(_group, "Build crates", topcrates, self._BuildCrates, self, _group, _unit) MENU_GROUP_COMMAND:New(_group, "Build crates", topcrates, self._BuildCrates, self, _group, _unit)
@@ -4401,8 +4563,16 @@ function CTLD:_RefreshF10Menus()
local removecratesmenu = MENU_GROUP:New(_group, "Remove crates", topcrates) local removecratesmenu = MENU_GROUP:New(_group, "Remove crates", topcrates)
MENU_GROUP_COMMAND:New(_group, "Remove crates nearby", removecratesmenu, self._RemoveCratesNearby, self, _group, _unit) MENU_GROUP_COMMAND:New(_group, "Remove crates nearby", removecratesmenu, self._RemoveCratesNearby, self, _group, _unit)
if self.onestepmenu then
local mPack=MENU_GROUP:New(_group,"Pack crates",topcrates)
MENU_GROUP_COMMAND:New(_group,"Pack",mPack,self._PackCratesNearby,self,_group,_unit)
MENU_GROUP_COMMAND:New(_group,"Pack and Load",mPack,self._PackAndLoad,self,_group,_unit)
MENU_GROUP_COMMAND:New(_group,"Pack and Remove",mPack,self._PackAndRemove,self,_group,_unit)
MENU_GROUP_COMMAND:New(_group, "List crates nearby", topcrates, self._ListCratesNearby, self, _group, _unit)
else
MENU_GROUP_COMMAND:New(_group, "Pack crates", topcrates, self._PackCratesNearby, self, _group, _unit) MENU_GROUP_COMMAND:New(_group, "Pack crates", topcrates, self._PackCratesNearby, self, _group, _unit)
MENU_GROUP_COMMAND:New(_group, "List crates nearby", topcrates, self._ListCratesNearby, self, _group, _unit) MENU_GROUP_COMMAND:New(_group, "List crates nearby", topcrates, self._ListCratesNearby, self, _group, _unit)
end
local uName = _unit:GetName() local uName = _unit:GetName()
local loadedData = self.Loaded_Cargo[uName] local loadedData = self.Loaded_Cargo[uName]
@@ -4423,8 +4593,6 @@ function CTLD:_RefreshF10Menus()
end end
end end
----------------------------------------------------- -----------------------------------------------------
-- Misc submenus -- Misc submenus
----------------------------------------------------- -----------------------------------------------------
@@ -4453,7 +4621,7 @@ function CTLD:_RefreshF10Menus()
-- Mark we built the menu -- Mark we built the menu
self.MenusDone[_unitName] = true self.MenusDone[_unitName] = true
self:_RefreshLoadCratesMenu(_group, _unit) self:_RefreshLoadCratesMenu(_group,_unit)
self:_RefreshDropCratesMenu(_group,_unit) self:_RefreshDropCratesMenu(_group,_unit)
end -- if _group end -- if _group
@@ -4464,45 +4632,53 @@ function CTLD:_RefreshF10Menus()
end -- for all pilot units end -- for all pilot units
return self return self
end end
--- (Internal) Function to refresh the menu for load crates. Triggered from land/getcrate/pack and more --- (Internal) Function to refresh the menu for load crates. Triggered from land/getcrate/pack and more
-- @param #CTLD self -- @param #CTLD self
-- @param Wrapper.Group#GROUP Group The calling group. -- @param Wrapper.Group#GROUP Group The calling group.
-- @param Wrapper.Unit#UNIT Unit The calling unit. -- @param Wrapper.Unit#UNIT Unit The calling unit.
-- @return #CTLD self -- @return #CTLD self
function CTLD:_RefreshLoadCratesMenu(Group, Unit) function CTLD:_RefreshLoadCratesMenu(Group,Unit)
if not Group.MyLoadCratesMenu then return end if not Group.MyLoadCratesMenu then return end
Group.MyLoadCratesMenu:RemoveSubMenus() Group.MyLoadCratesMenu:RemoveSubMenus()
local d = self.CrateDistance or 35 local d=self.CrateDistance or 35
local nearby, n = self:_FindCratesNearby(Group, Unit, d, true, true) local nearby,n=self:_FindCratesNearby(Group,Unit,d,true,true)
if n == 0 then if n==0 then
MENU_GROUP_COMMAND:New(Group, "No crates found! Rescan?", Group.MyLoadCratesMenu, function() self:_RefreshLoadCratesMenu(Group, Unit) end) MENU_GROUP_COMMAND:New(Group,"No crates found! Rescan?",Group.MyLoadCratesMenu,function() self:_RefreshLoadCratesMenu(Group,Unit) end)
return return
end end
MENU_GROUP_COMMAND:New(Group, "Load ALL", Group.MyLoadCratesMenu, self._LoadCratesNearby, self, Group, Unit) MENU_GROUP_COMMAND:New(Group,"Load ALL",Group.MyLoadCratesMenu,self._LoadCratesNearby,self,Group,Unit)
local cargoByName = {}
for _, crate in pairs(nearby) do local cargoByName={}
local cName = crate:GetName() for _,crate in pairs(nearby) do
cargoByName[cName] = cargoByName[cName] or {} local name=crate:GetName()
table.insert(cargoByName[cName], crate) cargoByName[name]=cargoByName[name] or{}
table.insert(cargoByName[name],crate)
end end
for cName, cList in pairs(cargoByName) do local lineIndex=1
local needed = cList[1]:GetCratesNeeded() or 1 for cName,list in pairs(cargoByName) do
local found = #cList local needed=list[1]:GetCratesNeeded() or 1
table.sort(list,function(a,b)return a:GetID()<b:GetID() end)
local line local i=1
if found >= needed then while i<=#list do
line = string.format("Load %s", cName) local left=#list-i+1
local label
if left>=needed then
label=string.format("%d. Load %s",lineIndex,cName)
i=i+needed
else else
MENU_GROUP_COMMAND:New(Group, "Rescan?", Group.MyLoadCratesMenu, function() self:_RefreshLoadCratesMenu(Group, Unit) end) label=string.format("%d. Load %s (%d/%d)",lineIndex,cName,left,needed)
line = string.format("Load %s (%d/%d)", cName, found, needed) i=#list+1
end end
MENU_GROUP_COMMAND:New(Group, line, Group.MyLoadCratesMenu, self._LoadSingleCrateSet, self, Group, Unit, cName) MENU_GROUP_COMMAND:New(Group,label,Group.MyLoadCratesMenu,self._LoadSingleCrateSet,self,Group,Unit,cName)
lineIndex=lineIndex+1
end end
end end
end
--- ---
-- Loads exactly `CratesNeeded` crates for one cargoName in range. -- Loads exactly `CratesNeeded` crates for one cargoName in range.
@@ -4745,6 +4921,7 @@ end
-- @param Wrapper.Unit#UNIT Unit The calling unit. -- @param Wrapper.Unit#UNIT Unit The calling unit.
-- @return #CTLD self -- @return #CTLD self
function CTLD:_RefreshDropCratesMenu(Group, Unit) function CTLD:_RefreshDropCratesMenu(Group, Unit)
if not Group.CTLDTopmenu then return end if not Group.CTLDTopmenu then return end
local topCrates = Group.MyTopCratesMenu local topCrates = Group.MyTopCratesMenu
if not topCrates then return end if not topCrates then return end
@@ -4780,7 +4957,15 @@ function CTLD:_RefreshDropCratesMenu(Group, Unit)
return return
end end
----------------------------------------------------------------------
-- DEFAULT (“classic”) versus ONE-STEP behaviour
----------------------------------------------------------------------
if not self.onestepmenu then
--------------------------------------------------------------------
-- classic menu
--------------------------------------------------------------------
MENU_GROUP_COMMAND:New(Group,"Drop ALL crates",dropCratesMenu,self._UnloadCrates,self,Group,Unit) MENU_GROUP_COMMAND:New(Group,"Drop ALL crates",dropCratesMenu,self._UnloadCrates,self,Group,Unit)
self.CrateGroupList=self.CrateGroupList or{} self.CrateGroupList=self.CrateGroupList or{}
self.CrateGroupList[Unit:GetName()]={} self.CrateGroupList[Unit:GetName()]={}
@@ -4815,7 +5000,53 @@ function CTLD:_RefreshDropCratesMenu(Group, Unit)
lineIndex=lineIndex+1 lineIndex=lineIndex+1
end end
end end
end
else
--------------------------------------------------------------------
-- one-step (enhanced) menu
--------------------------------------------------------------------
local mAll=MENU_GROUP:New(Group,"Drop ALL crates",dropCratesMenu)
MENU_GROUP_COMMAND:New(Group,"Drop",mAll,self._UnloadCrates,self,Group,Unit)
MENU_GROUP_COMMAND:New(Group,"Drop and build",mAll,self._DropAndBuild,self,Group,Unit)
self.CrateGroupList=self.CrateGroupList or{}
self.CrateGroupList[Unit:GetName()]={}
local lineIndex=1
for cName,list in pairs(cargoByName) do
local needed=list[1]:GetCratesNeeded() or 1
table.sort(list,function(a,b)return a:GetID()<b:GetID()end)
local i=1
while i<=#list do
local left=(#list-i+1)
if left>=needed then
local chunk={}
for n=i,i+needed-1 do
table.insert(chunk,list[n])
end
local label=string.format("%d. %s",lineIndex,cName)
table.insert(self.CrateGroupList[Unit:GetName()],chunk)
local setIndex=#self.CrateGroupList[Unit:GetName()]
local mSet=MENU_GROUP:New(Group,label,dropCratesMenu)
MENU_GROUP_COMMAND:New(Group,"Drop",mSet,self._UnloadSingleCrateSet,self,Group,Unit,setIndex)
MENU_GROUP_COMMAND:New(Group,"Drop and build",mSet,self._DropSingleAndBuild,self,Group,Unit,setIndex)
i=i+needed
else
local chunk={}
for n=i,#list do
table.insert(chunk,list[n])
end
local label=string.format("%d. %s %d/%d",lineIndex,cName,left,needed)
table.insert(self.CrateGroupList[Unit:GetName()],chunk)
local setIndex=#self.CrateGroupList[Unit:GetName()]
MENU_GROUP_COMMAND:New(Group,label,dropCratesMenu,self._UnloadSingleCrateSet,self,Group,Unit,setIndex)
i=#list+1
end
lineIndex=lineIndex+1
end
end
end
end
--- (Internal) Function to unload a single Troop group by ID. --- (Internal) Function to unload a single Troop group by ID.
-- @param #CTLD self -- @param #CTLD self
@@ -4864,7 +5095,7 @@ function CTLD:_UnloadSingleTroopByID(Group, Unit, chunkID)
return self return self
end end
-- Drop ONLY the FIRST cargo in that chunk -- Drop the FIRST cargo in that chunk
local foundCargo = chunk[1] local foundCargo = chunk[1]
if not foundCargo then if not foundCargo then
self:_SendMessage(string.format("No troop cargo at chunk %d!", chunkID), 10, false, Group) self:_SendMessage(string.format("No troop cargo at chunk %d!", chunkID), 10, false, Group)
@@ -5662,6 +5893,7 @@ function CTLD:IsUnitInZone(Unit,Zonetype)
if Zonetype == CTLD.CargoZoneType.SHIP then if Zonetype == CTLD.CargoZoneType.SHIP then
self:T("Checking Type Ship: "..zonename) self:T("Checking Type Ship: "..zonename)
local ZoneUNIT = UNIT:FindByName(zonename) local ZoneUNIT = UNIT:FindByName(zonename)
if not ZoneUNIT then return false end
zonecoord = ZoneUNIT:GetCoordinate() zonecoord = ZoneUNIT:GetCoordinate()
zoneradius = czone.shiplength zoneradius = czone.shiplength
zonewidth = czone.shipwidth zonewidth = czone.shipwidth
@@ -5739,16 +5971,23 @@ function CTLD:SmokeZoneNearBy(Unit, Flare)
for index,cargozone in pairs(zones[i]) do for index,cargozone in pairs(zones[i]) do
local CZone = cargozone --#CTLD.CargoZone local CZone = cargozone --#CTLD.CargoZone
local zonename = CZone.name local zonename = CZone.name
local zone = nil local zone = nil -- Core.Zone#ZONE_RADIUS
local airbasezone = false
if i == 4 then if i == 4 then
zone = UNIT:FindByName(zonename) zone = UNIT:FindByName(zonename)
else else
zone = ZONE:FindByName(zonename) zone = ZONE:FindByName(zonename)
if not zone then if not zone then
zone = AIRBASE:FindByName(zonename):GetZone() zone = AIRBASE:FindByName(zonename):GetZone()
airbasezone = true
end end
end end
local zonecoord = zone:GetCoordinate() local zonecoord = zone:GetCoordinate()
-- Avoid smoke/flares on runways
if (i==1 or 1==3) and airbasezone==true and zone:IsInstanceOf("ZONE_BASE") then
zonecoord = zone:GetRandomCoordinate(inner,outer,{land.SurfaceType.LAND})
end
if zonecoord then
local active = CZone.active local active = CZone.active
local color = CZone.color local color = CZone.color
local distance = self:_GetDistance(zonecoord,unitcoord) local distance = self:_GetDistance(zonecoord,unitcoord)
@@ -5767,6 +6006,7 @@ function CTLD:SmokeZoneNearBy(Unit, Flare)
end end
end end
end end
end
if not smoked then if not smoked then
local distance = UTILS.MetersToNM(self.smokedistance) local distance = UTILS.MetersToNM(self.smokedistance)
self:_SendMessage(string.format("Negative, need to be closer than %dnm to a zone!",distance), 10, false, Group) self:_SendMessage(string.format("Negative, need to be closer than %dnm to a zone!",distance), 10, false, Group)
@@ -6983,7 +7223,8 @@ end
-- right subtype? -- right subtype?
if Event == subtype and not task:IsDone() then if Event == subtype and not task:IsDone() then
local targetzone = task.Target:GetObject() -- Core.Zone#ZONE should be a zone in this case .... local targetzone = task.Target:GetObject() -- Core.Zone#ZONE should be a zone in this case ....
--self:T2({Name=Groupname,Property=task:GetProperty("ExtractName")}) self:T2({Name=Groupname,Property=task:GetProperty("ExtractName")})
if task:GetProperty("ExtractName") then
local okaygroup = string.find(Groupname,task:GetProperty("ExtractName"),1,true) local okaygroup = string.find(Groupname,task:GetProperty("ExtractName"),1,true)
if targetzone and targetzone.ClassName and string.match(targetzone.ClassName,"ZONE") and okaygroup then if targetzone and targetzone.ClassName and string.match(targetzone.ClassName,"ZONE") and okaygroup then
if task.Clients:HasUniqueID(playername) then if task.Clients:HasUniqueID(playername) then
@@ -6991,6 +7232,9 @@ end
task:__Success(-1) task:__Success(-1)
end end
end end
else
self:T({Text="'ExtractName' Property not set",Name=Groupname,Property=task.Type})
end
end end
end end
) )

View File

@@ -30,6 +30,8 @@
--- Governs multiple missions, the tasking and the reporting. --- Governs multiple missions, the tasking and the reporting.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Command centers govern missions, communicates the task assignments between human players of the coalition, and manages the menu flow. -- Command centers govern missions, communicates the task assignments between human players of the coalition, and manages the menu flow.
-- It can assign a random task to a player when requested. -- It can assign a random task to a player when requested.
-- The commandcenter provides the facilitites to communicate between human players online, executing a task. -- The commandcenter provides the facilitites to communicate between human players online, executing a task.

View File

@@ -5,6 +5,8 @@
-- The @{#DETECTION_MANAGER} class defines the core functions to report detected objects to groups. -- The @{#DETECTION_MANAGER} class defines the core functions to report detected objects to groups.
-- Reportings can be done in several manners, and it is up to the derived classes if DETECTION_MANAGER to model the reporting behaviour. -- Reportings can be done in several manners, and it is up to the derived classes if DETECTION_MANAGER to model the reporting behaviour.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- 1.1) DETECTION_MANAGER constructor: -- 1.1) DETECTION_MANAGER constructor:
-- ----------------------------------- -- -----------------------------------
-- * @{#DETECTION_MANAGER.New}(): Create a new DETECTION_MANAGER instance. -- * @{#DETECTION_MANAGER.New}(): Create a new DETECTION_MANAGER instance.

View File

@@ -27,6 +27,8 @@
--- Models goals to be achieved and can contain multiple tasks to be executed to achieve the goals. --- Models goals to be achieved and can contain multiple tasks to be executed to achieve the goals.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- A mission contains multiple tasks and can be of different task types. -- A mission contains multiple tasks and can be of different task types.
-- These tasks need to be assigned to human players to be executed. -- These tasks need to be assigned to human players to be executed.
-- --

View File

@@ -12,6 +12,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- # 1) Tasking from a player perspective. -- # 1) Tasking from a player perspective.
-- --
-- Tasking can be controlled by using the "other" menu in the radio menu of the player group. -- Tasking can be controlled by using the "other" menu in the radio menu of the player group.

View File

@@ -17,6 +17,8 @@
--- ---
-- # TASKINFO class, extends @{Core.Base#BASE} -- # TASKINFO class, extends @{Core.Base#BASE}
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ## The TASKINFO class implements the methods to contain information and display information of a task. -- ## The TASKINFO class implements the methods to contain information and display information of a task.
-- --
-- # Developer Note -- # Developer Note

View File

@@ -20,6 +20,9 @@ do -- TASK_A2A
--- Defines Air To Air tasks for a @{Core.Set} of Target Units, --- Defines Air To Air tasks for a @{Core.Set} of Target Units,
-- based on the tasking capabilities defined in @{Tasking.Task#TASK}. -- based on the tasking capabilities defined in @{Tasking.Task#TASK}.
--
-- ![Banner Image](..\Images\deprecated.png)
--
-- The TASK_A2A is implemented using a @{Core.Fsm#FSM_TASK}, and has the following statuses: -- The TASK_A2A is implemented using a @{Core.Fsm#FSM_TASK}, and has the following statuses:
-- --
-- * **None**: Start of the process -- * **None**: Start of the process

View File

@@ -31,6 +31,8 @@ do -- TASK_A2A_DISPATCHER
--- Orchestrates the dynamic dispatching of tasks upon groups of detected units determined a @{Core.Set} of EWR installation groups. --- Orchestrates the dynamic dispatching of tasks upon groups of detected units determined a @{Core.Set} of EWR installation groups.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ![Banner Image](..\Presentations\TASK_A2A_DISPATCHER\Dia3.JPG) -- ![Banner Image](..\Presentations\TASK_A2A_DISPATCHER\Dia3.JPG)
-- --
-- The EWR will detect units, will group them, and will dispatch @{Tasking.Task}s to groups. Depending on the type of target detected, different tasks will be dispatched. -- The EWR will detect units, will group them, and will dispatch @{Tasking.Task}s to groups. Depending on the type of target detected, different tasks will be dispatched.

View File

@@ -20,6 +20,9 @@ do -- TASK_A2G
--- The TASK_A2G class defines Air To Ground tasks for a @{Core.Set} of Target Units, --- The TASK_A2G class defines Air To Ground tasks for a @{Core.Set} of Target Units,
-- based on the tasking capabilities defined in @{Tasking.Task#TASK}. -- based on the tasking capabilities defined in @{Tasking.Task#TASK}.
--
-- ![Banner Image](..\Images\deprecated.png)
--
-- The TASK_A2G is implemented using a @{Core.Fsm#FSM_TASK}, and has the following statuses: -- The TASK_A2G is implemented using a @{Core.Fsm#FSM_TASK}, and has the following statuses:
-- --
-- * **None**: Start of the process -- * **None**: Start of the process

View File

@@ -34,6 +34,8 @@ do -- TASK_A2G_DISPATCHER
--- Orchestrates dynamic **A2G Task Dispatching** based on the detection results of a linked @{Functional.Detection} object. --- Orchestrates dynamic **A2G Task Dispatching** based on the detection results of a linked @{Functional.Detection} object.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- It uses the Tasking System within the MOOSE framework, which is a multi-player Tasking Orchestration system. -- It uses the Tasking System within the MOOSE framework, which is a multi-player Tasking Orchestration system.
-- It provides a truly dynamic battle environment for pilots and ground commanders to engage upon, -- It provides a truly dynamic battle environment for pilots and ground commanders to engage upon,
-- in a true co-operation environment wherein **Multiple Teams** will collaborate in Missions to **achieve a common Mission Goal**. -- in a true co-operation environment wherein **Multiple Teams** will collaborate in Missions to **achieve a common Mission Goal**.

View File

@@ -10,6 +10,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- ## Test Missions: -- ## Test Missions:
-- --
-- Test missions can be located on the main GITHUB site. -- Test missions can be located on the main GITHUB site.
@@ -1176,7 +1178,7 @@ do -- TASK_CARGO
end end
---@param Color Might be SMOKECOLOR.Blue, SMOKECOLOR.Red SMOKECOLOR.Orange, SMOKECOLOR.White or SMOKECOLOR.Green --@param Color Might be SMOKECOLOR.Blue, SMOKECOLOR.Red SMOKECOLOR.Orange, SMOKECOLOR.White or SMOKECOLOR.Green
function TASK_CARGO:SetSmokeColor(SmokeColor) function TASK_CARGO:SetSmokeColor(SmokeColor)
-- Makes sure Coloe is set -- Makes sure Coloe is set
if SmokeColor == nil then if SmokeColor == nil then

View File

@@ -76,6 +76,8 @@ do -- TASK_CAPTURE_DISPATCHER
--- Implements the dynamic dispatching of capture zone tasks. --- Implements the dynamic dispatching of capture zone tasks.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The **TASK_CAPTURE_DISPATCHER** allows you to setup various tasks for let human -- The **TASK_CAPTURE_DISPATCHER** allows you to setup various tasks for let human
-- players capture zones in a co-operation effort. -- players capture zones in a co-operation effort.
-- --

View File

@@ -20,6 +20,8 @@ do -- TASK_ZONE_GOAL
--- # TASK_ZONE_GOAL class, extends @{Tasking.Task#TASK} --- # TASK_ZONE_GOAL class, extends @{Tasking.Task#TASK}
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The TASK_ZONE_GOAL class defines the task to protect or capture a protection zone. -- The TASK_ZONE_GOAL class defines the task to protect or capture a protection zone.
-- The TASK_ZONE_GOAL is implemented using a @{Core.Fsm#FSM_TASK}, and has the following statuses: -- The TASK_ZONE_GOAL is implemented using a @{Core.Fsm#FSM_TASK}, and has the following statuses:
-- --

View File

@@ -44,6 +44,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- Please read through the @{Tasking.Task_CARGO} process to understand the mechanisms of tasking and cargo tasking and handling. -- Please read through the @{Tasking.Task_CARGO} process to understand the mechanisms of tasking and cargo tasking and handling.
-- --
-- The cargo will be a downed pilot, which is located somwhere on the battlefield. Use the menus system and facilities to -- The cargo will be a downed pilot, which is located somwhere on the battlefield. Use the menus system and facilities to

View File

@@ -3,6 +3,8 @@
-- The **TASK_CARGO_DISPATCHER** allows you to setup various tasks for let human -- The **TASK_CARGO_DISPATCHER** allows you to setup various tasks for let human
-- players transport cargo as part of a task. -- players transport cargo as part of a task.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- The cargo dispatcher will implement for you mechanisms to create cargo transportation tasks: -- The cargo dispatcher will implement for you mechanisms to create cargo transportation tasks:
-- --
-- * As setup by the mission designer. -- * As setup by the mission designer.

View File

@@ -1,5 +1,7 @@
--- **Tasking** - Models tasks for players to transport cargo. --- **Tasking** - Models tasks for players to transport cargo.
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- **Specific features:** -- **Specific features:**
-- --
-- * Creates a task to transport #Cargo.Cargo to and between deployment zones. -- * Creates a task to transport #Cargo.Cargo to and between deployment zones.

View File

@@ -2,6 +2,8 @@
-- --
-- === -- ===
-- --
-- ![Banner Image](..\Images\deprecated.png)
--
-- 1) @{Tasking.Task_Manager#TASK_MANAGER} class, extends @{Core.Fsm#FSM} -- 1) @{Tasking.Task_Manager#TASK_MANAGER} class, extends @{Core.Fsm#FSM}
-- === -- ===
-- The @{Tasking.Task_Manager#TASK_MANAGER} class defines the core functions to report tasks to groups. -- The @{Tasking.Task_Manager#TASK_MANAGER} class defines the core functions to report tasks to groups.

View File

@@ -12,27 +12,35 @@
-- @module Utilities.Utils -- @module Utilities.Utils
-- @image MOOSE.JPG -- @image MOOSE.JPG
--- --- Smoke color enum `trigger.smokeColor`.
-- @type SMOKECOLOR -- @type SMOKECOLOR
-- @field Green -- @field #number Green Green smoke (0)
-- @field Red -- @field #number Red Red smoke (1)
-- @field White -- @field #number White White smoke (2)
-- @field Orange -- @field #number Orange Orange smoke (3)
-- @field Blue -- @field #number Blue Blue smoke (4)
SMOKECOLOR = trigger.smokeColor -- #SMOKECOLOR SMOKECOLOR = trigger.smokeColor -- #SMOKECOLOR
--- --- Flare colur enum `trigger.flareColor`.
-- @type FLARECOLOR -- @type FLARECOLOR
-- @field Green -- @field #number Green (0)
-- @field Red -- @field #number Red Red flare (1)
-- @field White -- @field #number White White flare (2)
-- @field Yellow -- @field #number Yellow Yellow flare (3)
FLARECOLOR = trigger.flareColor -- #FLARECOLOR FLARECOLOR = trigger.flareColor -- #FLARECOLOR
--- Big smoke preset enum. --- Big smoke preset enum.
-- @type BIGSMOKEPRESET -- @type BIGSMOKEPRESET
-- @field #number SmallSmokeAndFire Small moke and fire (1)
-- @field #number MediumSmokeAndFire Medium smoke and fire (2)
-- @field #number LargeSmokeAndFire Large smoke and fire (3)
-- @field #number HugeSmokeAndFire Huge smoke and fire (4)
-- @field #number SmallSmoke Small smoke (5)
-- @field #number MediumSmoke Medium smoke (6)
-- @field #number LargeSmoke Large smoke (7)
-- @field #number HugeSmoke Huge smoke (8)
BIGSMOKEPRESET = { BIGSMOKEPRESET = {
SmallSmokeAndFire=1, SmallSmokeAndFire=1,
MediumSmokeAndFire=2, MediumSmokeAndFire=2,
@@ -351,7 +359,7 @@ end
-- @return #string Table as a string. -- @return #string Table as a string.
UTILS.OneLineSerialize = function( tbl ) -- serialization of a table all on a single line, no comments, made to replace old get_table_string function UTILS.OneLineSerialize = function( tbl ) -- serialization of a table all on a single line, no comments, made to replace old get_table_string function
lookup_table = {} local lookup_table = {}
local function _Serialize( tbl ) local function _Serialize( tbl )
@@ -490,7 +498,7 @@ end
--- Counts the number of elements in a table. --- Counts the number of elements in a table.
-- @param #table T Table to count -- @param #table T Table to count
-- @return #int Number of elements in the table -- @return #number Number of elements in the table
function UTILS.TableLength(T) function UTILS.TableLength(T)
local count = 0 local count = 0
for _ in pairs(T or {}) do count = count + 1 end for _ in pairs(T or {}) do count = count + 1 end
@@ -1906,6 +1914,13 @@ function UTILS.GetReportingName(Typename)
local typename = string.lower(Typename) local typename = string.lower(Typename)
-- special cases - Shark and Manstay have "A-50" in the name
if string.find(typename,"ka-50",1,true) then
return "Shark"
elseif string.find(typename,"a-50",1,true) then
return "Mainstay"
end
for name, value in pairs(ENUMS.ReportingName.NATO) do for name, value in pairs(ENUMS.ReportingName.NATO) do
local svalue = string.lower(value) local svalue = string.lower(value)
if string.find(typename,svalue,1,true) then if string.find(typename,svalue,1,true) then
@@ -2137,9 +2152,9 @@ function UTILS.GetSunRiseAndSet(DayOfYear, Latitude, Longitude, Rising, Tlocal)
local cosH = (cos(zenith) - (sinDec * sin(latitude))) / (cosDec * cos(latitude)) local cosH = (cos(zenith) - (sinDec * sin(latitude))) / (cosDec * cos(latitude))
if rising and cosH > 1 then if rising and cosH > 1 then
return "N/S" -- The sun never rises on this location on the specified date return "N/R" -- The sun never rises on this location on the specified date
elseif cosH < -1 then elseif cosH < -1 then
return "N/R" -- The sun never sets on this location on the specified date return "N/S" -- The sun never sets on this location on the specified date
end end
-- Finish calculating H and convert into hours -- Finish calculating H and convert into hours

View File

@@ -449,7 +449,6 @@ AIRBASE.TheChannel = {
-- * AIRBASE.Syria.Al_Dumayr -- * AIRBASE.Syria.Al_Dumayr
-- * AIRBASE.Syria.Al_Qusayr -- * AIRBASE.Syria.Al_Qusayr
-- * AIRBASE.Syria.Aleppo -- * AIRBASE.Syria.Aleppo
-- * AIRBASE.Syria.Amman
-- * AIRBASE.Syria.An_Nasiriyah -- * AIRBASE.Syria.An_Nasiriyah
-- * AIRBASE.Syria.At_Tanf -- * AIRBASE.Syria.At_Tanf
-- * AIRBASE.Syria.Bassel_Al_Assad -- * AIRBASE.Syria.Bassel_Al_Assad
@@ -511,8 +510,9 @@ AIRBASE.TheChannel = {
-- * AIRBASE.Syria.Wujah_Al_Hajar -- * AIRBASE.Syria.Wujah_Al_Hajar
-- * AIRBASE.Syria.Ben_Gurion -- * AIRBASE.Syria.Ben_Gurion
-- * AIRBASE.Syria.Hatzor -- * AIRBASE.Syria.Hatzor
-- * AIRBASE.Syria.Palmashim -- * AIRBASE.Syria.Palmachim
-- * AIRBASE.Syria.Tel_Nof -- * AIRBASE.Syria.Tel_Nof
-- * AIRBASE.Syria.Marka
-- --
--@field Syria --@field Syria
AIRBASE.Syria={ AIRBASE.Syria={
@@ -522,7 +522,6 @@ AIRBASE.Syria={
["Al_Dumayr"] = "Al-Dumayr", ["Al_Dumayr"] = "Al-Dumayr",
["Al_Qusayr"] = "Al Qusayr", ["Al_Qusayr"] = "Al Qusayr",
["Aleppo"] = "Aleppo", ["Aleppo"] = "Aleppo",
["Amman"] = "Amman",
["An_Nasiriyah"] = "An Nasiriyah", ["An_Nasiriyah"] = "An Nasiriyah",
["At_Tanf"] = "At Tanf", ["At_Tanf"] = "At Tanf",
["Bassel_Al_Assad"] = "Bassel Al-Assad", ["Bassel_Al_Assad"] = "Bassel Al-Assad",
@@ -554,6 +553,7 @@ AIRBASE.Syria={
["Kuweires"] = "Kuweires", ["Kuweires"] = "Kuweires",
["Lakatamia"] = "Lakatamia", ["Lakatamia"] = "Lakatamia",
["Larnaca"] = "Larnaca", ["Larnaca"] = "Larnaca",
["Marka"] = "Marka",
["Marj_Ruhayyil"] = "Marj Ruhayyil", ["Marj_Ruhayyil"] = "Marj Ruhayyil",
["Marj_as_Sultan_North"] = "Marj as Sultan North", ["Marj_as_Sultan_North"] = "Marj as Sultan North",
["Marj_as_Sultan_South"] = "Marj as Sultan South", ["Marj_as_Sultan_South"] = "Marj as Sultan South",
@@ -584,7 +584,7 @@ AIRBASE.Syria={
["Wujah_Al_Hajar"] = "Wujah Al Hajar", ["Wujah_Al_Hajar"] = "Wujah Al Hajar",
["Ben_Gurion"] = "Ben Gurion", ["Ben_Gurion"] = "Ben Gurion",
["Hatzor"] = "Hatzor", ["Hatzor"] = "Hatzor",
["Palmashim"] = "Palmashim", ["Palmachim"] = "Palmachim",
["Tel_Nof"] = "Tel Nof", ["Tel_Nof"] = "Tel Nof",
} }
@@ -689,7 +689,7 @@ AIRBASE.SouthAtlantic={
-- * AIRBASE.Sinai.Bilbeis_Air_Base -- * AIRBASE.Sinai.Bilbeis_Air_Base
-- * AIRBASE.Sinai.Bir_Hasanah -- * AIRBASE.Sinai.Bir_Hasanah
-- * AIRBASE.Sinai.Birma_Air_Base -- * AIRBASE.Sinai.Birma_Air_Base
-- * AIRBASE.Sinai.Borj_El_Arab_International_Airport -- * AIRBASE.Sinai.Borg_El_Arab_International_Airport
-- * AIRBASE.Sinai.Cairo_International_Airport -- * AIRBASE.Sinai.Cairo_International_Airport
-- * AIRBASE.Sinai.Cairo_West -- * AIRBASE.Sinai.Cairo_West
-- * AIRBASE.Sinai.Difarsuwar_Airfield -- * AIRBASE.Sinai.Difarsuwar_Airfield
@@ -737,7 +737,7 @@ AIRBASE.Sinai = {
["Bilbeis_Air_Base"] = "Bilbeis Air Base", ["Bilbeis_Air_Base"] = "Bilbeis Air Base",
["Bir_Hasanah"] = "Bir Hasanah", ["Bir_Hasanah"] = "Bir Hasanah",
["Birma_Air_Base"] = "Birma Air Base", ["Birma_Air_Base"] = "Birma Air Base",
["Borj_El_Arab_International_Airport"] = "Borj El Arab International Airport", ["Borg_El_Arab_International_Airport"] = "Borg El Arab International Airport",
["Cairo_International_Airport"] = "Cairo International Airport", ["Cairo_International_Airport"] = "Cairo International Airport",
["Cairo_West"] = "Cairo West", ["Cairo_West"] = "Cairo West",
["Difarsuwar_Airfield"] = "Difarsuwar Airfield", ["Difarsuwar_Airfield"] = "Difarsuwar Airfield",
@@ -790,9 +790,14 @@ AIRBASE.Sinai = {
-- * AIRBASE.Kola.Vidsel -- * AIRBASE.Kola.Vidsel
-- * AIRBASE.Kola.Vuojarvi -- * AIRBASE.Kola.Vuojarvi
-- * AIRBASE.Kola.Andoya -- * AIRBASE.Kola.Andoya
-- * AIRBASE.Kola.Alakourtti -- * AIRBASE.Kola.Alakurtti
-- * AIRBASE.Kola.Kittila -- * AIRBASE.Kola.Kittila
-- * AIRBASE.Kola.Bardufoss -- * AIRBASE.Kola.Bardufoss
-- * AIRBASE.Kola.Alta
-- * AIRBASE.Kola.Sodankyla
-- * AIRBASE.Kola.Enontekio
-- * AIRBASE.Kola.Evenes
-- * AIRBASE.Kola.Hosio
-- --
-- @field Kola -- @field Kola
AIRBASE.Kola = { AIRBASE.Kola = {
@@ -815,9 +820,14 @@ AIRBASE.Kola = {
["Vidsel"] = "Vidsel", ["Vidsel"] = "Vidsel",
["Vuojarvi"] = "Vuojarvi", ["Vuojarvi"] = "Vuojarvi",
["Andoya"] = "Andoya", ["Andoya"] = "Andoya",
["Alakourtti"] = "Alakourtti", ["Alakurtti"] = "Alakurtti",
["Kittila"] = "Kittila", ["Kittila"] = "Kittila",
["Bardufoss"] = "Bardufoss", ["Bardufoss"] = "Bardufoss",
["Alta"] = "Alta",
["Sodankyla"] = "Sodankyla",
["Enontekio"] = "Enontekio",
["Evenes"] = "Evenes",
["Hosio"] = "Hosio",
} }
--- Airbases of the Afghanistan map --- Airbases of the Afghanistan map
@@ -911,10 +921,10 @@ AIRBASE.Iraq = {
--- Airbases of the Germany Cold War map --- Airbases of the Germany Cold War map
-- * AIRBASE.GermanyCW.Airracing_Frankfurt -- * AIRBASE.GermanyCW.Airracing_Frankfurt
-- * AIRBASE.GermanyCW.Airracing_Frankfurt
-- * AIRBASE.GermanyCW.Airracing_Koblenz -- * AIRBASE.GermanyCW.Airracing_Koblenz
-- * AIRBASE.GermanyCW.Airracing_Luebeck -- * AIRBASE.GermanyCW.Airracing_Luebeck
-- * AIRBASE.GermanyCW.Allstedt -- * AIRBASE.GermanyCW.Allstedt
-- * AIRBASE.GermanyCW.Alt_Daber
-- * AIRBASE.GermanyCW.Altes_Lager -- * AIRBASE.GermanyCW.Altes_Lager
-- * AIRBASE.GermanyCW.Bad_Duerkheim -- * AIRBASE.GermanyCW.Bad_Duerkheim
-- * AIRBASE.GermanyCW.Barth -- * AIRBASE.GermanyCW.Barth
@@ -937,14 +947,13 @@ AIRBASE.Iraq = {
-- * AIRBASE.GermanyCW.Fritzlar -- * AIRBASE.GermanyCW.Fritzlar
-- * AIRBASE.GermanyCW.Fulda -- * AIRBASE.GermanyCW.Fulda
-- * AIRBASE.GermanyCW.Gardelegen -- * AIRBASE.GermanyCW.Gardelegen
-- * AIRBASE.GermanyCW.Garz
-- * AIRBASE.GermanyCW.Gatow -- * AIRBASE.GermanyCW.Gatow
-- * AIRBASE.GermanyCW.Gelnhausen -- * AIRBASE.GermanyCW.Gelnhausen
-- * AIRBASE.GermanyCW.Giebelstadt -- * AIRBASE.GermanyCW.Giebelstadt
-- * AIRBASE.GermanyCW.Glindbruchkippe -- * AIRBASE.GermanyCW.Glindbruchkippe
-- * AIRBASE.GermanyCW.Gross_Doelln
-- * AIRBASE.GermanyCW.Gross_Mohrdorf -- * AIRBASE.GermanyCW.Gross_Mohrdorf
-- * AIRBASE.GermanyCW.Grosse_Wiese -- * AIRBASE.GermanyCW.Grosse_Wiese
-- * AIRBASE.GermanyCW.Gaerz
-- * AIRBASE.GermanyCW.Guetersloh -- * AIRBASE.GermanyCW.Guetersloh
-- * AIRBASE.GermanyCW.H_FRG_01 -- * AIRBASE.GermanyCW.H_FRG_01
-- * AIRBASE.GermanyCW.H_FRG_02 -- * AIRBASE.GermanyCW.H_FRG_02
@@ -1016,10 +1025,11 @@ AIRBASE.Iraq = {
-- * AIRBASE.GermanyCW.H_GDR_31 -- * AIRBASE.GermanyCW.H_GDR_31
-- * AIRBASE.GermanyCW.H_GDR_32 -- * AIRBASE.GermanyCW.H_GDR_32
-- * AIRBASE.GermanyCW.H_GDR_33 -- * AIRBASE.GermanyCW.H_GDR_33
-- * AIRBASE.GermanyCW.H_GDR_34
-- * AIRBASE.GermanyCW.H_Med_FRG_01
-- * AIRBASE.GermanyCW.H_Med_FRG_02 -- * AIRBASE.GermanyCW.H_Med_FRG_02
-- * AIRBASE.GermanyCW.H_Med_FRG_04 -- * AIRBASE.GermanyCW.H_Med_FRG_04
-- * AIRBASE.GermanyCW.H_Med_FRG_06 -- * AIRBASE.GermanyCW.H_Med_FRG_06
-- * AIRBASE.GermanyCW.H_Med_FRG_09
-- * AIRBASE.GermanyCW.H_Med_FRG_11 -- * AIRBASE.GermanyCW.H_Med_FRG_11
-- * AIRBASE.GermanyCW.H_Med_FRG_12 -- * AIRBASE.GermanyCW.H_Med_FRG_12
-- * AIRBASE.GermanyCW.H_Med_FRG_13 -- * AIRBASE.GermanyCW.H_Med_FRG_13
@@ -1067,9 +1077,9 @@ AIRBASE.Iraq = {
-- * AIRBASE.GermanyCW.Koethen -- * AIRBASE.GermanyCW.Koethen
-- * AIRBASE.GermanyCW.Laage -- * AIRBASE.GermanyCW.Laage
-- * AIRBASE.GermanyCW.Langenselbold -- * AIRBASE.GermanyCW.Langenselbold
-- * AIRBASE.GermanyCW.Laerz
-- * AIRBASE.GermanyCW.Leipzig_Halle -- * AIRBASE.GermanyCW.Leipzig_Halle
-- * AIRBASE.GermanyCW.Leipzig_Mockau -- * AIRBASE.GermanyCW.Leipzig_Mockau
-- * AIRBASE.GermanyCW.Laerz
-- * AIRBASE.GermanyCW.Luebeck -- * AIRBASE.GermanyCW.Luebeck
-- * AIRBASE.GermanyCW.Lueneburg -- * AIRBASE.GermanyCW.Lueneburg
-- * AIRBASE.GermanyCW.Mahlwinkel -- * AIRBASE.GermanyCW.Mahlwinkel
@@ -1087,14 +1097,15 @@ AIRBASE.Iraq = {
-- * AIRBASE.GermanyCW.Pottschutthoehe -- * AIRBASE.GermanyCW.Pottschutthoehe
-- * AIRBASE.GermanyCW.Ramstein -- * AIRBASE.GermanyCW.Ramstein
-- * AIRBASE.GermanyCW.Rinteln -- * AIRBASE.GermanyCW.Rinteln
-- * AIRBASE.GermanyCW.Schweinfurt
-- * AIRBASE.GermanyCW.Schoenefeld -- * AIRBASE.GermanyCW.Schoenefeld
-- * AIRBASE.GermanyCW.Schweinfurt
-- * AIRBASE.GermanyCW.Sembach -- * AIRBASE.GermanyCW.Sembach
-- * AIRBASE.GermanyCW.Spangdahlem -- * AIRBASE.GermanyCW.Spangdahlem
-- * AIRBASE.GermanyCW.Sperenberg -- * AIRBASE.GermanyCW.Sperenberg
-- * AIRBASE.GermanyCW.Stendal -- * AIRBASE.GermanyCW.Stendal
-- * AIRBASE.GermanyCW.Tegel -- * AIRBASE.GermanyCW.Tegel
-- * AIRBASE.GermanyCW.Tempelhof -- * AIRBASE.GermanyCW.Tempelhof
-- * AIRBASE.GermanyCW.Templin
-- * AIRBASE.GermanyCW.Tutow -- * AIRBASE.GermanyCW.Tutow
-- * AIRBASE.GermanyCW.Uelzen -- * AIRBASE.GermanyCW.Uelzen
-- * AIRBASE.GermanyCW.Uetersen -- * AIRBASE.GermanyCW.Uetersen
@@ -1106,6 +1117,7 @@ AIRBASE.Iraq = {
-- * AIRBASE.GermanyCW.Weser_Wuemme -- * AIRBASE.GermanyCW.Weser_Wuemme
-- * AIRBASE.GermanyCW.Wiesbaden -- * AIRBASE.GermanyCW.Wiesbaden
-- * AIRBASE.GermanyCW.Wismar -- * AIRBASE.GermanyCW.Wismar
-- * AIRBASE.GermanyCW.Wittstock
-- * AIRBASE.GermanyCW.Worms -- * AIRBASE.GermanyCW.Worms
-- * AIRBASE.GermanyCW.Wunstorf -- * AIRBASE.GermanyCW.Wunstorf
-- * AIRBASE.GermanyCW.Zerbst -- * AIRBASE.GermanyCW.Zerbst
@@ -1117,7 +1129,6 @@ AIRBASE.GermanyCW = {
["Airracing_Koblenz"] = "Airracing Koblenz", ["Airracing_Koblenz"] = "Airracing Koblenz",
["Airracing_Luebeck"] = "Airracing Lubeck", ["Airracing_Luebeck"] = "Airracing Lubeck",
["Allstedt"] = "Allstedt", ["Allstedt"] = "Allstedt",
["Alt_Daber"] = "Alt Daber",
["Altes_Lager"] = "Altes Lager", ["Altes_Lager"] = "Altes Lager",
["Bad_Duerkheim"] = "Bad Durkheim", ["Bad_Duerkheim"] = "Bad Durkheim",
["Barth"] = "Barth", ["Barth"] = "Barth",
@@ -1140,14 +1151,13 @@ AIRBASE.GermanyCW = {
["Fritzlar"] = "Fritzlar", ["Fritzlar"] = "Fritzlar",
["Fulda"] = "Fulda", ["Fulda"] = "Fulda",
["Gardelegen"] = "Gardelegen", ["Gardelegen"] = "Gardelegen",
["Garz"] = "Garz",
["Gatow"] = "Gatow", ["Gatow"] = "Gatow",
["Gelnhausen"] = "Gelnhausen", ["Gelnhausen"] = "Gelnhausen",
["Giebelstadt"] = "Giebelstadt", ["Giebelstadt"] = "Giebelstadt",
["Glindbruchkippe_"] = "Glindbruchkippe ", ["Glindbruchkippe"] = "Glindbruchkippe ",
["Gross_Doelln"] = "Gross Dolln",
["Gross_Mohrdorf"] = "Gross Mohrdorf", ["Gross_Mohrdorf"] = "Gross Mohrdorf",
["Grosse_Wiese"] = "Grosse Wiese", ["Grosse_Wiese"] = "Grosse Wiese",
["Gaerz"] = "Garz",
["Guetersloh"] = "Gutersloh", ["Guetersloh"] = "Gutersloh",
["H_FRG_01"] = "H FRG 01", ["H_FRG_01"] = "H FRG 01",
["H_FRG_02"] = "H FRG 02", ["H_FRG_02"] = "H FRG 02",
@@ -1219,10 +1229,11 @@ AIRBASE.GermanyCW = {
["H_GDR_31"] = "H GDR 31", ["H_GDR_31"] = "H GDR 31",
["H_GDR_32"] = "H GDR 32", ["H_GDR_32"] = "H GDR 32",
["H_GDR_33"] = "H GDR 33", ["H_GDR_33"] = "H GDR 33",
["H_GDR_34"] = "H GDR 34",
["H_Med_FRG_01"] = "H Med FRG 01",
["H_Med_FRG_02"] = "H Med FRG 02", ["H_Med_FRG_02"] = "H Med FRG 02",
["H_Med_FRG_04"] = "H Med FRG 04", ["H_Med_FRG_04"] = "H Med FRG 04",
["H_Med_FRG_06"] = "H Med FRG 06", ["H_Med_FRG_06"] = "H Med FRG 06",
["H_Med_FRG_09"] = "H Med FRG 09",
["H_Med_FRG_11"] = "H Med FRG 11", ["H_Med_FRG_11"] = "H Med FRG 11",
["H_Med_FRG_12"] = "H Med FRG 12", ["H_Med_FRG_12"] = "H Med FRG 12",
["H_Med_FRG_13"] = "H Med FRG 13", ["H_Med_FRG_13"] = "H Med FRG 13",
@@ -1270,9 +1281,9 @@ AIRBASE.GermanyCW = {
["Koethen"] = "Kothen", ["Koethen"] = "Kothen",
["Laage"] = "Laage", ["Laage"] = "Laage",
["Langenselbold"] = "Langenselbold", ["Langenselbold"] = "Langenselbold",
["Laerz"] = "Larz",
["Leipzig_Halle"] = "Leipzig Halle", ["Leipzig_Halle"] = "Leipzig Halle",
["Leipzig_Mockau"] = "Leipzig Mockau", ["Leipzig_Mockau"] = "Leipzig Mockau",
["Laerz"] = "Larz",
["Luebeck"] = "Lubeck", ["Luebeck"] = "Lubeck",
["Lueneburg"] = "Luneburg", ["Lueneburg"] = "Luneburg",
["Mahlwinkel"] = "Mahlwinkel", ["Mahlwinkel"] = "Mahlwinkel",
@@ -1290,14 +1301,15 @@ AIRBASE.GermanyCW = {
["Pottschutthoehe"] = "Pottschutthohe", ["Pottschutthoehe"] = "Pottschutthohe",
["Ramstein"] = "Ramstein", ["Ramstein"] = "Ramstein",
["Rinteln"] = "Rinteln", ["Rinteln"] = "Rinteln",
["Schweinfurt"] = "Schweinfurt",
["Schoenefeld"] = "Schonefeld", ["Schoenefeld"] = "Schonefeld",
["Schweinfurt"] = "Schweinfurt",
["Sembach"] = "Sembach", ["Sembach"] = "Sembach",
["Spangdahlem"] = "Spangdahlem", ["Spangdahlem"] = "Spangdahlem",
["Sperenberg"] = "Sperenberg", ["Sperenberg"] = "Sperenberg",
["Stendal"] = "Stendal", ["Stendal"] = "Stendal",
["Tegel"] = "Tegel", ["Tegel"] = "Tegel",
["Tempelhof"] = "Tempelhof", ["Tempelhof"] = "Tempelhof",
["Templin"] = "Templin",
["Tutow"] = "Tutow", ["Tutow"] = "Tutow",
["Uelzen"] = "Uelzen", ["Uelzen"] = "Uelzen",
["Uetersen"] = "Uetersen", ["Uetersen"] = "Uetersen",
@@ -1309,6 +1321,7 @@ AIRBASE.GermanyCW = {
["Weser_Wuemme"] = "Weser Wumme", ["Weser_Wuemme"] = "Weser Wumme",
["Wiesbaden"] = "Wiesbaden", ["Wiesbaden"] = "Wiesbaden",
["Wismar"] = "Wismar", ["Wismar"] = "Wismar",
["Wittstock"] = "Wittstock",
["Worms"] = "Worms", ["Worms"] = "Worms",
["Wunstorf"] = "Wunstorf", ["Wunstorf"] = "Wunstorf",
["Zerbst"] = "Zerbst", ["Zerbst"] = "Zerbst",
@@ -2581,7 +2594,7 @@ function AIRBASE:_InitRunways(IncludeInverse)
runway.name=string.format("%02d", tonumber(namefromheading)) runway.name=string.format("%02d", tonumber(namefromheading))
else else
runway.name=string.format("%02d", tonumber(name)) runway.name=string.format("%02d", tonumber(name))
self:I("RunwayName: "..runway.name) --self:I("RunwayName: "..runway.name)
end end
--runway.name=string.format("%02d", tonumber(name)) --runway.name=string.format("%02d", tonumber(name))

View File

@@ -912,15 +912,18 @@ function GROUP:GetVelocityVec3()
if DCSGroup and DCSGroup:isExist() then if DCSGroup and DCSGroup:isExist() then
local GroupUnits = DCSGroup:getUnits() local GroupUnits = DCSGroup:getUnits()
local GroupCount = #GroupUnits local GroupCount = 0
local VelocityVec3 = { x = 0, y = 0, z = 0 } local VelocityVec3 = { x = 0, y = 0, z = 0 }
for _, DCSUnit in pairs( GroupUnits ) do for _, DCSUnit in pairs( GroupUnits ) do
if DCSUnit:isExist() and DCSUnit:isActive() then
local UnitVelocityVec3 = DCSUnit:getVelocity() local UnitVelocityVec3 = DCSUnit:getVelocity()
VelocityVec3.x = VelocityVec3.x + UnitVelocityVec3.x VelocityVec3.x = VelocityVec3.x + UnitVelocityVec3.x
VelocityVec3.y = VelocityVec3.y + UnitVelocityVec3.y VelocityVec3.y = VelocityVec3.y + UnitVelocityVec3.y
VelocityVec3.z = VelocityVec3.z + UnitVelocityVec3.z VelocityVec3.z = VelocityVec3.z + UnitVelocityVec3.z
GroupCount = GroupCount + 1
end
end end
VelocityVec3.x = VelocityVec3.x / GroupCount VelocityVec3.x = VelocityVec3.x / GroupCount
@@ -1754,6 +1757,7 @@ function GROUP:GetMaxVelocity()
for Index, UnitData in pairs( DCSGroup:getUnits() ) do for Index, UnitData in pairs( DCSGroup:getUnits() ) do
if UnitData:isExist() and UnitData:isActive() then
local UnitVelocityVec3 = UnitData:getVelocity() local UnitVelocityVec3 = UnitData:getVelocity()
local UnitVelocity = math.abs( UnitVelocityVec3.x ) + math.abs( UnitVelocityVec3.y ) + math.abs( UnitVelocityVec3.z ) local UnitVelocity = math.abs( UnitVelocityVec3.x ) + math.abs( UnitVelocityVec3.y ) + math.abs( UnitVelocityVec3.z )
@@ -1761,6 +1765,7 @@ function GROUP:GetMaxVelocity()
GroupVelocityMax = UnitVelocity GroupVelocityMax = UnitVelocity
end end
end end
end
return GroupVelocityMax return GroupVelocityMax
end end

View File

@@ -897,7 +897,7 @@ function UNIT:GetAmmunition()
nAPshells = nAPshells + Nammo nAPshells = nAPshells + Nammo
end end
if ammotable[w].desc.typeName and string.find(ammotable[w].desc.typeName, "_HE", 1, true) then if ammotable[w].desc.typeName and (string.find(ammotable[w].desc.typeName, "_HE", 1, true) or string.find(ammotable[w].desc.typeName, "HESH", 1, true)) then
nHEshells = nHEshells + Nammo nHEshells = nHEshells + Nammo
end end
@@ -1107,7 +1107,6 @@ function UNIT:GetUnits()
if DCSUnit then if DCSUnit then
Units[1] = UNIT:Find(DCSUnit) Units[1] = UNIT:Find(DCSUnit)
- self:T3(Units)
return Units return Units
end end