From 3c2d91b63d423344e39996bd2c51a02aa0272b6c Mon Sep 17 00:00:00 2001 From: Zenon Seth Date: Fri, 10 Nov 2023 00:12:07 +0000 Subject: [PATCH] Reworked suppliers to be chests that passively supply items --- api/controller.lua | 18 ++-- api/supplier.lua | 101 +++++++----------- logic/controller.lua | 37 ++----- logic/groups.lua | 1 + logic/injector.lua | 7 +- logic/network_cache.lua | 24 +++-- logic/network_storage.lua | 59 ++++++++++ logic/requester.lua | 7 +- logic/supplier.lua | 43 ++------ textures/logistica_item_supplier_back.png | Bin 2125 -> 0 bytes textures/logistica_item_supplier_front.png | Bin 2305 -> 0 bytes textures/logistica_item_supplier_side.png | Bin 2258 -> 0 bytes .../logistica_passive_supplier_bottom.png | Bin 0 -> 2372 bytes textures/logistica_passive_supplier_front.png | Bin 0 -> 2366 bytes textures/logistica_passive_supplier_side.png | Bin 0 -> 2396 bytes textures/logistica_passive_supplier_top.png | Bin 0 -> 2324 bytes util/common.lua | 14 ++- util/util.lua | 2 +- 18 files changed, 155 insertions(+), 158 deletions(-) delete mode 100644 textures/logistica_item_supplier_back.png delete mode 100644 textures/logistica_item_supplier_front.png delete mode 100644 textures/logistica_item_supplier_side.png create mode 100644 textures/logistica_passive_supplier_bottom.png create mode 100644 textures/logistica_passive_supplier_front.png create mode 100644 textures/logistica_passive_supplier_side.png create mode 100644 textures/logistica_passive_supplier_top.png diff --git a/api/controller.lua b/api/controller.lua index 4e9ef54..de9de65 100644 --- a/api/controller.lua +++ b/api/controller.lua @@ -12,8 +12,6 @@ local function get_controller_formspec(pos) "button[5.6,0.6;3,0.8;"..SET_BUTTON..";Set]" end - - local function show_controller_formspec(pos, playerName) local pInfo = {} pInfo.position = pos @@ -37,7 +35,12 @@ local function on_controller_receive_fields(player, formname, fields) return true end +local function after_controller_place(pos) + logistica.start_controller_timer(pos) +end + -- registration stuff + minetest.register_on_player_receive_fields(on_controller_receive_fields) --[[ @@ -52,7 +55,7 @@ minetest.register_on_player_receive_fields(on_controller_receive_fields) tier may be `nil` which will result in the controller connecting to everything ]] -function logistica.register_controller(simpleName, def, tier) +function logistica.register_controller(name, def, tier) local controller_group = nil if not tier then tier = logistica.TIER_ALL @@ -62,7 +65,7 @@ function logistica.register_controller(simpleName, def, tier) logistica.tiers[ltier] = true controller_group = logistica.get_machine_group(ltier) end - local controller_name = "logistica:" .. string.lower(simpleName:gsub(" ", "_")) .. "_controller" + local controller_name = "logistica:" .. string.lower(name:gsub(" ", "_")) logistica.controllers[controller_name] = tier local on_construct = function(pos) @@ -70,15 +73,16 @@ function logistica.register_controller(simpleName, def, tier) logistica.on_controller_change(pos, nil) end local after_destruct = logistica.on_controller_change - local on_timer = logistica.on_controller_timer if not def.groups then def.groups = {} end def.groups[controller_group] = 1 + def.groups[logistica.TIER_CONTROLLER] = 1 + def.on_timer = logistica.on_controller_timer def.on_construct = on_construct def.after_destruct = after_destruct - def.on_timer = logistica.on_timer_powered(on_timer) + def.after_place_node = after_controller_place def.drop = controller_name def.on_rightclick = function(pos, node, clicker, itemstack, pointed_thing) if clicker and clicker:is_player() then @@ -101,7 +105,7 @@ function logistica.register_controller(simpleName, def, tier) minetest.register_node(controller_name.."_disabled", def_disabled) end -logistica.register_controller("Simple Controller", { +logistica.register_controller("simple_controller", { description = "Simple Controller", tiles = { "logistica_silver_cable.png" }, groups = { diff --git a/api/supplier.lua b/api/supplier.lua index cf7b126..b41c21c 100644 --- a/api/supplier.lua +++ b/api/supplier.lua @@ -1,24 +1,21 @@ -local NUM_SUPPLY_SLOTS = 8 -local PULL_LIST_PICKER = "pull_pick" -local ON_OFF_BUTTON = "on_off_btn" local FORMSPEC_NAME = "logistica_supplier" +local ON_OFF_BUTTON = "on_off_btn" local supplierForms = {} local function get_supplier_formspec(pos) local posForm = "nodemeta:"..pos.x..","..pos.y..","..pos.z - local pushPos = logistica.get_supplier_target(pos) - local selectedList = logistica.get_supplier_target_list(pos) local isOn = logistica.is_machine_on(pos) + return "formspec_version[4]" .. - "size[10.6,8]" .. + "size[10.5,12]" .. logistica.ui.background.. - logistica.ui.pull_list_picker(PULL_LIST_PICKER, 6.7, 0.7, pushPos, selectedList, "Supply from:").. - logistica.ui.on_off_btn(isOn, 9.3, 0.5, ON_OFF_BUTTON, "Enable").. - "label[0.6,1.2;Items to make available as Supply. If left empty, nothing is supplied]".. - "list["..posForm..";filter;0.5,1.5;"..NUM_SUPPLY_SLOTS..",1;0]".. - "list[current_player;main;0.5,3;8,4;0]" + logistica.ui.on_off_btn(isOn, 9.0, 0.3, ON_OFF_BUTTON, "Enable").. + "label[0.6,1.0;Passive Supplier: Items become available to network requests.]".. + "list["..posForm..";main;0.4,1.4;8,4;0]".. + "list[current_player;main;0.4,7.0;8,4;0]".. + "listring[]" end local function show_supplier_formspec(playerName, pos) @@ -40,13 +37,6 @@ local function on_player_receive_fields(player, formname, fields) if not pos then return false end logistica.toggle_machine_on_off(pos) show_supplier_formspec(player:get_player_name(), pos) - elseif fields[PULL_LIST_PICKER] then - local selected = fields[PULL_LIST_PICKER] - if logistica.is_allowed_pull_list(selected) then - local pos = supplierForms[playerName].position - if not pos then return false end - logistica.set_supplier_target_list(pos, selected) - end end return true end @@ -56,40 +46,32 @@ local function on_supplier_rightclick(pos, node, clicker, itemstack, pointed_thi show_supplier_formspec(clicker:get_player_name(), pos) end -local function after_place_supplier(pos, placer, itemstack, numRequestSlots) +local function after_place_supplier(pos, placer, itemstack) local meta = minetest.get_meta(pos) - if placer and placer:is_player() then - meta:set_string("owner", placer:get_player_name()) - end - logistica.toggle_machine_on_off(pos) - logistica.set_supplier_target_list(pos, "dst") local inv = meta:get_inventory() - inv:set_size("filter", numRequestSlots) + inv:set_size("main", logistica.get_supplier_inv_size(pos)) + logistica.set_node_tooltip_from_state(pos) logistica.on_supplier_change(pos) end local function allow_supplier_storage_inv_put(pos, listname, index, stack, player) - if listname ~= "filter" then return 0 end - local inv = minetest.get_meta(pos):get_inventory() - local newStack = ItemStack(stack) - newStack:set_count(1) - inv:set_stack(listname, index, newStack) - logistica.update_cache_at_pos(pos, LOG_CACHE_SUPPLIER) - return 0 + return stack:get_count() end local function allow_supplier_inv_take(pos, listname, index, stack, player) - if listname ~= "filter" then return 0 end - local inv = minetest.get_meta(pos):get_inventory() - local slotStack = inv:get_stack(listname, index) - slotStack:take_item(stack:get_count()) - inv:set_stack(listname, index, slotStack) - logistica.update_cache_at_pos(pos, LOG_CACHE_SUPPLIER) - return 0 + return stack:get_count() end local function allow_supplier_inv_move(pos, from_list, from_index, to_list, to_index, count, player) - return 0 + return count +end + +local function on_suppler_inventory_put(pos, listname, index, stack, player) + logistica.update_cache_at_pos(pos, LOG_CACHE_SUPPLIER) +end + +local function on_suppler_inventory_take(pos, listname, index, stack, player) + logistica.update_cache_at_pos(pos, LOG_CACHE_SUPPLIER) end ---------------------------------------------------------------- @@ -102,41 +84,34 @@ minetest.register_on_player_receive_fields(on_player_receive_fields) -- Public Registration API ---------------------------------------------------------------- -- `simpleName` is used for the description and for the name (can contain spaces) --- `maxTransferRate` indicates how many nodes at a time this supplier can take when asked -function logistica.register_supplier(simpleName, maxTransferRate) - local lname = string.lower(simpleName:gsub(" ", "_")) - local supplier_name = "logistica:supplier_"..lname +-- `inventorySize` should be 32 at max (aka regular chest) +function logistica.register_supplier(desc, name, inventorySize, tiles) + local lname = string.lower(name:gsub(" ", "_")) + local supplier_name = "logistica:passive_supplier_"..lname logistica.suppliers[supplier_name] = true local grps = {oddly_breakable_by_hand = 3, cracky = 3 } grps[logistica.TIER_ALL] = 1 local def = { - description = simpleName.." Supplier", + description = desc, drawtype = "normal", - tiles = { - "logistica_"..lname.."_supplier_side.png^[transformR270", - "logistica_"..lname.."_supplier_side.png^[transformR90", - "logistica_"..lname.."_supplier_side.png^[transformR180", - "logistica_"..lname.."_supplier_side.png", - "logistica_"..lname.."_supplier_back.png", - "logistica_"..lname.."_supplier_front.png", - }, + tiles = tiles, paramtype = "light", paramtype2 = "facedir", is_ground_content = false, groups = grps, drop = supplier_name, sounds = logistica.node_sound_metallic(), - after_place_node = function (pos, placer, itemstack) - after_place_supplier(pos, placer, itemstack, NUM_SUPPLY_SLOTS) - end, + after_place_node = after_place_supplier, after_destruct = logistica.on_supplier_change, on_rightclick = on_supplier_rightclick, allow_metadata_inventory_put = allow_supplier_storage_inv_put, allow_metadata_inventory_take = allow_supplier_inv_take, allow_metadata_inventory_move = allow_supplier_inv_move, + on_metadata_inventory_put = on_suppler_inventory_put, + on_metadata_inventory_take = on_suppler_inventory_take, logistica = { - supplier_transfer_rate = maxTransferRate, - on_power = function() end, -- necessary for power toggle to work + inventory_size = inventorySize, + on_power = function(pos, power) logistica.set_node_tooltip_from_state(pos, nil, power) end } } @@ -159,5 +134,11 @@ function logistica.register_supplier(simpleName, maxTransferRate) end -logistica.register_supplier("Item", 1) -logistica.register_supplier("Stack", 99) +logistica.register_supplier("Passive Supplier", "simple", 32, { + "logistica_passive_supplier_top.png", + "logistica_passive_supplier_bottom.png", + "logistica_passive_supplier_side.png^[transformFX", + "logistica_passive_supplier_side.png", + "logistica_passive_supplier_side.png", + "logistica_passive_supplier_front.png", +}) -- default supplier diff --git a/logic/controller.lua b/logic/controller.lua index 7790e05..ce1dbaf 100644 --- a/logic/controller.lua +++ b/logic/controller.lua @@ -1,42 +1,19 @@ ---[[ -Outline of controller tick/s: -1. Gather request from each requester, add them to queue - - smart queue needed, unify request per requester -2. For the first N requests, check each supplier and if applicable fulfil request -3. Gather all storage slots - - cached, hopefully -4. For each storage slot, check each supplier, and pull up to S items per slot into storage -]] -local TIMER_DURATION_SHORT = 0.5 -local TIMER_DURATION_LONG = 2.0 +local TIMER_DURATION_LONG = 5 function logistica.start_controller_timer(pos, duration) if duration == nil then duration = TIMER_DURATION_LONG end - local timer = minetest.get_node_timer(pos) - timer:start(duration) + logistica.start_node_timer(pos, duration) end function logistica.on_controller_timer(pos, elapsed) - if pos then return false end -- - local node = minetest.get_node(pos) - if not node then return false end -- what? - if node.name:find("_disabled") then return false end -- disabled controllers don't do anything - - local had_demand = false + local node = minetest.get_node_or_nil(pos) + if not node then return true end -- what? + if not logistica.is_controller(node.name) then return false end local network = logistica.get_network_or_nil(pos) if not network then - logistica.on_controller_change(pos, nil) -- this should re-scan the network + logistica.on_controller_change(pos) -- this should re-scan the network end - network = logistica.get_network_or_nil(pos) - if not network then return true end -- something went wrong, retry again - - if had_demand then - logistica.start_controller_timer(pos, TIMER_DURATION_SHORT) - else - logistica.start_controller_timer(pos, TIMER_DURATION_LONG) - end - - return false + return true end diff --git a/logic/groups.lua b/logic/groups.lua index 78076d2..039f0bd 100644 --- a/logic/groups.lua +++ b/logic/groups.lua @@ -10,6 +10,7 @@ logistica.item_storage = {} logistica.tiers = {} logistica.TIER_ALL = "logistica_all_tiers" logistica.GROUP_ALL = "group:" .. logistica.TIER_ALL +logistica.TIER_CONTROLLER = "controller" function logistica.get_cable_group(tier) return "logistica_" .. tier .. "_cable" diff --git a/logic/injector.lua b/logic/injector.lua index be7de2e..c241371 100644 --- a/logic/injector.lua +++ b/logic/injector.lua @@ -38,12 +38,9 @@ function logistica.start_injector_timer(pos) end function logistica.on_injector_timer(pos, elapsed) + if not logistica.is_machine_on(pos) then return false end local networkId = logistica.get_network_id_or_nil(pos) - if not networkId then - logistica.toggle_machine_on_off(pos) - logistica.set_node_tooltip_from_state(pos) - return false - end + if not networkId then return false end logistica.set_node_tooltip_from_state(pos) local node = minetest.get_node_or_nil(pos) diff --git a/logic/network_cache.lua b/logic/network_cache.lua index b694b09..131a4ee 100644 --- a/logic/network_cache.lua +++ b/logic/network_cache.lua @@ -10,7 +10,7 @@ LOG_CACHE_MASS_STORAGE = { nodes = function (network) return network.mass_storage end, } LOG_CACHE_SUPPLIER = { - listName = "filter", + listName = "main", clear = function (network) network.supplier_cache = {} end, cache = function (network) return network.supplier_cache end, nodes = function (network) return network.suppliers end, @@ -38,7 +38,11 @@ end local function list_to_cache_nameset(list) local ret = {} - for i, item in ipairs(list) do ret[item:get_name()] = true end + for i, item in ipairs(list) do + if item:get_name() ~= "" then + ret[item:get_name()] = true + end + end return ret end @@ -90,10 +94,12 @@ local function update_network_cache(network, cacheOps) logistica.load_position(storagePos) local nodeMeta = get_meta(storagePos) local list = nodeMeta:get_inventory():get_list(listName) or {} - for _, itemStack in pairs(list) do + for _, itemStack in ipairs(list) do local name = itemStack:get_name() - if not cache[name] then cache[name] = {} end - cache[name][hash] = true + if name ~= "" then + if not cache[name] then cache[name] = {} end + cache[name][hash] = true + end end save_prev_cache(nodeMeta, listName, list_to_cache_nameset(list)) end @@ -112,12 +118,12 @@ local function update_network_cache_for_pos(pos, cacheOps) local cache = cacheOps.cache(network) local remAndAdd = diff(prevCacheItems, currCacheItems) for name, _ in pairs(remAndAdd[1]) do - local posCache = cache[name] - if posCache then posCache[hash] = nil end + if cache[name] then cache[name][hash] = nil end + if logistica.table_is_empty(cache[name]) then cache[name] = nil end end for name, _ in pairs(remAndAdd[2]) do - local posCache = cache[name] - if posCache then posCache[hash] = true end + if not cache[name] then cache[name] = {} end + if cache[name] then cache[name][hash] = true end end save_prev_cache(meta, listName, currCacheItems) end diff --git a/logic/network_storage.lua b/logic/network_storage.lua index b22156c..a5d3347 100644 --- a/logic/network_storage.lua +++ b/logic/network_storage.lua @@ -1,17 +1,30 @@ local MASS_STORAGE_LIST_NAME = "storage" local ITEM_STORAGE_LIST_NAME = "main" +local SUPPLIER_LIST_NAME = "main" local function get_meta(pos) logistica.load_position(pos) return minetest.get_meta(pos) end +local function updateSupplierCacheFor(supplierPosList) + for _, pos in ipairs(supplierPosList) do + logistica.update_cache_at_pos(pos, LOG_CACHE_SUPPLIER) + end +end + -- tries to take a stack from the network locations -- calls the collectorFunc with the stack - collectorFunc needs to return how many were left-over
-- `collectorFunc = function(stackToInsert)`
-- note that it may be called multiple times as the itemstack is gathered from mass storage function logistica.take_stack_from_network(stackToTake, network, collectorFunc, isAutomatedRequest) + if not network then return false end + -- first check suppliers + if logistica.take_stack_from_suppliers(stackToTake, network, collectorFunc, isAutomatedRequest) then + return + end + -- then check storages if stackToTake:get_stack_max() <= 1 then logistica.take_stack_from_item_storage(stackToTake, network, collectorFunc, isAutomatedRequest) else @@ -19,6 +32,52 @@ function logistica.take_stack_from_network(stackToTake, network, collectorFunc, end end +-- tries to take the given stack from the passive suppliers on the network +-- calls the collectorFunc with the stack when necessary +-- note that it may be called multiple times as the itemstack is gathered from mass storage +function logistica.take_stack_from_suppliers(stackToTake, network, collectorFunc, isAutomatedRequest) + local requestedAmount = stackToTake:get_count() + local remaining = requestedAmount + local stackName = stackToTake:get_name() + local validSupplers = network.supplier_cache[stackName] or {} + local modifiedPos = {} + for hash, _ in pairs(validSupplers) do + local supplierPos = minetest.get_position_from_hash(hash) + local supplierInv = get_meta(supplierPos):get_inventory() + local machineIsOn = logistica.is_machine_on(supplierPos) + local supplyList = (machineIsOn and supplierInv:get_list(SUPPLIER_LIST_NAME)) or {} + for i, supplyStack in ipairs(supplyList) do + if supplyStack:get_name() == stackName then + table.insert(modifiedPos, supplierPos) + local supplyCount = supplyStack:get_count() + if supplyCount >= remaining then -- enough to fulfil requested + local toSend = ItemStack(supplyStack) ; toSend:set_count(remaining) + local leftover = collectorFunc(toSend) + supplyStack:set_count(supplyCount - remaining + leftover) + supplierInv:set_stack(SUPPLIER_LIST_NAME, i, supplyStack) + updateSupplierCacheFor(modifiedPos) + return true + else -- not enough to fulfil requested + local toSend = ItemStack(supplyStack) + local leftover = collectorFunc(toSend) + remaining = remaining - (supplyCount - leftover) + supplyStack:set_count(leftover) + if leftover > 0 then -- for some reason we could not insert all - exit early + supplierInv:set_stack(SUPPLIER_LIST_NAME, i, supplyStack) + updateSupplierCacheFor(modifiedPos) + return true + end + end + end + end + -- if we get there, we did not fulfil the request from this supplier + -- but some items still may have been inserted + if machineIsOn then supplierInv:set_list(SUPPLIER_LIST_NAME, supplyList) end + end + updateSupplierCacheFor(modifiedPos) + return false +end + -- calls the collectorFunc with the stack - collectorFunc needs to return how many were left-over
-- `collectorFunc = function(stackToInsert)`
-- returns true if item successfully found and given to collector, false otherwise diff --git a/logic/requester.lua b/logic/requester.lua index 48ca804..69ec66c 100644 --- a/logic/requester.lua +++ b/logic/requester.lua @@ -139,12 +139,9 @@ function logistica.start_requester_timer(pos, duration) end function logistica.on_requester_timer(pos, elapsed) + if not logistica.is_machine_on(pos) then return false end local network = logistica.get_network_or_nil(pos) - if not network then - logistica.toggle_machine_on_off(pos) - logistica.set_node_tooltip_from_state(pos) - return false - end + if not network then return false end logistica.set_node_tooltip_from_state(pos) update_requester_actual_request(pos) if take_requested_items_from_network(pos, network) then diff --git a/logic/supplier.lua b/logic/supplier.lua index 8d1c7fe..459e30d 100644 --- a/logic/supplier.lua +++ b/logic/supplier.lua @@ -1,34 +1,12 @@ -local META_SUPPLIER_LISTNAME = "suptarlist" +local META_SUPPLIER_LIST = "main" -function logistica.get_supplier_target(pos) - local node = minetest.get_node_or_nil(pos) - if not node then return nil end - local shift = logistica.get_rot_directions(node.param2).backward - if not shift then return nil end - return {x = (pos.x + shift.x), - y = (pos.y + shift.y), - z = (pos.z + shift.z)} -end - -function logistica.get_supplier_target_list(pos) - logistica.load_position(pos) - local meta = minetest.get_meta(pos) - return meta:get_string(META_SUPPLIER_LISTNAME) -end - -function logistica.set_supplier_target_list(pos, listName) - logistica.load_position(pos) - local meta = minetest.get_meta(pos) - meta:set_string(META_SUPPLIER_LISTNAME, listName) -end - -function logistica.get_supplier_max_item_transfer(pos) +function logistica.get_supplier_inv_size(pos) local node = minetest.get_node_or_nil(pos) if not node then return 0 end local def = minetest.registered_nodes[node.name] - if def and def.logistica and def.logistica.supplier_transfer_rate then - return def.logistica.supplier_transfer_rate + if def and def.logistica and def.logistica.inventory_size then + return def.logistica.inventory_size else return 0 end @@ -39,15 +17,6 @@ function logistica.take_item_from_supplier(pos, stack) logistica.load_position(pos) if not logistica.is_machine_on(pos) then return ItemStack("") end local meta = minetest.get_meta(pos) - local canTake = math.min(stack:get_count(), logistica.get_supplier_max_item_transfer(pos)) - local copyStack = ItemStack(stack) - copyStack:set_count(canTake) - - local targetListName = meta:get_string(META_SUPPLIER_LISTNAME) - local targetPos = logistica.get_supplier_target(pos) - logistica.load_position(targetPos) - local targetInv = minetest.get_meta(targetPos):get_inventory() - local targetList = targetInv:get_list(targetListName) - if not targetList then copyStack:set_count(0); return copyStack end - return targetInv:remove_item(targetListName, copyStack) + local inv = meta:get_inventory() + return inv:remove_item(META_SUPPLIER_LIST, stack) end diff --git a/textures/logistica_item_supplier_back.png b/textures/logistica_item_supplier_back.png deleted file mode 100644 index 676c70356898464f497a900b1919e5ba4fb5a168..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2125 zcmaJ@c~BE)6kkv*MlE*0dW=d~L_tk9370GhXM$uj6gea~T3nJZ$;u|1W*3rh)K)Em zSS!%tU{w@5Q>`2hW9fL5qJRiGMaMF&Iu)3jI(|B`u2!c#g#>ms+$sJV_omXbdG8 zYG7G2j$u}-RcH+q(iS}?4hsvzL=sFQ5kL(AV>hvcO<-btISMC-955OSX=X{<#OFAP zOgfvDp(w=pgXCJx5VtwoLOGbV8Vpdt2uv)4iG^Zpq&~2b!_kx77@`5LlHbAN6Bupv;t06XGgS_un?*27+sq0u@W2`gvkCvro= zhl42+I-6+7!fF7JZQL|sBX99CDk(N5Zs(;(EDmVrJcA1fZZ>RawLxKMIRX>hh!(i| z(sP$iMi7^eNm%?bMMn_-((KZ%B`w6<_Ka&qI@D|Hyo$4AQ1Y!?N89}8HU_kSfd{*; z{(h}5Tv^wdttc+ZcX-Iot6M=qQ{&aLf_)KPcb}Z9y8BPBJ;Fono9_4Z z&vu_(nBlX{|l%b!uM}<8`(EbW`HJ zbbHn9yrP=(Y3oiunE$x*X+@iNL!`ky;LiOb_zs(Fj!$P0WQr&ExFEat%z_o-E9KEC z{-vLmg(pl{HC55|WSLL=(Rpj|R$ig(;sSTnE2{cNd3=71;TK-@K@c8Q=2NNP=99AX zf}m#6fV#1M-{1Kj$c{R1$%5(rqRQD|vCDz;es0SIZcla?{L7{1FKjTj>Ml>n zU%Opq-&@$#vB2y4p3suEOJDT72uPaL-$tIi?ClEO{N~xzT2Ozxc@8_!;vO?Gv2x)i zWa5^uy!DR9w diff --git a/textures/logistica_item_supplier_front.png b/textures/logistica_item_supplier_front.png deleted file mode 100644 index 1c22f47f0dc10fc47746da6172a5549b2c42fe9b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2305 zcmaJ@dsI_(9KV!22LP82~tN{qCSe9-T1$Rn*k?zZpm^ZkCl-{1Fj zSE!F$IMH{yF9bmowXy1W@a@MxKI6b=X_;9HLEbTBVltPkTP!!yRw0Jd>4eZ}wF4Z2 z6e_13Gg=4^PA4)*n-aO%a1?<_T!|RMbRwNSnlO{GD;XkTWn7|hrNt=25mmUa!YKy? zR)WJ|rE98EI>93~7CijZ($Si#^XdAvGi$QVdU z#LRJaIf^k> zk=usPoLp*kWH{ICy=qlc-R1ICJHyXk`LnU|%B^dz@X5)6 zDM259=Xzx`YOdPV88&r?BTQjz)y}rwNiV92Th|(Rp|)hf>!!wQp_Yr`{RhH=%8!iO z6!X&(%|+i6{wEUld0*_d{xm7bf00k6Z}!~!UBB<&+q&ppI&-9X`7BGB9;)7dqK12} zbzkx+vkY^|df(2{gmkv%6b61&IdRc%&pUSeBLy?3R;-_rR^Szbzr1_$%=-s-$29fN zTb)mwO2U_>L>mj|zToRrr=gEH*uoFvDcst2b;Kdjt^O=v34 z?{k@_buLWH&MVFdT0H>ecWTh3bNj<#U zA2{Bmznj<*D@r4kY&rMj_*18+YwF6$6}qbJZTj}yvQnSDODhk(G;KlDl&TGPEp-iV&9*wE z*1-?9{rq`fWm{k0weId5=2Go8%f7v@O=+LHN0rT5|7`j7Q2vhn8|D<9Uv{H@U&*DL zUe<(XyaH0oR~>oq``=v(`{CMm4%d3EubDXWfa+>P#U~q9G~ud~cN%+CTt)9|ZzkoZ zy;`yx{i40Iq#oK-lC`-cYfbt0@AmgG>2ai=Y>&?qIrHa76rDYH_kLX>thw!*^YaM7ws+?pIwT$Rf+r2Wc;IU@|0f61YU0#2QEBh}1MYBK3jhEB diff --git a/textures/logistica_item_supplier_side.png b/textures/logistica_item_supplier_side.png deleted file mode 100644 index 2a8a05ba3b13b5d1f33d626f2703971e498e8a30..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2258 zcmaJ@2~ZPf6kZq^HHuWhqn66LNGsK3Nq{g}5|EN0(T1iR5L}4cM@O`H%V@{iT5YG$iU(Hd0aaVkTD1Qr$f4GmY?AkX?|tw6?@CJb zX_Es*qeTz|1!_~(>EQD<;Thl$-dC4f*Fd>NvBBcuh1XhyA zVV9M*ahOYmczH4KT{uP&*sH?lsStxs4<|D$3CBueB~eI%2v)KtGnTGS=`seA3bF9K z9Yay4(u5^LKp#lQbqxz`xl=*+u z1>^;FyM^Hy&cfKcgX-g=8-BqMr2FM2F5LbyWu5NT>Q-x?YjC_KA0)1;2z_FD=77s| z+etK?M^hguGyS%0-nZ;4ZQrE<+EdLgHj-FE=?ag}Up2d85-Y zCJPqS(GeVER~9* z(OvLOoQ7on=f8f;4$A3+~`UImXO8ah6QV1-+y~lFVibRL%|Sg&~2#U`9!N zP1J4Sw2*-9rD;Ta-{M(RO7w-eeV6XFIDnn+3@jwD+0gFQ288bANZPC|8Rk!cAx)Xv7;W-gs{NNtD z9<^+#ZjK%KsWVndG-%(pJ~S@#q%Ca-zkFa-{6zE7*66$|2_1W5BP#0rD^sq2pt&MC z8GJHhcfgev>-8ZK!BYoRi3(#5SN~bFt6}QDMz-$s?6>mD_0XQ0lOBF}!*0Vlivo8m z+Ggf!BAXlLm4#W_HQr{7`u$VlTWtx_g zOq9mFE^?`7mH(GHi#3rRziRWs3$bQQJf6X8KLJV_DK~U2sWf zd)u~$#1Z2%amqILPpL*d))l1YC4dz;T# z4@HkI8h;^hzi04FbiEC4+O$BwDLXE9duYX-;YEMndYrX*Kz>`$3`b2(UEQVSE1(bP zNvoI3$1J+Jzbs@*gQPai+c zJS;9Y$EE6u=ZsrrjJ|v0g8Nuu2Rr1ldL&;u%v{Z*?3AIug03(HZC*TfV)iVQt`5>|h)4E~E5Hs}LhB2DCPG(Q k{4VblH_D0V!Uuna9TeaC@+6;DEBqDFYSPr6cjqkm4>oT#-~a#s diff --git a/textures/logistica_passive_supplier_bottom.png b/textures/logistica_passive_supplier_bottom.png new file mode 100644 index 0000000000000000000000000000000000000000..4b07b2285d75fa900c1f6c7eddc4a1767da455f1 GIT binary patch literal 2372 zcmaJ@dsGu=7N1}}OJiB6FVObbI8rRO$t00iW)mgrj1;jR{|whDr0g+;fvvImvJQbbu!+12BsRYX_B{gNP$YWv3|x!>>J z-@V^`O+HFqxgvl&p9?`yfI4280=|PhkG~)I+~u}JLC|zHq03-1G)bs|whAyKt;YpU zs}0}~B#m?0Fhd^B^7Ocwpk(l1Lo>`Hj50VqQX|yZ6u5qLn&BQJz6!gyUkl zQYQ)stT>DDoK})zP^S#`@}l6k=NN%`UKKV^24`rJc?#N&^CAV20wEmBO9iyujEE!>2_h6DVlf|R@EI4yVopBAEb>tJIFvYJuoE_x zpede*6VuZURtCcW=Z%pY4ddK4hn@5?8x06f;#Qnu8AK!yA(QoSCovHX#f+s3Bo6T) zKwUURoh3}apzcAQQ@2@YmS!xpZ9J$cF2>>K3_-eIY~sXhFH+WMeqG&aopKF^RTY55 zjTK=^OwSxJI+qPcQgDWL*bTU<0Az2GH*uc4pvi<2Co_};NGb!WA%jIxKLay=0aVZ= zZP$V(#DS65#*;ZzZNlj<6INxNjPQxIpB$mba+}Jl_J1h#1mW@6POH+79*3~ zWWEp@uLJ6hPD2|(a7(>}6OdY=NVd}^f&>_ovSK+;tx`mZBvDa(vB2j66b%Kogvq7E zSfC{qikI?5BEC?f6N^xh5EaK{c}cyBU~G&Si~WkKr|)@EqXA_Jmc+f1Zw}-n>yvyU zNqCwcB{9k@gPnXMZo(WS3&)bQnP6DLfaO>*gN2}QMv8dGh9t(gywWo=DKf>A6a=Z! zpz(l#w!0=d*W&q8oqMN`$Mg0SiWxj5k-;`QZFCrLqxZhx8a|YvO>7}%$K__wPBK_- zG7+G7E?%-{PIzE8g#uq6jaw92aKQG$Od^wS@hmDS@?6}$OHbMzz|MCDb`n@_$oO^x z!uWo~DX96Z7$$Eom zmI4#qE6u5{jBdW%c(;fS)13T!!N)USYo0qYoh&<%qD(mX=Z^w9nBA50FVu9O8ep1- zcXyl_*sN6_uFCw^H2!Ci%jM1H4cI@l!%2&VjA#I3x znq_#0s=IzLc!Acj=xu4Z^i25`>$SO*R_p%!&Y>?mcg^7T{x~dAYhDvHykC z=A`K^3_t0=bZp6~x{Ijmm9+Rz;ce-cYjisklS&p;xWnk-r*zJDE$z97PIm{MSXDlB zb(&*!@;ez<2lnD~cAg#b53WoYy~)|$xNYr0OV8u>Mvl2+4*&GDf$H|rJu9}K-`PL2 zFl^?XB0tTH_M(7*#C^NVh9ynE!Lyrgatns{q<ehLGRzX<7w!Q?vRq7-XOB)2L;vE zZ>tqu5BtOKg8$pmANUi$)c-yBP9GnwUmT%=497txcV^uQqQ^nu*I8;p`hdb`EK6Ru3l;k-_rR~dFYPSn)MsV;=R&%cPeW59suIIn(+uVmdG9c>EFp~}@|xj_T@BZHm2oRRyN z-sq_-S+;ONy(};|IM`&Gd8{{3QvGqs`QcQ_KmqkqO-Me^vYmUN9K+-M>`A9FK*s* z$(^b0qtVkLb?TdHY}2(qA|x^Vsv|ofvw{qR;ZmM_*DILbFX*d=4|jjk_9yrI`&aQx zY7;oBi167}O;}J~NG8cZk_nl?1nO%& ztbn*GSfwbX(oD3X1zDK_1mM=S-6OfA@a( z{`ZwsW-Lw#40t5~f}lXTOsWK*L7wM1Kk&Y_+9-ga$#O!ip*4zhp_VkWF&&wYvmItD zz#&Mq&|$^2g*Xl8;|9VaMsBsb5SY-3k*rt+M`4xVMnYCQyZLfUXRmL1FHAPE7m$fnZ^mD0bA z7z0U+7-`xnL{Yol&bIT}q|JbGZGVRP1SmObY?-!W-k#jA3GA0S_JL zCi|JtXdQ&!=oF+51jqLhjzMyXB*RAP2@}95Wl9n(PnHO{@d5#h$M$&uMH2#BLSG`q zXrRU8@c1k)m&J)!^SDAzoRB|1$4lx}1Y@JaXzWi^J$(<0bXp-z&?ej~`Q{+eMEfM4 zXd*n#FEn8mgBWqJbhsWXHql6ei8K%tO=z)PGp02X7Mv2Hp0P0zBV1nT37H6;;7J66 zR49Zpz(Cqc#yMBvMH8KSrw@j`Jtf4no|1?WtBuqZYjK_TzTg@@lp^)C9kbzy2GCAo zBvG#?K=Df849}dvU^Y2yUmuNH*o`<~duArl@wa#ql?Z(*Zr`QH?G9k)I|DljEH`v? zy8&TzKjId!6m4MpMf1=806~nu5}^K1)g6N7R2NrYm?wQRv|}M(aM`PVBqPJh+)(!RvfhfB9HH z<#IP%Z0ldIlJDD@{fj?qTWnII%diIfm&%>a95~#WxJ(*5P7e8sD3LYfND;~y%!G6J+}9pu;lrrvKpi+>)U$umbCPWh}!BX(*2ms{pMt6UbFM^i$|91 z80hjZUX~G~>FRI9!?v6lcrLsyb@&=%)A6bmdyG9poyQr5+Ax;WzkgTf@a~jNr?>P@ zw?|FCUFxTp)>#@DnAX&=-5uXP1%IpkTEI&8?yU0*(6#=lrwrZP6NTa6XKbofmQ6v> zv=Gn3fOgi;fFQpY zc>dTshgKXY#~lB=*UY$o^-=lxn0<2>ErR?W_bj;*(;B%aB5+eh^MmrUuLqvcZ2ls7 zP9>^5r@z`L2;+u@5JB!8%0oFDGq1nV-M~VAjad9KGc$drP`;zD*U8jncvumLZ*uih~ch8cp1A}!-$&7|9(K*#f5OA} z`>&`r!!VLjk+S@?j!Ol&K5ABL&$}(n_4iH>#`fw6OJh?gpU>XL-hcMxyto``924oE zbYkk1f}rwTOff2R55yT|@-&Jr_c)@KcS{`Sa|7fU})%3J?` D1mkem literal 0 HcmV?d00001 diff --git a/textures/logistica_passive_supplier_side.png b/textures/logistica_passive_supplier_side.png new file mode 100644 index 0000000000000000000000000000000000000000..13e470d37f69ecfb5b9bf36b48dbe1eea0fd55e0 GIT binary patch literal 2396 zcmaJ@dsGu=79U<)M5(ACY}v&)uxKgCB%xq4O?V~L@Q9`)2v}Vll1VZp$%M>=gj8F~ zv8~pgBcMV7i;pd~jcuy7Vg&_SEi9IoOIO!Lz*DK5Y70IJSw&^P1msa||Cl8A``!Dy z_q(sjcIleczCO?RKoI1cEEc7MZ$Ibb?G8RmN;NSMDiBu^0yAsiM5nXQjoh?!{g)Kt1a;t(eS z)Y)^?X+rfo>Q3Y_b%TbaNlHT+rh}T}Vj6zT5TyIbCKk-_BxQ-@kJWX$IoF`*qymt* zsUpmY>5&6UUTDCPbetkhMg^W!0J0bAN}MwX}DhfTfiBa*5qu33_Stv!kyvDn!yC{DlRh1 zP4*L^={lgU=p>{P1Q+EZoPm;sLaC8d5n6yz>8leN$w|T(4lgE#$z@G?07XNAEuktD zVKmUY}HuIXbiTs?(i3TH_Ku)#h_?d?4| zL^U~TdQJ}&%aRXQWncAR?ut%KXi~q9otHV%LPx*sPIyHWJz9BlYhuRuS7)%+>ez;L zqtwKDMWo(#<>SB*nJM%+{ z!|nxrn6pma=6EpJbu8kftsN~~uufbC@5uaquY6}}+P092(s0r-LFROv?cVfBeec5K zYs*J3c$i+1MrK_YI)Df4Y##LvtW0@$-R-?oJO2K$rf|LXVt zxpQ!_IehU=tGi@=x7F7-wYFxDgV*>JzOnJTPl029X6Gv84Ud!-^(9VoULbgl%`=Fz zDF~Xs#QC^EReOUV$UQPylptSODku@?!!rEe>N-8rXx}$naQ=2y`G4lMwfl$#FUEiP zw0Fr%iGJ~rr`XT0WKqekBOVuW8}em+KiaGrBYnamRp*}?M_x3V9b>=V|9RN7u{EeQ z-xFfAh>cZ;4iV+}r4h%Lfu{PCN2!6P@w+F^McN|b<01DhEvSF(+>hhq zT^;Q$_|iIiSpV9im$nie5xEiJWy@;^{ffU0(jBiaJCkvvGyT+&Bh3L}o<)p?)J55J z_R_*T_awb_TLuRD`#bMkc5Jz5;;ExkoPyDoM8Bf2 zH`6z_JsqDEDV8$xDtqpAJW$v5>GL~x?ihk`=?)Cb}j!zZ)N57?|yo|MH2zT%k1xR zuJM+v94y;$lJ#A#szuj*!4~9Z{kq=%`NX|CebrU=?xIBhO{RlockXIU8#5Eqp0~xz zeVZOWY+e7CcCUjFCzOEs39eb-F4x!s@J?UA)%H>~#^ z@IkpB13$ey^V`2YB8i)a7< literal 0 HcmV?d00001 diff --git a/textures/logistica_passive_supplier_top.png b/textures/logistica_passive_supplier_top.png new file mode 100644 index 0000000000000000000000000000000000000000..e49d650bd571f5c7be6aaefee7665ddae066950c GIT binary patch literal 2324 zcmaJ@dsGu=7N20Op-}5GRefuge07z zuE)N#ts)AIS|59S)T*uBf~_LLE-Ka1mDbm3tKd0$q+(m3EJj7?ev=@NYWv3|x!>>J z-@V^`P2S1RTM!xXd;|nRk(w-Z0r-yMp71d6xuMb~gP`#mQg2`l+FZ;;+l9E9HWEUw z-3f3AlBau}xT%z2VIyHB9SWqoz7c^*vjSO^q7`YKD#Au)mAeRCd7j=>UTR7;Bk5@o zaxVr5>;#L$UOVMrFs}j$@?zjOcZ?!%P=zg3AO>wdtfE~6oFYsSijcGjSne`gumW}F zkTH-Hh>c~P7>as49-&7nq+M22oSK@7iX^B+A^;i!#^+#hufV~?a}*&CHNlu%q?09S z2h4HeM%v9P5Cq`x5V_ej%`*{PkIT;pe8|58Bh%cB9{FDEcz2rMN_m( z2bz!oMnM}cbC|}CTZu)anY9gbjhyEa4(lHQE;7o^wZbb765K^H!eto26v!M2I?7Ga z6QSWcV8Q6Lv>5~^4HAw(8kH*FMO#P;U`)Y+`LHHKB@?I0WCDpWJ zB@s!a07vbU6JZYC7hEHRGPH&D;4VUG1?{9jloksK zisys#xjBKsY>I@TJ{q?0*a*P(#7v^2Z}BK9Ir>=Kp-Ye29l$Ph26hryZs_oK1H$lr zBphHVy1@2}X`1GRAl^SnQ2)p34nZ?2-IeENsTWRZNtdclzHQuP$o%LTwQbi&>m*ly|gM0M?PG~ESjLg}yeRCl7#M8v$6I~Hyft`!~I|p4kF8j3gdvQ}~EO?DQ{ftV*#vIrA{HToXUoM~9_;bSP&2dv#&oqSVZvMO~Sr_xc%ct(m z-S|?&uU|Jc`FH&LVNc(_bJ3OlijK?0Ez6&Rc3zrEZrO|TtBIp0POR|xZVj~a9^CD( zXFj$3EgXig-KrQod^_T^OxX-+XH0tIO2+eIjkHc%)ibf#qT5>+cPle#D*xN;zRLM`o`}S12wXqL=wMI}R=>KL&*-Wbys`JNvF=tJib~ z1`1~E+nso5IxqTY?NcSYV`HR$_Z_~Cb^KE1wdWLj*Vgdal6bySDR{~JwQpIUe4x2m zC9RNC>-;;XBrKLIAq}7J_jLAlb)CKX;hF2p4_kC#|hUuU~L~7^p~33M_UfY1SqyH*C@`JsqVDK$1vCXWqo~pL&LO|&u$;X`M-8|PkgJ{^11Kz*RMFfi0*y5s$|}DQ{v_E+@BduMxOeU I`6a9W4>@^W{{R30 literal 0 HcmV?d00001 diff --git a/util/common.lua b/util/common.lua index 7c5845d..2b41c99 100644 --- a/util/common.lua +++ b/util/common.lua @@ -99,11 +99,13 @@ function logistica.toggle_machine_on_off(pos) return nil end --- isOn is optional --- extraText is optional -function logistica.set_node_tooltip_from_state(pos, extraText) +-- `isOn` is optional +-- `extraText` is optional +-- `overrideState` is optional +function logistica.set_node_tooltip_from_state(pos, extraText, overrideState) if extraText == nil then extraText = "" else extraText = "\n"..extraText end - local isOn = logistica.is_machine_on(pos) + local isOn = overrideState + if isOn == nil then isOn = logistica.is_machine_on(pos) end logistica.load_position(pos) local meta = minetest.get_meta(pos) local node = minetest.get_node(pos) @@ -178,4 +180,8 @@ function logistica.on_timer_powered(func) return function(pos, elapsed) if logistica.is_machine_on(pos) then func(pos, elapsed) end end +end + +function logistica.table_is_empty(table) + return table == nil or (next(table) == nil) end \ No newline at end of file diff --git a/util/util.lua b/util/util.lua index fc2cf04..e267ea4 100644 --- a/util/util.lua +++ b/util/util.lua @@ -10,7 +10,7 @@ dofile(path.."/sound.lua") -- bad debug d = {} d.ttos = logistica.ttos -d.print = minetest.chat_send_all +d.log = minetest.chat_send_all function table.map(self, f) local t = {} for k,v in pairs(self) do