From a21da81d54194a55bcf379036af345c5360e124c Mon Sep 17 00:00:00 2001 From: MayaTheShy Date: Sun, 15 Mar 2026 23:49:23 -0400 Subject: [PATCH] Add network broadcasting functionality for client displays and command handling --- inventoryManager.lua | 119 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 119 insertions(+) diff --git a/inventoryManager.lua b/inventoryManager.lua index a1c6a9a..e936432 100644 --- a/inventoryManager.lua +++ b/inventoryManager.lua @@ -15,6 +15,11 @@ local CACHE_FILE = ".inventory_cache" -- persistent cache file local SMELTER_MONITOR_SIDE = "top" local DISABLED_RECIPES_FILE = ".disabled_recipes" +-- Network sync (for client displays) +local BROADCAST_CHANNEL = 4200 +local ORDER_CHANNEL = 4201 +local BROADCAST_INTERVAL = 1 -- seconds between state broadcasts + ------------------------------------------------- -- Furnace types to manage ------------------------------------------------- @@ -651,6 +656,8 @@ local mon = nil local monName = nil local smelterMon = nil local smelterMonName = nil +local networkModem = nil +local networkModemName = nil local function setupMonitor() mon = peripheral.wrap(MONITOR_SIDE) @@ -2133,6 +2140,36 @@ local function handleSmelterTouch(x, y) end end +------------------------------------------------- +-- Network broadcast (sends state to client displays) +------------------------------------------------- + +local function broadcastState() + if not networkModem then return end + local state = { + type = "state", + cache = { + itemList = cache.itemList, + grandTotal = cache.grandTotal, + chestCount = cache.chestCount, + totalSlots = cache.totalSlots, + usedSlots = cache.usedSlots, + freeSlots = cache.freeSlots, + usedRatio = cache.usedRatio, + dropperOk = cache.dropperOk, + barrelOk = cache.barrelOk, + furnaceCount = cache.furnaceCount, + furnaceStatus = cache.furnaceStatus, + }, + activity = activity, + alerts = activeAlerts, + smeltingPaused = smeltingPaused, + disabledRecipes = disabledRecipes, + smeltable = SMELTABLE, + } + networkModem.transmit(BROADCAST_CHANNEL, ORDER_CHANNEL, state) +end + ------------------------------------------------- -- Main ------------------------------------------------- @@ -2167,6 +2204,21 @@ local function main() print("[WARN] No smelter monitor on " .. SMELTER_MONITOR_SIDE) end + -- Find modem for client communication + for _, name in ipairs(peripheral.getNames()) do + if peripheral.getType(name) == "modem" then + networkModem = peripheral.wrap(name) + networkModemName = name + networkModem.open(ORDER_CHANNEL) + break + end + end + if networkModem then + print("[OK] Network modem: " .. networkModemName) + else + print("[WARN] No modem found for client sync") + end + -- Load recipe toggles from disk loadDisabledRecipes() if smeltingPaused then @@ -2404,6 +2456,73 @@ local function main() handleTouch(x, y) end end + end, + + -- Task 10: Network state broadcast + function() + while true do + pcall(broadcastState) + sleep(BROADCAST_INTERVAL) + end + end, + + -- Task 11: Network order/command listener + function() + if not networkModem then return end + while true do + local event, side, channel, replyChannel, message, distance = os.pullEvent("modem_message") + if channel == ORDER_CHANNEL and type(message) == "table" then + if message.type == "order" and message.itemName and message.amount then + print(string.format("[NET] Order: %s x%d", message.itemName, message.amount)) + local success = orderItem(message.itemName, message.amount) + networkModem.transmit(replyChannel, ORDER_CHANNEL, { + type = "order_result", + success = success, + message = statusMessage, + color = statusColor, + }) + pcall(broadcastState) + elseif message.type == "scan" then + print("[NET] Scan request from client") + pcall(refreshCache) + pcall(checkAlerts) + needsRedraw = true + smelterNeedsRedraw = true + pcall(broadcastState) + elseif message.type == "toggle_pause" then + smeltingPaused = not smeltingPaused + print("[NET] Smelting " .. (smeltingPaused and "PAUSED" or "RESUMED")) + saveDisabledRecipes() + smelterNeedsRedraw = true + needsRedraw = true + pcall(broadcastState) + elseif message.type == "toggle_recipe" and message.recipe then + if disabledRecipes[message.recipe] then + disabledRecipes[message.recipe] = nil + else + disabledRecipes[message.recipe] = true + end + print("[NET] Recipe toggle: " .. message.recipe) + saveDisabledRecipes() + smelterNeedsRedraw = true + pcall(broadcastState) + elseif message.type == "enable_all" then + disabledRecipes = {} + print("[NET] All recipes enabled") + saveDisabledRecipes() + smelterNeedsRedraw = true + pcall(broadcastState) + elseif message.type == "disable_all" then + for inputName in pairs(SMELTABLE) do + disabledRecipes[inputName] = true + end + print("[NET] All recipes disabled") + saveDisabledRecipes() + smelterNeedsRedraw = true + pcall(broadcastState) + end + end + end end ) end