145 lines
3.0 KiB
Lua
145 lines
3.0 KiB
Lua
-- Do not lose state when reset (chunkloading etc)
|
|
local state = (function ()
|
|
local path = ".state"
|
|
local state_table = {}
|
|
|
|
if fs.exists(path) then
|
|
local f = fs.open(path, "r")
|
|
state_table = textutils.unserialize(f.readAll())
|
|
f.close()
|
|
end
|
|
|
|
return setmetatable({}, {
|
|
__index = state_table,
|
|
|
|
__newindex = function(self, k, v)
|
|
rawset(state_table, k, v)
|
|
local f = fs.open(path, "w")
|
|
f.write(textutils.serialize(state_table))
|
|
f.close()
|
|
end,
|
|
})
|
|
end)()
|
|
|
|
-- Not sure whether this is a good idea
|
|
--[[
|
|
if state.x == nil or state.y == nil or state.z == nil or state.o == nil then
|
|
printError("[lib] position is not set")
|
|
printError("[lib] defaulting to 0, 0, 0, +z")
|
|
state.x = 0
|
|
state.y = 0
|
|
state.z = 0
|
|
state.o = 0
|
|
end
|
|
]]
|
|
|
|
local function setPosition(x, y, z, direction)
|
|
local o = ({
|
|
["+z"] = 0,
|
|
["-x"] = 1,
|
|
["-z"] = 2,
|
|
["+x"] = 3,
|
|
})[direction]
|
|
|
|
state.x = x
|
|
state.y = y
|
|
state.z = z
|
|
state.o = o
|
|
end
|
|
|
|
--[[
|
|
orientation:
|
|
0 = South (+z)
|
|
1 = West (-x)
|
|
2 = North (-z)
|
|
3 = East (+x)
|
|
]]
|
|
|
|
local function move(raw_move, position_update)
|
|
return function()
|
|
success, err = raw_move()
|
|
if not success then
|
|
return false, err
|
|
end
|
|
position_update()
|
|
return true
|
|
end
|
|
end
|
|
|
|
local fwd = move(turtle.forward, function()
|
|
if state.o == 1 or state.o == 3 then
|
|
state.x = state.x + ((state.o == 1) and -1 or 1)
|
|
elseif state.o == 0 or state.o == 2 then
|
|
state.z = state.z + ((state.o == 2) and -1 or 1)
|
|
end
|
|
end)
|
|
|
|
local back = move(turtle.back, function()
|
|
if state.o == 1 or state.o == 3 then
|
|
state.x = state.x + ((state.o == 1 and 1 or -1))
|
|
elseif state.o == 0 or state.o == 2 then
|
|
state.z = state.z + ((state.o == 2) and 1 or -1)
|
|
end
|
|
end)
|
|
|
|
local up = move(turtle.up, function()
|
|
state.y = state.y + 1
|
|
end)
|
|
|
|
local down = move(turtle.down, function()
|
|
state.y = state.y - 1
|
|
end)
|
|
|
|
local left = move(turtle.turnLeft, function()
|
|
state.o = (state.o - 1) % 4
|
|
end)
|
|
|
|
local right = move(turtle.turnRight, function()
|
|
state.o = (state.o + 1) % 4
|
|
end)
|
|
|
|
local function getOrientation()
|
|
return ({"+z", "-x", "-z", "+x"})[1 + state.o]
|
|
end
|
|
|
|
local function rotateTowards(direction)
|
|
local target_o = ({
|
|
["+z"] = 0,
|
|
["-x"] = 1,
|
|
["-z"] = 2,
|
|
["+x"] = 3,
|
|
})[direction]
|
|
|
|
if not target_o then
|
|
error(tostring(direction) .. " is not a valid direction.")
|
|
end
|
|
|
|
local delta_o = (target_o - state.o) % 4
|
|
|
|
if delta_o == 0 then
|
|
-- orientation already correct
|
|
elseif delta_o == 1 then
|
|
right()
|
|
elseif delta_o == 2 then
|
|
right()
|
|
right()
|
|
elseif delta_o == 3 then
|
|
left()
|
|
end
|
|
end
|
|
|
|
|
|
return {
|
|
state = state,
|
|
|
|
fwd = fwd,
|
|
back = back,
|
|
up = up,
|
|
down = down,
|
|
left = left,
|
|
right = right,
|
|
|
|
setPosition = setPosition,
|
|
getOrientation = getOrientation,
|
|
rotateTowards = rotateTowards,
|
|
} |