mirror of
https://github.com/FlightControl-Master/MOOSE.git
synced 2025-10-29 16:58:06 +00:00
Merge branch 'master' into funkyfranky
This commit is contained in:
commit
1e2a84608f
565
Moose Development/Documentation/DCS_ControlAPI.txt
Normal file
565
Moose Development/Documentation/DCS_ControlAPI.txt
Normal file
@ -0,0 +1,565 @@
|
|||||||
|
DCS Simulation Control User Scripts
|
||||||
|
====================================
|
||||||
|
|
||||||
|
The behaviour of the DCS can be altered using the *GameGUI.lua scripts.
|
||||||
|
You define the hooks to the DCS events, and then do what you want using the provided API.
|
||||||
|
===================================================================================================
|
||||||
|
|
||||||
|
When loading, DCS searches for Saved Games\DCS\Scripts\*GameGUI.lua files,
|
||||||
|
sorts them by name and then loads into the GUI Lua-state.
|
||||||
|
Each user script is loaded into an isolated environment, so the only
|
||||||
|
thing they share is the state of the simulator.
|
||||||
|
|
||||||
|
Each script defines a set of callbacks to the DCS events and sets them with the call
|
||||||
|
DCS.setUserCallbacks(cb_table)
|
||||||
|
For each callback type the hooks of all user scripts will be called in order of loading.
|
||||||
|
|
||||||
|
For callbacks which are supposed to returning a value, currently there are 3 of them:
|
||||||
|
onPlayerTryConnect
|
||||||
|
onPlayerTrySendChat
|
||||||
|
onPlayerTryChangeSlot
|
||||||
|
returning a value means breaking the hook call chain.
|
||||||
|
Returning nothing (or nil) means continuing the hook chain, which ends with the default allow-all handlers.
|
||||||
|
|
||||||
|
The example user script 'testGameGUI.lua':
|
||||||
|
----------------------------------------------------------------------------------------------
|
||||||
|
local test = {}
|
||||||
|
|
||||||
|
function test.onPlayerTryConnect(ipaddr, name, ucid, playerID)
|
||||||
|
print('onPlayerTryConnect(%s, %s, %s, %d)', ipaddr, name, ucid, playerID)
|
||||||
|
-- if you want to gently intercept the call, allowing other user scripts to get it,
|
||||||
|
-- you better return nothing here
|
||||||
|
return true -- allow the player to connect
|
||||||
|
end
|
||||||
|
|
||||||
|
function test.onSimulationStart()
|
||||||
|
print('Current mission is '..DCS.getMissionName())
|
||||||
|
end
|
||||||
|
|
||||||
|
DCS.setUserCallbacks(test) -- here we set our callbacks
|
||||||
|
----------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
The available API are documented below.
|
||||||
|
The full list of the callbacks is at the end of this document.
|
||||||
|
|
||||||
|
In addition, all standard lua 5.1 libraries are available as well, namely:
|
||||||
|
base api, like print, etc,
|
||||||
|
math.*
|
||||||
|
table.*
|
||||||
|
string.*
|
||||||
|
io.*
|
||||||
|
os.*
|
||||||
|
debug.*
|
||||||
|
|
||||||
|
===================================================================================================
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Lua File System (lfs) API
|
||||||
|
-------------------------------
|
||||||
|
lfs.currentdir() -> string
|
||||||
|
Returns the path of the DCS install folder
|
||||||
|
|
||||||
|
lfs.writedir() -> string
|
||||||
|
Returns the path of the current 'Saved Games\DCS' folder.
|
||||||
|
|
||||||
|
lfs.tempdir() -> string
|
||||||
|
Returns the pat of the DCS Temp folder (AppData\Local\Temp\DCS).
|
||||||
|
|
||||||
|
lfs.mkdir()
|
||||||
|
lfs.rmdir()
|
||||||
|
lfs.attributes()
|
||||||
|
lfs.dir()
|
||||||
|
lfs.normpath()
|
||||||
|
lfs.realpath()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
DCS Control API, table 'DCS.*'
|
||||||
|
-------------------------------
|
||||||
|
|
||||||
|
DCS.setPause(bool)
|
||||||
|
Pauses/resumes the simulation. Server-side only.
|
||||||
|
|
||||||
|
DCS.getPause() -> bool
|
||||||
|
true if simulation is paused
|
||||||
|
|
||||||
|
DCS.stopMission()
|
||||||
|
stops current mission
|
||||||
|
|
||||||
|
DCS.exitProcess()
|
||||||
|
Exits the DCS process.
|
||||||
|
|
||||||
|
DCS.isMultiplayer() -> bool
|
||||||
|
True when running in the multiplayer mode.
|
||||||
|
|
||||||
|
DCS.isServer() -> bool
|
||||||
|
True when running as a server or in the single-player mode.
|
||||||
|
|
||||||
|
DCS.getModelTime() -> number
|
||||||
|
returns current DCS simulation time in seconds.
|
||||||
|
|
||||||
|
DCS.getRealTime() -> number
|
||||||
|
returns current DCS real time in seconds relative to the DCS start time.
|
||||||
|
|
||||||
|
DCS.getMissionOptions() -> table
|
||||||
|
Returns the value of 'mission.options'
|
||||||
|
|
||||||
|
DCS.getMissionDescription() -> string
|
||||||
|
translated mission.descriptionText string
|
||||||
|
|
||||||
|
DCS.getAvailableCoalitions() -> table {
|
||||||
|
[coalition_id] = { name = "coalition name", }
|
||||||
|
...
|
||||||
|
}
|
||||||
|
Returns a list of coalitions which have available slots.
|
||||||
|
|
||||||
|
DCS.getAvailableSlots(coalitionID) -> array of {unitId, type, role, callsign, groupName, country}
|
||||||
|
Returns the list of available slots.
|
||||||
|
NOTE: the returned unitID is actually a slotID, which for multi-seat units is 'unitID_seatID'
|
||||||
|
|
||||||
|
DCS.getCurrentMission() -> table with the currently loaded mission
|
||||||
|
NOTE: to get valid mission.options use DCS.getMissionOptions()
|
||||||
|
|
||||||
|
DCS.getMissionName() -> string
|
||||||
|
Returns the name of the current mission
|
||||||
|
|
||||||
|
DCS.getMissionFilename() -> string
|
||||||
|
Returns the file name of the current mission (returns nil when acting as a multiplayer client).
|
||||||
|
|
||||||
|
DCS.getMissionResult(string side) -> integer [0, 100]
|
||||||
|
Gets missin result for either 'red' or 'blue'
|
||||||
|
|
||||||
|
DCS.getUnitProperty(missionId, propertyId) -> string
|
||||||
|
propertyId:
|
||||||
|
DCS.UNIT_RUNTIME_ID, // unique within runtime mission. int
|
||||||
|
DCS.UNIT_MISSION_ID, // unique within mission file. int>0
|
||||||
|
DCS.UNIT_NAME, // unit name, as assigned by mission designer.
|
||||||
|
DCS.UNIT_TYPE, // unit type (Ural, ZU-23, etc)
|
||||||
|
DCS.UNIT_CATEGORY,
|
||||||
|
DCS.UNIT_GROUP_MISSION_ID, // group ID, unique within mission file. int>0
|
||||||
|
DCS.UNIT_GROUPNAME, // group name, as assigned by mission designer.
|
||||||
|
DCS.UNIT_GROUPCATEGORY,
|
||||||
|
DCS.UNIT_CALLSIGN,
|
||||||
|
DCS.UNIT_HIDDEN,// ME hiding
|
||||||
|
DCS.UNIT_COALITION,// "blue", "red" or "unknown"
|
||||||
|
DCS.UNIT_COUNTRY_ID,
|
||||||
|
DCS.UNIT_TASK, //"unit.group.task"
|
||||||
|
DCS.UNIT_PLAYER_NAME, // valid for network "humanable" units
|
||||||
|
DCS.UNIT_ROLE,//"artillery_commander", "instructor", etc
|
||||||
|
DCS.UNIT_INVISIBLE_MAP_ICON,//ME invisible map icon
|
||||||
|
|
||||||
|
DCS.getUnitType(missionId) -> typeId
|
||||||
|
a shortcut for DCS.getUnitProperty(missionId, DCS.UNIT_TYPE)
|
||||||
|
|
||||||
|
DCS.getUnitTypeAttribute(typeId, attr) -> string
|
||||||
|
Returns a value from Database: Objects[typeId][attr],
|
||||||
|
for example DCS.getUnitTypeAttribute("Ural", "DisplayName")
|
||||||
|
|
||||||
|
DCS.writeDebriefing(str)
|
||||||
|
Writes a custom string to the debriefing file
|
||||||
|
|
||||||
|
DCS.setUserCallbacks(cb_table)
|
||||||
|
Hooks the callbacks using the handlers from the provided table.
|
||||||
|
See: "GameGUI scripts" section.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Logging API 'log.*'
|
||||||
|
------------------------
|
||||||
|
Logging works as follows:
|
||||||
|
a) each log message is accompanied with 2 attributes: a subsystem, and level.
|
||||||
|
b) after each messages gets into a logger it passes (asynchronously) through
|
||||||
|
a series of output filters which decide where the message will be written to.
|
||||||
|
|
||||||
|
Writing to log is done by:
|
||||||
|
|
||||||
|
log.write(SUBSYSTEM_NAME, LOG_LEVEL, message, ...)
|
||||||
|
if there are any arguments after 'message',
|
||||||
|
the actual string is formed as string.format(message, ...)
|
||||||
|
|
||||||
|
SUBSYSTEM_NAME is a string
|
||||||
|
LOG_LEVEL is one of the values, listed below
|
||||||
|
see log.set_output()
|
||||||
|
|
||||||
|
log.set_output(log_file_name_wo_ext, rule_subsystem_name, rule_level_mask, rule_output_mode)
|
||||||
|
|
||||||
|
the args:
|
||||||
|
log_file_name_wo_ext: resulting log will be written to $WRITE_DIR/Logs/<log_file_name_wo_ext>.log
|
||||||
|
|
||||||
|
rule_subsytem_name: the name of the subsystem whose messages to write or empty string to match all subsystems
|
||||||
|
|
||||||
|
rule_level_mask: a sum of log-level bit flags to match messages
|
||||||
|
valid flags are:
|
||||||
|
log.ALERT
|
||||||
|
log.ERROR
|
||||||
|
log.WARNING
|
||||||
|
log.INFO
|
||||||
|
log.DEBUG
|
||||||
|
log.ALL - includes all of the above
|
||||||
|
log.TRACE - a special level which is excluded from dcs.log file
|
||||||
|
|
||||||
|
rule_output_mode: a sum of output flags:
|
||||||
|
log.MESSAGE
|
||||||
|
log.TIME
|
||||||
|
log.MODULE - this is a 'subsystem', not a dlc
|
||||||
|
log.LEVEL
|
||||||
|
log.FULL - all of the above
|
||||||
|
|
||||||
|
So, in order to save net.trace(msg) messages to a file, you should issue a call:
|
||||||
|
log.set_output('lua-net', 'LuaNET', log.TRACE, log.MESSAGE + log.TIME)
|
||||||
|
|
||||||
|
This will write to a Logs/lua-net.log file
|
||||||
|
|
||||||
|
Or, to save everything lua-network-related:
|
||||||
|
log.set_output('lua-net', 'LuaNET', log.TRACE + log.ALL, log.MESSAGE + log.TIME + log.LEVEL)
|
||||||
|
|
||||||
|
To close the log file, you must use
|
||||||
|
log.set_output('lua-net', '', 0, 0)
|
||||||
|
|
||||||
|
log.* API is available in the 'Saved Games\DCS\Config\autoexec.cfg' file as well so you can control log output in you local machine.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Network specific API, available through the table 'net.'
|
||||||
|
----------------------------------------------------------------
|
||||||
|
|
||||||
|
net.log(msg) -- equivalent to log.write('LuaNET', log.INFO, msg)
|
||||||
|
net.trace(msg) -- equivalent to log.write('LuaNET', log.TRACE, msg)
|
||||||
|
|
||||||
|
What is the difference: log() always writes to dcs.log, but may lose messages if the output rate is too high.
|
||||||
|
trace() output never appears in the dcs.log file, it must be explicitly directed to a log file.
|
||||||
|
It never loses messages when there's an active output, but it may block if output rate is higher than writing to the log file.
|
||||||
|
To control logger output you can use $WRITE_DIR/Config/autoexec.cfg file, or call this from your network script
|
||||||
|
(log.* API, see above)
|
||||||
|
|
||||||
|
|
||||||
|
net.dostring_in(state, string) -> string
|
||||||
|
Executes a lua-string in a given internal lua-state and returns a string result
|
||||||
|
Valid state names are:
|
||||||
|
'config': the state in which $INSTALL_DIR/Config/main.cfg is executed, as well as $WRITE_DIR/Config/autoexec.cfg
|
||||||
|
used for configuration settings
|
||||||
|
'mission': holds current mission
|
||||||
|
'export': runs $WRITE_DIR/Scripts/Export.lua and the relevant export API
|
||||||
|
|
||||||
|
net.send_chat(string message, bool all)
|
||||||
|
Send chat message. If not all, then send to my coalition (side) only.
|
||||||
|
|
||||||
|
net.send_chat_to(string message, playerID to)
|
||||||
|
Send direct chat message to a player
|
||||||
|
Server-side only:
|
||||||
|
net.send_chat_to(string message, playerID to[, playerID from])
|
||||||
|
|
||||||
|
net.recv_chat(message[, int from=0])
|
||||||
|
Receive chat message locally[, pretending it was sent by another player].
|
||||||
|
from = 0 means from the system
|
||||||
|
|
||||||
|
net.load_mission(miz_filename)
|
||||||
|
Loads a specified mission, temporarily overriding the server mission list.
|
||||||
|
SERVER ONLY
|
||||||
|
|
||||||
|
net.load_next_mission() -> bool
|
||||||
|
Load the next mission from the server mission list. Returns false if list end is reached
|
||||||
|
SERVER ONLY
|
||||||
|
|
||||||
|
net.get_player_list() -> array of playerID
|
||||||
|
Returns the list of currently connected players
|
||||||
|
|
||||||
|
net.get_my_player_id() -> playerID
|
||||||
|
Returns the playerID of the local player. Currently always 1 for the server.
|
||||||
|
|
||||||
|
net.get_server_id() -> playerID
|
||||||
|
Returns playerID of the server. Currently, always 1.
|
||||||
|
|
||||||
|
net.get_player_info(playerID) -> table
|
||||||
|
Returns a table of all player attributes or nil if playerID is invalid
|
||||||
|
|
||||||
|
net.get_player_info(playerID, attrName) -> value
|
||||||
|
Returns a value of a given attribute for the playerID.
|
||||||
|
|
||||||
|
Currently defined attributes are:
|
||||||
|
'id': playerID
|
||||||
|
'name': player name
|
||||||
|
'side': 0 - spectators, 1 - red, 2 - blue
|
||||||
|
'slot': slotID of the player or ''
|
||||||
|
'ping': ping of the player in ms
|
||||||
|
'ipaddr': IP address of the player, SERVER ONLY
|
||||||
|
'ucid': Unique Client Identifier, SERVER ONLY
|
||||||
|
|
||||||
|
net.kick(id, message)
|
||||||
|
Kick a player.
|
||||||
|
|
||||||
|
net.get_stat(playerID, statID) -> integer
|
||||||
|
Get statistics for player. statIDs are:
|
||||||
|
net.PS_PING (0) - ping (in ms)
|
||||||
|
net.PS_CRASH (1) - number of crashes
|
||||||
|
net.PS_CAR (2) - number of destroyed vehicles
|
||||||
|
net.PS_PLANE (3) - ... planes/helicopters
|
||||||
|
net.PS_SHIP (4) - ... ships
|
||||||
|
net.PS_SCORE (5) - total score
|
||||||
|
net.PS_LAND (6) - number of landings
|
||||||
|
net.PS_EJECT (7) - of ejects
|
||||||
|
|
||||||
|
|
||||||
|
net.get_name(playerID) -> string
|
||||||
|
The same as net.get_player_info(playerID, 'name')
|
||||||
|
FIXME: implement in ServMan_compat.lua ?
|
||||||
|
|
||||||
|
net.get_slot(playerID) -> sideID, slotID
|
||||||
|
The same as:
|
||||||
|
net.get_player_info(playerID, 'side'), net.get_player_info(playerID, 'slot')
|
||||||
|
FIXME: implement in ServMan_compat.lua ?
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
net.set_slot(sideID, slotID)
|
||||||
|
Try to set the local player's slot. Empty slotID ('') puts the player into spectators.
|
||||||
|
|
||||||
|
net.force_player_slot(playerID, sideID, slotID) -> boolean
|
||||||
|
Forces a player to occupy a set slot. Slot '' means no slot (moves player to spectators)
|
||||||
|
SideID: 0 - spectators, 1 - red, 2 - blue
|
||||||
|
|
||||||
|
net.set_name(playerID, name) -- OBSOLETE, works only locally
|
||||||
|
|
||||||
|
|
||||||
|
net.lua2json(value) -> string
|
||||||
|
Convert a Lua value to JSON string
|
||||||
|
|
||||||
|
net.json2lua(json_string) -> value
|
||||||
|
Convert JSON string to a Lua value
|
||||||
|
|
||||||
|
|
||||||
|
LuaExport API 'Export.Lo*'
|
||||||
|
----------------------------------------------------------------
|
||||||
|
See Scripts/Export.lua for the documentation. Note that all export
|
||||||
|
API functions are available here in the Export. namespace, not the global one.
|
||||||
|
In multiplayer the availability of the API on clients depends on the server setting.
|
||||||
|
|
||||||
|
The calls to check export capabilities:
|
||||||
|
Export.LoIsObjectExportAllowed() -- returns the value of server.advanced.allow_object_export
|
||||||
|
Export.LoIsSensorExportAllowed() -- returns the value of server.advanced.allow_sensor_export
|
||||||
|
Export.LoIsOwnshipExportAllowed() -- returns the value of server.advanced.allow_ownship_export
|
||||||
|
|
||||||
|
These calls are only available on clients when LoIsObjectExportAllowed() is true:
|
||||||
|
Export.LoGetObjectById
|
||||||
|
Export.LoGetWorldObjects
|
||||||
|
|
||||||
|
These calls are only available on clients when LoIsSensorExportAllowed() is true:
|
||||||
|
Export.LoGetTWSInfo
|
||||||
|
Export.LoGetTargetInformation
|
||||||
|
Export.LoGetLockedTargetInformation
|
||||||
|
Export.LoGetF15_TWS_Contacts
|
||||||
|
Export.LoGetSightingSystemInfo
|
||||||
|
Export.LoGetWingTargets
|
||||||
|
|
||||||
|
These calls are only available on clients when LoIsOwnshipExportAllowed() is true:
|
||||||
|
Export.LoGetPlayerPlaneId
|
||||||
|
Export.LoGetIndicatedAirSpeed
|
||||||
|
Export.LoGetAngleOfAttack
|
||||||
|
Export.LoGetAngleOfSideSlip
|
||||||
|
Export.LoGetAccelerationUnits
|
||||||
|
Export.LoGetVerticalVelocity
|
||||||
|
Export.LoGetADIPitchBankYaw
|
||||||
|
Export.LoGetTrueAirSpeed
|
||||||
|
Export.LoGetAltitudeAboveSeaLevel
|
||||||
|
Export.LoGetAltitudeAboveGroundLevel
|
||||||
|
Export.LoGetMachNumber
|
||||||
|
Export.LoGetRadarAltimeter
|
||||||
|
Export.LoGetMagneticYaw
|
||||||
|
Export.LoGetGlideDeviation
|
||||||
|
Export.LoGetSideDeviation
|
||||||
|
Export.LoGetSlipBallPosition
|
||||||
|
Export.LoGetBasicAtmospherePressure
|
||||||
|
Export.LoGetControlPanel_HSI
|
||||||
|
Export.LoGetEngineInfo
|
||||||
|
Export.LoGetSelfData
|
||||||
|
Export.LoGetCameraPosition
|
||||||
|
Export.LoSetCameraPosition
|
||||||
|
Export.LoSetCommand
|
||||||
|
Export.LoGetMCPState
|
||||||
|
Export.LoGetRoute
|
||||||
|
Export.LoGetNavigationInfo
|
||||||
|
Export.LoGetPayloadInfo
|
||||||
|
Export.LoGetWingInfo
|
||||||
|
Export.LoGetMechInfo
|
||||||
|
Export.LoGetRadioBeaconsStatus
|
||||||
|
Export.LoGetVectorVelocity
|
||||||
|
Export.LoGetVectorWindVelocity
|
||||||
|
Export.LoGetSnares
|
||||||
|
Export.LoGetAngularVelocity
|
||||||
|
Export.LoGetHeightWithObjects
|
||||||
|
Export.LoGetFMData
|
||||||
|
|
||||||
|
These functions are always available:
|
||||||
|
Export.LoGetPilotName
|
||||||
|
Export.LoGetAltitude
|
||||||
|
Export.LoGetNameByType
|
||||||
|
Export.LoGeoCoordinatesToLoCoordinates
|
||||||
|
Export.LoCoordinatesToGeoCoordinates
|
||||||
|
Export.LoGetVersionInfo
|
||||||
|
Export.LoGetWindAtPoint
|
||||||
|
Export.LoGetModelTime
|
||||||
|
Export.LoGetMissionStartTime
|
||||||
|
|
||||||
|
These are not available in the *GameGUI state:
|
||||||
|
-- Export.LoSetSharedTexture
|
||||||
|
-- Export.LoRemoveSharedTexture
|
||||||
|
-- Export.LoUpdateSharedTexture
|
||||||
|
|
||||||
|
|
||||||
|
-------------------------------------------------------------------------------------------
|
||||||
|
--- The Callbacks.
|
||||||
|
-------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
function onMissionLoadBegin()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onMissionLoadProgress(progress, message)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onMissionLoadEnd()
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function onSimulationStart()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onSimulationStop()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onSimulationFrame()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onSimulationPause()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onSimulationResume()
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function onGameEvent(eventName,arg1,arg2,arg3,arg4)
|
||||||
|
--"friendly_fire", playerID, weaponName, victimPlayerID
|
||||||
|
--"mission_end", winner, msg
|
||||||
|
--"kill", killerPlayerID, killerUnitType, killerSide, victimPlayerID, victimUnitType, victimSide, weaponName
|
||||||
|
--"self_kill", playerID
|
||||||
|
--"change_slot", playerID, slotID, prevSide
|
||||||
|
--"connect", playerID, name
|
||||||
|
--"disconnect", playerID, name, playerSide, reason_code
|
||||||
|
--"crash", playerID, unit_missionID
|
||||||
|
--"eject", playerID, unit_missionID
|
||||||
|
--"takeoff", playerID, unit_missionID, airdromeName
|
||||||
|
--"landing", playerID, unit_missionID, airdromeName
|
||||||
|
--"pilot_death", playerID, unit_missionID
|
||||||
|
end
|
||||||
|
|
||||||
|
function onNetConnect(localPlayerID)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onNetMissionChanged(newMissionName)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onNetDisconnect(reason_msg, err_code)
|
||||||
|
end
|
||||||
|
|
||||||
|
-- disconnect reason codes:
|
||||||
|
net.ERR_INVALID_ADDRESS
|
||||||
|
net.ERR_CONNECT_FAILED
|
||||||
|
net.ERR_WRONG_VERSION
|
||||||
|
net.ERR_PROTOCOL_ERROR
|
||||||
|
net.ERR_TAINTED_CLIENT
|
||||||
|
net.ERR_INVALID_PASSWORD
|
||||||
|
net.ERR_BANNED
|
||||||
|
net.ERR_BAD_CALLSIGN
|
||||||
|
|
||||||
|
net.ERR_TIMEOUT
|
||||||
|
net.ERR_KICKED
|
||||||
|
|
||||||
|
|
||||||
|
function onPlayerConnect(id)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onPlayerDisconnect(id, err_code)
|
||||||
|
-- this is never called for local playerID
|
||||||
|
end
|
||||||
|
|
||||||
|
function onPlayerStart(id)
|
||||||
|
-- a player entered the simulation
|
||||||
|
-- this is never called for local playerID
|
||||||
|
end
|
||||||
|
|
||||||
|
function onPlayerStop(id)
|
||||||
|
-- a player left the simulation (happens right before a disconnect, if player exited by desire)
|
||||||
|
-- this is never called for local playerID
|
||||||
|
end
|
||||||
|
|
||||||
|
function onPlayerChangeSlot(id)
|
||||||
|
-- a player successfully changed the slot
|
||||||
|
-- this will also come as onGameEvent('change_slot', playerID, slotID),
|
||||||
|
-- if allowed by server.advanced.event_Connect setting
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- These 3 functions are different from the rest:
|
||||||
|
--- 1. they are called directly from the network code, so try to make them as fast as possible
|
||||||
|
--- 2. they return a result
|
||||||
|
-- The code shows the default implementations.
|
||||||
|
|
||||||
|
function onPlayerTryConnect(addr, name, ucid, playerID) --> true | false, "disconnect reason"
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
|
||||||
|
function onPlayerTrySendChat(playerID, msg, all) -- -> filteredMessage | "" - empty string drops the message
|
||||||
|
return msg
|
||||||
|
end
|
||||||
|
|
||||||
|
function onPlayerTryChangeSlot(playerID, side, slotID) -- -> true | false
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
-- GUI callbacks
|
||||||
|
function onChatMessage(message, from)
|
||||||
|
-- this one may be useful for chat archiving
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowRadioMenu(a_h)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowPool()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowGameMenu()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowBriefing()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowChatAll()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowChatTeam()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowChatRead()
|
||||||
|
end
|
||||||
|
|
||||||
|
function onShowMessage(a_text, a_duration)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onTriggerMessage(message, duration, clearView)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onRadioMessage(message, duration)
|
||||||
|
end
|
||||||
|
|
||||||
|
function onRadioCommand(command_message)
|
||||||
|
end
|
||||||
|
|
||||||
|
===================================================================================================
|
||||||
|
|
||||||
|
Happy hacking!
|
||||||
|
|
||||||
|
Sincerely,
|
||||||
|
dsb at eagle dot ru
|
||||||
@ -529,7 +529,7 @@ do -- CARGO_REPRESENTABLE
|
|||||||
-- @extends #CARGO
|
-- @extends #CARGO
|
||||||
-- @field test
|
-- @field test
|
||||||
|
|
||||||
---
|
--- Models CARGO that is representable by a Unit.
|
||||||
-- @field #CARGO_REPRESENTABLE CARGO_REPRESENTABLE
|
-- @field #CARGO_REPRESENTABLE CARGO_REPRESENTABLE
|
||||||
CARGO_REPRESENTABLE = {
|
CARGO_REPRESENTABLE = {
|
||||||
ClassName = "CARGO_REPRESENTABLE"
|
ClassName = "CARGO_REPRESENTABLE"
|
||||||
@ -549,6 +549,18 @@ do -- CARGO_REPRESENTABLE
|
|||||||
|
|
||||||
return self
|
return self
|
||||||
end
|
end
|
||||||
|
|
||||||
|
--- CARGO_REPRESENTABLE Destructor.
|
||||||
|
-- @param #CARGO_REPRESENTABLE self
|
||||||
|
-- @return #CARGO_REPRESENTABLE
|
||||||
|
function CARGO_REPRESENTABLE:Destroy()
|
||||||
|
|
||||||
|
-- Cargo objects are deleted from the _DATABASE and SET_CARGO objects.
|
||||||
|
self:F( { CargoName = self:GetName() } )
|
||||||
|
_EVENTDISPATCHER:CreateEventDeleteCargo( self )
|
||||||
|
|
||||||
|
return self
|
||||||
|
end
|
||||||
|
|
||||||
--- Route a cargo unit to a PointVec2.
|
--- Route a cargo unit to a PointVec2.
|
||||||
-- @param #CARGO_REPRESENTABLE self
|
-- @param #CARGO_REPRESENTABLE self
|
||||||
@ -678,7 +690,7 @@ end
|
|||||||
|
|
||||||
do -- CARGO_UNIT
|
do -- CARGO_UNIT
|
||||||
|
|
||||||
--- Hello
|
--- Models CARGO in the form of units, which can be boarded, unboarded, loaded, unloaded.
|
||||||
-- @type CARGO_UNIT
|
-- @type CARGO_UNIT
|
||||||
-- @extends #CARGO_REPRESENTABLE
|
-- @extends #CARGO_REPRESENTABLE
|
||||||
|
|
||||||
@ -695,346 +707,425 @@ do -- CARGO_UNIT
|
|||||||
ClassName = "CARGO_UNIT"
|
ClassName = "CARGO_UNIT"
|
||||||
}
|
}
|
||||||
|
|
||||||
--- CARGO_UNIT Constructor.
|
--- CARGO_UNIT Constructor.
|
||||||
-- @param #CARGO_UNIT self
|
-- @param #CARGO_UNIT self
|
||||||
-- @param Wrapper.Unit#UNIT CargoUnit
|
-- @param Wrapper.Unit#UNIT CargoUnit
|
||||||
-- @param #string Type
|
-- @param #string Type
|
||||||
-- @param #string Name
|
-- @param #string Name
|
||||||
-- @param #number Weight
|
-- @param #number Weight
|
||||||
-- @param #number ReportRadius (optional)
|
-- @param #number ReportRadius (optional)
|
||||||
-- @param #number NearRadius (optional)
|
-- @param #number NearRadius (optional)
|
||||||
-- @return #CARGO_UNIT
|
-- @return #CARGO_UNIT
|
||||||
function CARGO_UNIT:New( CargoUnit, Type, Name, Weight, NearRadius )
|
function CARGO_UNIT:New( CargoUnit, Type, Name, Weight, NearRadius )
|
||||||
local self = BASE:Inherit( self, CARGO_REPRESENTABLE:New( CargoUnit, Type, Name, Weight, NearRadius ) ) -- #CARGO_UNIT
|
local self = BASE:Inherit( self, CARGO_REPRESENTABLE:New( CargoUnit, Type, Name, Weight, NearRadius ) ) -- #CARGO_UNIT
|
||||||
self:F( { Type, Name, Weight, NearRadius } )
|
self:F( { Type, Name, Weight, NearRadius } )
|
||||||
|
|
||||||
self:T( CargoUnit )
|
|
||||||
self.CargoObject = CargoUnit
|
|
||||||
|
|
||||||
self:T( self.ClassName )
|
|
||||||
|
|
||||||
-- self:HandleEvent( EVENTS.Dead,
|
|
||||||
-- --- @param #CARGO Cargo
|
|
||||||
-- -- @param Core.Event#EVENTDATA EventData
|
|
||||||
-- function( Cargo, EventData )
|
|
||||||
-- if Cargo:GetObjectName() == EventData.IniUnit:GetName() then
|
|
||||||
-- self:E( { "Cargo destroyed", Cargo } )
|
|
||||||
-- Cargo:Destroyed()
|
|
||||||
-- end
|
|
||||||
-- end
|
|
||||||
-- )
|
|
||||||
|
|
||||||
self:SetEventPriority( 5 )
|
|
||||||
|
|
||||||
return self
|
|
||||||
end
|
|
||||||
|
|
||||||
--- CARGO_UNIT Destructor.
|
|
||||||
-- @param #CARGO_UNIT self
|
|
||||||
-- @return #CARGO_UNIT
|
|
||||||
function CARGO_UNIT:Destroy()
|
|
||||||
|
|
||||||
-- Cargo objects are deleted from the _DATABASE and SET_CARGO objects.
|
|
||||||
self:F( { CargoName = self:GetName() } )
|
|
||||||
_EVENTDISPATCHER:CreateEventDeleteCargo( self )
|
|
||||||
|
|
||||||
return self
|
|
||||||
end
|
|
||||||
|
|
||||||
--- Enter UnBoarding State.
|
|
||||||
-- @param #CARGO_UNIT self
|
|
||||||
-- @param #string Event
|
|
||||||
-- @param #string From
|
|
||||||
-- @param #string To
|
|
||||||
-- @param Core.Point#POINT_VEC2 ToPointVec2
|
|
||||||
function CARGO_UNIT:onenterUnBoarding( From, Event, To, ToPointVec2, NearRadius )
|
|
||||||
self:F( { From, Event, To, ToPointVec2, NearRadius } )
|
|
||||||
|
|
||||||
NearRadius = NearRadius or 25
|
|
||||||
|
|
||||||
local Angle = 180
|
|
||||||
local Speed = 60
|
|
||||||
local DeployDistance = 9
|
|
||||||
local RouteDistance = 60
|
|
||||||
|
|
||||||
if From == "Loaded" then
|
|
||||||
|
|
||||||
local CargoCarrier = self.CargoCarrier -- Wrapper.Controllable#CONTROLLABLE
|
|
||||||
|
|
||||||
local CargoCarrierPointVec2 = CargoCarrier:GetPointVec2()
|
|
||||||
local CargoCarrierHeading = self.CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
|
||||||
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
|
||||||
|
|
||||||
|
|
||||||
local CargoRoutePointVec2 = CargoCarrierPointVec2:Translate( RouteDistance, CargoDeployHeading )
|
|
||||||
|
|
||||||
|
|
||||||
-- if there is no ToPointVec2 given, then use the CargoRoutePointVec2
|
|
||||||
ToPointVec2 = ToPointVec2 or CargoRoutePointVec2
|
|
||||||
local DirectionVec3 = CargoCarrierPointVec2:GetDirectionVec3(ToPointVec2)
|
|
||||||
local Angle = CargoCarrierPointVec2:GetAngleDegrees(DirectionVec3)
|
|
||||||
|
|
||||||
local CargoDeployPointVec2 = CargoCarrierPointVec2:Translate( DeployDistance, Angle )
|
|
||||||
|
|
||||||
local FromPointVec2 = CargoCarrierPointVec2
|
|
||||||
|
|
||||||
-- Respawn the group...
|
|
||||||
if self.CargoObject then
|
|
||||||
self.CargoObject:ReSpawn( CargoDeployPointVec2:GetVec3(), CargoDeployHeading )
|
|
||||||
self:F( { "CargoUnits:", self.CargoObject:GetGroup():GetName() } )
|
|
||||||
self.CargoCarrier = nil
|
|
||||||
|
|
||||||
local Points = {}
|
|
||||||
Points[#Points+1] = CargoCarrierPointVec2:WaypointGround( Speed )
|
|
||||||
|
|
||||||
Points[#Points+1] = ToPointVec2:WaypointGround( Speed )
|
|
||||||
|
|
||||||
local TaskRoute = self.CargoObject:TaskRoute( Points )
|
self:T( CargoUnit )
|
||||||
self.CargoObject:SetTask( TaskRoute, 1 )
|
self.CargoObject = CargoUnit
|
||||||
|
|
||||||
|
self:T( self.ClassName )
|
||||||
self:__UnBoarding( 1, ToPointVec2, NearRadius )
|
|
||||||
end
|
self:SetEventPriority( 5 )
|
||||||
end
|
|
||||||
|
return self
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Leave UnBoarding State.
|
--- Enter UnBoarding State.
|
||||||
-- @param #CARGO_UNIT self
|
-- @param #CARGO_UNIT self
|
||||||
-- @param #string Event
|
-- @param #string Event
|
||||||
-- @param #string From
|
-- @param #string From
|
||||||
-- @param #string To
|
-- @param #string To
|
||||||
-- @param Core.Point#POINT_VEC2 ToPointVec2
|
-- @param Core.Point#POINT_VEC2 ToPointVec2
|
||||||
function CARGO_UNIT:onleaveUnBoarding( From, Event, To, ToPointVec2, NearRadius )
|
function CARGO_UNIT:onenterUnBoarding( From, Event, To, ToPointVec2, NearRadius )
|
||||||
self:F( { From, Event, To, ToPointVec2, NearRadius } )
|
self:F( { From, Event, To, ToPointVec2, NearRadius } )
|
||||||
|
|
||||||
NearRadius = NearRadius or 25
|
NearRadius = NearRadius or 25
|
||||||
|
|
||||||
local Angle = 180
|
local Angle = 180
|
||||||
local Speed = 10
|
local Speed = 60
|
||||||
local Distance = 5
|
local DeployDistance = 9
|
||||||
|
local RouteDistance = 60
|
||||||
if From == "UnBoarding" then
|
|
||||||
if self:IsNear( ToPointVec2, NearRadius ) then
|
if From == "Loaded" then
|
||||||
return true
|
|
||||||
else
|
local CargoCarrier = self.CargoCarrier -- Wrapper.Controllable#CONTROLLABLE
|
||||||
|
|
||||||
self:__UnBoarding( 1, ToPointVec2, NearRadius )
|
|
||||||
end
|
|
||||||
return false
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
--- UnBoard Event.
|
|
||||||
-- @param #CARGO_UNIT self
|
|
||||||
-- @param #string Event
|
|
||||||
-- @param #string From
|
|
||||||
-- @param #string To
|
|
||||||
-- @param Core.Point#POINT_VEC2 ToPointVec2
|
|
||||||
function CARGO_UNIT:onafterUnBoarding( From, Event, To, ToPointVec2, NearRadius )
|
|
||||||
self:F( { From, Event, To, ToPointVec2, NearRadius } )
|
|
||||||
|
|
||||||
NearRadius = NearRadius or 25
|
|
||||||
|
|
||||||
self.CargoInAir = self.CargoObject:InAir()
|
|
||||||
|
|
||||||
self:T( self.CargoInAir )
|
|
||||||
|
|
||||||
-- Only unboard the cargo when the carrier is not in the air.
|
|
||||||
-- (eg. cargo can be on a oil derrick, moving the cargo on the oil derrick will drop the cargo on the sea).
|
|
||||||
if not self.CargoInAir then
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
self:__UnLoad( 1, ToPointVec2, NearRadius )
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
--- Enter UnLoaded State.
|
|
||||||
-- @param #CARGO_UNIT self
|
|
||||||
-- @param #string Event
|
|
||||||
-- @param #string From
|
|
||||||
-- @param #string To
|
|
||||||
-- @param Core.Point#POINT_VEC2
|
|
||||||
function CARGO_UNIT:onenterUnLoaded( From, Event, To, ToPointVec2 )
|
|
||||||
self:F( { ToPointVec2, From, Event, To } )
|
|
||||||
|
|
||||||
local Angle = 180
|
|
||||||
local Speed = 10
|
|
||||||
local Distance = 5
|
|
||||||
|
|
||||||
if From == "Loaded" then
|
|
||||||
local StartPointVec2 = self.CargoCarrier:GetPointVec2()
|
|
||||||
local CargoCarrierHeading = self.CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
|
||||||
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
|
||||||
local CargoDeployCoord = StartPointVec2:Translate( Distance, CargoDeployHeading )
|
|
||||||
|
|
||||||
ToPointVec2 = ToPointVec2 or POINT_VEC2:New( CargoDeployCoord.x, CargoDeployCoord.z )
|
|
||||||
|
|
||||||
-- Respawn the group...
|
|
||||||
if self.CargoObject then
|
|
||||||
self.CargoObject:ReSpawn( ToPointVec2:GetVec3(), 0 )
|
|
||||||
self.CargoCarrier = nil
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
if self.OnUnLoadedCallBack then
|
|
||||||
self.OnUnLoadedCallBack( self, unpack( self.OnUnLoadedParameters ) )
|
|
||||||
self.OnUnLoadedCallBack = nil
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
--- Board Event.
|
|
||||||
-- @param #CARGO_UNIT self
|
|
||||||
-- @param #string Event
|
|
||||||
-- @param #string From
|
|
||||||
-- @param #string To
|
|
||||||
function CARGO_UNIT:onafterBoard( From, Event, To, CargoCarrier, NearRadius, ... )
|
|
||||||
self:F( { From, Event, To, CargoCarrier, NearRadius } )
|
|
||||||
|
|
||||||
local NearRadius = NearRadius or 25
|
|
||||||
|
|
||||||
self.CargoInAir = self.CargoObject:InAir()
|
|
||||||
|
|
||||||
self:T( self.CargoInAir )
|
|
||||||
|
|
||||||
-- Only move the group to the carrier when the cargo is not in the air
|
|
||||||
-- (eg. cargo can be on a oil derrick, moving the cargo on the oil derrick will drop the cargo on the sea).
|
|
||||||
if not self.CargoInAir then
|
|
||||||
if self:IsNear( CargoCarrier:GetPointVec2(), NearRadius ) then
|
|
||||||
self:Load( CargoCarrier, NearRadius, ... )
|
|
||||||
else
|
|
||||||
local Speed = 90
|
|
||||||
local Angle = 180
|
|
||||||
local Distance = 5
|
|
||||||
|
|
||||||
NearRadius = NearRadius or 25
|
|
||||||
|
|
||||||
local CargoCarrierPointVec2 = CargoCarrier:GetPointVec2()
|
local CargoCarrierPointVec2 = CargoCarrier:GetPointVec2()
|
||||||
local CargoCarrierHeading = CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
local CargoCarrierHeading = self.CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
||||||
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
||||||
local CargoDeployPointVec2 = CargoCarrierPointVec2:Translate( Distance, CargoDeployHeading )
|
|
||||||
|
|
||||||
|
local CargoRoutePointVec2 = CargoCarrierPointVec2:Translate( RouteDistance, CargoDeployHeading )
|
||||||
|
|
||||||
|
|
||||||
|
-- if there is no ToPointVec2 given, then use the CargoRoutePointVec2
|
||||||
|
ToPointVec2 = ToPointVec2 or CargoRoutePointVec2
|
||||||
|
local DirectionVec3 = CargoCarrierPointVec2:GetDirectionVec3(ToPointVec2)
|
||||||
|
local Angle = CargoCarrierPointVec2:GetAngleDegrees(DirectionVec3)
|
||||||
|
|
||||||
|
local CargoDeployPointVec2 = CargoCarrierPointVec2:Translate( DeployDistance, Angle )
|
||||||
|
|
||||||
|
local FromPointVec2 = CargoCarrierPointVec2
|
||||||
|
|
||||||
|
-- Respawn the group...
|
||||||
|
if self.CargoObject then
|
||||||
|
self.CargoObject:ReSpawn( CargoDeployPointVec2:GetVec3(), CargoDeployHeading )
|
||||||
|
self:F( { "CargoUnits:", self.CargoObject:GetGroup():GetName() } )
|
||||||
|
self.CargoCarrier = nil
|
||||||
|
|
||||||
|
local Points = {}
|
||||||
|
Points[#Points+1] = CargoCarrierPointVec2:WaypointGround( Speed )
|
||||||
|
|
||||||
|
Points[#Points+1] = ToPointVec2:WaypointGround( Speed )
|
||||||
|
|
||||||
local Points = {}
|
local TaskRoute = self.CargoObject:TaskRoute( Points )
|
||||||
|
self.CargoObject:SetTask( TaskRoute, 1 )
|
||||||
local PointStartVec2 = self.CargoObject:GetPointVec2()
|
|
||||||
|
|
||||||
Points[#Points+1] = PointStartVec2:WaypointGround( Speed )
|
self:__UnBoarding( 1, ToPointVec2, NearRadius )
|
||||||
Points[#Points+1] = CargoDeployPointVec2:WaypointGround( Speed )
|
end
|
||||||
|
|
||||||
local TaskRoute = self.CargoObject:TaskRoute( Points )
|
|
||||||
self.CargoObject:SetTask( TaskRoute, 2 )
|
|
||||||
self:__Boarding( -1, CargoCarrier, NearRadius )
|
|
||||||
self.RunCount = 0
|
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
--- Leave UnBoarding State.
|
||||||
|
-- @param #CARGO_UNIT self
|
||||||
|
-- @param #string Event
|
||||||
--- Boarding Event.
|
-- @param #string From
|
||||||
-- @param #CARGO_UNIT self
|
-- @param #string To
|
||||||
-- @param #string Event
|
-- @param Core.Point#POINT_VEC2 ToPointVec2
|
||||||
-- @param #string From
|
function CARGO_UNIT:onleaveUnBoarding( From, Event, To, ToPointVec2, NearRadius )
|
||||||
-- @param #string To
|
self:F( { From, Event, To, ToPointVec2, NearRadius } )
|
||||||
-- @param Wrapper.Unit#UNIT CargoCarrier
|
|
||||||
-- @param #number NearRadius
|
|
||||||
function CARGO_UNIT:onafterBoarding( From, Event, To, CargoCarrier, NearRadius, ... )
|
|
||||||
self:F( { From, Event, To, CargoCarrier.UnitName, NearRadius } )
|
|
||||||
|
|
||||||
|
NearRadius = NearRadius or 25
|
||||||
|
|
||||||
if CargoCarrier and CargoCarrier:IsAlive() then
|
local Angle = 180
|
||||||
if CargoCarrier:InAir() == false then
|
local Speed = 10
|
||||||
if self:IsNear( CargoCarrier:GetPointVec2(), NearRadius ) then
|
local Distance = 5
|
||||||
self:__Load( 1, CargoCarrier, ... )
|
|
||||||
|
if From == "UnBoarding" then
|
||||||
|
if self:IsNear( ToPointVec2, NearRadius ) then
|
||||||
|
return true
|
||||||
else
|
else
|
||||||
self:__Boarding( -1, CargoCarrier, NearRadius, ... )
|
|
||||||
self.RunCount = self.RunCount + 1
|
self:__UnBoarding( 1, ToPointVec2, NearRadius )
|
||||||
if self.RunCount >= 20 then
|
end
|
||||||
self.RunCount = 0
|
return false
|
||||||
local Speed = 90
|
end
|
||||||
local Angle = 180
|
|
||||||
local Distance = 5
|
end
|
||||||
|
|
||||||
|
--- UnBoard Event.
|
||||||
|
-- @param #CARGO_UNIT self
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string To
|
||||||
|
-- @param Core.Point#POINT_VEC2 ToPointVec2
|
||||||
|
function CARGO_UNIT:onafterUnBoarding( From, Event, To, ToPointVec2, NearRadius )
|
||||||
|
self:F( { From, Event, To, ToPointVec2, NearRadius } )
|
||||||
|
|
||||||
|
NearRadius = NearRadius or 25
|
||||||
|
|
||||||
|
self.CargoInAir = self.CargoObject:InAir()
|
||||||
|
|
||||||
|
self:T( self.CargoInAir )
|
||||||
|
|
||||||
|
-- Only unboard the cargo when the carrier is not in the air.
|
||||||
|
-- (eg. cargo can be on a oil derrick, moving the cargo on the oil derrick will drop the cargo on the sea).
|
||||||
|
if not self.CargoInAir then
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
self:__UnLoad( 1, ToPointVec2, NearRadius )
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
--- Enter UnLoaded State.
|
||||||
|
-- @param #CARGO_UNIT self
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string To
|
||||||
|
-- @param Core.Point#POINT_VEC2
|
||||||
|
function CARGO_UNIT:onenterUnLoaded( From, Event, To, ToPointVec2 )
|
||||||
|
self:F( { ToPointVec2, From, Event, To } )
|
||||||
|
|
||||||
|
local Angle = 180
|
||||||
|
local Speed = 10
|
||||||
|
local Distance = 5
|
||||||
|
|
||||||
|
if From == "Loaded" then
|
||||||
|
local StartPointVec2 = self.CargoCarrier:GetPointVec2()
|
||||||
|
local CargoCarrierHeading = self.CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
||||||
|
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
||||||
|
local CargoDeployCoord = StartPointVec2:Translate( Distance, CargoDeployHeading )
|
||||||
|
|
||||||
|
ToPointVec2 = ToPointVec2 or COORDINATE:New( CargoDeployCoord.x, CargoDeployCoord.z )
|
||||||
|
|
||||||
|
-- Respawn the group...
|
||||||
|
if self.CargoObject then
|
||||||
|
self.CargoObject:ReSpawn( ToPointVec2:GetVec3(), 0 )
|
||||||
|
self.CargoCarrier = nil
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.OnUnLoadedCallBack then
|
||||||
|
self.OnUnLoadedCallBack( self, unpack( self.OnUnLoadedParameters ) )
|
||||||
|
self.OnUnLoadedCallBack = nil
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
--- Board Event.
|
||||||
|
-- @param #CARGO_UNIT self
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string To
|
||||||
|
function CARGO_UNIT:onafterBoard( From, Event, To, CargoCarrier, NearRadius, ... )
|
||||||
|
self:F( { From, Event, To, CargoCarrier, NearRadius } )
|
||||||
|
|
||||||
|
local NearRadius = NearRadius or 25
|
||||||
|
|
||||||
|
self.CargoInAir = self.CargoObject:InAir()
|
||||||
|
|
||||||
|
self:T( self.CargoInAir )
|
||||||
|
|
||||||
|
-- Only move the group to the carrier when the cargo is not in the air
|
||||||
|
-- (eg. cargo can be on a oil derrick, moving the cargo on the oil derrick will drop the cargo on the sea).
|
||||||
|
if not self.CargoInAir then
|
||||||
|
if self:IsNear( CargoCarrier:GetPointVec2(), NearRadius ) then
|
||||||
|
self:Load( CargoCarrier, NearRadius, ... )
|
||||||
|
else
|
||||||
|
local Speed = 90
|
||||||
|
local Angle = 180
|
||||||
|
local Distance = 5
|
||||||
|
|
||||||
|
NearRadius = NearRadius or 25
|
||||||
|
|
||||||
|
local CargoCarrierPointVec2 = CargoCarrier:GetPointVec2()
|
||||||
|
local CargoCarrierHeading = CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
||||||
|
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
||||||
|
local CargoDeployPointVec2 = CargoCarrierPointVec2:Translate( Distance, CargoDeployHeading )
|
||||||
|
|
||||||
|
local Points = {}
|
||||||
|
|
||||||
|
local PointStartVec2 = self.CargoObject:GetPointVec2()
|
||||||
|
|
||||||
|
Points[#Points+1] = PointStartVec2:WaypointGround( Speed )
|
||||||
|
Points[#Points+1] = CargoDeployPointVec2:WaypointGround( Speed )
|
||||||
|
|
||||||
|
local TaskRoute = self.CargoObject:TaskRoute( Points )
|
||||||
|
self.CargoObject:SetTask( TaskRoute, 2 )
|
||||||
|
self:__Boarding( -1, CargoCarrier, NearRadius )
|
||||||
|
self.RunCount = 0
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- Boarding Event.
|
||||||
|
-- @param #CARGO_UNIT self
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string To
|
||||||
|
-- @param Wrapper.Unit#UNIT CargoCarrier
|
||||||
|
-- @param #number NearRadius
|
||||||
|
function CARGO_UNIT:onafterBoarding( From, Event, To, CargoCarrier, NearRadius, ... )
|
||||||
|
self:F( { From, Event, To, CargoCarrier.UnitName, NearRadius } )
|
||||||
|
|
||||||
|
|
||||||
|
if CargoCarrier and CargoCarrier:IsAlive() then
|
||||||
|
if CargoCarrier:InAir() == false then
|
||||||
|
if self:IsNear( CargoCarrier:GetPointVec2(), NearRadius ) then
|
||||||
|
self:__Load( 1, CargoCarrier, ... )
|
||||||
|
else
|
||||||
|
self:__Boarding( -1, CargoCarrier, NearRadius, ... )
|
||||||
|
self.RunCount = self.RunCount + 1
|
||||||
|
if self.RunCount >= 20 then
|
||||||
|
self.RunCount = 0
|
||||||
|
local Speed = 90
|
||||||
|
local Angle = 180
|
||||||
|
local Distance = 5
|
||||||
|
|
||||||
|
NearRadius = NearRadius or 25
|
||||||
|
|
||||||
NearRadius = NearRadius or 25
|
local CargoCarrierPointVec2 = CargoCarrier:GetPointVec2()
|
||||||
|
local CargoCarrierHeading = CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
||||||
local CargoCarrierPointVec2 = CargoCarrier:GetPointVec2()
|
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
||||||
local CargoCarrierHeading = CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
local CargoDeployPointVec2 = CargoCarrierPointVec2:Translate( Distance, CargoDeployHeading )
|
||||||
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
|
||||||
local CargoDeployPointVec2 = CargoCarrierPointVec2:Translate( Distance, CargoDeployHeading )
|
local Points = {}
|
||||||
|
|
||||||
local Points = {}
|
local PointStartVec2 = self.CargoObject:GetPointVec2()
|
||||||
|
|
||||||
local PointStartVec2 = self.CargoObject:GetPointVec2()
|
Points[#Points+1] = PointStartVec2:WaypointGround( Speed )
|
||||||
|
Points[#Points+1] = CargoDeployPointVec2:WaypointGround( Speed )
|
||||||
Points[#Points+1] = PointStartVec2:WaypointGround( Speed )
|
|
||||||
Points[#Points+1] = CargoDeployPointVec2:WaypointGround( Speed )
|
local TaskRoute = self.CargoObject:TaskRoute( Points )
|
||||||
|
self.CargoObject:SetTask( TaskRoute, 0.2 )
|
||||||
local TaskRoute = self.CargoObject:TaskRoute( Points )
|
end
|
||||||
self.CargoObject:SetTask( TaskRoute, 0.2 )
|
|
||||||
end
|
end
|
||||||
|
else
|
||||||
|
self.CargoObject:MessageToGroup( "Cancelling Boarding... Get back on the ground!", 5, CargoCarrier:GetGroup(), self:GetName() )
|
||||||
|
self:CancelBoarding( CargoCarrier, NearRadius, ... )
|
||||||
|
self.CargoObject:SetCommand( self.CargoObject:CommandStopRoute( true ) )
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
self.CargoObject:MessageToGroup( "Cancelling Boarding... Get back on the ground!", 5, CargoCarrier:GetGroup(), self:GetName() )
|
self:E("Something is wrong")
|
||||||
self:CancelBoarding( CargoCarrier, NearRadius, ... )
|
|
||||||
self.CargoObject:SetCommand( self.CargoObject:CommandStopRoute( true ) )
|
|
||||||
end
|
end
|
||||||
else
|
|
||||||
self:E("Something is wrong")
|
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
--- Enter Boarding State.
|
|
||||||
-- @param #CARGO_UNIT self
|
|
||||||
-- @param #string Event
|
|
||||||
-- @param #string From
|
|
||||||
-- @param #string To
|
|
||||||
-- @param Wrapper.Unit#UNIT CargoCarrier
|
|
||||||
function CARGO_UNIT:onenterBoarding( From, Event, To, CargoCarrier, NearRadius, ... )
|
|
||||||
self:F( { From, Event, To, CargoCarrier.UnitName, NearRadius } )
|
|
||||||
|
|
||||||
local Speed = 90
|
--- Enter Boarding State.
|
||||||
local Angle = 180
|
-- @param #CARGO_UNIT self
|
||||||
local Distance = 5
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
local NearRadius = NearRadius or 25
|
-- @param #string To
|
||||||
|
-- @param Wrapper.Unit#UNIT CargoCarrier
|
||||||
if From == "UnLoaded" or From == "Boarding" then
|
function CARGO_UNIT:onenterBoarding( From, Event, To, CargoCarrier, NearRadius, ... )
|
||||||
|
self:F( { From, Event, To, CargoCarrier.UnitName, NearRadius } )
|
||||||
|
|
||||||
|
local Speed = 90
|
||||||
|
local Angle = 180
|
||||||
|
local Distance = 5
|
||||||
|
|
||||||
|
local NearRadius = NearRadius or 25
|
||||||
|
|
||||||
|
if From == "UnLoaded" or From == "Boarding" then
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
--- Loaded State.
|
||||||
|
-- @param #CARGO_UNIT self
|
||||||
--- Loaded State.
|
-- @param #string Event
|
||||||
-- @param #CARGO_UNIT self
|
-- @param #string From
|
||||||
-- @param #string Event
|
-- @param #string To
|
||||||
-- @param #string From
|
-- @param Wrapper.Unit#UNIT CargoCarrier
|
||||||
-- @param #string To
|
function CARGO_UNIT:onenterLoaded( From, Event, To, CargoCarrier )
|
||||||
-- @param Wrapper.Unit#UNIT CargoCarrier
|
self:F( { From, Event, To, CargoCarrier } )
|
||||||
function CARGO_UNIT:onenterLoaded( From, Event, To, CargoCarrier )
|
|
||||||
self:F( { From, Event, To, CargoCarrier } )
|
|
||||||
|
|
||||||
self.CargoCarrier = CargoCarrier
|
|
||||||
|
|
||||||
-- Only destroy the CargoObject is if there is a CargoObject (packages don't have CargoObjects).
|
self.CargoCarrier = CargoCarrier
|
||||||
if self.CargoObject then
|
|
||||||
self:T("Destroying")
|
-- Only destroy the CargoObject is if there is a CargoObject (packages don't have CargoObjects).
|
||||||
self.CargoObject:Destroy()
|
if self.CargoObject then
|
||||||
|
self:T("Destroying")
|
||||||
|
self.CargoObject:Destroy()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
end -- CARGO_UNIT
|
||||||
|
|
||||||
|
|
||||||
|
do -- CARGO_CRATE
|
||||||
|
|
||||||
|
--- Models the behaviour of cargo crates, which can be slingloaded and boarded on helicopters using the DCS menus.
|
||||||
|
-- @type CARGO_CRATE
|
||||||
|
-- @extends #CARGO_REPRESENTABLE
|
||||||
|
|
||||||
|
--- # CARGO\_CRATE class, extends @{#CARGO_REPRESENTABLE}
|
||||||
|
--
|
||||||
|
-- The CARGO\_CRATE class 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.
|
||||||
|
--
|
||||||
|
-- ===
|
||||||
|
--
|
||||||
|
-- @field #CARGO_CRATE
|
||||||
|
CARGO_CRATE = {
|
||||||
|
ClassName = "CARGO_CRATE"
|
||||||
|
}
|
||||||
|
|
||||||
|
--- CARGO_CRATE Constructor.
|
||||||
|
-- @param #CARGO_CRATE self
|
||||||
|
-- @param #string CrateName
|
||||||
|
-- @param #string Type
|
||||||
|
-- @param #string Name
|
||||||
|
-- @param #number Weight
|
||||||
|
-- @param #number ReportRadius (optional)
|
||||||
|
-- @param #number NearRadius (optional)
|
||||||
|
-- @return #CARGO_CRATE
|
||||||
|
function CARGO_CRATE:New( CargoCrateName, Type, Name, NearRadius )
|
||||||
|
local self = BASE:Inherit( self, CARGO_REPRESENTABLE:New( CargoCrateName, Type, Name, nil, NearRadius ) ) -- #CARGO_CRATE
|
||||||
|
self:F( { Type, Name, NearRadius } )
|
||||||
|
|
||||||
|
self:T( CargoCrateName )
|
||||||
|
_DATABASE:AddStatic( CargoCrateName )
|
||||||
|
|
||||||
|
self.CargoObject = STATIC:FindByName( CargoCrateName )
|
||||||
|
|
||||||
|
self:T( self.ClassName )
|
||||||
|
|
||||||
|
self:SetEventPriority( 5 )
|
||||||
|
|
||||||
|
return self
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
--- Enter UnLoaded State.
|
||||||
|
-- @param #CARGO_CRATE self
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string To
|
||||||
|
-- @param Core.Point#POINT_VEC2
|
||||||
|
function CARGO_CRATE:onenterUnLoaded( From, Event, To, ToPointVec2 )
|
||||||
|
self:F( { ToPointVec2, From, Event, To } )
|
||||||
|
|
||||||
|
local Angle = 180
|
||||||
|
local Speed = 10
|
||||||
|
local Distance = 10
|
||||||
|
|
||||||
|
if From == "Loaded" then
|
||||||
|
local StartCoordinate = self.CargoCarrier:GetCoordinate()
|
||||||
|
local CargoCarrierHeading = self.CargoCarrier:GetHeading() -- Get Heading of object in degrees.
|
||||||
|
local CargoDeployHeading = ( ( CargoCarrierHeading + Angle ) >= 360 ) and ( CargoCarrierHeading + Angle - 360 ) or ( CargoCarrierHeading + Angle )
|
||||||
|
local CargoDeployCoord = StartCoordinate:Translate( Distance, CargoDeployHeading )
|
||||||
|
|
||||||
|
ToPointVec2 = ToPointVec2 or COORDINATE:NewFromVec2( { x= CargoDeployCoord.x, y = CargoDeployCoord.z } )
|
||||||
|
|
||||||
|
-- Respawn the group...
|
||||||
|
if self.CargoObject then
|
||||||
|
self.CargoObject:ReSpawn( ToPointVec2, 0 )
|
||||||
|
self.CargoCarrier = nil
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.OnUnLoadedCallBack then
|
||||||
|
self.OnUnLoadedCallBack( self, unpack( self.OnUnLoadedParameters ) )
|
||||||
|
self.OnUnLoadedCallBack = nil
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- Loaded State.
|
||||||
|
-- @param #CARGO_CRATE self
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string To
|
||||||
|
-- @param Wrapper.Unit#UNIT CargoCarrier
|
||||||
|
function CARGO_CRATE:onenterLoaded( From, Event, To, CargoCarrier )
|
||||||
|
self:F( { From, Event, To, CargoCarrier } )
|
||||||
|
|
||||||
|
self.CargoCarrier = CargoCarrier
|
||||||
|
|
||||||
|
-- Only destroy the CargoObject is if there is a CargoObject (packages don't have CargoObjects).
|
||||||
|
if self.CargoObject then
|
||||||
|
self:T("Destroying")
|
||||||
|
self.CargoObject:Destroy()
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
do -- CARGO_GROUP
|
do -- CARGO_GROUP
|
||||||
|
|
||||||
--- @type CARGO_GROUP
|
--- @type CARGO_GROUP
|
||||||
|
|||||||
@ -522,7 +522,7 @@ function DATABASE:_RegisterStaticTemplate( StaticTemplate, CoalitionID, Category
|
|||||||
|
|
||||||
|
|
||||||
TraceTable[#TraceTable+1] = "Static"
|
TraceTable[#TraceTable+1] = "Static"
|
||||||
TraceTable[#TraceTable+1] = self.Templates.Statics[StaticTemplateName].GroupName
|
TraceTable[#TraceTable+1] = self.Templates.Statics[StaticTemplateName].StaticName
|
||||||
|
|
||||||
TraceTable[#TraceTable+1] = "Coalition"
|
TraceTable[#TraceTable+1] = "Coalition"
|
||||||
TraceTable[#TraceTable+1] = self.Templates.Statics[StaticTemplateName].CoalitionID
|
TraceTable[#TraceTable+1] = self.Templates.Statics[StaticTemplateName].CoalitionID
|
||||||
@ -649,6 +649,7 @@ end
|
|||||||
function DATABASE:_RegisterStatics()
|
function DATABASE:_RegisterStatics()
|
||||||
|
|
||||||
local CoalitionsData = { GroupsRed = coalition.getStaticObjects( coalition.side.RED ), GroupsBlue = coalition.getStaticObjects( coalition.side.BLUE ) }
|
local CoalitionsData = { GroupsRed = coalition.getStaticObjects( coalition.side.RED ), GroupsBlue = coalition.getStaticObjects( coalition.side.BLUE ) }
|
||||||
|
self:E( { Statics = CoalitionsData } )
|
||||||
for CoalitionId, CoalitionData in pairs( CoalitionsData ) do
|
for CoalitionId, CoalitionData in pairs( CoalitionsData ) do
|
||||||
for DCSStaticId, DCSStatic in pairs( CoalitionData ) do
|
for DCSStaticId, DCSStatic in pairs( CoalitionData ) do
|
||||||
|
|
||||||
|
|||||||
@ -157,8 +157,13 @@ function SPAWNSTATIC:SpawnFromPointVec2( PointVec2, Heading, NewName ) --R2.1
|
|||||||
|
|
||||||
local StaticTemplate = _DATABASE:GetStaticUnitTemplate( self.SpawnTemplatePrefix )
|
local StaticTemplate = _DATABASE:GetStaticUnitTemplate( self.SpawnTemplatePrefix )
|
||||||
|
|
||||||
StaticTemplate.x = PointVec2:GetLat()
|
StaticTemplate.x = PointVec2.x
|
||||||
StaticTemplate.y = PointVec2:GetLon()
|
StaticTemplate.y = PointVec2.z
|
||||||
|
|
||||||
|
StaticTemplate.units = nil
|
||||||
|
StaticTemplate.route = nil
|
||||||
|
StaticTemplate.groupId = nil
|
||||||
|
|
||||||
|
|
||||||
StaticTemplate.name = NewName or string.format("%s#%05d", self.SpawnTemplatePrefix, self.SpawnIndex )
|
StaticTemplate.name = NewName or string.format("%s#%05d", self.SpawnTemplatePrefix, self.SpawnIndex )
|
||||||
StaticTemplate.heading = ( Heading / 180 ) * math.pi
|
StaticTemplate.heading = ( Heading / 180 ) * math.pi
|
||||||
|
|||||||
@ -108,6 +108,8 @@ function AIRBASEPOLICE_BASE:New( SetClient, Airbases )
|
|||||||
)
|
)
|
||||||
|
|
||||||
self.AirbaseMonitor = SCHEDULER:New( self, self._AirbaseMonitor, {}, 0, 2, 0.05 )
|
self.AirbaseMonitor = SCHEDULER:New( self, self._AirbaseMonitor, {}, 0, 2, 0.05 )
|
||||||
|
|
||||||
|
trigger.action.setUserFlag("SSB",100)
|
||||||
|
|
||||||
return self
|
return self
|
||||||
end
|
end
|
||||||
@ -181,22 +183,9 @@ function AIRBASEPOLICE_BASE:_AirbaseMonitor()
|
|||||||
Client:Message( "You are speeding on the taxiway! Slow down or you will be removed from this airbase! Your current velocity is " .. string.format( "%2.0f km/h", Velocity ), 5, "Warning " .. SpeedingWarnings .. " / 3" )
|
Client:Message( "You are speeding on the taxiway! Slow down or you will be removed from this airbase! Your current velocity is " .. string.format( "%2.0f km/h", Velocity ), 5, "Warning " .. SpeedingWarnings .. " / 3" )
|
||||||
Client:SetState( self, "Warnings", SpeedingWarnings + 1 )
|
Client:SetState( self, "Warnings", SpeedingWarnings + 1 )
|
||||||
else
|
else
|
||||||
MESSAGE:New( "Player " .. Client:GetPlayerName() .. " is being damaged at the airbase, due to a speeding violation ...", 10, "Airbase Police" ):ToAll()
|
MESSAGE:New( "Player " .. Client:GetPlayerName() .. " is being kicked from the airbase, due to a speeding violation ...", 10, "Airbase Police" ):ToAll()
|
||||||
--- @param Wrapper.Client#CLIENT Client
|
--- @param Wrapper.Client#CLIENT Client
|
||||||
local function DestroyUntilHeavilyDamaged( Client )
|
Client:Destroy()
|
||||||
local ClientCoord = Client:GetCoordinate()
|
|
||||||
ClientCoord:Explosion( 100 )
|
|
||||||
local Damage = Client:GetLife()
|
|
||||||
local InitialLife = Client:GetLife0()
|
|
||||||
MESSAGE:New( "Player " .. Client:GetPlayerName() .. " Damage ... " .. Damage, 5, "Airbase Police" ):ToAll()
|
|
||||||
if ( Damage / InitialLife ) * 100 < 80 then
|
|
||||||
Client:ScheduleStop( DestroyUntilHeavilyDamaged )
|
|
||||||
end
|
|
||||||
end
|
|
||||||
Client:ScheduleOnce( 1, DestroyUntilHeavilyDamaged, Client )
|
|
||||||
--Client:ScheduleRepeat( 1, 1, 0, nil, DestroyUntilHeavilyDamaged, Client )
|
|
||||||
--Client:Destroy()
|
|
||||||
trigger.action.setUserFlag( "AIRCRAFT_"..Client:GetID(), 100)
|
|
||||||
Client:SetState( self, "Speeding", false )
|
Client:SetState( self, "Speeding", false )
|
||||||
Client:SetState( self, "Warnings", 0 )
|
Client:SetState( self, "Warnings", 0 )
|
||||||
end
|
end
|
||||||
|
|||||||
452
Moose Development/Moose/Functional/ZoneGoalCargo.lua
Normal file
452
Moose Development/Moose/Functional/ZoneGoalCargo.lua
Normal file
@ -0,0 +1,452 @@
|
|||||||
|
--- **Functional (WIP)** -- Base class that models processes to achieve goals involving a Zone and Cargo.
|
||||||
|
--
|
||||||
|
-- ====
|
||||||
|
--
|
||||||
|
-- ZONE_GOAL_CARGO models processes that have a Goal with a defined achievement involving a Zone and Cargo.
|
||||||
|
-- Derived classes implement the ways how the achievements can be realized.
|
||||||
|
--
|
||||||
|
-- ====
|
||||||
|
--
|
||||||
|
-- ### Author: **Sven Van de Velde (FlightControl)**
|
||||||
|
--
|
||||||
|
-- ====
|
||||||
|
--
|
||||||
|
-- @module ZoneGoalCargo
|
||||||
|
|
||||||
|
do -- ZoneGoal
|
||||||
|
|
||||||
|
--- @type ZONE_GOAL_CARGO
|
||||||
|
-- @extends Functional.ZoneGoal#ZONE_GOAL
|
||||||
|
|
||||||
|
|
||||||
|
--- # ZONE_GOAL_CARGO class, extends @{ZoneGoal#ZONE_GOAL}
|
||||||
|
--
|
||||||
|
-- ZONE_GOAL_CARGO models processes that have a Goal with a defined achievement involving a Zone and Cargo.
|
||||||
|
-- Derived classes implement the ways how the achievements can be realized.
|
||||||
|
--
|
||||||
|
-- ## 1. ZONE_GOAL_CARGO constructor
|
||||||
|
--
|
||||||
|
-- * @{#ZONE_GOAL_CARGO.New}(): Creates a new ZONE_GOAL_CARGO object.
|
||||||
|
--
|
||||||
|
-- ## 2. ZONE_GOAL_CARGO is a finite state machine (FSM).
|
||||||
|
--
|
||||||
|
-- ### 2.1 ZONE_GOAL_CARGO States
|
||||||
|
--
|
||||||
|
-- * **Deployed**: The Zone has been captured by an other coalition.
|
||||||
|
-- * **Airborne**: The Zone is currently intruded by an other coalition. There are units of the owning coalition and an other coalition in the Zone.
|
||||||
|
-- * **Loaded**: The Zone is guarded by the owning coalition. There is no other unit of an other coalition in the Zone.
|
||||||
|
-- * **Empty**: The Zone is empty. There is not valid unit in the Zone.
|
||||||
|
--
|
||||||
|
-- ### 2.2 ZONE_GOAL_CARGO Events
|
||||||
|
--
|
||||||
|
-- * **Capture**: The Zone has been captured by an other coalition.
|
||||||
|
-- * **Attack**: The Zone is currently intruded by an other coalition. There are units of the owning coalition and an other coalition in the Zone.
|
||||||
|
-- * **Guard**: The Zone is guarded by the owning coalition. There is no other unit of an other coalition in the Zone.
|
||||||
|
-- * **Empty**: The Zone is empty. There is not valid unit in the Zone.
|
||||||
|
--
|
||||||
|
-- ### 2.3 ZONE_GOAL_CARGO State Machine
|
||||||
|
--
|
||||||
|
-- @field #ZONE_GOAL_CARGO
|
||||||
|
ZONE_GOAL_CARGO = {
|
||||||
|
ClassName = "ZONE_GOAL_CARGO",
|
||||||
|
}
|
||||||
|
|
||||||
|
--- @field #table ZONE_GOAL_CARGO.States
|
||||||
|
ZONE_GOAL_CARGO.States = {}
|
||||||
|
|
||||||
|
--- ZONE_GOAL_CARGO Constructor.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param Core.Zone#ZONE Zone A @{Zone} object with the goal to be achieved.
|
||||||
|
-- @param DCSCoalition.DCSCoalition#coalition Coalition The initial coalition owning the zone.
|
||||||
|
-- @return #ZONE_GOAL_CARGO
|
||||||
|
function ZONE_GOAL_CARGO:New( Zone, Coalition )
|
||||||
|
|
||||||
|
local self = BASE:Inherit( self, ZONE_GOAL:New( Zone ) ) -- #ZONE_GOAL_CARGO
|
||||||
|
self:F( { Zone = Zone, Coalition = Coalition } )
|
||||||
|
|
||||||
|
self:SetCoalition( Coalition )
|
||||||
|
|
||||||
|
do
|
||||||
|
|
||||||
|
--- Captured State Handler OnLeave for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnLeaveCaptured
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Captured State Handler OnEnter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnEnterCaptured
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
do
|
||||||
|
|
||||||
|
--- Attacked State Handler OnLeave for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnLeaveAttacked
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Attacked State Handler OnEnter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnEnterAttacked
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
do
|
||||||
|
|
||||||
|
--- Guarded State Handler OnLeave for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnLeaveGuarded
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Guarded State Handler OnEnter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnEnterGuarded
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
do
|
||||||
|
|
||||||
|
--- Empty State Handler OnLeave for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnLeaveEmpty
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Empty State Handler OnEnter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnEnterEmpty
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
self:AddTransition( "*", "Guard", "Guarded" )
|
||||||
|
|
||||||
|
--- Guard Handler OnBefore for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnBeforeGuard
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Guard Handler OnAfter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnAfterGuard
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
--- Guard Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] Guard
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
|
||||||
|
--- Guard Asynchronous Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] __Guard
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #number Delay
|
||||||
|
|
||||||
|
self:AddTransition( "*", "Empty", "Empty" )
|
||||||
|
|
||||||
|
--- Empty Handler OnBefore for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnBeforeEmpty
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Empty Handler OnAfter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnAfterEmpty
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
--- Empty Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] Empty
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
|
||||||
|
--- Empty Asynchronous Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] __Empty
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #number Delay
|
||||||
|
|
||||||
|
|
||||||
|
self:AddTransition( { "Guarded", "Empty" }, "Attack", "Attacked" )
|
||||||
|
|
||||||
|
--- Attack Handler OnBefore for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnBeforeAttack
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Attack Handler OnAfter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnAfterAttack
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
--- Attack Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] Attack
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
|
||||||
|
--- Attack Asynchronous Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] __Attack
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #number Delay
|
||||||
|
|
||||||
|
self:AddTransition( { "Guarded", "Attacked", "Empty" }, "Capture", "Captured" )
|
||||||
|
|
||||||
|
--- Capture Handler OnBefore for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnBeforeCapture
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
-- @return #boolean
|
||||||
|
|
||||||
|
--- Capture Handler OnAfter for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] OnAfterCapture
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #string From
|
||||||
|
-- @param #string Event
|
||||||
|
-- @param #string To
|
||||||
|
|
||||||
|
--- Capture Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] Capture
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
|
||||||
|
--- Capture Asynchronous Trigger for ZONE_GOAL_CARGO
|
||||||
|
-- @function [parent=#ZONE_GOAL_CARGO] __Capture
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param #number Delay
|
||||||
|
|
||||||
|
return self
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- Set the owning coalition of the zone.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @param DCSCoalition.DCSCoalition#coalition Coalition
|
||||||
|
function ZONE_GOAL_CARGO:SetCoalition( Coalition )
|
||||||
|
self.Coalition = Coalition
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- Get the owning coalition of the zone.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @return DCSCoalition.DCSCoalition#coalition Coalition.
|
||||||
|
function ZONE_GOAL_CARGO:GetCoalition()
|
||||||
|
return self.Coalition
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- Get the owning coalition name of the zone.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
-- @return #string Coalition name.
|
||||||
|
function ZONE_GOAL_CARGO:GetCoalitionName()
|
||||||
|
|
||||||
|
if self.Coalition == coalition.side.BLUE then
|
||||||
|
return "Blue"
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.Coalition == coalition.side.RED then
|
||||||
|
return "Red"
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.Coalition == coalition.side.NEUTRAL then
|
||||||
|
return "Neutral"
|
||||||
|
end
|
||||||
|
|
||||||
|
return ""
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:IsGuarded()
|
||||||
|
|
||||||
|
local IsGuarded = self.Zone:IsAllInZoneOfCoalition( self.Coalition )
|
||||||
|
self:E( { IsGuarded = IsGuarded } )
|
||||||
|
return IsGuarded
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:IsEmpty()
|
||||||
|
|
||||||
|
local IsEmpty = self.Zone:IsNoneInZone()
|
||||||
|
self:E( { IsEmpty = IsEmpty } )
|
||||||
|
return IsEmpty
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:IsCaptured()
|
||||||
|
|
||||||
|
local IsCaptured = self.Zone:IsAllInZoneOfOtherCoalition( self.Coalition )
|
||||||
|
self:E( { IsCaptured = IsCaptured } )
|
||||||
|
return IsCaptured
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:IsAttacked()
|
||||||
|
|
||||||
|
local IsAttacked = self.Zone:IsSomeInZoneOfCoalition( self.Coalition )
|
||||||
|
self:E( { IsAttacked = IsAttacked } )
|
||||||
|
return IsAttacked
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
--- Mark.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
function ZONE_GOAL_CARGO:Mark()
|
||||||
|
|
||||||
|
local Coord = self.Zone:GetCoordinate()
|
||||||
|
local ZoneName = self:GetZoneName()
|
||||||
|
local State = self:GetState()
|
||||||
|
|
||||||
|
if self.MarkRed and self.MarkBlue then
|
||||||
|
self:E( { MarkRed = self.MarkRed, MarkBlue = self.MarkBlue } )
|
||||||
|
Coord:RemoveMark( self.MarkRed )
|
||||||
|
Coord:RemoveMark( self.MarkBlue )
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.Coalition == coalition.side.BLUE then
|
||||||
|
self.MarkBlue = Coord:MarkToCoalitionBlue( "Guard Zone: " .. ZoneName .. "\nStatus: " .. State )
|
||||||
|
self.MarkRed = Coord:MarkToCoalitionRed( "Capture Zone: " .. ZoneName .. "\nStatus: " .. State )
|
||||||
|
else
|
||||||
|
self.MarkRed = Coord:MarkToCoalitionRed( "Guard Zone: " .. ZoneName .. "\nStatus: " .. State )
|
||||||
|
self.MarkBlue = Coord:MarkToCoalitionBlue( "Capture Zone: " .. ZoneName .. "\nStatus: " .. State )
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
--- Bound.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
function ZONE_GOAL_CARGO:onenterGuarded()
|
||||||
|
|
||||||
|
--self:GetParent( self ):onenterGuarded()
|
||||||
|
|
||||||
|
if self.Coalition == coalition.side.BLUE then
|
||||||
|
--elf.ProtectZone:BoundZone( 12, country.id.USA )
|
||||||
|
else
|
||||||
|
--self.ProtectZone:BoundZone( 12, country.id.RUSSIA )
|
||||||
|
end
|
||||||
|
|
||||||
|
self:Mark()
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:onenterCaptured()
|
||||||
|
|
||||||
|
--self:GetParent( self ):onenterCaptured()
|
||||||
|
|
||||||
|
local NewCoalition = self.Zone:GetCoalition()
|
||||||
|
self:E( { NewCoalition = NewCoalition } )
|
||||||
|
self:SetCoalition( NewCoalition )
|
||||||
|
|
||||||
|
self:Mark()
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:onenterEmpty()
|
||||||
|
|
||||||
|
--self:GetParent( self ):onenterEmpty()
|
||||||
|
|
||||||
|
self:Mark()
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:onenterAttacked()
|
||||||
|
|
||||||
|
--self:GetParent( self ):onenterAttacked()
|
||||||
|
|
||||||
|
self:Mark()
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--- When started, check the Coalition status.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
function ZONE_GOAL_CARGO:onafterGuard()
|
||||||
|
|
||||||
|
--self:E({BASE:GetParent( self )})
|
||||||
|
--BASE:GetParent( self ).onafterGuard( self )
|
||||||
|
|
||||||
|
if not self.SmokeScheduler then
|
||||||
|
self.SmokeScheduler = self:ScheduleRepeat( 1, 1, 0.1, nil, self.StatusSmoke, self )
|
||||||
|
end
|
||||||
|
if not self.ScheduleStatusZone then
|
||||||
|
self.ScheduleStatusZone = self:ScheduleRepeat( 15, 15, 0.1, nil, self.StatusZone, self )
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:IsCaptured()
|
||||||
|
|
||||||
|
local IsCaptured = self.Zone:IsAllInZoneOfOtherCoalition( self.Coalition )
|
||||||
|
self:E( { IsCaptured = IsCaptured } )
|
||||||
|
return IsCaptured
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function ZONE_GOAL_CARGO:IsAttacked()
|
||||||
|
|
||||||
|
local IsAttacked = self.Zone:IsSomeInZoneOfCoalition( self.Coalition )
|
||||||
|
self:E( { IsAttacked = IsAttacked } )
|
||||||
|
return IsAttacked
|
||||||
|
end
|
||||||
|
|
||||||
|
--- Check status Coalition ownership.
|
||||||
|
-- @param #ZONE_GOAL_CARGO self
|
||||||
|
function ZONE_GOAL_CARGO:StatusZone()
|
||||||
|
|
||||||
|
local State = self:GetState()
|
||||||
|
self:E( { State = self:GetState() } )
|
||||||
|
|
||||||
|
self.Zone:Scan()
|
||||||
|
|
||||||
|
if State ~= "Guarded" and self:IsGuarded() then
|
||||||
|
self:Guard()
|
||||||
|
end
|
||||||
|
|
||||||
|
if State ~= "Empty" and self:IsEmpty() then
|
||||||
|
self:Empty()
|
||||||
|
end
|
||||||
|
|
||||||
|
if State ~= "Attacked" and self:IsAttacked() then
|
||||||
|
self:Attack()
|
||||||
|
end
|
||||||
|
|
||||||
|
if State ~= "Captured" and self:IsCaptured() then
|
||||||
|
self:Capture()
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
@ -206,6 +206,7 @@ do -- TASK_ZONE_CAPTURE
|
|||||||
ClassName = "TASK_ZONE_CAPTURE",
|
ClassName = "TASK_ZONE_CAPTURE",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
--- Instantiates a new TASK_ZONE_CAPTURE.
|
--- Instantiates a new TASK_ZONE_CAPTURE.
|
||||||
-- @param #TASK_ZONE_CAPTURE self
|
-- @param #TASK_ZONE_CAPTURE self
|
||||||
-- @param Tasking.Mission#MISSION Mission
|
-- @param Tasking.Mission#MISSION Mission
|
||||||
@ -236,6 +237,7 @@ do -- TASK_ZONE_CAPTURE
|
|||||||
return self
|
return self
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
--- Instantiates a new TASK_ZONE_CAPTURE.
|
--- Instantiates a new TASK_ZONE_CAPTURE.
|
||||||
-- @param #TASK_ZONE_CAPTURE self
|
-- @param #TASK_ZONE_CAPTURE self
|
||||||
function TASK_ZONE_CAPTURE:UpdateTaskInfo()
|
function TASK_ZONE_CAPTURE:UpdateTaskInfo()
|
||||||
@ -247,6 +249,7 @@ do -- TASK_ZONE_CAPTURE
|
|||||||
self:SetInfo( "Zone Coalition", self.ZoneGoal:GetCoalitionName(), 11 )
|
self:SetInfo( "Zone Coalition", self.ZoneGoal:GetCoalitionName(), 11 )
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
function TASK_ZONE_CAPTURE:ReportOrder( ReportGroup )
|
function TASK_ZONE_CAPTURE:ReportOrder( ReportGroup )
|
||||||
local Coordinate = self:GetInfo( "Coordinate" )
|
local Coordinate = self:GetInfo( "Coordinate" )
|
||||||
--local Coordinate = self.TaskInfo.Coordinates.TaskInfoText
|
--local Coordinate = self.TaskInfo.Coordinates.TaskInfoText
|
||||||
|
|||||||
@ -224,6 +224,7 @@ function GROUP:Destroy()
|
|||||||
for Index, UnitData in pairs( DCSGroup:getUnits() ) do
|
for Index, UnitData in pairs( DCSGroup:getUnits() ) do
|
||||||
self:CreateEventCrash( timer.getTime(), UnitData )
|
self:CreateEventCrash( timer.getTime(), UnitData )
|
||||||
end
|
end
|
||||||
|
USERFLAG:New( self:GetName() ):Set( 100 )
|
||||||
DCSGroup:destroy()
|
DCSGroup:destroy()
|
||||||
DCSGroup = nil
|
DCSGroup = nil
|
||||||
end
|
end
|
||||||
@ -231,6 +232,7 @@ function GROUP:Destroy()
|
|||||||
return nil
|
return nil
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
--- Returns category of the DCS Group.
|
--- Returns category of the DCS Group.
|
||||||
-- @param #GROUP self
|
-- @param #GROUP self
|
||||||
-- @return Dcs.DCSWrapper.Group#Group.Category The category ID
|
-- @return Dcs.DCSWrapper.Group#Group.Category The category ID
|
||||||
|
|||||||
@ -79,7 +79,7 @@ function OBJECT:Destroy()
|
|||||||
local DCSObject = self:GetDCSObject()
|
local DCSObject = self:GetDCSObject()
|
||||||
|
|
||||||
if DCSObject then
|
if DCSObject then
|
||||||
|
--BASE:CreateEventCrash( timer.getTime(), DCSObject )
|
||||||
DCSObject:destroy()
|
DCSObject:destroy()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@ -61,7 +61,6 @@ function STATIC:FindByName( StaticName, RaiseError )
|
|||||||
|
|
||||||
if StaticFound then
|
if StaticFound then
|
||||||
StaticFound:F3( { StaticName } )
|
StaticFound:F3( { StaticName } )
|
||||||
|
|
||||||
return StaticFound
|
return StaticFound
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -92,4 +91,18 @@ end
|
|||||||
function STATIC:GetThreatLevel()
|
function STATIC:GetThreatLevel()
|
||||||
|
|
||||||
return 1, "Static"
|
return 1, "Static"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
--- Respawn the @{Unit} using a (tweaked) template of the parent Group.
|
||||||
|
-- @param #UNIT self
|
||||||
|
-- @param Core.Point#COORDINATE Coordinate The coordinate where to spawn the new Static.
|
||||||
|
-- @param #number Heading The heading of the unit respawn.
|
||||||
|
function STATIC:ReSpawn( Coordinate, Heading )
|
||||||
|
|
||||||
|
|
||||||
|
-- todo: need to fix country
|
||||||
|
local SpawnStatic = SPAWNSTATIC:NewFromStatic( self.StaticName, country.id.USA )
|
||||||
|
|
||||||
|
SpawnStatic:SpawnFromPointVec2( Coordinate, Heading, self.StaticName )
|
||||||
|
end
|
||||||
|
|
||||||
|
|||||||
@ -159,6 +159,24 @@ function UNIT:GetDCSObject()
|
|||||||
return nil
|
return nil
|
||||||
end
|
end
|
||||||
|
|
||||||
|
--- Destroys the UNIT.
|
||||||
|
-- @param #UNIT self
|
||||||
|
-- @return #nil The DCS Unit is not existing or alive.
|
||||||
|
function UNIT:Destroy()
|
||||||
|
self:F2( self.ObjectName )
|
||||||
|
|
||||||
|
local DCSObject = self:GetDCSObject()
|
||||||
|
|
||||||
|
if DCSObject then
|
||||||
|
USERFLAG:New( self:GetGroup():GetName() ):Set( 100 )
|
||||||
|
--BASE:CreateEventCrash( timer.getTime(), DCSObject )
|
||||||
|
DCSObject:destroy()
|
||||||
|
end
|
||||||
|
|
||||||
|
return nil
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
--- Respawn the @{Unit} using a (tweaked) template of the parent Group.
|
--- Respawn the @{Unit} using a (tweaked) template of the parent Group.
|
||||||
--
|
--
|
||||||
-- This function will:
|
-- This function will:
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user