mirror of
https://github.com/Refactorio/RedMew.git
synced 2025-01-18 03:21:47 +02:00
infinite storage chests
This commit is contained in:
parent
5fe365a3d1
commit
90f38f33e6
17
control.lua
17
control.lua
@ -10,6 +10,7 @@ require 'walk_distance'
|
||||
require 'follow'
|
||||
require 'autodeconstruct'
|
||||
require 'corpse_util'
|
||||
require 'infinite_storage_chest'
|
||||
require 'fish_market'
|
||||
require 'reactor_meltdown'
|
||||
require 'map_layout'
|
||||
@ -140,9 +141,23 @@ Event.add(defines.events.on_console_chat, hodor)
|
||||
Event.add(
|
||||
defines.events.on_player_joined_game,
|
||||
function(event)
|
||||
local gui = game.players[event.player_index].gui
|
||||
local player = game.players[event.player_index]
|
||||
if not player or not player.valid then
|
||||
return
|
||||
end
|
||||
|
||||
if player.name == 'grilledham' then
|
||||
-- pink
|
||||
player.color = {r = 0.9290000202716064, g = 0.3860000739097595, b = 0.51399999856948853, a = 0.5}
|
||||
player.chat_color = {r = 1, g = 0.51999998092651367, b = 0.63300001621246338, a = 0.5}
|
||||
end
|
||||
|
||||
local gui = player.gui
|
||||
gui.top.style = 'slot_table_spacing_horizontal_flow'
|
||||
gui.left.style = 'slot_table_spacing_vertical_flow'
|
||||
|
||||
--[[ player.insert {name = 'infinity-chest', count = 10}
|
||||
player.insert {name = 'electric-energy-interface', count = 10}
|
||||
player.cheat_mode = true ]]
|
||||
end
|
||||
)
|
||||
|
214
infinite_storage_chest.lua
Normal file
214
infinite_storage_chest.lua
Normal file
@ -0,0 +1,214 @@
|
||||
local Event = require 'utils.event'
|
||||
local Gui = require 'utils.gui'
|
||||
local Token = require 'utils.global_token'
|
||||
local Task = require 'utils.Task'
|
||||
|
||||
local chests = {}
|
||||
local chests_data = {chests = chests}
|
||||
local chests_data_token = Token.register_global(chests_data)
|
||||
|
||||
Event.on_load(
|
||||
function()
|
||||
chests_data = Token.get_global(chests_data_token)
|
||||
chests = chests_data.chests
|
||||
end
|
||||
)
|
||||
|
||||
local chest_gui_frame_name = Gui.uid_name()
|
||||
|
||||
local function built_entity(event)
|
||||
local entity = event.created_entity
|
||||
if not entity or not entity.valid or entity.name ~= 'infinity-chest' then
|
||||
return
|
||||
end
|
||||
|
||||
local pos = entity.position
|
||||
|
||||
chests[pos.x .. ',' .. pos.y] = {entity = entity, storage = {}}
|
||||
end
|
||||
|
||||
local function mined_entity(event)
|
||||
local entity = event.entity
|
||||
if not entity or not entity.valid or entity.name ~= 'infinity-chest' then
|
||||
return
|
||||
end
|
||||
|
||||
local pos = entity.position
|
||||
|
||||
chests[pos.x .. ',' .. pos.y] = nil
|
||||
end
|
||||
|
||||
local function get_stack_size(name)
|
||||
local proto = game.item_prototypes[name]
|
||||
if not proto then
|
||||
game.print('item prototype not found')
|
||||
end
|
||||
|
||||
return proto.stack_size
|
||||
end
|
||||
|
||||
local function do_item(name, count, inv, storage)
|
||||
local size = get_stack_size(name)
|
||||
local diff = count - size
|
||||
|
||||
if diff == 0 then
|
||||
return
|
||||
end
|
||||
|
||||
local new_amount = 0
|
||||
|
||||
if diff > 0 then
|
||||
inv.remove({name = name, count = diff})
|
||||
local prev = storage[name] or 0
|
||||
new_amount = prev + diff
|
||||
elseif diff < 0 then
|
||||
local prev = storage[name]
|
||||
if not prev then
|
||||
return
|
||||
end
|
||||
|
||||
diff = math.min(prev, -diff)
|
||||
|
||||
new_amount = prev - diff
|
||||
inv.insert({name = name, count = diff})
|
||||
end
|
||||
|
||||
if new_amount == 0 then
|
||||
storage[name] = nil
|
||||
else
|
||||
storage[name] = new_amount
|
||||
end
|
||||
end
|
||||
|
||||
local function tick()
|
||||
local current = chests_data.next
|
||||
chests_data.next = next(chests, current)
|
||||
|
||||
if not current then
|
||||
return
|
||||
end
|
||||
|
||||
local chest = chests[current]
|
||||
|
||||
local entity = chest.entity
|
||||
if not entity or not entity.valid then
|
||||
chests[current] = nil
|
||||
else
|
||||
local storage = chest.storage
|
||||
local inv = entity.get_inventory(1) --defines.inventory.chest
|
||||
local contents = inv.get_contents()
|
||||
|
||||
for name, count in pairs(contents) do
|
||||
do_item(name, count, inv, storage)
|
||||
end
|
||||
|
||||
for name, _ in pairs(storage) do
|
||||
if not contents[name] then
|
||||
do_item(name, 0, inv, storage)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local function create_chest_gui_content(frame, player, chest)
|
||||
local storage = chest.storage
|
||||
local inv = chest.entity.get_inventory(1).get_contents()
|
||||
|
||||
local grid = frame.add {type = 'table', column_count = 10, style = 'slot_table'}
|
||||
|
||||
for name, count in pairs(storage) do
|
||||
local number = count + (inv[name] or 0)
|
||||
grid.add {
|
||||
type = 'sprite-button',
|
||||
sprite = 'item/' .. name,
|
||||
number = number,
|
||||
tooltip = name,
|
||||
style = 'slot_button'
|
||||
}
|
||||
end
|
||||
|
||||
for name, count in pairs(inv) do
|
||||
if not storage[name] then
|
||||
grid.add {
|
||||
type = 'sprite-button',
|
||||
sprite = 'item/' .. name,
|
||||
number = count,
|
||||
tooltip = name,
|
||||
style = 'slot_button'
|
||||
}
|
||||
end
|
||||
end
|
||||
|
||||
player.opened = frame
|
||||
end
|
||||
|
||||
local chest_gui_content_callback
|
||||
chest_gui_content_callback =
|
||||
Token.register(
|
||||
function(data)
|
||||
local player = data.player
|
||||
|
||||
if not player or not player.valid then
|
||||
return
|
||||
end
|
||||
|
||||
local opened = data.opened
|
||||
if not opened or not opened.valid then
|
||||
return
|
||||
end
|
||||
|
||||
if not player.connected then
|
||||
player.opened = nil
|
||||
opened.destroy()
|
||||
end
|
||||
|
||||
opened.clear()
|
||||
create_chest_gui_content(opened, player, data.chest)
|
||||
|
||||
Task.set_timeout_in_ticks(60, chest_gui_content_callback, data)
|
||||
end
|
||||
)
|
||||
|
||||
local function gui_opened(event)
|
||||
if not event.gui_type == defines.gui_type.entity then
|
||||
return
|
||||
end
|
||||
|
||||
local entity = event.entity
|
||||
if not entity or not entity.valid or entity.name ~= 'infinity-chest' then
|
||||
return
|
||||
end
|
||||
|
||||
local pos = entity.position
|
||||
local chest = chests[pos.x .. ',' .. pos.y]
|
||||
|
||||
if not chest then
|
||||
return
|
||||
end
|
||||
|
||||
local player = game.players[event.player_index]
|
||||
if not player or not player.valid then
|
||||
return
|
||||
end
|
||||
|
||||
local frame =
|
||||
player.gui.center.add {type = 'frame', name = chest_gui_frame_name, caption = 'Infinite Storage Chest'}
|
||||
|
||||
create_chest_gui_content(frame, player, chest)
|
||||
|
||||
Task.set_timeout_in_ticks(60, chest_gui_content_callback, {player = player, chest = chest, opened = frame})
|
||||
end
|
||||
|
||||
Event.add(defines.events.on_built_entity, built_entity)
|
||||
Event.add(defines.events.on_robot_built_entity, built_entity)
|
||||
Event.add(defines.events.on_player_mined_entity, mined_entity)
|
||||
Event.add(defines.events.on_robot_mined_entity, mined_entity)
|
||||
Event.on_nth_tick(1, tick)
|
||||
Event.add(defines.events.on_gui_opened, gui_opened)
|
||||
|
||||
Gui.on_custom_close(
|
||||
chest_gui_frame_name,
|
||||
function(event)
|
||||
event.element.destroy()
|
||||
end
|
||||
)
|
Loading…
Reference in New Issue
Block a user