You've already forked ComfyFactorio
mirror of
https://github.com/ComfyFactory/ComfyFactorio.git
synced 2025-10-08 22:42:06 +02:00
266 lines
8.2 KiB
Lua
266 lines
8.2 KiB
Lua
local Event = require 'utils.event'
|
|
local Global = require 'utils.global'
|
|
local SpamProtection = require 'utils.spam_protection'
|
|
local BottomFrame = require 'utils.gui.bottom_frame'
|
|
local Gui = require 'utils.gui'
|
|
local Task = require 'utils.task_token'
|
|
|
|
local melee_mode_name = Gui.uid_name()
|
|
|
|
local state = {}
|
|
Global.register(state, function (s) state = s end)
|
|
|
|
local delay_add_inner_frame_token =
|
|
Task.register(
|
|
function (event)
|
|
local player_index = event.player_index
|
|
local player = game.get_player(player_index)
|
|
if not player or not player.valid then
|
|
return
|
|
end
|
|
|
|
local activate_custom_buttons = BottomFrame.get('activate_custom_buttons')
|
|
|
|
if activate_custom_buttons then
|
|
BottomFrame.add_inner_frame(
|
|
{
|
|
player = player,
|
|
element_name = melee_mode_name,
|
|
tooltip =
|
|
{
|
|
'modules_melee.tooltip'
|
|
},
|
|
sprite = 'item/pistol',
|
|
section_override = 1
|
|
}
|
|
)
|
|
end
|
|
end
|
|
)
|
|
|
|
local function create_gui_button(player)
|
|
if player.gui.top[melee_mode_name] then
|
|
return
|
|
end
|
|
local tooltip = { "modules_melee.tooltip" }
|
|
local b = player.gui.top.add(
|
|
{
|
|
type = 'sprite-button',
|
|
sprite = 'item/pistol',
|
|
name = melee_mode_name,
|
|
tooltip = tooltip
|
|
})
|
|
b.style.font_color = { r = 0.11, g = 0.8, b = 0.44 }
|
|
b.style.font = 'heading-1'
|
|
b.style.minimal_height = 40
|
|
b.style.maximal_width = 40
|
|
b.style.minimal_width = 38
|
|
b.style.maximal_height = 38
|
|
b.style.padding = 1
|
|
b.style.margin = 0
|
|
end
|
|
|
|
local function on_player_joined_game(event)
|
|
local activate_custom_buttons = BottomFrame.get('activate_custom_buttons')
|
|
local player = game.get_player(event.player_index)
|
|
|
|
if not activate_custom_buttons then
|
|
create_gui_button(player)
|
|
else
|
|
Task.set_timeout_in_ticks(5, delay_add_inner_frame_token, { player_index = event.player_index })
|
|
end
|
|
end
|
|
|
|
local function move_to_main(player, from, to)
|
|
local ret = {}
|
|
if from == nil or to == nil then
|
|
return {}
|
|
end
|
|
for i = 1, #from do
|
|
local c = from[i]
|
|
if c.valid_for_read then
|
|
if to.can_insert(c) then
|
|
local amt = to.insert(c)
|
|
ret[#ret + 1] = { name = c.name, count = amt, quality = c.quality }
|
|
c.count = c.count - amt
|
|
else
|
|
player.print('Unable to move ' .. c.name .. ' to main inventory')
|
|
end
|
|
end
|
|
end
|
|
return ret
|
|
end
|
|
|
|
local function change_to_melee(player)
|
|
local main_inv = player.get_main_inventory()
|
|
local gun_inv = player.get_inventory(defines.inventory.character_guns)
|
|
local ammo_inv = player.get_inventory(defines.inventory.character_ammo)
|
|
if main_inv == nil or gun_inv == nil or ammo_inv == nil then
|
|
return false
|
|
end
|
|
local gun_moved = move_to_main(player, gun_inv, main_inv)
|
|
local ammo_moved = move_to_main(player, ammo_inv, main_inv)
|
|
|
|
state[player.index] = { gun = gun_moved, ammo = ammo_moved }
|
|
return true
|
|
end
|
|
|
|
local function try_move_from_main(main, to, what)
|
|
if what == nil or main == nil or to == nil then
|
|
return
|
|
end
|
|
for i = 1, #what do
|
|
local amt_out = main.remove(what[i])
|
|
if amt_out > 0 then
|
|
local amt_in = to.insert({ name = what[i].name, count = amt_out, quality = what[i].quality })
|
|
if amt_in < amt_out then
|
|
main.insert({ name = what[i].name, count = amt_out - amt_in, quality = what[i].quality })
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|
|
local function change_to_ranged(player)
|
|
local moved = state[player.index]
|
|
if moved == nil then
|
|
moved = {}
|
|
end
|
|
local main_inv = player.get_main_inventory()
|
|
local gun_inv = player.get_inventory(defines.inventory.character_guns)
|
|
local ammo_inv = player.get_inventory(defines.inventory.character_ammo)
|
|
if main_inv == nil or gun_inv == nil or ammo_inv == nil then
|
|
return false
|
|
end
|
|
try_move_from_main(main_inv, gun_inv, moved.gun)
|
|
try_move_from_main(main_inv, ammo_inv, moved.ammo)
|
|
state[player.index] = {}
|
|
return true
|
|
end
|
|
|
|
local function on_gui_click(event)
|
|
local activate_custom_buttons = BottomFrame.get('activate_custom_buttons')
|
|
if activate_custom_buttons then
|
|
return
|
|
end
|
|
|
|
if not event.element then
|
|
return
|
|
end
|
|
if not event.element.valid then
|
|
return
|
|
end
|
|
if event.element.name ~= melee_mode_name then
|
|
return
|
|
end
|
|
local player = game.get_player(event.player_index)
|
|
if not player or not player.valid then
|
|
return
|
|
end
|
|
local mm = player.gui.top[melee_mode_name]
|
|
if mm and mm.valid and mm.sprite == 'item/pistol' then
|
|
if change_to_melee(player) then
|
|
player.print({ "modules_melee.change_to_melee" })
|
|
mm.sprite = 'technology/steel-axe'
|
|
else
|
|
player.print({ "modules_melee.change_to_melee_failed" })
|
|
end
|
|
else
|
|
if change_to_ranged(player) then
|
|
player.print({ "modules_melee.change_to_ranged" })
|
|
mm.sprite = 'item/pistol'
|
|
else
|
|
player.print({ "modules_melee.change_to_ranged_failed" })
|
|
end
|
|
end
|
|
end
|
|
|
|
local function moved_to_string(tbl)
|
|
local ret = ''
|
|
for i = 1, #tbl do
|
|
if ret ~= '' then
|
|
ret = ret .. ', '
|
|
end
|
|
ret = ret .. tbl[i].count .. ' ' .. tbl[i].name
|
|
end
|
|
return ret
|
|
end
|
|
|
|
local function player_inventory_changed(player_index, inv_id, name)
|
|
local player = game.get_player(player_index)
|
|
if not player or not player.valid then
|
|
return
|
|
end
|
|
|
|
local activate_custom_buttons = BottomFrame.get('activate_custom_buttons')
|
|
if activate_custom_buttons then
|
|
local old_frame = BottomFrame.get_frame_by_element_name(player, melee_mode_name)
|
|
if old_frame and old_frame.sprite == 'item/pistol' then
|
|
return
|
|
end
|
|
else
|
|
if player.gui.top[melee_mode_name] and player.gui.top[melee_mode_name].valid and player.gui.top[melee_mode_name].sprite == 'item/pistol' then
|
|
return
|
|
end
|
|
end
|
|
|
|
local inv = player.get_inventory(inv_id)
|
|
local moved = move_to_main(player, inv, player.get_main_inventory())
|
|
if #moved > 0 then
|
|
player.print({ "modules_melee.move_to_main_inventory", moved_to_string(moved) })
|
|
end
|
|
if not inv or not inv.is_empty() then
|
|
player.print({ "modules_melee.move_to_main_inventory_failed", name })
|
|
end
|
|
end
|
|
|
|
local function on_player_ammo_inventory_changed(event)
|
|
if event.tick < 200 then return end
|
|
player_inventory_changed(event.player_index, defines.inventory.character_ammo, 'ammo')
|
|
end
|
|
|
|
local function on_player_gun_inventory_changed(event)
|
|
if event.tick < 200 then return end
|
|
player_inventory_changed(event.player_index, defines.inventory.character_guns, 'guns')
|
|
end
|
|
|
|
Gui.on_click(
|
|
melee_mode_name,
|
|
function (event)
|
|
local is_spamming = SpamProtection.is_spamming(event.player, nil, 'Mtn v3 Spectate Ready Button')
|
|
if is_spamming then
|
|
return
|
|
end
|
|
|
|
local player = event.player
|
|
if not player or not player.valid or not player.connected then
|
|
return
|
|
end
|
|
|
|
local old_frame = BottomFrame.get_frame_by_element_name(player, melee_mode_name)
|
|
if old_frame and old_frame.sprite == 'item/pistol' then
|
|
if change_to_melee(player) then
|
|
player.print({ "modules_melee.change_to_melee" })
|
|
old_frame.sprite = 'technology/steel-axe'
|
|
BottomFrame.refresh_inner_frames(player)
|
|
else
|
|
player.print({ "modules_melee.change_to_melee_failed" })
|
|
end
|
|
else
|
|
if change_to_ranged(player) then
|
|
player.print({ "modules_melee.change_to_ranged" })
|
|
old_frame.sprite = 'item/pistol'
|
|
BottomFrame.refresh_inner_frames(player)
|
|
else
|
|
player.print({ "modules_melee.change_to_ranged_failed" })
|
|
end
|
|
end
|
|
|
|
on_gui_click(event)
|
|
end
|
|
)
|
|
|
|
Event.add(defines.events.on_player_joined_game, on_player_joined_game)
|
|
Event.add(defines.events.on_gui_click, on_gui_click)
|
|
Event.add(defines.events.on_player_ammo_inventory_changed, on_player_ammo_inventory_changed)
|
|
Event.add(defines.events.on_player_gun_inventory_changed, on_player_gun_inventory_changed)
|