mirror of
https://github.com/weyne85/DML.git
synced 2025-10-29 16:57:49 +00:00
Version 2.2.0
"maybe" for boolean inBuiltup for csarManager
This commit is contained in:
parent
6088c4cfa1
commit
eb2bef85b8
Binary file not shown.
Binary file not shown.
@ -1,5 +1,5 @@
|
||||
rndFlags = {}
|
||||
rndFlags.version = "2.0.0"
|
||||
rndFlags.version = "2.0.1"
|
||||
rndFlags.verbose = false
|
||||
rndFlags.requiredLibs = {
|
||||
"dcsCommon", -- always
|
||||
@ -14,7 +14,8 @@ rndFlags.requiredLibs = {
|
||||
Version History
|
||||
|
||||
2.0.0 - dmlZones, OOP
|
||||
|
||||
2.0.1 - a little less verbosity
|
||||
|
||||
--]]
|
||||
|
||||
rndFlags.rndGen = {}
|
||||
@ -164,7 +165,9 @@ function rndFlags.fire(theZone)
|
||||
for i=1, pollSize do
|
||||
-- check there are still flags left
|
||||
if #availableFlags < 1 then
|
||||
trigger.action.outText("+++RND: no flags left in " .. theZone.name .. " in index " .. i, 30)
|
||||
if rndFlags.verbose or theZone.verbose then
|
||||
trigger.action.outText("+++RND: no flags left in <" .. theZone.name .. "> in index " .. i, 30)
|
||||
end
|
||||
theZone.myFlags = {}
|
||||
if theZone.reshuffle then
|
||||
rndFlags.reshuffle(theZone)
|
||||
@ -180,7 +183,7 @@ function rndFlags.fire(theZone)
|
||||
|
||||
--rndFlags.pollFlag(theFlag, theZone.rndMethod)
|
||||
if rndFlags.verbose or theZone.verbose then
|
||||
trigger.action.outText("+++RND: polling " .. theFlag .. " with " .. theZone.rndMethod, 30)
|
||||
trigger.action.outText("+++RND: polling <" .. theFlag .. "> with " .. theZone.rndMethod, 30)
|
||||
end
|
||||
|
||||
theZone:pollFlag(theFlag, theZone.rndMethod)
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
cfxZones = {}
|
||||
cfxZones.version = "4.2.0"
|
||||
cfxZones.version = "4.3.0"
|
||||
|
||||
-- cf/x zone management module
|
||||
-- reads dcs zones and makes them accessible and mutable
|
||||
@ -45,6 +45,7 @@ cfxZones.version = "4.2.0"
|
||||
- 4.1.1 - evalRemainder() updates
|
||||
- 4.1.2 - hash property missing warning
|
||||
- 4.2.0 - new createRandomPointInPopulatedZone()
|
||||
- 4.3.0 - boolean supports maybe, random, rnd, ?
|
||||
|
||||
--]]--
|
||||
|
||||
@ -1618,6 +1619,7 @@ function cfxZones.doPollFlag(theFlag, method, theZone) -- no OOP equivalent
|
||||
end
|
||||
|
||||
function cfxZones.pollFlag(theFlag, method, theZone)
|
||||
--trigger.action.outText("enter pollflag for flag <" .. theFlag .. "> of zone <" .. theZone.name .. ">", 30)
|
||||
local allFlags = {}
|
||||
if dcsCommon.containsString(theFlag, ",") then
|
||||
if cfxZones.verbose then
|
||||
@ -2429,6 +2431,11 @@ function cfxZones.getBoolFromZoneProperty(theZone, theProperty, defaultVal)
|
||||
return theBool
|
||||
end
|
||||
|
||||
-- special: return a random value if p == "rnd" or "?" or "maybe"
|
||||
if (p == "?") or (p == "rnd") or (p == "random") or (p == "maybe") then
|
||||
return (math.random(1000) < 500) -- 50:50
|
||||
end
|
||||
|
||||
local theBool = true
|
||||
-- only go false if exactly no or false or "0"
|
||||
theBool = (p ~= 'false') and (p ~= 'no') and (p ~= "0") and (p~="off")
|
||||
@ -2455,6 +2462,11 @@ function dmlZone:getBoolFromZoneProperty(theProperty, defaultVal)
|
||||
return theBool
|
||||
end
|
||||
|
||||
-- special: return a random value if p == "rnd" or "?" or "maybe"
|
||||
if (p == "?") or (p == "rnd") or (p == "random") or (p == "maybe") then
|
||||
return (math.random(1000) < 500) -- 50:50
|
||||
end
|
||||
|
||||
local theBool = true
|
||||
-- only go false if exactly no or false or "0"
|
||||
theBool = (p ~= 'false') and (p ~= 'no') and (p ~= "0") and (p ~= "off")
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
cloneZones = {}
|
||||
cloneZones.version = "2.0.1"
|
||||
cloneZones.version = "2.1.0"
|
||||
cloneZones.verbose = false
|
||||
cloneZones.requiredLibs = {
|
||||
"dcsCommon", -- always
|
||||
@ -20,8 +20,10 @@ cloneZones.uniqueCounter = 9200000 -- we start group numbering here
|
||||
cloneZones.lclUniqueCounter = 1 -- zone-local init value, can be config'dHeading
|
||||
cloneZones.globalCounter = 1 -- module-global count
|
||||
|
||||
cloneZones.allClones = {} -- all clones spawned, regularly GC'd
|
||||
cloneZones.allClones = {} -- all clones spawned, regularly GC'd
|
||||
-- contains DATA blocks!
|
||||
cloneZones.allCObjects = {} -- all clones objects
|
||||
cloneZones.despawnPlan = {} -- used with despawnIn
|
||||
|
||||
cloneZones.respawnOnGroupID = true
|
||||
|
||||
@ -40,6 +42,8 @@ cloneZones.respawnOnGroupID = true
|
||||
2.0.0 - clean-up
|
||||
2.0.1 - improved empty! logic to account for deferred spawn
|
||||
when pre-wipe is active
|
||||
2.1.0 - despawnIn option
|
||||
- inBuiltup option for rndLoc
|
||||
--]]--
|
||||
|
||||
--
|
||||
@ -332,6 +336,10 @@ function cloneZones.createClonerWithZone(theZone) -- has "Cloner"
|
||||
end
|
||||
|
||||
theZone.useAI = theZone:getBoolFromZoneProperty("useAI", true)
|
||||
|
||||
if theZone:hasProperty("despawnIn") then
|
||||
theZone.despawnInMin, theZone.despawnInMax = theZone:getPositiveRangeFromZoneProperty("despawnIn", 2,2)
|
||||
end
|
||||
-- we end with clear plate
|
||||
end
|
||||
|
||||
@ -1214,6 +1222,20 @@ function cloneZones.spawnWithTemplateForZone(theZone, spawnZone)
|
||||
-- SPAWN NOW!!!!
|
||||
theGroup = coalition.addGroup(rawData.CZctry, rawData.CZtheCat, rawData)
|
||||
table.insert(spawnedGroups, theGroup)
|
||||
|
||||
-- see if this is an auto-despawner
|
||||
if spawnZone.despawnInMin then
|
||||
local now = timer.getTime()
|
||||
local timeLimit = dcsCommon.randomBetween(spawnZone.despawnInMin, spawnZone.despawnInMax)
|
||||
local info = {}
|
||||
info.theGroup = theGroup
|
||||
info.name = theData.name
|
||||
info.isObject = false
|
||||
info.timeLimit = now + timeLimit
|
||||
info.cloneZone = spawnZone
|
||||
table.insert(cloneZones.despawnPlan, info)
|
||||
-- trigger.action.outText("+++clne: scheduled auto-despawn for <" .. info.name .. "> in <" .. timeLimit .. "> secs", 30)
|
||||
end
|
||||
|
||||
-- turn off AI if disabled
|
||||
if not rawData.useAI then
|
||||
@ -1393,6 +1415,18 @@ function cloneZones.spawnWithTemplateForZone(theZone, spawnZone)
|
||||
local theStatic = coalition.addStaticObject(ctry, rawData)
|
||||
local newStaticID = tonumber(theStatic:getID())
|
||||
table.insert(spawnedStatics, theStatic)
|
||||
if spawnZone.despawnInMin then
|
||||
local now = timer.getTime()
|
||||
local timeLimit = dcsCommon.randomBetween(spawnZone.despawnInMin, spawnZone.despawnInMax)
|
||||
local info = {}
|
||||
info.theGroup = theStatic
|
||||
info.name = theData.name
|
||||
info.isObject = true
|
||||
info.timeLimit = now + timeLimit
|
||||
info.cloneZone = spawnZone
|
||||
table.insert(cloneZones.despawnPlan, info)
|
||||
-- trigger.action.outText("+++clne: scheduled auto-despawn for OBJECT <" .. info.name .. "> in <" .. timeLimit .. "> secs", 30)
|
||||
end
|
||||
-- we don't mix groups with units, so no lookup tables for
|
||||
-- statics
|
||||
if newStaticID == rawData.CZTargetID then
|
||||
@ -1677,7 +1711,7 @@ function cloneZones.update()
|
||||
local willSpawn = false -- init to false.
|
||||
if aZone:testZoneFlag(aZone.spawnFlag, aZone.cloneTriggerMethod, "lastSpawnValue") then
|
||||
if cloneZones.verbose or aZone.verbose then
|
||||
trigger.action.outText("+++clnZ: spawn triggered for <" .. aZone.name .. ">", 30)
|
||||
trigger.action.outText("+++clnZ: spawn triggered for <" .. aZone.name .. "> on flag <" .. aZone.spawnFlag .. ">", 30)
|
||||
end
|
||||
cloneZones.spawnWithCloner(aZone)
|
||||
willSpawn = true -- in case prewipe, we delay
|
||||
@ -1702,6 +1736,30 @@ function cloneZones.update()
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
-- now remove all scheduled despawns
|
||||
local now = timer.getTime()
|
||||
local filtered = {}
|
||||
for idx, theInfo in pairs(cloneZones.despawnPlan) do
|
||||
if theInfo.timeLimit < now then
|
||||
-- trigger.action.outText("+++clne: auto-despawning <" .. theInfo.name .. ">", 30)
|
||||
if theInfo.isObject then
|
||||
-- dealloc static object
|
||||
local theObject = theInfo.theGroup
|
||||
if theObject and StaticObject.isExist(theObject) then
|
||||
StaticObject.destroy(theObject)
|
||||
end
|
||||
else
|
||||
local theGroup = theInfo.theGroup
|
||||
if theGroup and Group.isExist(theGroup) then
|
||||
Group.destroy(theGroup)
|
||||
end
|
||||
end
|
||||
else
|
||||
table.insert(filtered, theInfo)
|
||||
end
|
||||
end
|
||||
cloneZones.despawnPlan = filtered
|
||||
end
|
||||
|
||||
function cloneZones.doOnStart()
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
csarManager = {}
|
||||
csarManager.version = "3.2.2"
|
||||
csarManager.version = "3.2.5"
|
||||
csarManager.ups = 1
|
||||
|
||||
--[[-- VERSION HISTORY
|
||||
@ -37,6 +37,9 @@ csarManager.ups = 1
|
||||
3.2.2 - reset helicopter weight on birth
|
||||
- cleanup
|
||||
3.2.3 - hardening against *accidental* multi-unit player groups.
|
||||
3.2.4 - pass theZone with missionCreateCB when created from zone
|
||||
3.2.5 - smoke callbacks
|
||||
- useRanks option
|
||||
|
||||
|
||||
INTEGRATES AUTOMATICALLY WITH playerScore
|
||||
@ -79,6 +82,7 @@ csarManager.csarCompleteCB = {}
|
||||
csarManager.csarCreatedCB = {}
|
||||
csarManager.csarRemoveCB = {}
|
||||
csarManager.csarPickupCB = {}
|
||||
csarManager.csarSmokeCB = {}
|
||||
--
|
||||
-- CREATING A CSAR
|
||||
--
|
||||
@ -168,6 +172,13 @@ function csarManager.createCSARMissionData(point, theSide, freq, name, numCrew,
|
||||
trigger.action.outText("+++csar: 'downed' procced for <" .. name .. ">", 30)
|
||||
end
|
||||
end
|
||||
|
||||
if csarManager.useRanks then
|
||||
-- local ranks = csarManager.ranks -- {"Lt", "Lt", "Lt", "Col", "Cpt", "WO", "WO"}
|
||||
local myRank = dcsCommon.pickRandom(csarManager.ranks)
|
||||
name = myRank .. " " .. name
|
||||
end
|
||||
|
||||
if not inRadius then inRadius = csarManager.rescueRadius end
|
||||
newMission.name = name .. " (ID#" .. csarManager.missionID .. ")" -- make it uuid-capable
|
||||
if csarManager.addPrefix then
|
||||
@ -199,9 +210,9 @@ function csarManager.createCSARMissionData(point, theSide, freq, name, numCrew,
|
||||
return newMission
|
||||
end
|
||||
|
||||
function csarManager.addMission(theMission)
|
||||
function csarManager.addMission(theMission, theZone)
|
||||
table.insert(csarManager.openMissions, theMission)
|
||||
csarManager.invokeNewMissionCallbacks(theMission)
|
||||
csarManager.invokeNewMissionCallbacks(theMission, theZone)
|
||||
end
|
||||
|
||||
function csarManager.removeMission(theMission, pickup)
|
||||
@ -1134,6 +1145,13 @@ function csarManager.update() -- every second
|
||||
|
||||
-- also pop smoke if not popped already, or more than 5 minutes ago
|
||||
if csarManager.useSmoke and (timer.getTime() - csarMission.lastSmokeTime) >= 5 * 60 then
|
||||
if csarMission.lastSmokeTime < 0 then
|
||||
-- this is the first time that this mission pops smoke
|
||||
-- trigger.action.outText("***will invoke smoke cb", 30)
|
||||
csarManager.invokeSmokeCallbacks(csarMission, uName)
|
||||
else
|
||||
--trigger.action.outText("nope smoke's a dope", 30)
|
||||
end
|
||||
local smokePoint = dcsCommon.randomPointOnPerimeter(
|
||||
csarManager.smokeDist, csarMission.zone.point.x, csarMission.zone.point.z)
|
||||
dcsCommon.markPointWithSmoke(smokePoint, csarManager.smokeColor)
|
||||
@ -1242,7 +1260,7 @@ function csarManager.update() -- every second
|
||||
-- if currVal ~= theZone.lastCSARVal then
|
||||
if theZone:testZoneFlag(theZone.startCSAR, theZone.triggerMethod, "lastCSARVal") then
|
||||
local theMission = csarManager.createCSARMissionFromZone(theZone)
|
||||
csarManager.addMission(theMission)
|
||||
csarManager.addMission(theMission, theZone)
|
||||
--theZone.lastCSARVal = currVal
|
||||
if csarManager.verbose or theZone.verbose then
|
||||
trigger.action.outText("+++csar: started CSAR mission for <" .. theZone.csarName .. ">", 30)
|
||||
@ -1399,7 +1417,13 @@ function csarManager.readCSARZone(theZone)
|
||||
trigger.action.outText("warning: competing 'onRoad' and 'inPopulated' attributes in zone <" .. theZone.name .. ">. Using 'onRoad'.", 30)
|
||||
end
|
||||
|
||||
-- add to list of startable csar
|
||||
if theZone.startCSAR then
|
||||
csarManager.addCSARZone(theZone)
|
||||
end
|
||||
|
||||
if (not deferred) then
|
||||
--[[--
|
||||
local mPoint = theZone:getPoint()
|
||||
if theZone.rndLoc then mPoint = theZone:createRandomPointInZone() end
|
||||
if theZone.onRoad then
|
||||
@ -1418,13 +1442,12 @@ function csarManager.readCSARZone(theZone)
|
||||
theZone.csarMapMarker,
|
||||
0.1, -- theZone.radius,
|
||||
nil) -- parashoo unit
|
||||
csarManager.addMission(theMission)
|
||||
csarManager.addMission(theMission, theZone)
|
||||
--]]--
|
||||
local theMission = csarManager.createCSARMissionFromZone(theZone)
|
||||
csarManager.addMission(theMission, theZone)
|
||||
end
|
||||
|
||||
-- add to list of startable csar
|
||||
if theZone.startCSAR then
|
||||
csarManager.addCSARZone(theZone)
|
||||
end
|
||||
|
||||
if deferred and not theZone.startCSAR then
|
||||
trigger.action.outText("+++csar: warning - CSAR Mission in Zone <" .. theZone.name .. "> can't be started", 30)
|
||||
@ -1449,16 +1472,19 @@ function csarManager.invokeCallbacks(theCoalition, success, numRescued, notes, t
|
||||
-- invoke anyone who wants to know that a group
|
||||
-- of people was rescued.
|
||||
for idx, cb in pairs(csarManager.csarCompleteCB) do
|
||||
-- notes =
|
||||
-- "KIA" when evacuee is killed (success = false)
|
||||
-- "success" when mission done (success = true)
|
||||
-- "lost" when evacuee timed out (success = false)
|
||||
cb(theCoalition, success, numRescued, notes, theMission)
|
||||
end
|
||||
end
|
||||
|
||||
-- mission created cb(theMission)
|
||||
function csarManager.invokeNewMissionCallbacks(theMission)
|
||||
--trigger.action.outText("enter invoke new mission cb", 30)
|
||||
function csarManager.invokeNewMissionCallbacks(theMission, theZone)
|
||||
-- invoke anyone who wants to know that a new mission was created
|
||||
for idx, cb in pairs(csarManager.csarCreatedCB) do
|
||||
cb(theMission)
|
||||
cb(theMission, theZone)
|
||||
end
|
||||
end
|
||||
|
||||
@ -1470,6 +1496,12 @@ function csarManager.invokePickUpCallbacks(theMission)
|
||||
end
|
||||
end
|
||||
|
||||
function csarManager.invokeSmokeCallbacks(theMission, uName)
|
||||
for idx, cb in pairs(csarManager.csarSmokeCB) do
|
||||
cb(theMission, uName)
|
||||
end
|
||||
end
|
||||
|
||||
function csarManager.installCallback(theCB)
|
||||
table.insert(csarManager.csarCompleteCB, theCB)
|
||||
end
|
||||
@ -1482,6 +1514,10 @@ function csarManager.installPickupCallback(theCB)
|
||||
table.insert(csarManager.csarPickupCB, theCB)
|
||||
end
|
||||
|
||||
function csarManager.installSmokeCallback(theCB)
|
||||
table.insert(csarManager.csarSmokeCB, theCB)
|
||||
end
|
||||
|
||||
function csarManager.readConfigZone()
|
||||
csarManager.name = "csarManagerConfig" -- compat with cfxZones
|
||||
local theZone = cfxZones.getZoneByName("csarManagerConfig")
|
||||
@ -1545,6 +1581,11 @@ function csarManager.readConfigZone()
|
||||
end
|
||||
|
||||
csarManager.addPrefix = theZone:getBoolFromZoneProperty("addPrefix", true)
|
||||
csarManager.useRanks = theZone:getBoolFromZoneProperty("useRanks", false)
|
||||
local lRanks= theZone:getStringFromZoneProperty("ranks", "Lt, Lt, Lt, Col, Cpt, WO, WO")
|
||||
local typeArray = dcsCommon.splitString(lRanks, ",")
|
||||
typeArray = dcsCommon.trimArray(typeArray)
|
||||
csarManager.ranks = typeArray
|
||||
|
||||
csarManager.maxMissions = theZone:getNumberFromZoneProperty("maxMissions", 15)
|
||||
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
factoryZone = {}
|
||||
factoryZone.version = "3.1.0"
|
||||
factoryZone.version = "3.1.1"
|
||||
factoryZone.verbose = false
|
||||
factoryZone.name = "factoryZone"
|
||||
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
groupTracker = {}
|
||||
groupTracker.version = "2.0.0"
|
||||
groupTracker.version = "2.0.1"
|
||||
groupTracker.verbose = false
|
||||
groupTracker.ups = 1
|
||||
groupTracker.requiredLibs = {
|
||||
@ -11,6 +11,7 @@ groupTracker.trackers = {}
|
||||
--[[--
|
||||
Version History
|
||||
2.0.0 - dmlZones, OOP, clean-up, legacy support
|
||||
2.0.1 - fix to verbosity, better verbosity
|
||||
|
||||
--]]--
|
||||
|
||||
@ -473,6 +474,9 @@ function groupTracker.update()
|
||||
-- see if we need to bang on empty!
|
||||
local currCount = #theZone.trackedGroups + dcsCommon.getSizeOfTable(theZone.limbo)
|
||||
if theZone.allGoneFlag and currCount == 0 and currCount ~= theZone.lastGroupCount then
|
||||
if theZone.verbose or groupTracker.verbose then
|
||||
trigger.action.outText("+++gTrk: all groups for tracker <" .. theZone.name .. "> gone, polling <" .. theZone.allGoneFlag .. ">", 30)
|
||||
end
|
||||
cfxZones.pollFlag(theZone.allGoneFlag, theZone.trackerMethod, theZone)
|
||||
end
|
||||
theZone.lastGroupCount = currCount
|
||||
@ -558,7 +562,7 @@ function groupTracker.trackGroupsInZone(theZone)
|
||||
for idy, aGroup in pairs(theGroups) do
|
||||
groupTracker.addGroupToTracker(aGroup, theTracker)
|
||||
if groupTracker.verbose or theZone.verbose then
|
||||
trigger.action.outText("+++gTrk-TW: added " .. theGroup:getName() .. " to tracker " .. theName, 30)
|
||||
trigger.action.outText("+++gTrk-TW: added " .. aGroup:getName() .. " to tracker " .. theName, 30)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
cfxPlayerScore = {}
|
||||
cfxPlayerScore.version = "3.0.1"
|
||||
cfxPlayerScore.version = "3.1.0"
|
||||
cfxPlayerScore.name = "cfxPlayerScore" -- compatibility with flag bangers
|
||||
cfxPlayerScore.badSound = "Death BRASS.wav"
|
||||
cfxPlayerScore.scoreSound = "Quest Snare 3.wav"
|
||||
@ -13,6 +13,7 @@ cfxPlayerScore.firstSave = true -- to force overwrite
|
||||
- DCS 2.9 safe
|
||||
3.0.1 - cleanup
|
||||
3.0.2 - interface with ObjectDestructDetector for scoring scenery objects
|
||||
3.1.0 - shared data for persistence
|
||||
|
||||
--]]--
|
||||
|
||||
@ -1198,6 +1199,9 @@ function cfxPlayerScore.readConfigZone(theZone)
|
||||
theZone:setFlagValue(cfxPlayerScore.blueScoreOut, cfxPlayerScore.coalitionScore[2])
|
||||
end
|
||||
|
||||
if theZone:hasProperty("sharedData") then
|
||||
cfxPlayerScore.sharedData = theZone:getStringFromZoneProperty("sharedData", "cfxNameMissing")
|
||||
end
|
||||
end
|
||||
|
||||
--
|
||||
@ -1218,15 +1222,15 @@ function cfxPlayerScore.saveData()
|
||||
featZones[theZone.name] = theFeat
|
||||
end
|
||||
theData.featData = featZones
|
||||
return theData
|
||||
return theData, cfxPlayerScore.sharedData
|
||||
end
|
||||
|
||||
function cfxPlayerScore.loadData()
|
||||
if not persistence then return end
|
||||
local theData = persistence.getSavedDataForModule("cfxPlayerScore")
|
||||
local theData = persistence.getSavedDataForModule("cfxPlayerScore", cfxPlayerScore.sharedData)
|
||||
if not theData then
|
||||
if cfxPlayerScore.verbose then
|
||||
trigger.action.outText("+++playerscore: no save date received, skipping.", 30)
|
||||
trigger.action.outText("+++playerscore: no save data received, skipping.", 30)
|
||||
end
|
||||
return
|
||||
end
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
sequencer = {}
|
||||
sequencer.version = "1.0.0"
|
||||
sequencer.version = "2.0.0"
|
||||
sequencer.verbose = false
|
||||
sequencer.requiredLibs = {
|
||||
"dcsCommon", -- always
|
||||
@ -8,7 +8,11 @@ sequencer.requiredLibs = {
|
||||
--[[--
|
||||
Sequencer: pull flags in a sequence with oodles of features
|
||||
|
||||
Copyright (c) 2022 by Christian Franz
|
||||
Copyright (c) 2022-24 by Christian Franz
|
||||
|
||||
Version History
|
||||
1.0.0 - initial version
|
||||
2.0.0 - dmlZones
|
||||
--]]--
|
||||
|
||||
sequencer.sequencers = {}
|
||||
@ -31,12 +35,12 @@ end
|
||||
--
|
||||
|
||||
function sequencer.createSequenceWithZone(theZone)
|
||||
local seqRaw = cfxZones.getStringFromZoneProperty(theZone, "sequence!", "none")
|
||||
local seqRaw = theZone:getStringFromZoneProperty("sequence!", "none")
|
||||
local theFlags = dcsCommon.flagArrayFromString(seqRaw)
|
||||
theZone.sequence = theFlags
|
||||
local interRaw = cfxZones.getStringFromZoneProperty(theZone, "intervals", "86400")
|
||||
if cfxZones.hasProperty(theZone, "interval") then
|
||||
interRaw = cfxZones.getStringFromZoneProperty(theZone, "interval", "86400") -- = 24 * 3600 = 24 hours default interval
|
||||
local interRaw = theZone:getStringFromZoneProperty("intervals", "86400")
|
||||
if theZone:hasProperty("interval") then
|
||||
interRaw = theZone:getStringFromZoneProperty("interval", "86400") -- = 24 * 3600 = 24 hours default interval
|
||||
end
|
||||
|
||||
local theIntervals = dcsCommon.rangeArrayFromString(interRaw, false)
|
||||
@ -45,53 +49,52 @@ function sequencer.createSequenceWithZone(theZone)
|
||||
theZone.seqIndex = 1 -- we start at one
|
||||
theZone.intervalIndex = 1 -- here too
|
||||
|
||||
theZone.onStart = cfxZones.getBoolFromZoneProperty(theZone, "onStart", false)
|
||||
theZone.zeroSequence = cfxZones.getBoolFromZoneProperty(theZone, "zeroSequence", true)
|
||||
theZone.onStart = theZone:getBoolFromZoneProperty("onStart", false)
|
||||
theZone.zeroSequence = theZone:getBoolFromZoneProperty("zeroSequence", true)
|
||||
|
||||
theZone.seqLoop = cfxZones.getBoolFromZoneProperty(theZone, "loop", false)
|
||||
theZone.seqLoop = theZone:getBoolFromZoneProperty("loop", false)
|
||||
|
||||
theZone.seqRunning = false
|
||||
theZone.seqComplete = false
|
||||
theZone.seqStarted = false
|
||||
|
||||
theZone.timeLimit = 0 -- will be set to when we expire
|
||||
if cfxZones.hasProperty(theZone, "done!") then
|
||||
theZone.seqDone = cfxZones.getStringFromZoneProperty(theZone, "done!", "<none>")
|
||||
elseif cfxZones.hasProperty(theZone, "seqDone!") then
|
||||
theZone.seqDone = cfxZones.getStringFromZoneProperty(theZone, "seqDone!", "<none>")
|
||||
if theZone:hasProperty("done!") then
|
||||
theZone.seqDone = theZone:getStringFromZoneProperty("done!", "<none>")
|
||||
elseif theZone:hasProperty("seqDone!") then
|
||||
theZone.seqDone = theZone:getStringFromZoneProperty("seqDone!", "<none>")
|
||||
end
|
||||
|
||||
if cfxZones.hasProperty(theZone, "next?") then
|
||||
theZone.nextSeq = cfxZones.getStringFromZoneProperty(theZone, "next?", "<none>")
|
||||
theZone.lastNextSeq = cfxZones.getFlagValue(theZone.nextSeq, theZone)
|
||||
if theZone:hasProperty("next?") then
|
||||
theZone.nextSeq = theZone:getStringFromZoneProperty("next?", "<none>")
|
||||
theZone.lastNextSeq = theZone:getFlagValue(theZone.nextSeq)
|
||||
end
|
||||
|
||||
if cfxZones.hasProperty(theZone, "startSeq?") then
|
||||
theZone.startSeq = cfxZones.getStringFromZoneProperty(theZone, "startSeq?", "<none>")
|
||||
theZone.lastStartSeq = cfxZones.getFlagValue(theZone.startSeq, theZone)
|
||||
--trigger.action.outText("read as " .. theZone.startSeq, 30)
|
||||
if theZone:hasProperty("startSeq?") then
|
||||
theZone.startSeq = theZone:getStringFromZoneProperty("startSeq?", "<none>")
|
||||
theZone.lastStartSeq = theZone:getFlagValue(theZone.startSeq)
|
||||
end
|
||||
|
||||
if cfxZones.hasProperty(theZone, "stopSeq?") then
|
||||
theZone.stopSeq = cfxZones.getStringFromZoneProperty(theZone, "stopSeq?", "<none>")
|
||||
theZone.lastStopSeq = cfxZones.getFlagValue(theZone.stopSeq, theZone)
|
||||
if theZone:hasProperty("stopSeq?") then
|
||||
theZone.stopSeq = theZone:getStringFromZoneProperty("stopSeq?", "<none>")
|
||||
theZone.lastStopSeq = theZone:getFlagValue(theZone.stopSeq)
|
||||
end
|
||||
|
||||
if cfxZones.hasProperty(theZone, "resetSeq?") then
|
||||
theZone.resetSeq = cfxZones.getStringFromZoneProperty(theZone, "resetSeq?", "<none>")
|
||||
theZone.lastResetSeq = cfxZones.getFlagValue(theZone.resetSeq, theZone)
|
||||
if theZone:hasProperty("resetSeq?") then
|
||||
theZone.resetSeq = theZone:getStringFromZoneProperty("resetSeq?", "<none>")
|
||||
theZone.lastResetSeq = theZone:getFlagValue(theZone.resetSeq)
|
||||
end
|
||||
|
||||
|
||||
-- methods
|
||||
theZone.seqMethod = cfxZones.getStringFromZoneProperty(theZone, "method", "inc")
|
||||
if cfxZones.hasProperty(theZone, "seqMethod") then
|
||||
theZone.seqMethod = cfxZones.getStringFromZoneProperty(theZone, "seqMethod", "inc")
|
||||
theZone.seqMethod = theZone:getStringFromZoneProperty("method", "inc")
|
||||
if theZone:hasProperty("seqMethod") then
|
||||
theZone.seqMethod = theZone:getStringFromZoneProperty("seqMethod", "inc")
|
||||
end
|
||||
|
||||
theZone.seqTriggerMethod = cfxZones.getStringFromZoneProperty(theZone, "triggerMethod", "change")
|
||||
if cfxZones.hasProperty(theZone, "seqTriggerMethod") then
|
||||
theZone.seqTriggerMethod = cfxZones.getStringFromZoneProperty(theZone, "seqTriggerMethod", "change")
|
||||
theZone.seqTriggerMethod = theZone:getStringFromZoneProperty("triggerMethod", "change")
|
||||
if theZone:hasProperty("seqTriggerMethod") then
|
||||
theZone.seqTriggerMethod = theZone:getStringFromZoneProperty("seqTriggerMethod", "change")
|
||||
end
|
||||
|
||||
if (not theZone.onStart) and not (theZone.startSeq) then
|
||||
@ -103,7 +106,7 @@ function sequencer.fire(theZone)
|
||||
-- time's up. poll flag at index
|
||||
local theFlag = theZone.sequence[theZone.seqIndex]
|
||||
if theFlag then
|
||||
cfxZones.pollFlag(theFlag, theZone.seqMethod, theZone)
|
||||
theZone:pollFlag(theFlag, theZone.seqMethod)
|
||||
if theZone.verbose or sequencer.verbose then
|
||||
trigger.action.outText("+++seq: triggering flag <" .. theFlag .. "> for index <" .. theZone.seqIndex .. "> in sequence <" .. theZone.name .. ">", 30)
|
||||
end
|
||||
@ -160,7 +163,7 @@ function sequencer.continue(theZone)
|
||||
-- reset any lingering 'next' flags so they don't
|
||||
-- trigger a newly started sequence
|
||||
if theZone.nextSeq then
|
||||
theZone.lastNextSeq = cfxZones.getFlagValue(theZone.nextSeq, theZone)
|
||||
theZone.lastNextSeq = theZone:getFlagValue(theZone.nextSeq)
|
||||
end
|
||||
|
||||
if not theZone.seqStarted then
|
||||
@ -204,14 +207,13 @@ function sequencer.update()
|
||||
|
||||
for idx, theZone in pairs(sequencer.sequencers) do
|
||||
-- see if reset was pulled
|
||||
if theZone.resetSeq and cfxZones.testZoneFlag(theZone, theZone.resetSeq, theZone.seqTriggerMethod, "lastResetSeq") then
|
||||
if theZone.resetSeq and theZone:testZoneFlag(theZone.resetSeq, theZone.seqTriggerMethod, "lastResetSeq") then
|
||||
sequencer.reset(theZone)
|
||||
end
|
||||
|
||||
--trigger.action.outText("have as " .. theZone.startSeq, 30)
|
||||
-- first, check if we need to pause or continue
|
||||
if (not theZone.seqRunning) and theZone.startSeq and
|
||||
cfxZones.testZoneFlag(theZone, theZone.startSeq, theZone.seqTriggerMethod, "lastStartSeq") then
|
||||
theZone:testZoneFlag(theZone.startSeq, theZone.seqTriggerMethod, "lastStartSeq") then
|
||||
sequencer.continue(theZone)
|
||||
if theZone.verbose or sequencer.verbose then
|
||||
trigger.action.outText("+++seq: continuing sequencer <" .. theZone.name .. ">", 30)
|
||||
@ -220,19 +222,19 @@ function sequencer.update()
|
||||
-- synch the start flag so we don't immediately trigger
|
||||
-- when it starts
|
||||
if theZone.startSeq then
|
||||
theZone.lastStartSeq = cfxZones.getFlagValue(theZone.startSeq, theZone)
|
||||
theZone.lastStartSeq = theZone:getFlagValue(theZone.startSeq)
|
||||
end
|
||||
end
|
||||
|
||||
if theZone.seqRunning and theZone.stopSeq and
|
||||
cfxZones.testZoneFlag(theZone, theZone.stopSeq, theZone.seqTriggerMethod, "lastStopSeq") then
|
||||
theZone:testZoneFlag(theZone.stopSeq, theZone.seqTriggerMethod, "lastStopSeq") then
|
||||
sequencer.pause(theZone)
|
||||
if theZone.verbose or sequencer.verbose then
|
||||
trigger.action.outText("+++seq: pausing sequencer <" .. theZone.name .. ">", 30)
|
||||
end
|
||||
else
|
||||
if theZone.stopSeq then
|
||||
theZone.lastStopSeq = cfxZones.getFlagValue(theZone.stopSeq, theZone)
|
||||
theZone.lastStopSeq = theZone:getFlagValue(theZone.stopSeq)
|
||||
end
|
||||
end
|
||||
|
||||
@ -241,7 +243,7 @@ function sequencer.update()
|
||||
-- check if we have received a 'next' signal
|
||||
local doNext = false
|
||||
if theZone.nextSeq then
|
||||
doNext = cfxZones.testZoneFlag(theZone, theZone.nextSeq, theZone.seqTriggerMethod, "lastNextSeq")
|
||||
doNext = theZone:testZoneFlag(theZone.nextSeq, theZone.seqTriggerMethod, "lastNextSeq")
|
||||
if doNext and (sequencer.verbose or theZone.verbose) then
|
||||
trigger.action.outText("+++seq: 'next' command received for sequencer <" .. theZone.name .. "> on <" .. theZone.nextSeq .. ">", 30)
|
||||
end
|
||||
@ -251,7 +253,7 @@ function sequencer.update()
|
||||
if doNext or (theZone.timeLimit < now) then
|
||||
-- we are timed out or triggered!
|
||||
if theZone.nextSeq then
|
||||
theZone.lastNextSeq = cfxZones.getFlagValue(theZone.nextSeq, theZone)
|
||||
theZone.lastNextSeq = theZone:getFlagValue(theZone.nextSeq)
|
||||
end
|
||||
sequencer.fire(theZone)
|
||||
sequencer.advanceInterval(theZone)
|
||||
@ -260,7 +262,7 @@ function sequencer.update()
|
||||
sequencer.startWaitCycle(theZone)
|
||||
else
|
||||
if theZone.seqDone then
|
||||
cfxZones.pollFlag(theZone.seqDone, theZone.seqMethod, theZone)
|
||||
theZone:pollFlag(theZone.seqDone, theZone.seqMethod)
|
||||
if theZone.verbose or sequencer.verbose then
|
||||
trigger.action.outText("+++seq: banging done! flag <" .. theZone.seqDone .. "> for sequence <" .. theZone.name .. ">", 30)
|
||||
end
|
||||
@ -364,13 +366,10 @@ function sequencer.readConfigZone()
|
||||
-- note: must match exactly!!!!
|
||||
local theZone = cfxZones.getZoneByName("sequencerConfig")
|
||||
if not theZone then
|
||||
theZone = cfxZones.createSimpleZone("sequencerConfig")
|
||||
if sequencer.verbose then
|
||||
trigger.action.outText("***RND: NO config zone!", 30)
|
||||
end
|
||||
theZone = cfxZones.createSimpleZone("sequencerConfig")
|
||||
end
|
||||
|
||||
sequencer.verbose = cfxZones.getBoolFromZoneProperty(theZone, "verbose", false)
|
||||
sequencer.verbose = theZone.verbose
|
||||
|
||||
if sequencer.verbose then
|
||||
trigger.action.outText("***RND: read config", 30)
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
stopGap = {}
|
||||
stopGap.version = "1.1.0 STANDALONE"
|
||||
stopGap.version = "1.1.1 STANDALONE"
|
||||
stopGap.verbose = false
|
||||
stopGap.ssbEnabled = true
|
||||
stopGap.ignoreMe = "-sg"
|
||||
@ -36,7 +36,8 @@ stopGap.kickTheDead = true -- kick players to spectators on death to prevent re-
|
||||
1.0.8 - added refreshInterval option as requested
|
||||
1.0.9 - optimization when turning on stopgap
|
||||
1.1.0 - kickTheDead option
|
||||
|
||||
1.1.1 - filter "from runway" clients
|
||||
|
||||
--]]--
|
||||
|
||||
stopGap.standInGroups ={}
|
||||
@ -131,6 +132,7 @@ function stopGap.isGroundStart(theGroup)
|
||||
if action == "Fly Over Point" then return false end
|
||||
if action == "Turning Point" then return false end
|
||||
if action == "Landing" then return false end
|
||||
if action == "From Runway" then return false end
|
||||
-- looks like aircraft is on the ground
|
||||
-- but is it in water (carrier)?
|
||||
local u1 = theGroup.units[1]
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
stopGap = {}
|
||||
stopGap.version = "1.1.0"
|
||||
stopGap.version = "1.1.1"
|
||||
stopGap.verbose = false
|
||||
stopGap.ssbEnabled = true
|
||||
stopGap.ignoreMe = "-sg"
|
||||
@ -50,6 +50,7 @@ stopGap.requiredLibs = {
|
||||
1.0.9 - in line with standalone (optimization not required for DML)
|
||||
1.0.10 - some more verbosity for spIgnore and sgIgnore zones (DML only)
|
||||
1.1.0 - kickTheDead option
|
||||
1.1.1 - filter "from runway" clients
|
||||
|
||||
--]]--
|
||||
|
||||
@ -90,6 +91,7 @@ function stopGap.isGroundStart(theGroup)
|
||||
if action == "Fly Over Point" then return false end
|
||||
if action == "Turning Point" then return false end
|
||||
if action == "Landing" then return false end
|
||||
if action == "From Runway" then return false end
|
||||
-- looks like aircraft is on the ground
|
||||
-- but is it in water (carrier)?
|
||||
local u1 = theGroup.units[1]
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
valet = {}
|
||||
valet.version = "1.0.3"
|
||||
valet.version = "1.1.0"
|
||||
valet.verbose = false
|
||||
valet.requiredLibs = {
|
||||
"dcsCommon", -- always
|
||||
@ -13,7 +13,7 @@ valet.valets = {}
|
||||
1.0.1 - typos in verbosity corrected
|
||||
1.0.2 - also scan birth events
|
||||
1.0.3 - outSoundFile now working correctly
|
||||
|
||||
1.1.0 - hysteresis is now time-based (10 seconds)
|
||||
--]]--
|
||||
|
||||
function valet.addValet(theZone)
|
||||
@ -236,6 +236,8 @@ function valet.checkZoneAgainstPlayers(theZone, allPlayers)
|
||||
p.y = 0 -- sanity first
|
||||
local maxRad = theZone.maxRadius
|
||||
-- set up hysteresis
|
||||
-- new hysteresis: 10 seconds outside time
|
||||
local now = timer.getTime()
|
||||
local outside = maxRad * 1.2
|
||||
for playerName, aPlayerUnit in pairs (allPlayers) do
|
||||
local unitName = aPlayerUnit:getName()
|
||||
@ -269,6 +271,7 @@ function valet.checkZoneAgainstPlayers(theZone, allPlayers)
|
||||
if not theDesc then
|
||||
theDesc = {}
|
||||
theDesc.currentlyIn = false
|
||||
theDesc.lastTimeIn = 99999999
|
||||
theDesc.greets = 0
|
||||
theDesc.byes = 0
|
||||
theDesc.unitName = unitName
|
||||
@ -278,6 +281,7 @@ function valet.checkZoneAgainstPlayers(theZone, allPlayers)
|
||||
else
|
||||
-- ha!!! player changed planes!
|
||||
theDesc.currentlyIn = false
|
||||
theDesc.lastTimeIn = 99999999
|
||||
theDesc.greets = 0
|
||||
theDesc.byes = 0
|
||||
theDesc.unitName = unitName
|
||||
@ -289,11 +293,14 @@ function valet.checkZoneAgainstPlayers(theZone, allPlayers)
|
||||
valet.greetPlayer(playerName, aPlayerUnit, theZone, theDesc)
|
||||
end
|
||||
|
||||
elseif (dist > outside) and theDesc then
|
||||
theDesc.lastTimeIn = now
|
||||
|
||||
elseif theDesc and now > theDesc.lastTimeIn + 10 then --(dist > outside) and theDesc then
|
||||
if theDesc.unitName == unitName then
|
||||
else
|
||||
-- ha!!! player changed planes!
|
||||
theDesc.currentlyIn = false
|
||||
theDesc.lastTimeIn = 99999999
|
||||
theDesc.greets = 0
|
||||
theDesc.byes = 0
|
||||
theDesc.unitName = unitName
|
||||
@ -306,6 +313,7 @@ function valet.checkZoneAgainstPlayers(theZone, allPlayers)
|
||||
else
|
||||
-- was outside before
|
||||
end
|
||||
theDesc.lastTimeIn = 99999999
|
||||
else
|
||||
-- we are in the twilight zone (hysteresis). Do nothing.
|
||||
end
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user