199 lines
5.7 KiB
Lua
199 lines
5.7 KiB
Lua
|
require('forth')
|
||
|
|
||
|
function init_storage()
|
||
|
-- storage.valid = false
|
||
|
if not storage.valid then
|
||
|
storage.players = {}
|
||
|
storage.computers = {}
|
||
|
storage.guis = {}
|
||
|
storage.valid = true
|
||
|
end
|
||
|
end
|
||
|
|
||
|
function computer_for_ent(entity)
|
||
|
for _, computer in pairs(storage.computers) do
|
||
|
if computer.entity == entity then
|
||
|
return computer
|
||
|
end
|
||
|
end
|
||
|
return nil
|
||
|
end
|
||
|
|
||
|
script.on_event(defines.events.on_tick, function(event)
|
||
|
init_storage()
|
||
|
|
||
|
for _, computer in pairs(storage.computers) do
|
||
|
for _=1,250 do
|
||
|
local ok, result = pcall(forth_tick, computer.ctx)
|
||
|
if ok and result then break end
|
||
|
if not ok then
|
||
|
game.print(result)
|
||
|
computer.ctx = forth_initialize(computer.entity)
|
||
|
end
|
||
|
end
|
||
|
if #computer.ctx.outbuf > 0 then
|
||
|
local out = ''
|
||
|
for i, v in pairs(computer.ctx.outbuf) do
|
||
|
out = out..v
|
||
|
end
|
||
|
computer.screen = computer.screen..out
|
||
|
computer.ctx.outbuf = {}
|
||
|
end
|
||
|
end
|
||
|
|
||
|
for player_index, player in pairs(storage.players) do
|
||
|
if player.opened_combinator then
|
||
|
local computer = computer_for_ent(player.opened_combinator)
|
||
|
local ui = game.get_player(player_index).gui.screen.forth_combinator_gui
|
||
|
ui.forth_combinator_console.text = computer.screen
|
||
|
end
|
||
|
end
|
||
|
end)
|
||
|
|
||
|
script.on_event(defines.events.on_gui_text_changed, function(event)
|
||
|
if not event.element or event.element.name ~= 'forth_combinator_editor' then return end
|
||
|
|
||
|
local player = storage.players[event.player_index]
|
||
|
player.curtext = event.element.text
|
||
|
end)
|
||
|
|
||
|
function create_ui(player, computer)
|
||
|
local frame = player.gui.screen.add{type = "frame", name = "forth_combinator_gui", caption = "Console"}
|
||
|
frame.force_auto_center()
|
||
|
|
||
|
local editor = frame.add{type = 'text-box', name = 'forth_combinator_editor'}
|
||
|
editor.style.minimal_height = 600
|
||
|
editor.style.minimal_width = 800
|
||
|
editor.style.maximal_height = 600
|
||
|
editor.style.maximal_width = 800
|
||
|
editor.text = computer.script
|
||
|
local console = frame.add{type = 'text-box', name = 'forth_combinator_console'}
|
||
|
console.style.minimal_height = 600
|
||
|
console.style.minimal_width = 400
|
||
|
console.style.maximal_height = 600
|
||
|
console.style.maximal_width = 400
|
||
|
console.text = computer.screen
|
||
|
local run_button = frame.add{type = 'button', name = 'forth_combinator_run', caption = "Do Shit"}
|
||
|
-- console.selectable = false
|
||
|
|
||
|
|
||
|
|
||
|
return frame
|
||
|
end
|
||
|
|
||
|
script.on_event(defines.events.on_gui_opened, function(event)
|
||
|
if not event.entity or event.entity.name ~= 'forth-combinator' then return end
|
||
|
init_storage()
|
||
|
|
||
|
local player = game.get_player(event.player_index)
|
||
|
|
||
|
if not storage.players[event.player_index] then
|
||
|
storage.players[event.player_index] = {}
|
||
|
end
|
||
|
|
||
|
if player.gui.screen.forth_combinator_gui then
|
||
|
player.gui.screen.forth_combinator_gui.destroy()
|
||
|
end
|
||
|
|
||
|
if player.opened then
|
||
|
player.opened = nil
|
||
|
end
|
||
|
|
||
|
player.opened = create_ui(player, computer_for_ent(event.entity))
|
||
|
storage.players[event.player_index].opened_combinator = event.entity
|
||
|
end)
|
||
|
|
||
|
script.on_event(defines.events.on_gui_closed, function(event)
|
||
|
local player = game.get_player(event.player_index)
|
||
|
|
||
|
if player.gui.screen.forth_combinator_gui then
|
||
|
player.gui.screen.forth_combinator_gui.destroy()
|
||
|
if storage.players[event.player_index] then
|
||
|
storage.players[event.player_index].opened_combinator = nil
|
||
|
end
|
||
|
end
|
||
|
end)
|
||
|
|
||
|
script.on_event(defines.events.on_gui_click, function(event)
|
||
|
local player = game.get_player(event.player_index)
|
||
|
local entity = storage.players[event.player_index].opened_combinator
|
||
|
|
||
|
if event.element.name == 'forth_combinator_run' then
|
||
|
local computer = computer_for_ent(entity)
|
||
|
if not computer then
|
||
|
game.print('Invalid computer in gui click')
|
||
|
return
|
||
|
end
|
||
|
computer.ctx = forth_initialize(entity)
|
||
|
|
||
|
-- Hack, idc
|
||
|
local text = storage.players[event.player_index].curtext
|
||
|
for c in text:gmatch('.') do
|
||
|
table.insert(computer.ctx.keybuf, string.byte(c))
|
||
|
end
|
||
|
table.insert(computer.ctx.keybuf, 10)
|
||
|
|
||
|
computer.screen = ''
|
||
|
computer.script = text
|
||
|
end
|
||
|
end)
|
||
|
|
||
|
function OnBuiltEntity(event)
|
||
|
local entity = event.entity
|
||
|
if entity.name ~= 'forth-combinator' then return end
|
||
|
init_storage()
|
||
|
|
||
|
local computer = {
|
||
|
ctx = forth_initialize(entity),
|
||
|
entity = entity,
|
||
|
screen = '',
|
||
|
script = '',
|
||
|
}
|
||
|
|
||
|
table.insert(storage.computers, computer)
|
||
|
end
|
||
|
|
||
|
function OnEntityDied(event)
|
||
|
local entity = event.entity
|
||
|
if entity.name ~= 'forth-combinator' then return end
|
||
|
init_storage()
|
||
|
|
||
|
local removals = {}
|
||
|
for i, comp in pairs(storage.computers) do
|
||
|
if comp.entity == entity then
|
||
|
table.insert(removals, i)
|
||
|
end
|
||
|
end
|
||
|
for _, i in pairs(removals) do
|
||
|
table.remove(storage.computers, i)
|
||
|
end
|
||
|
end
|
||
|
|
||
|
script.on_event(defines.events.on_built_entity, OnBuiltEntity)
|
||
|
script.on_event(defines.events.on_robot_built_entity, OnBuiltEntity)
|
||
|
-- script.on_event(defines.events.on_pre_ghost_deconstructed, OnPreGhostDeconstructed)
|
||
|
script.on_event(defines.events.on_entity_died, OnEntityDied)
|
||
|
script.on_event(defines.events.on_pre_player_mined_item, OnEntityDied)
|
||
|
script.on_event(defines.events.on_robot_pre_mined, OnEntityDied)
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
-- player.surface.create_entity({
|
||
|
-- name = 'laser-beam',
|
||
|
-- position = entity.position,
|
||
|
-- source_position = entity.position,
|
||
|
-- target = player.position,
|
||
|
-- })
|