fix: æg-markør genkendes som hønsehus når det er nærmere end en løs læssestation (Pickup 1+2 blev Pigsty); palletildeling måler til hele spawn-området (alle rækker, start-slut) (v1.28.2.0)
This commit is contained in:
@@ -24,10 +24,6 @@ local function getHusbandryPalletSpawners(placeable)
|
||||
return spec ~= nil and spec.fillTypeIndexToPalletSpawner or nil
|
||||
end
|
||||
|
||||
local function firstSpawnerNode(spawner)
|
||||
return spawner ~= nil and spawner.spawnPlaces ~= nil and spawner.spawnPlaces[1] ~= nil and spawner.spawnPlaces[1].startNode or nil
|
||||
end
|
||||
|
||||
|
||||
local function distance2(ax, az, bx, bz)
|
||||
local dx, dz = ax - bx, az - bz
|
||||
@@ -130,7 +126,8 @@ local function findPlaceableNear(wayPoint, farmId, predicate)
|
||||
end
|
||||
end
|
||||
end
|
||||
return best
|
||||
-- (afstand i meter som 2. værdi)
|
||||
return best, best ~= nil and math.sqrt(bestDistance) or nil
|
||||
end
|
||||
|
||||
local function isObjectStorage(placeable)
|
||||
@@ -177,9 +174,15 @@ function ADSources.identifyUncached(adEnv, wayPointId, farmId)
|
||||
end
|
||||
-- Det strenge opslag (trigger bag næsen) passer til silorækker; en mælketank eller fabrik ligger
|
||||
-- ofte ved siden af markøren. Løst opslag inden for 40 m — men aldrig for siloer.
|
||||
-- stald med egne pallespawnere (hønsehus: æg) — markøren står ved spawneren, ingen læssestation
|
||||
local palletBarn, palletBarnDistance = findPlaceableNear(wayPoint, farmId, function(placeable) return placeable.getHusbandryFillLevel ~= nil and getHusbandryPalletSpawners(placeable) ~= nil end)
|
||||
if placeable == nil and ADSmartPickup.getLoadStationNearWayPointId ~= nil then
|
||||
local loose = ADSmartPickup.getLoadStationNearWayPointId(adEnv, wayPointId, farmId, ADSources.MAX_DISTANCE)
|
||||
local loose, looseDistance = ADSmartPickup.getLoadStationNearWayPointId(adEnv, wayPointId, farmId, ADSources.MAX_DISTANCE)
|
||||
local loosePlaceable = loose ~= nil and loose.owningPlaceable or nil
|
||||
-- et nærmere hønsehus vinder over en fjernere læssestation (gyllestation 23 m fra "Æg Pickup 1")
|
||||
if palletBarn ~= nil and looseDistance ~= nil and palletBarnDistance ~= nil and palletBarnDistance < looseDistance then
|
||||
loosePlaceable = nil
|
||||
end
|
||||
if loosePlaceable ~= nil and loosePlaceable.spec_silo == nil then
|
||||
if getProductionPoint(loosePlaceable) ~= nil then
|
||||
return {kind = "factory", placeable = loosePlaceable, station = loose, wayPointId = wayPointId, name = getPlaceableName(loosePlaceable, markerName)}
|
||||
@@ -188,8 +191,6 @@ function ADSources.identifyUncached(adEnv, wayPointId, farmId)
|
||||
end
|
||||
end
|
||||
end
|
||||
-- stald med egne pallespawnere (hønsehus: æg) — markøren står ved spawneren, ingen læssestation
|
||||
local palletBarn = findPlaceableNear(wayPoint, farmId, function(placeable) return placeable.getHusbandryFillLevel ~= nil and getHusbandryPalletSpawners(placeable) ~= nil end)
|
||||
if palletBarn ~= nil then
|
||||
return {kind = "husbandry", placeable = palletBarn, station = nil, wayPointId = wayPointId, name = getPlaceableName(palletBarn, markerName)}
|
||||
end
|
||||
@@ -254,55 +255,99 @@ local function getPalletContent(vehicle)
|
||||
return nil, 0
|
||||
end
|
||||
|
||||
-- Liter af varen på paller der står ved fabrikkens spawner (pallespawneren tømmer lageret
|
||||
-- ud på jorden løbende, så det er dér varen fysisk er).
|
||||
-- Alle andre pallespawnere der kan lave varen (stalde med spawner for fillType, fabrikkers
|
||||
-- pallespawner): {{x, z}, ...}. Står bygningerne tættere end PALLET_RADIUS (hønsehuse på række),
|
||||
-- tilhører en palle den nærmeste spawner — ellers tæller et tomt hus naboernes paller med.
|
||||
-- Spawnerens område som segmenter {ax, az, bx, bz}: hver spawnPlace fra start til slut (startNode/endNode,
|
||||
-- eller PlacementUtil-felterne startX/startZ + dirX/dirZ*width). Et hønsehus har to rækker; måles kun
|
||||
-- til første række, ligger den anden række tættere på naboens start end husets egen.
|
||||
local function spawnerSegments(spawner)
|
||||
local segments = {}
|
||||
for _, place in ipairs(spawner ~= nil and spawner.spawnPlaces or {}) do
|
||||
local ax, az = getNodePosition(place.startNode)
|
||||
local bx, bz = getNodePosition(place.endNode)
|
||||
if ax == nil and place.startX ~= nil and place.startZ ~= nil then
|
||||
ax, az = place.startX, place.startZ
|
||||
if place.dirX ~= nil and place.dirZ ~= nil and place.width ~= nil then
|
||||
bx, bz = ax + place.dirX * place.width, az + place.dirZ * place.width
|
||||
end
|
||||
end
|
||||
if ax ~= nil then table.insert(segments, {ax, az, bx or ax, bz or az}) end
|
||||
end
|
||||
return segments
|
||||
end
|
||||
|
||||
-- Kvadreret afstand fra (x, z) til nærmeste punkt på et af segmenterne.
|
||||
local function segmentsDistance2(segments, x, z)
|
||||
local best = math.huge
|
||||
for _, s in ipairs(segments) do
|
||||
local ax, az, bx, bz = s[1], s[2], s[3], s[4]
|
||||
local dx, dz = bx - ax, bz - az
|
||||
local len2 = dx * dx + dz * dz
|
||||
local t = len2 > 0 and math.max(0, math.min(1, ((x - ax) * dx + (z - az) * dz) / len2)) or 0
|
||||
local d = distance2(x, z, ax + dx * t, az + dz * t)
|
||||
if d < best then best = d end
|
||||
end
|
||||
return best
|
||||
end
|
||||
|
||||
-- Alle pallespawnere der kan lave varen (stalde med spawner for fillType, fabrikkers pallespawner) som
|
||||
-- {placeable, segments}. Står bygningerne tættere end PALLET_RADIUS (hønsehuse på række), tilhører en
|
||||
-- palle den spawner hvis område er nærmest — ellers tæller et tomt hus naboernes paller med.
|
||||
local function findRivalSpawners(fillType)
|
||||
local rivals = {}
|
||||
local placeables = g_currentMission ~= nil and g_currentMission.placeableSystem ~= nil and g_currentMission.placeableSystem.placeables or {}
|
||||
for _, placeable in pairs(placeables) do
|
||||
local husbandrySpawners = getHusbandryPalletSpawners(placeable)
|
||||
local productionPoint = getProductionPoint(placeable)
|
||||
local node = firstSpawnerNode(husbandrySpawners ~= nil and husbandrySpawners[fillType] or nil)
|
||||
or firstSpawnerNode(productionPoint ~= nil and productionPoint.palletSpawner or nil)
|
||||
local x, z = getNodePosition(node)
|
||||
if x ~= nil then table.insert(rivals, {x = x, z = z}) end
|
||||
local spawner = husbandrySpawners ~= nil and husbandrySpawners[fillType] or (productionPoint ~= nil and productionPoint.palletSpawner or nil)
|
||||
local segments = spawnerSegments(spawner)
|
||||
if #segments > 0 then table.insert(rivals, {placeable = placeable, segments = segments}) end
|
||||
end
|
||||
return rivals
|
||||
end
|
||||
|
||||
local function isNearestSpawner(rivals, sx, sz, x, z)
|
||||
local own = distance2(sx, sz, x, z)
|
||||
local function isNearestSpawner(rivals, placeable, own, x, z)
|
||||
for _, rival in ipairs(rivals) do
|
||||
if distance2(rival.x, rival.z, x, z) < own then return false end
|
||||
if rival.placeable ~= placeable and segmentsDistance2(rival.segments, x, z) < own then return false end
|
||||
end
|
||||
return true
|
||||
end
|
||||
|
||||
local function getPalletsNearSpawner(placeable, fillType, farmId, spawnerNode)
|
||||
ADSources.lastPalletNote = {}
|
||||
|
||||
-- Liter af varen på paller ved spawneren (pallespawneren tømmer lageret ud på jorden løbende, så
|
||||
-- det er dér varen fysisk er). spawner = staldens spawner for varen; nil = fabrikkens pallespawner.
|
||||
local function getPalletsNearSpawner(placeable, fillType, farmId, spawner)
|
||||
local productionPoint = getProductionPoint(placeable)
|
||||
local spawner = productionPoint ~= nil and productionPoint.palletSpawner or nil
|
||||
local node = spawnerNode or (spawner ~= nil and spawner.spawnPlaces ~= nil and spawner.spawnPlaces[1] ~= nil and spawner.spawnPlaces[1].startNode) or placeable.rootNode
|
||||
local sx, sz = getNodePosition(node)
|
||||
if sx == nil then
|
||||
return 0
|
||||
local segments = spawnerSegments(spawner or (productionPoint ~= nil and productionPoint.palletSpawner or nil))
|
||||
if #segments == 0 then
|
||||
local rx, rz = getNodePosition(placeable.rootNode)
|
||||
if rx == nil then return 0, 0 end
|
||||
segments = {{rx, rz, rx, rz}}
|
||||
end
|
||||
local rivals = cacheGet("palletSpawners", fillType, 10000, function() return findRivalSpawners(fillType) end)
|
||||
local vehicles = g_currentMission ~= nil and g_currentMission.vehicleSystem ~= nil and g_currentMission.vehicleSystem.vehicles or {}
|
||||
local total, count = 0, 0
|
||||
local total, count, lost = 0, 0, 0
|
||||
local radius2 = ADSources.PALLET_RADIUS * ADSources.PALLET_RADIUS
|
||||
for _, vehicle in pairs(vehicles) do
|
||||
if isPalletVehicle(vehicle) and (vehicle.getOwnerFarmId == nil or vehicle:getOwnerFarmId() == farmId) then
|
||||
local palletFillType, level = getPalletContent(vehicle)
|
||||
local x, z = getNodePosition(vehicle.rootNode)
|
||||
if palletFillType == fillType and x ~= nil and distance2(sx, sz, x, z) <= radius2 and isNearestSpawner(rivals, sx, sz, x, z) then
|
||||
total = total + level
|
||||
count = count + 1
|
||||
local own = (palletFillType == fillType and x ~= nil) and segmentsDistance2(segments, x, z) or math.huge
|
||||
if own <= radius2 then
|
||||
if isNearestSpawner(rivals, placeable, own, x, z) then
|
||||
total = total + level
|
||||
count = count + 1
|
||||
else
|
||||
lost = lost + 1
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
-- diagnose: paller inden for rækkevidde, men alle tildelt en nabo (højst én gang pr. minut pr. bygning)
|
||||
local now = g_currentMission ~= nil and g_currentMission.time or nil
|
||||
if count == 0 and lost > 0 and now ~= nil and (ADSources.lastPalletNote[placeable] or -math.huge) + 60000 < now then
|
||||
ADSources.lastPalletNote[placeable] = now
|
||||
Logging.info(ADSources.LOG_PREFIX .. "%s: %d paller inden for %d m tilhører nabo-spawnere (0 egne)", getPlaceableName(placeable, "?"), lost, ADSources.PALLET_RADIUS)
|
||||
end
|
||||
return total, count
|
||||
end
|
||||
|
||||
@@ -434,7 +479,7 @@ local function getHusbandryPalletProducts(source, farmId)
|
||||
local products = {}
|
||||
local spec = source.placeable.spec_husbandryPallets
|
||||
for fillType, spawner in pairs(getHusbandryPalletSpawners(source.placeable) or {}) do
|
||||
local liters, count = getPalletsNearSpawner(source.placeable, fillType, farmId, firstSpawnerNode(spawner))
|
||||
local liters, count = getPalletsNearSpawner(source.placeable, fillType, farmId, spawner)
|
||||
local capacity = spec ~= nil and spec.capacities ~= nil and spec.capacities[fillType] or 0
|
||||
local product = newProduct(fillType, liters, liters, math.max(capacity or 0, liters), true)
|
||||
product.palletLiters, product.palletCount = liters, count
|
||||
|
||||
Reference in New Issue
Block a user