Program update

- Added onError and onDone events
- Added enviroments (you can add a env into the enviroment, but you will have to setup the enviroment before executing the program)
This commit is contained in:
Robert Jelic
2022-09-23 18:15:28 +02:00
parent 6907a44781
commit 9de0485538
3 changed files with 85 additions and 16 deletions

View File

@@ -2,14 +2,29 @@ local processes = {}
local process = {} local process = {}
local processId = 0 local processId = 0
function process:new(path, window, ...) function process:new(path, window, newEnv, ...)
local args = {...} local args = {...}
local newP = setmetatable({ path = path }, { __index = self }) local newP = setmetatable({ path = path }, { __index = self })
newP.window = window newP.window = window
window.current = term.current
window.redirect = term.redirect
newP.processId = processId newP.processId = processId
if(type(path)=="string")then if(type(path)=="string")then
newP.coroutine = coroutine.create(function() newP.coroutine = coroutine.create(function()
shell.execute(path, table.unpack(args)) local env = setmetatable(newEnv, {__index=_ENV})
env.shell = shell
env.basaltProgram=true
env.arg = {[0]=path, table.unpack(args)}
local pPath = shell.resolveProgram(path)
if(fs.exists(pPath))then
local file = fs.open(pPath, "r")
local content = file.readAll()
file.close()
local program = load(content, path, "bt", env)
if(program~=nil)then
return program()
end
end
end) end)
elseif(type(path)=="function")then elseif(type(path)=="function")then
newP.coroutine = coroutine.create(function() newP.coroutine = coroutine.create(function()
@@ -24,17 +39,21 @@ function process:new(path, window, ...)
end end
function process:resume(event, ...) function process:resume(event, ...)
local cur = term.current()
term.redirect(self.window) term.redirect(self.window)
if(self.filter~=nil)then if(self.filter~=nil)then
if(event~=self.filter)then return end if(event~=self.filter)then return end
self.filter=nil self.filter=nil
end end
local ok, result = coroutine.resume(self.coroutine, event, ...) local ok, result = coroutine.resume(self.coroutine, event, ...)
if ok then if ok then
self.filter = result self.filter = result
else else
error(result) printError(result)
end end
term.redirect(cur)
return ok, result
end end
function process:isDead() function process:isDead()

View File

@@ -52,8 +52,12 @@ return function(name)
elseif(format=="bimg")then elseif(format=="bimg")then
for y,v in ipairs(image[1])do for y,v in ipairs(image[1])do
self.parent:blit(obx, oby+y-1, unpack(v)) local t, f, b = unpack(v)
t = t:sub(1,w)
f = f:sub(1,w)
b = b:sub(1,w)
self.parent:blit(obx, oby+y-1, t, f, b)
if(y==h)then break end
end end
end end
end end

View File

@@ -12,6 +12,7 @@ return function(name, parent)
base:setZIndex(5) base:setZIndex(5)
local object local object
local cachedPath local cachedPath
local enviroment = {}
local function createBasaltWindow(x, y, width, height, self) local function createBasaltWindow(x, y, width, height, self)
local xCursor, yCursor = 1, 1 local xCursor, yCursor = 1, 1
@@ -432,6 +433,22 @@ return function(name, parent)
end end
end end
local function resumeProcess(self, event, ...)
local ok, result = curProcess:resume(event, ...)
if (ok==false)and(result~=nil)and(result~="Terminated")then
log(result)
local val = self:sendEvent("program_error", self, result)
log(val)
if(val~=false)then
error("Basalt Program - "..result)
end
end
if(curProcess:getStatus()=="dead")then
self:sendEvent("program_done", self)
end
end
local function mouseEvent(self, event, p1, x, y) local function mouseEvent(self, event, p1, x, y)
if (curProcess == nil) then if (curProcess == nil) then
return false return false
@@ -439,7 +456,7 @@ return function(name, parent)
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
if not (paused) then if not (paused) then
local absX, absY = self:getAbsolutePosition(self:getAnchorPosition(nil, nil, true)) local absX, absY = self:getAbsolutePosition(self:getAnchorPosition(nil, nil, true))
curProcess:resume(event, p1, x-absX+1, y-absY+1) resumeProcess(self, event, p1, x-absX+1, y-absY+1)
updateCursor(self) updateCursor(self)
end end
end end
@@ -452,7 +469,7 @@ return function(name, parent)
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
if not (paused) then if not (paused) then
if (self.draw) then if (self.draw) then
curProcess:resume(event, key, isHolding) resumeProcess(self, event, key, isHolding)
updateCursor(self) updateCursor(self)
end end
end end
@@ -511,9 +528,14 @@ return function(name, parent)
return "inactive" return "inactive"
end; end;
setEnviroment = function(self, env)
enviroment = env or {}
return self
end,
execute = function(self, path, ...) execute = function(self, path, ...)
cachedPath = path or cachedPath cachedPath = path or cachedPath
curProcess = process:new(cachedPath, pWindow, ...) curProcess = process:new(cachedPath, pWindow, enviroment, ...)
pWindow.setBackgroundColor(colors.black) pWindow.setBackgroundColor(colors.black)
pWindow.setTextColor(colors.white) pWindow.setTextColor(colors.white)
pWindow.clear() pWindow.clear()
@@ -521,7 +543,7 @@ return function(name, parent)
pWindow.setBackgroundColor(self.bgColor) pWindow.setBackgroundColor(self.bgColor)
pWindow.setTextColor(self.fgColor) pWindow.setTextColor(self.fgColor)
pWindow.basalt_setVisible(true) pWindow.basalt_setVisible(true)
curProcess:resume() resumeProcess(self)
paused = false paused = false
if(self.parent~=nil)then if(self.parent~=nil)then
self.parent:addEvent("mouse_click", self) self.parent:addEvent("mouse_click", self)
@@ -539,7 +561,7 @@ return function(name, parent)
stop = function(self) stop = function(self)
if (curProcess ~= nil) then if (curProcess ~= nil) then
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
curProcess:resume("terminate") resumeProcess(self, "terminate")
if (curProcess:isDead()) then if (curProcess:isDead()) then
if (self.parent ~= nil) then if (self.parent ~= nil) then
self.parent:setCursor(false) self.parent:setCursor(false)
@@ -572,7 +594,7 @@ return function(name, parent)
if (curProcess ~= nil) then if (curProcess ~= nil) then
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
if (paused == false) or (ign) then if (paused == false) or (ign) then
curProcess:resume(event, p1, p2, p3, p4) resumeProcess(self, event, p1, p2, p3, p4)
else else
table.insert(queuedEvent, { event = event, args = { p1, p2, p3, p4 } }) table.insert(queuedEvent, { event = event, args = { p1, p2, p3, p4 } })
end end
@@ -594,7 +616,7 @@ return function(name, parent)
if (curProcess ~= nil) then if (curProcess ~= nil) then
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
for _, value in pairs(events) do for _, value in pairs(events) do
curProcess:resume(value.event, table.unpack(value.args)) resumeProcess(self, value.event, table.unpack(value.args))
end end
end end
end end
@@ -699,7 +721,7 @@ return function(name, parent)
if(w~=pW)or(h~=pH)then if(w~=pW)or(h~=pH)then
pWindow.basalt_resize(pW, pH) pWindow.basalt_resize(pW, pH)
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
curProcess:resume("term_resize") resumeProcess(self, "term_resize")
end end
end end
pWindow.basalt_reposition(self:getAnchorPosition()) pWindow.basalt_reposition(self:getAnchorPosition())
@@ -708,7 +730,7 @@ return function(name, parent)
if not (curProcess:isDead()) then if not (curProcess:isDead()) then
if not (paused) then if not (paused) then
if(event ~= "terminate") then if(event ~= "terminate") then
curProcess:resume(event, p1, p2, p3, p4) resumeProcess(self, event, p1, p2, p3, p4)
end end
if (self:isFocused()) then if (self:isFocused()) then
local obx, oby = self:getAnchorPosition() local obx, oby = self:getAnchorPosition()
@@ -721,8 +743,7 @@ return function(name, parent)
end end
if (event == "terminate") then if (event == "terminate") then
log(self:isFocused()) resumeProcess(self, event)
curProcess:resume(event)
self.parent:setCursor(false) self.parent:setCursor(false)
return true return true
end end
@@ -746,6 +767,31 @@ return function(name, parent)
end end
end, end,
onError = function(self, ...)
log("Registered event")
for _,v in pairs(table.pack(...))do
if(type(v)=="function")then
self:registerEvent("program_error", v)
end
end
if(self.parent~=nil)then
self.parent:addEvent("other_event", self)
end
return self
end,
onDone = function(self, ...)
for _,v in pairs(table.pack(...))do
if(type(v)=="function")then
self:registerEvent("program_done", v)
end
end
if(self.parent~=nil)then
self.parent:addEvent("other_event", self)
end
return self
end,
init = function(self) init = function(self)
self.bgColor = self.parent:getTheme("ProgramBG") self.bgColor = self.parent:getTheme("ProgramBG")
end, end,