979b7f72d5
Slukker spilleren en produktion, hvis vare et tændt flow kører (manuel vare eller målet tager den i auto), en stald æder eller en aktiv kæde bruger, kommer én besked pr. slukning med brugere og lagerdage, og en rød post 'Slukket men nødvendig' i Kræver handling og statusvinduet så længe den er slukket og nødvendig. Ingen advarsel når en anden tændt produktion dækker, lageret rækker over 60 dage, kæden selv slukkede den eller den var slukket ved indlæsning. Tjekket kører i kædens tick også uden kæder; ren logik i adDependency.lua.
158 lines
7.9 KiB
Lua
158 lines
7.9 KiB
Lua
-- Smart Pickup — "Kræver handling" -> flow (v1.60)
|
|
-- En "løber tør"-linje i lagerfanerne kan klikkes: findes der et flow der leverer varen til forbrugerne, åbnes
|
|
-- det; ligger varen andre steder på gården, åbnes "Nyt flow" udfyldt (ind til forbrugerne, varen valgt); ellers
|
|
-- siges det at et flow ikke hjælper (producér/køb). Afgørelsen er ADStorageStats.flowAdvice (testet).
|
|
-- Funktionerne lægges på SmartPickupFrame (indlæses efter SmartPickupFrame.lua).
|
|
|
|
-- Lagerfanen for en bygningstype (TAB_KINDS), fx "factory" -> fanen Fabrikker.
|
|
function SmartPickupFrame.tabOfKind(kind)
|
|
for tab, tabKind in pairs(SmartPickupFrame.TAB_KINDS or {}) do
|
|
if tabKind == kind then return tab end
|
|
end
|
|
return SmartPickupFrame.TAB_OVERVIEW
|
|
end
|
|
|
|
local function fillTypeName(fillType)
|
|
return g_fillTypeManager ~= nil and g_fillTypeManager:getFillTypeNameByIndex(fillType) or tostring(fillType)
|
|
end
|
|
|
|
-- Forsyningsflow der allerede leverer varen til en af forbrugerne -> run eller nil.
|
|
local function existingSupplyRun(consumerIds, name)
|
|
for _, run in ipairs(ADRunsController.store.runs) do
|
|
if run.kind ~= "outbound" then
|
|
local carries = run.ingredientMode ~= "manual"
|
|
for _, ingredient in ipairs(run.ingredients or {}) do
|
|
if ingredient == name then carries = true end
|
|
end
|
|
if carries then
|
|
for _, id in ipairs(run.targetBuildingIds or {}) do
|
|
if consumerIds[id] then return run end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
return nil
|
|
end
|
|
|
|
-- Udkørselsflow der allerede sælger varen fra en af bygningerne -> run eller nil.
|
|
local function existingSellRun(sourceIds, name)
|
|
for _, run in ipairs(ADRunsController.store.runs) do
|
|
if run.kind == "outbound" then
|
|
local sells = false
|
|
for _, product in ipairs(run.products or {}) do
|
|
if product.fillType == name and (product.policy == "sell" or product.policy == "sellElseStore") then sells = true end
|
|
end
|
|
if sells then
|
|
for _, id in ipairs(run.sourceBuildingIds or {}) do
|
|
if sourceIds[id] then return run end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
return nil
|
|
end
|
|
|
|
-- "Sælg nu": kilder = fanens bygninger med varen.
|
|
local function sellAdviceFor(stat)
|
|
local sourceIds, ids = {}, {}
|
|
for _, building in ipairs(stat.buildings or {}) do
|
|
local id = building.placeable ~= nil and ADBuildings.getId(building.placeable) or nil
|
|
if id ~= nil and not sourceIds[id] then
|
|
sourceIds[id] = true
|
|
table.insert(ids, id)
|
|
end
|
|
end
|
|
local name = fillTypeName(stat.fillType)
|
|
local run = existingSellRun(sourceIds, name)
|
|
local advice = ADStorageStats.sellAdvice({sourceCount = #ids, existingRunId = run ~= nil and run.id or nil})
|
|
return advice, {buildingIds = ids, run = run, name = name, stat = stat, sell = true}
|
|
end
|
|
|
|
-- entry fra ADStorageStats.attentionList -> advice ("open"|"flow"|"produce"|"none"), info
|
|
function SmartPickupFrame:attentionAdvice(entry)
|
|
-- kæde-forslag og manglende led har ingen vare (stat): klik fører til fanen Kæder
|
|
if entry ~= nil and (entry.kind == "chainSuggest" or entry.kind == "chainProblem") then return "chain", nil end
|
|
-- slukket men nødvendig: fanen Fabrikker (Kæder når kun en kæde bruger varen)
|
|
if entry ~= nil and entry.kind == "dependencyOff" then return entry.onlyChain and "chain" or "factories", nil end
|
|
if entry ~= nil and entry.kind == "sell" and entry.stat ~= nil then return sellAdviceFor(entry.stat) end
|
|
if entry == nil or entry.kind ~= "empty" or entry.stat == nil then return "none", nil end
|
|
local stat = entry.stat
|
|
local consumers = ADStorageStats.consumersOf(self.lastFullInventory, stat.fillType)
|
|
local consumerIds, consumerLevel, ids = {}, 0, {}
|
|
for _, consumer in ipairs(consumers) do
|
|
consumerLevel = consumerLevel + consumer.level
|
|
local id = consumer.placeable ~= nil and ADBuildings.getId(consumer.placeable) or nil
|
|
if id ~= nil and not consumerIds[id] then
|
|
consumerIds[id] = true
|
|
table.insert(ids, id)
|
|
end
|
|
end
|
|
local name = fillTypeName(stat.fillType)
|
|
local run = existingSupplyRun(consumerIds, name)
|
|
local advice = ADStorageStats.flowAdvice({farmLevel = stat.farmLevel or stat.level, consumerLevel = consumerLevel,
|
|
perDay = stat.consumption, consumerCount = #ids, existingRunId = run ~= nil and run.id or nil})
|
|
return advice, {consumers = consumers, buildingIds = ids, run = run, name = name, stat = stat}
|
|
end
|
|
|
|
function SmartPickupFrame:attentionHint(advice, info)
|
|
if advice == "chain" then return self.i18n:getText("spu_attention_hintChain") end
|
|
if advice == "factories" then return self.i18n:getText("spu_attention_hintFactories") end
|
|
if advice == "open" then return string.format(self.i18n:getText("spu_attention_hintOpen"), tostring(info.run.name)) end
|
|
if advice == "flow" then return self.i18n:getText(info.sell and "spu_attention_hintSellFlow" or "spu_attention_hintFlow") end
|
|
if advice == "produce" then return self.i18n:getText("spu_attention_hintProduce") end
|
|
return ""
|
|
end
|
|
|
|
function SmartPickupFrame:onAttentionClick(entry)
|
|
self:safe(function(frame)
|
|
if entry ~= nil and (entry.kind == "chainSuggest" or entry.kind == "chainProblem") then
|
|
-- manglende led: kæden foldes ud, så problemteksten står under den røde linje
|
|
if entry.kind == "chainProblem" and entry.rootKey ~= nil then
|
|
frame.chainExpanded = frame.chainExpanded or {}
|
|
frame.chainExpanded[entry.rootKey] = true
|
|
end
|
|
frame:switchTab(SmartPickupFrame.TAB_CHAINS)
|
|
return
|
|
end
|
|
if entry ~= nil and entry.kind == "dependencyOff" then
|
|
frame:switchTab(entry.onlyChain and SmartPickupFrame.TAB_CHAINS or SmartPickupFrame.tabOfKind("factory"))
|
|
return
|
|
end
|
|
local adEnv = frame.getAdEnv()
|
|
local advice, info = frame:attentionAdvice(entry)
|
|
if adEnv == nil or advice == "none" then return end
|
|
if advice == "open" then
|
|
frame.selectedRunId = info.run.id
|
|
frame:switchTab(SmartPickupFrame.TAB_FLOWS)
|
|
frame:openEditPanel("flow", info.run.id)
|
|
return
|
|
end
|
|
if advice == "produce" then
|
|
local text = string.format(frame.i18n:getText("spu_attention_produce"), tostring(info.stat.title),
|
|
SmartPickupFrame.formatCompact(info.stat.farmLevel or 0))
|
|
frame.statusOverride, frame.statusOverrideTicks = text, SmartPickupFrame.STATUS_OVERRIDE_TICKS
|
|
if ADFieldJobs ~= nil and ADFieldJobs.notify ~= nil then ADFieldJobs.notify(text, false) end
|
|
return
|
|
end
|
|
local guide
|
|
if info.sell then
|
|
-- udfyldt "Nyt flow": ud af bygningerne med varen, varen til salg
|
|
local name = string.format(frame.i18n:getText("spu_attention_sellFlowName"), tostring(info.stat.title))
|
|
guide = ADFlowGuide.openNew(name, {})
|
|
guide.draft.kind = "outbound"
|
|
guide.draft.sourceBuildingIds = info.buildingIds
|
|
guide.draft.products = {{fillType = info.name, policy = "sell"}}
|
|
else
|
|
-- udfyldt "Nyt flow": ind til forbrugerne, kun denne vare; guiden åbnes på oversigten (Gem/Start eller [Ret])
|
|
local name = string.format(frame.i18n:getText("spu_attention_flowName"), tostring(info.stat.title), tostring(info.consumers[1].name))
|
|
guide = ADFlowGuide.openNew(name, {})
|
|
guide.draft.targetBuildingIds = info.buildingIds
|
|
guide.draft.ingredientMode = "manual"
|
|
guide.draft.ingredients = {info.name}
|
|
end
|
|
guide = ADGuide.new(ADFlowGuide.DEF, guide.draft, frame:flowGuideContext(adEnv, guide.draft), {step = "summary"})
|
|
frame:switchTab(SmartPickupFrame.TAB_FLOWS)
|
|
frame:openGuide("flow", guide)
|
|
end)
|
|
end
|