mirror of
https://github.com/20kdc/OC-KittenOS.git
synced 2024-11-09 20:18:07 +11:00
0d9583fcff
This isn't getting pushed until AmandaC's tested it. I'm not sure this is such a good idea, anyway ; if it's for load/save workflow improvements, wouldn't it be better to have a file access method that allows for file re-opening? That said, there's a limit to *that* before you just have to say, "Just use /data/".
221 lines
5.8 KiB
Lua
221 lines
5.8 KiB
Lua
-- This is released into the public domain.
|
|
-- No warranty is provided, implied or otherwise.
|
|
|
|
-- Used by filedialog to provide a sane relative environment.
|
|
-- Essentially, the filedialog is just a 'thin' UI wrapper over this.
|
|
-- Returns the root node.
|
|
|
|
local function dialog(name, parent)
|
|
return {
|
|
name = name,
|
|
list = function () return {{"Back", function () return nil, parent end}} end,
|
|
unknownAvailable = false,
|
|
selectUnknown = function (text) end
|
|
}
|
|
end
|
|
|
|
local getFsNode, getRoot
|
|
local setupCopyNode
|
|
function setupCopyNode(parent, myRoot, op, complete)
|
|
local function handleResult(aRes, res)
|
|
if aRes then
|
|
return complete(res, true)
|
|
else
|
|
return nil, setupCopyNode(parent, res, op, complete)
|
|
end
|
|
end
|
|
return {
|
|
name = "(" .. op .. ") " .. myRoot.name,
|
|
list = function ()
|
|
local l = {}
|
|
table.insert(l, {"Cancel Operation: " .. op, function ()
|
|
complete(nil, false)
|
|
return false, parent
|
|
end})
|
|
for _, v in ipairs(myRoot.list()) do
|
|
table.insert(l, {v[1], function ()
|
|
return handleResult(v[2]())
|
|
end})
|
|
end
|
|
return l
|
|
end,
|
|
unknownAvailable = myRoot.unknownAvailable,
|
|
selectUnknown = function (tx)
|
|
return handleResult(myRoot.selectUnknown(tx))
|
|
end
|
|
}
|
|
end
|
|
local function setupCopyVirtualEnvironment(fs, parent, fwrap, impliedName)
|
|
if not fwrap then
|
|
return false, dialog("Could not open source", parent)
|
|
end
|
|
local myRoot = getRoot(fs, true, impliedName)
|
|
-- Setup wrapping node
|
|
return setupCopyNode(parent, myRoot, "Copy", function (fwrap2, intent)
|
|
if not fwrap2 then
|
|
fwrap.close()
|
|
if intent then
|
|
return false, dialog("Could not open dest.", parent)
|
|
end
|
|
return false, parent
|
|
end
|
|
local data = fwrap.read(neo.readBufSize)
|
|
while data do
|
|
fwrap2.write(data)
|
|
data = fwrap.read(neo.readBufSize)
|
|
end
|
|
fwrap.close()
|
|
fwrap2.close()
|
|
return false, dialog("Completed copy.", parent)
|
|
end)
|
|
end
|
|
function getFsNode(fs, parent, fsc, path, mode, impliedName)
|
|
local va = fsc.address:sub(1, 4)
|
|
local fscrw = not fsc.isReadOnly()
|
|
local dir = path:sub(#path, #path) == "/"
|
|
local confirmedDel = false
|
|
local t
|
|
local function selectUnknown(text)
|
|
-- Relies on text being nil if used in leaf node
|
|
local rt, re = require("sys-filewrap").create(fsc, path .. (text or ""), mode)
|
|
if not rt then
|
|
return false, dialog("Open Error: " .. tostring(re), parent)
|
|
end
|
|
return true, rt
|
|
end
|
|
t = {
|
|
name = ((dir and "DIR: ") or "FILE: ") .. va .. path,
|
|
list = function ()
|
|
local n = {}
|
|
n[1] = {"..", function ()
|
|
return nil, parent
|
|
end}
|
|
if dir then
|
|
for k, v in ipairs(fsc.list(path)) do
|
|
local nm = "F: " .. v
|
|
local fp = path .. v
|
|
if fsc.isDirectory(fp) then
|
|
nm = "D: " .. v
|
|
end
|
|
n[k + 1] = {nm, function () return nil, getFsNode(fs, t, fsc, fp, mode, impliedName) end}
|
|
end
|
|
end
|
|
if fscrw then
|
|
if dir then
|
|
table.insert(n, {"Mk. Directory", function ()
|
|
return nil, {
|
|
name = "MKDIR...",
|
|
list = function () return {{
|
|
"Cancel", function ()
|
|
return false, t
|
|
end
|
|
}} end,
|
|
unknownAvailable = true,
|
|
selectUnknown = function (text)
|
|
fsc.makeDirectory(path .. text)
|
|
return nil, dialog("Done!", t)
|
|
end
|
|
}
|
|
end})
|
|
end
|
|
if path ~= "/" then
|
|
local delText = "Delete"
|
|
if confirmedDel then
|
|
delText = "Delete <ARMED>"
|
|
end
|
|
table.insert(n, {delText, function ()
|
|
if not confirmedDel then
|
|
confirmedDel = true
|
|
return nil, t
|
|
end
|
|
fsc.remove(path)
|
|
return nil, dialog("Done.", parent)
|
|
end})
|
|
else
|
|
table.insert(n, {"Relabel Disk", function ()
|
|
return nil, {
|
|
name = "Disk Relabel...",
|
|
list = function () return {{
|
|
fsc.getLabel() or "Cancel",
|
|
function ()
|
|
return false, t
|
|
end
|
|
}} end,
|
|
unknownAvailable = true,
|
|
selectUnknown = function (tx)
|
|
fsc.setLabel(tx)
|
|
return false, t
|
|
end
|
|
}
|
|
end})
|
|
end
|
|
end
|
|
if not dir then
|
|
table.insert(n, {"Copy", function ()
|
|
local rt, re = require("sys-filewrap").create(fsc, path, false)
|
|
if not rt then
|
|
return false, dialog("Open Error: " .. tostring(re), parent)
|
|
end
|
|
return nil, setupCopyVirtualEnvironment(fs, parent, rt, path:match("[^/]*$") or "")
|
|
end})
|
|
if (fscrw or mode == false) and (mode ~= nil) then
|
|
local tx = "Open"
|
|
if mode == true then
|
|
tx = "Save (Overwrite)"
|
|
elseif mode == "append" then
|
|
tx = "Append"
|
|
end
|
|
if fscrw or mode == false then
|
|
table.insert(n, {tx, selectUnknown})
|
|
end
|
|
end
|
|
elseif impliedName then
|
|
table.insert(n, {"Implied: " .. impliedName, function ()
|
|
return selectUnknown(impliedName)
|
|
end})
|
|
end
|
|
return n
|
|
end,
|
|
unknownAvailable = dir and (mode ~= nil) and ((mode == false) or fscrw),
|
|
selectUnknown = selectUnknown
|
|
}
|
|
return t
|
|
end
|
|
function getRoot(fs, mode, defName)
|
|
local t
|
|
t = {
|
|
name = "DRVS:",
|
|
list = function ()
|
|
local l = {}
|
|
for fsi in fs.list() do
|
|
local id = fsi.getLabel()
|
|
if fsi == fs.primary then
|
|
id = "NEO" .. ((id and (":" .. id)) or " Disk")
|
|
elseif fsi == fs.temporary then
|
|
id = "RAM" .. ((id and (" " .. id)) or "Disk")
|
|
else
|
|
id = id or "Disk"
|
|
end
|
|
local used, total = fsi.spaceUsed(), fsi.spaceTotal()
|
|
local amount = string.format("%02i", math.ceil((used / total) * 100))
|
|
local mb = math.floor(total / (1024 * 1024))
|
|
if fsi.isReadOnly() then
|
|
id = "RO " .. amount .. "% " .. mb .. "M " .. id
|
|
else
|
|
id = "RW " .. amount .. "% " .. mb .. "M " .. id
|
|
end
|
|
table.insert(l, {fsi.address:sub(1, 4) .. " " .. id, function ()
|
|
return nil, getFsNode(fs, t, fsi, "/", mode, defName)
|
|
end})
|
|
end
|
|
return l
|
|
end,
|
|
unknownAvailable = false,
|
|
selectUnknown = function (text)
|
|
return false, dialog("Ow, that hurt...", t)
|
|
end
|
|
}
|
|
return t
|
|
end
|
|
return getRoot
|