Updated Moose

This commit is contained in:
iTracerFacer 2025-11-09 14:43:37 -06:00
parent 271c495b8c
commit dedad683c0
2 changed files with 252 additions and 165 deletions

View File

@ -1,4 +1,4 @@
env.info('*** MOOSE GITHUB Commit Hash ID: 2025-11-05T06:23:06+01:00-d5792fb02a61ac2cbf52d595759e60ab318feca8 ***')
env.info('*** MOOSE GITHUB Commit Hash ID: 2025-11-09T17:19:57+01:00-c10e57ec3bbf021ddeeb85eb49920b6d9a1dd8d9 ***')
if not MOOSE_DEVELOPMENT_FOLDER then
MOOSE_DEVELOPMENT_FOLDER='Scripts'
end
@ -12957,6 +12957,19 @@ List={},
Index={},
Database=nil,
CallScheduler=nil,
Filter={},
FilterCoalitionNumbers={
[coalition.side.RED+1]="red",
[coalition.side.BLUE+1]="blue",
[coalition.side.NEUTRAL+1]="neutral",
},
FilterMeta={
Coalitions={
["red"]=coalition.side.RED,
["blue"]=coalition.side.BLUE,
["neutral"]=coalition.side.NEUTRAL,
},
},
}
function SET_BASE:New(Database)
local self=BASE:Inherit(self,FSM:New())
@ -12998,6 +13011,20 @@ self:Remove(Name,not TriggerEvent)
end
return self
end
function SET_BASE:FilterCoalitions(Coalitions,Clear)
if Clear or(not self.Filter.Coalitions)then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then Coalitions={Coalitions}end
for CoalitionID,Coalition in pairs(Coalitions)do
local coalition=Coalition
if type(Coalition)=="number"then
coalition=self.FilterCoalitionNumbers[Coalition+1]or"unknown"
end
self.Filter.Coalitions[coalition]=coalition
end
return self
end
function SET_BASE:_Find(ObjectName)
local ObjectFound=self.Set[ObjectName]
return ObjectFound
@ -13481,16 +13508,6 @@ self.Filter.Zones[zonename]=Zone
end
return self
end
function SET_GROUP:FilterCoalitions(Coalitions,Clear)
if Clear or(not self.Filter.Coalitions)then
self.Filter.Coalitions={}
end
Coalitions=UTILS.EnsureTable(Coalitions,false)
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_GROUP:FilterCategories(Categories,Clear)
if Clear or not self.Filter.Categories then
self.Filter.Categories={}
@ -13945,16 +13962,6 @@ function SET_UNIT:FindUnit(UnitName)
local UnitFound=self.Set[UnitName]
return UnitFound
end
function SET_UNIT:FilterCoalitions(Coalitions)
self.Filter.Coalitions={}
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_UNIT:FilterCategories(Categories)
if not self.Filter.Categories then
self.Filter.Categories={}
@ -14599,18 +14606,6 @@ function SET_STATIC:FindStatic(StaticName)
local StaticFound=self.Set[StaticName]
return StaticFound
end
function SET_STATIC:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_STATIC:FilterZones(Zones)
if not self.Filter.Zones then
self.Filter.Zones={}
@ -15037,18 +15032,6 @@ self.Filter.Playernames[playername]=playername
end
return self
end
function SET_CLIENT:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_CLIENT:FilterCategories(Categories)
if not self.Filter.Categories then
self.Filter.Categories={}
@ -15437,18 +15420,6 @@ function SET_PLAYER:FindClient(PlayerName)
local ClientFound=self.Set[PlayerName]
return ClientFound
end
function SET_PLAYER:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_PLAYER:FilterZones(Zones)
if not self.Filter.Zones then
self.Filter.Zones={}
@ -15702,18 +15673,6 @@ function SET_AIRBASE:GetRandomAirbase()
local RandomAirbase=self:GetRandom()
return RandomAirbase
end
function SET_AIRBASE:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_AIRBASE:FilterCategories(Categories)
if not self.Filter.Categories then
self.Filter.Categories={}
@ -15874,18 +15833,6 @@ function SET_CARGO:FindCargo(CargoName)
local CargoFound=self.Set[CargoName]
return CargoFound
end
function SET_CARGO:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_CARGO:FilterTypes(Types)
if not self.Filter.Types then
self.Filter.Types={}
@ -16505,16 +16452,6 @@ self.Filter.Prefixes[Prefix]=Prefix
end
return self
end
function SET_OPSZONE:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
Coalitions=UTILS.EnsureTable(Coalitions,false)
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_OPSZONE:FilterOnce()
for ObjectName,Object in pairs(self.Database)do
self:Remove(ObjectName,true)
@ -16759,18 +16696,6 @@ function SET_OPSGROUP:FindNavyGroup(GroupName)
local GroupFound=self:FindGroup(GroupName)
return GroupFound
end
function SET_OPSGROUP:FilterCoalitions(Coalitions,Clear)
if Clear or not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_OPSGROUP:FilterCategories(Categories,Clear)
if Clear or not self.Filter.Categories then
self.Filter.Categories={}
@ -17252,18 +17177,6 @@ DCargoInclude=DCargoInclude and MClientFunc
end
return DCargoInclude
end
function SET_DYNAMICCARGO:FilterCoalitions(Coalitions)
if not self.Filter.Coalitions then
self.Filter.Coalitions={}
end
if type(Coalitions)~="table"then
Coalitions={Coalitions}
end
for CoalitionID,Coalition in pairs(Coalitions)do
self.Filter.Coalitions[Coalition]=Coalition
end
return self
end
function SET_DYNAMICCARGO:FilterTypes(Types)
if not self.Filter.Types then
self.Filter.Types={}
@ -23514,6 +23427,15 @@ end
self:F(self.ClassName.." "..self.IdentifiableName.." not found!")
return nil
end
function IDENTIFIABLE:IsRed()
return self:GetCoalition()==coalition.side.RED
end
function IDENTIFIABLE:IsBlue()
return self:GetCoalition()==coalition.side.BLUE
end
function IDENTIFIABLE:IsNeutral()
return self:GetCoalition()==coalition.side.NEUTRAL
end
function IDENTIFIABLE:GetCoalitionName()
self:F2(self.IdentifiableName)
local DCSIdentifiable=self:GetDCSObject()
@ -28477,33 +28399,45 @@ end
function GROUP:GetTypeName()
local DCSGroup=self:GetDCSObject()
if DCSGroup then
local GroupTypeName=DCSGroup:getUnit(1):getTypeName()
local unit=DCSGroup:getUnit(1)
if unit then
local GroupTypeName=unit:getTypeName()
return(GroupTypeName)
end
end
return nil
end
function GROUP:GetNatoReportingName()
local DCSGroup=self:GetDCSObject()
if DCSGroup then
local GroupTypeName=DCSGroup:getUnit(1):getTypeName()
local unit=DCSGroup:getUnit(1)
if unit then
local GroupTypeName=unit:getTypeName()
return UTILS.GetReportingName(GroupTypeName)
end
end
return"Bogey"
end
function GROUP:GetPlayerName()
local DCSGroup=self:GetDCSObject()
if DCSGroup then
local PlayerName=DCSGroup:getUnit(1):getPlayerName()
local unit=DCSGroup:getUnit(1)
if unit then
local PlayerName=unit:getPlayerName()
return(PlayerName)
end
end
return nil
end
function GROUP:GetCallsign()
local DCSGroup=self:GetDCSObject()
if DCSGroup then
local GroupCallSign=DCSGroup:getUnit(1):getCallsign()
local unit=DCSGroup:getUnit(1)
if unit then
local GroupCallSign=unit:getCallsign()
return GroupCallSign
end
end
BASE:E({"Cannot GetCallsign",Positionable=self,Alive=self:IsAlive()})
return nil
end
@ -34264,8 +34198,9 @@ REMOVED="REMOVED",
}
DYNAMICCARGO.AircraftTypes={
["CH-47Fbl1"]="CH-47Fbl1",
["Mi-8MTV2"]="CH-47Fbl1",
["Mi-8MT"]="CH-47Fbl1",
["Mi-8MTV2"]="Mi-8MTV2",
["Mi-8MT"]="Mi-8MT",
["C-130J-30"]="C-130J-30",
}
DYNAMICCARGO.AircraftDimensions={
["CH-47Fbl1"]={
@ -34286,8 +34221,14 @@ DYNAMICCARGO.AircraftDimensions={
["length"]=15,
["ropelength"]=30,
},
["C-130J-30"]={
["width"]=4,
["height"]=12,
["length"]=35,
["ropelength"]=0,
},
}
DYNAMICCARGO.version="0.0.9"
DYNAMICCARGO.version="0.1.0"
function DYNAMICCARGO:Register(CargoName)
local self=BASE:Inherit(self,POSITIONABLE:New(CargoName))
self.StaticName=CargoName
@ -73781,6 +73722,7 @@ CTLD.UnitTypeCapabilities={
["Mi-24P"]={type="Mi-24P",crates=true,troops=true,cratelimit=2,trooplimit=8,length=18,cargoweightlimit=700},
["Mi-24V"]={type="Mi-24V",crates=true,troops=true,cratelimit=2,trooplimit=8,length=18,cargoweightlimit=700},
["Hercules"]={type="Hercules",crates=true,troops=true,cratelimit=7,trooplimit=64,length=25,cargoweightlimit=19000},
["C-130J-30"]={type="C-130J-30",crates=true,troops=true,cratelimit=7,trooplimit=64,length=35,cargoweightlimit=21500},
["UH-60L"]={type="UH-60L",crates=true,troops=true,cratelimit=2,trooplimit=20,length=16,cargoweightlimit=3500},
["UH-60L_DAP"]={type="UH-60L_DAP",crates=false,troops=true,cratelimit=0,trooplimit=2,length=16,cargoweightlimit=500},
["MH-60R"]={type="MH-60R",crates=true,troops=true,cratelimit=2,trooplimit=20,length=16,cargoweightlimit=3500},
@ -73797,8 +73739,9 @@ CTLD.FixedWingTypes={
["Hercules"]="Hercules",
["Bronco"]="Bronco",
["Mosquito"]="Mosquito",
["C-130J-30"]="C-130J-30",
}
CTLD.version="1.3.38"
CTLD.version="1.3.39"
function CTLD:New(Coalition,Prefixes,Alias)
local self=BASE:Inherit(self,FSM:New())
BASE:T({Coalition,Prefixes,Alias})
@ -73902,6 +73845,7 @@ self.movetroopstowpzone=true
self.movetroopsdistance=5000
self.returntroopstobase=true
self.troopdropzoneradius=100
self.buildPairSeparation=25
self.loadSavedCrates=true
self.VehicleMoveFormation=AI.Task.VehicleFormation.VEE
self.enableHercules=false
@ -75753,19 +75697,55 @@ else
self:T(text)
end
if canbuild then
local notified=false
for _,_build in pairs(buildables)do
local build=_build
if build.CanBuild then
self:_CleanUpCrates(crates,build,number)
local required=build.Required or 1
if required<1 then required=1 end
local full=math.floor((build.Found or 0)/required)
if full<1 then full=1 end
local sep=self.buildPairSeparation or 25
local hdg=(Unit:GetHeading()+180)%360
local lat=(hdg+90)%360
local base=Unit:GetCoordinate():Translate(20,hdg)
if full==1 then
local cratesNow,numberNow=self:_FindCratesNearby(Group,Unit,finddist,true,true)
self:_CleanUpCrates(cratesNow,build,numberNow)
self:_RefreshLoadCratesMenu(Group,Unit)
if self.buildtime and self.buildtime>0 then
local buildtimer=TIMER:New(self._BuildObjectFromCrates,self,Group,Unit,build,false,Group:GetCoordinate(),MultiDrop)
buildtimer:Start(self.buildtime)
if not notified then
self:_SendMessage(string.format("Build started, ready in %d seconds!",self.buildtime),15,false,Group)
notified=true
end
self:__CratesBuildStarted(1,Group,Unit,build.Name)
else
self:_BuildObjectFromCrates(Group,Unit,build,false,nil,MultiDrop)
end
else
local start=-((full-1)*sep)/2
for n=1,full do
local cratesNow,numberNow=self:_FindCratesNearby(Group,Unit,finddist,true,true)
self:_CleanUpCrates(cratesNow,build,numberNow)
self:_RefreshLoadCratesMenu(Group,Unit)
local off=start+(n-1)*sep
local coord=base:Translate(off,lat):GetVec2()
local b={Name=build.Name,Required=build.Required,Template=build.Template,CanBuild=true,Type=build.Type,Coord=coord}
if self.buildtime and self.buildtime>0 then
local buildtimer=TIMER:New(self._BuildObjectFromCrates,self,Group,Unit,b,false,Group:GetCoordinate(),MultiDrop)
buildtimer:Start(self.buildtime)
if not notified then
self:_SendMessage(string.format("Build started, ready in %d seconds!",self.buildtime),15,false,Group)
notified=true
end
self:__CratesBuildStarted(1,Group,Unit,build.Name)
else
self:_BuildObjectFromCrates(Group,Unit,b,false,nil,MultiDrop)
end
end
end
end
end
end
@ -75778,24 +75758,32 @@ function CTLD:_PackCratesNearby(Group,Unit)
self:T(self.lid.." _PackCratesNearby")
local location=Group:GetCoordinate()
local nearestGroups=SET_GROUP:New():FilterCoalitions("blue"):FilterZones({ZONE_RADIUS:New("TempZone",location:GetVec2(),self.PackDistance,false)}):FilterOnce()
local packedAny=false
for _,_Group in pairs(nearestGroups.Set)do
local didPackThisGroup=false
for _,_Template in pairs(_DATABASE.Templates.Groups)do
if(string.match(_Group:GetName(),_Template.GroupName))then
if string.match(_Group:GetName(),_Template.GroupName)then
for _,_entry in pairs(self.Cargo_Crates)do
if(_entry.Templates[1]==_Template.GroupName)then
if _entry.Templates[1]==_Template.GroupName then
_Group:Destroy()
self:_GetCrates(Group,Unit,_entry,nil,false,true)
self:_RefreshLoadCratesMenu(Group,Unit)
self:__CratesPacked(1,Group,Unit,_entry)
return true
packedAny=true
didPackThisGroup=true
break
end
end
end
if didPackThisGroup then break end
end
end
if not packedAny then
self:_SendMessage("Nothing to pack at this distance pilot!",10,false,Group)
return false
end
return true
end
function CTLD:_RepairCrates(Group,Unit,Engineering)
self:T(self.lid.." _RepairCrates")
local finddist=self.CrateDistance or 35
@ -75963,7 +75951,8 @@ local thisID=nowcrate:GetID()
if name==nametype then
table.insert(destIDs,thisID)
found=found+1
nowcrate:GetPositionable():Destroy(false)
local pos=nowcrate:GetPositionable()
if pos then pos:Destroy(false)end
nowcrate.Positionable=nil
nowcrate.HasBeenDropped=false
end
@ -76859,29 +76848,62 @@ for cName,list in pairs(cargoByName)do
local needed=list[1]:GetCratesNeeded()or 1
table.sort(list,function(a,b)return a:GetID()<b:GetID()end)
local i=1
while i<=#list do
local left=(#list-i+1)
if left>=needed then
local sets=math.floor(#list/(needed>0 and needed or 1))
if sets>0 then
local parentLabel=string.format("%d. %s (%d SET)",lineIndex,cName,sets)
local parentMenu=MENU_GROUP:New(Group,parentLabel,dropCratesMenu)
for s=1,sets do
local chunk={}
for n=i,i+needed-1 do
table.insert(chunk,list[n])
end
local label=string.format("%d. %s",lineIndex,cName)
for n=i,i+needed-1 do table.insert(chunk,list[n])end
table.insert(self.CrateGroupList[Unit:GetName()],chunk)
local setIndex=#self.CrateGroupList[Unit:GetName()]
MENU_GROUP_COMMAND:New(Group,label,dropCratesMenu,self._UnloadSingleCrateSet,self,Group,Unit,setIndex)
i=i+needed
else
local chunk={}
for n=i,#list do
table.insert(chunk,list[n])
end
local label=string.format("%d. %s %d/%d",lineIndex,cName,left,needed)
if sets==1 then
MENU_GROUP_COMMAND:New(Group,"Drop",parentMenu,function(selfArg,GroupArg,UnitArg,cNameArg,neededArg,qty)
local uName=UnitArg:GetName()
for k=1,qty do
local lst=selfArg.CrateGroupList and selfArg.CrateGroupList[uName]
if not lst then break end
local idx=nil
for j=1,#lst do
local ch=lst[j]
local first=ch and ch[1]
if first and(not first:WasDropped())and first:GetName()==cNameArg and#ch>=neededArg then idx=j break end
end
if not idx then break end
selfArg:_UnloadSingleCrateSet(GroupArg,UnitArg,idx)
end
end,self,Group,Unit,cName,needed,1)
else
for q=1,sets do
local qm=MENU_GROUP:New(Group,string.format("Drop %d Set%s",q,q>1 and"s"or""),parentMenu)
MENU_GROUP_COMMAND:New(Group,"Drop",qm,function(selfArg,GroupArg,UnitArg,cNameArg,neededArg,qty)
local uName=UnitArg:GetName()
for k=1,qty do
local lst=selfArg.CrateGroupList and selfArg.CrateGroupList[uName]
if not lst then break end
local idx=nil
for j=1,#lst do
local ch=lst[j]
local first=ch and ch[1]
if first and(not first:WasDropped())and first:GetName()==cNameArg and#ch>=neededArg then idx=j break end
end
if not idx then break end
selfArg:_UnloadSingleCrateSet(GroupArg,UnitArg,idx)
end
end,self,Group,Unit,cName,needed,q)
end
end
lineIndex=lineIndex+1
end
if i<=#list then
local left=#list-i+1
local chunk={}
for n=i,#list do table.insert(chunk,list[n])end
table.insert(self.CrateGroupList[Unit:GetName()],chunk)
local setIndex=#self.CrateGroupList[Unit:GetName()]
local label=string.format("%d. %s %d/%d",lineIndex,cName,left,needed)
MENU_GROUP_COMMAND:New(Group,label,dropCratesMenu,self._UnloadSingleCrateSet,self,Group,Unit,setIndex)
i=#list+1
end
lineIndex=lineIndex+1
end
end
@ -76898,33 +76920,98 @@ for cName,list in pairs(cargoByName)do
local needed=list[1]:GetCratesNeeded()or 1
table.sort(list,function(a,b)return a:GetID()<b:GetID()end)
local i=1
while i<=#list do
local left=(#list-i+1)
if left>=needed then
local sets=math.floor(#list/(needed>0 and needed or 1))
if sets>0 then
local parentLabel=string.format("%d. %s (%d SET)",lineIndex,cName,sets)
local parentMenu=MENU_GROUP:New(Group,parentLabel,dropCratesMenu)
for s=1,sets do
local chunk={}
for n=i,i+needed-1 do
table.insert(chunk,list[n])
end
local label=string.format("%d. %s",lineIndex,cName)
for n=i,i+needed-1 do table.insert(chunk,list[n])end
table.insert(self.CrateGroupList[Unit:GetName()],chunk)
local setIndex=#self.CrateGroupList[Unit:GetName()]
local mSet=MENU_GROUP:New(Group,label,dropCratesMenu)
MENU_GROUP_COMMAND:New(Group,"Drop",mSet,self._UnloadSingleCrateSet,self,Group,Unit,setIndex)
if not(self:IsUnitInAir(Unit)and self:IsFixedWing(Unit))then
MENU_GROUP_COMMAND:New(Group,"Drop and build",mSet,self._DropSingleAndBuild,self,Group,Unit,setIndex)
end
i=i+needed
else
local chunk={}
for n=i,#list do
table.insert(chunk,list[n])
end
local label=string.format("%d. %s %d/%d",lineIndex,cName,left,needed)
if sets==1 then
MENU_GROUP_COMMAND:New(Group,"Drop",parentMenu,function(selfArg,GroupArg,UnitArg,cNameArg,neededArg,qty)
local uName=UnitArg:GetName()
for k=1,qty do
local lst=selfArg.CrateGroupList and selfArg.CrateGroupList[uName]
if not lst then break end
local idx=nil
for j=1,#lst do
local ch=lst[j]
local first=ch and ch[1]
if first and(not first:WasDropped())and first:GetName()==cNameArg and#ch>=neededArg then idx=j break end
end
if not idx then break end
selfArg:_UnloadSingleCrateSet(GroupArg,UnitArg,idx)
end
end,self,Group,Unit,cName,needed,1)
if not(self:IsUnitInAir(Unit)and self:IsFixedWing(Unit))then
MENU_GROUP_COMMAND:New(Group,"Drop and build",parentMenu,function(selfArg,GroupArg,UnitArg,cNameArg,neededArg,qty)
local uName=UnitArg:GetName()
for k=1,qty do
local lst=selfArg.CrateGroupList and selfArg.CrateGroupList[uName]
if not lst then break end
local idx=nil
for j=1,#lst do
local ch=lst[j]
local first=ch and ch[1]
if first and(not first:WasDropped())and first:GetName()==cNameArg and#ch>=neededArg then idx=j break end
end
if not idx then break end
selfArg:_UnloadSingleCrateSet(GroupArg,UnitArg,idx)
end
selfArg:_BuildCrates(GroupArg,UnitArg)
end,self,Group,Unit,cName,needed,1)
end
else
for q=1,sets do
local qm=MENU_GROUP:New(Group,string.format("Drop %d Set%s",q,q>1 and"s"or""),parentMenu)
MENU_GROUP_COMMAND:New(Group,"Drop",qm,function(selfArg,GroupArg,UnitArg,cNameArg,neededArg,qty)
local uName=UnitArg:GetName()
for k=1,qty do
local lst=selfArg.CrateGroupList and selfArg.CrateGroupList[uName]
if not lst then break end
local idx=nil
for j=1,#lst do
local ch=lst[j]
local first=ch and ch[1]
if first and(not first:WasDropped())and first:GetName()==cNameArg and#ch>=neededArg then idx=j break end
end
if not idx then break end
selfArg:_UnloadSingleCrateSet(GroupArg,UnitArg,idx)
end
end,self,Group,Unit,cName,needed,q)
if not(self:IsUnitInAir(Unit)and self:IsFixedWing(Unit))then
MENU_GROUP_COMMAND:New(Group,"Drop and build",qm,function(selfArg,GroupArg,UnitArg,cNameArg,neededArg,qty)
local uName=UnitArg:GetName()
for k=1,qty do
local lst=selfArg.CrateGroupList and selfArg.CrateGroupList[uName]
if not lst then break end
local idx=nil
for j=1,#lst do
local ch=lst[j]
local first=ch and ch[1]
if first and(not first:WasDropped())and first:GetName()==cNameArg and#ch>=neededArg then idx=j break end
end
if not idx then break end
selfArg:_UnloadSingleCrateSet(GroupArg,UnitArg,idx)
end
selfArg:_BuildCrates(GroupArg,UnitArg)
end,self,Group,Unit,cName,needed,q)
end
end
end
lineIndex=lineIndex+1
end
if i<=#list then
local left=#list-i+1
local chunk={}
for n=i,#list do table.insert(chunk,list[n])end
table.insert(self.CrateGroupList[Unit:GetName()],chunk)
local setIndex=#self.CrateGroupList[Unit:GetName()]
local label=string.format("%d. %s %d/%d",lineIndex,cName,left,needed)
MENU_GROUP_COMMAND:New(Group,label,dropCratesMenu,self._UnloadSingleCrateSet,self,Group,Unit,setIndex)
i=#list+1
end
lineIndex=lineIndex+1
end
end
@ -78928,7 +79015,7 @@ elseif cargotype==CTLD_CARGO.Enum.TROOPS or cargotype==CTLD_CARGO.Enum.ENGINEERS
local injecttroops=CTLD_CARGO:New(nil,cargoname,cargotemplates,cargotype,true,true,size,nil,true,mass)
self:InjectTroops(dropzone,injecttroops,self.surfacetypes,self.useprecisecoordloads,structure,timestamp)
end
elseif self.loadSavedCrates and((type(groupname)=="string"and groupname=="STATIC")or cargotype==CTLD_CARGO.Enum.REPAIR)then
elseif self.loadSavedCrates and(type(groupname)=="string"and groupname=="STATIC")or cargotype==CTLD_CARGO.Enum.REPAIR then
local dropzone=ZONE_RADIUS:New("DropZone",vec2,20)
local injectstatic=nil
if cargotype==CTLD_CARGO.Enum.VEHICLE or cargotype==CTLD_CARGO.Enum.FOB then