Computercraft Mouse File Browser by Stiepen irc(Kilobyte), Cruor, BigSHinyToys
--[[
Mouse File Browser
by:
Stiepen irc(Kilobyte)
Cruor
BigSHinyToys
note: send link to nightin9ale on CC forums
--]]
local tArgs = {...}
local ver = "1.4"
local sTitle = "File Browser"
local bugTest, norun, dir, showAll
local _tArgs = {}
local config = "mouse.cfg"
local temp
if shell and shell.getRunningProgram then
temp = shell.getRunningProgram()
end
temp = temp or "/bla"
local localPath = string.sub(temp,1,#temp-string.len(fs.getName(temp)))
temp = nil -- just because not needed
-- load config file
local configSet = {}
local cnf = {}
if fs.exists(localPath.."/"..config) then
local file = fs.open(localPath.."/"..config,"r")
if file then
local item = file.readLine()
while item do
table.insert(cnf,item)
item = file.readLine()
end
file.close()
end
end
for i = 1,10 do
local test,data = pcall(textutils.unserialize,cnf[i])
if test then
configSet[i] = data
else
configSet[i] = nil
end
end
cnf = nil
-- color configuration work in progress
local titleBar = configSet[1] or {txt = colors.black,back = colors.blue}
local addressBar = configSet[2] or {txt = colors.black,back = colors.lightGray}
local itemWindo = configSet[3] or {txt = colors.black,back = colors.cyan}
local rcmList = configSet[4] or {txt = colors.black,back = colors.lightGray} -- rcm = Right Click Menu List
local rcmTitle = configSet[5] or {txt = colors.black,back = colors.blue}
local dialogTitle = configSet[6] or {txt = colors.black,back = colors.blue}
local dialogWindo = configSet[7] or {txt = colors.black,back = colors.white}
local scrollCol = configSet[8] or {off = colors.gray, button = colors.gray,back = colors.lightGray}
local tIcons = configSet[9] or {
back = {tCol = "lightGray",bCol = "blue",txt = " < "},
disk = {tCol = "lime",bCol = "green",txt = "[*]"},
audio = {tCol = "yellow",bCol = "red",txt = "(o)"},
folder = {tCol = "lightGray",bCol = "blue",txt = "[=]"},
file = {tCol = nil ,bCol = nil ,txt = nil}
}
local customLaunch = configSet[10] or {
["Edit"] = "rom/programs/edit",
["Paint"] = "rom/programs/color/paint"
}
local function saveCFG(overWrite)
if not fs.exists(localPath.."/"..config) or overWrite then
local cnf = {}
local file = fs.open(localPath.."/"..config,"w")
if file then
file.write(textutils.serialize(titleBar).."\n")
file.write(textutils.serialize(addressBar).."\n")
file.write(textutils.serialize(itemWindo).."\n")
file.write(textutils.serialize(rcmList).."\n")
file.write(textutils.serialize(rcmTitle).."\n")
file.write(textutils.serialize(dialogTitle).."\n")
file.write(textutils.serialize(dialogWindo).."\n")
file.write(textutils.serialize(scrollCol).."\n")
file.write(textutils.serialize(tIcons).."\n")
file.write(textutils.serialize(customLaunch).."\n")
file.close()
elseif overWrite then
end
end
end
saveCFG()
-- end configuration
local function help()
print([[Usage: browser [-d] [-h] [-a] [-u] [--debug] [--help] [--dir <dir>] [--all] [--update]
--debug or -d: enable debug mode
--help or -h: display this screen
--dir: define initial directory
--all or -a: show hidden files
--update -u: update]])
end
local function inBouwndry(clickX,clickY,boxX,boxY,width,hight)
return ( clickX >= boxX and clickX < boxX + width and clickY >= boxY and clickY < boxY + hight )
end
local function update()
print("Checking for Updates")
local isHTTP = false
local response
if http then
isHTTP = true
print("http on")
response = http.get("http://pastebin.com/raw.php?i=rLbnyM1U")
end
local flag = false
local isNewFlag = false
local newVerID
if response and isHTTP then
print("recived")
local sInfo = response.readLine()
print(sInfo)
while sInfo do
print(sInfo)
if flag then
if sInfo == ver then
print("Mouse File Browser is up to date")
break
else
newVerID = sInfo
flag = false
isNewFlag = true
end
elseif sInfo == sTitle then
flag = true
elseif isNewFlag then
isNewFlag = sInfo
response.close()
break
end
sInfo = response.readLine()
end
if isNewFlag then
print("New vershion avalible "..newVerID)
print('downloading to \Browser')
if fs.exists("Browser") then
write("Browser exists OverWrite Browser Y/N : ")
local input = string.lower(read())
while input ~= "y" and input ~= "n" do
print("y or n required")
input = string.lower(read())
end
if input == "y" then
print("Over Writeing Browser")
print("Downloading new File")
local response = http.get("http://pastebin.com/raw.php?i="..isNewFlag)
if response then
print("file downloaded")
print("installing")
fs.delete("Browser")
local handel = fs.open("Browser","w")
if handel then
handel.write(response.readAll())
handel.close()
print("Update Complete")
end
response.close()
end
else
print("Update aborted")
end
else
print("Downloading new File")
local response = http.get("http://pastebin.com/raw.php?i="..isNewFlag)
if response then
print("file downloaded")
print("installing")
local handel = fs.open("Browser","w")
if handel then
handel.write(response.readAll())
handel.close()
print("Update Complete")
end
response.close()
end
end
end
elseif isHTTP then
print("Error downloading update file Please contact BigSHinyToys on the CC forums")
print("http://www.computercraft.info/forums2/index.php?/topic/5509-advanced-computer-mouse-file-browser/")
elseif not isHTTP then
print("HTTP API is turned off")
print("Access Computer Craft Configer and change line")
print([[enableapi_http {
# Enable the "http" API on Computers
general=false
}
TO THIS :
enableapi_http {
# Enable the "http" API on Computers
general=true
}]])
end
notCMD = false
norun = true
end
for a = 1, #tArgs do
if tArgs[a]:sub(1,2) == "--" then
local cmd = tArgs[a]:sub(3):lower()
if cmd == "debug" then
bugTest = true
elseif cmd == "help" then
help()
norun = true
elseif cmd == "dir" then
dir = tArgs[a+1]
a = a + 1
elseif cmd == "all" then
showAll = true
elseif cmd == "update" then
update()
end
elseif tArgs[a]:sub(1,1) == "-" then
for b = 2, #tArgs[a] do
cmd = tArgs[a]:sub(b, b)
if cmd == "d" then
bugTest = true
elseif cmd == "h" then
help()
norun = true
elseif cmd == "p" then
dir = tArgs[a+1]
a = a + 1
elseif cmd == "a" then
showAll = true
elseif cmd == "u" then
update()
end
end
else
table.insert(_tArgs, tArgs[a])
end
end
if (not dir) and shell and shell.dir then
dir = shell.dir()
end
if dir and shell and shell.resolve then
dir = shell.resolve(dir)
end
dir = dir or "/"
if bugTest then -- this is that the var is for testing
print("Dir: "..dir)
os.startTimer(4)
os.pullEvent()
end
local function clear()
term.setBackgroundColor(colors.black)
term.setTextColor(colors.white)
term.clear()
term.setCursorBlink(false)
term.setCursorPos(1,1)
end
--[[
Code thanks to Cruor
http://www.computercraft.info/forums2/index.php?/topic/5802-support-for-shell/
]]--
local function fixArgs(...)
local tReturn={}
local str=table.concat({...}," ")
local sMatch
while str and #str>0 do
if string.sub(str,1,1)=="\"" then
sMatch, str=string.match(str, "\"(.-)\"%s*(.*)")
else
sMatch, str=string.match(str, "(%S+)%s*(.*)")
end
table.insert(tReturn,sMatch)
end
return tReturn
end
--[[ end Cruor function ]]--
-- modified read made to play nice with coroutines
local function readMOD( _sReplaceChar, _tHistory,_wdth)
local sLine = ""
term.setCursorBlink( true )
local nHistoryPos = nil
local nPos = 0
if _sReplaceChar then
_sReplaceChar = string.sub( _sReplaceChar, 1, 1 )
end
local sx, sy = term.getCursorPos()
local w, h = term.getSize()
if _wdth and type(_wdth) == "number" then
w = sx + _wdth - 1
end
local function redraw( _sCustomReplaceChar )
local nScroll = 0
if sx + nPos >= w then
nScroll = (sx + nPos) - w
end
term.setCursorPos( sx + _wdth - 1, sy )
term.write(" ")
term.setCursorPos( sx, sy )
local sReplace = _sCustomReplaceChar or _sReplaceChar
if sReplace then
term.write( string.rep(sReplace,_wdth) )
else
term.write( string.sub( sLine, nScroll + 1 ,nScroll + _wdth) )
end
term.setCursorPos( sx + nPos - nScroll, sy )
end
while true do
local sEvent, param = os.pullEvent()
if sEvent == "char" then
sLine = string.sub( sLine, 1, nPos ) .. param .. string.sub( sLine, nPos + 1 )
nPos = nPos + 1
redraw()
elseif sEvent == "key" then
if param == keys.left then
-- Left
if nPos > 0 then
nPos = nPos - 1
redraw()
end
elseif param == keys.right then
-- Right
if nPos < string.len(sLine) then
nPos = nPos + 1
redraw()
end
elseif param == keys.up or param == keys.down then
-- Up or down
if _tHistory then
redraw(" ");
if param == keys.up then
-- Up
if nHistoryPos == nil then
if #_tHistory > 0 then
nHistoryPos = #_tHistory
end
elseif nHistoryPos > 1 then
nHistoryPos = nHistoryPos - 1
end
else
-- Down
if nHistoryPos == #_tHistory then
nHistoryPos = nil
elseif nHistoryPos ~= nil then
nHistoryPos = nHistoryPos + 1
end
end
if nHistoryPos then
sLine = _tHistory[nHistoryPos]
nPos = string.len( sLine )
else
sLine = ""
nPos = 0
end
redraw()
end
elseif param == keys.backspace then
-- Backspace
if nPos > 0 then
redraw(" ");
sLine = string.sub( sLine, 1, nPos - 1 ) .. string.sub( sLine, nPos + 1 )
nPos = nPos - 1
redraw()
end
elseif param == keys.home then
-- Home
nPos = 0
redraw()
elseif param == keys.delete then
if nPos < string.len(sLine) then
redraw(" ");
sLine = string.sub( sLine, 1, nPos ) .. string.sub( sLine, nPos + 2 )
redraw()
end
elseif param == keys["end"] then
-- End
nPos = string.len(sLine)
redraw()
end
elseif sEvent == "redraw" then
redraw()
elseif sEvent == "return" then
term.setCursorBlink( false )
return sLine
end
end
term.setCursorBlink( false )
return sLine
end
-- end modified read
local function printC(posX,posY,textCol,backCol,text)
term.setCursorPos(posX,posY)
term.setTextColor(colors[textCol] or textCol)
term.setBackgroundColor(colors[backCol] or backCol)
term.write(text)
end
local function InputBox(title)
local boxW,boxH = 26,3
local termX,termY = term.getSize()
local ofsX,ofsY = math.ceil((termX/2) - (boxW/2)) , math.ceil((termY/2) - (boxH/2)) -- offset from top left
local options = {"ok","cancel"}
local selected = 1
local space = 0
local range = {}
for i = 1,#options do
range[i] = {s = space,f = space + string.len(options[i])}
space = space + string.len(options[i])+3
end
local ofC = (boxW/2) - (space/2)
local function drawBox()
printC(ofsX,ofsY,colors.black,colors.blue,string.rep(" ",boxW))
printC(ofsX+1,ofsY,colors.black,colors.blue,(title or "User Input"))
printC(ofsX,ofsY+1,colors.black,colors.white,string.rep(" ",boxW))
printC(ofsX,ofsY+2,colors.black,colors.white,string.rep(" ",boxW))
printC(ofsX,ofsY+3,colors.black,colors.white,string.rep(" ",boxW))
for i = 1,#options do
if i == selected then
term.setBackgroundColor(colors.lightGray)
term.setCursorPos(range[i].s + ofC + ofsX - 1,ofsY + 3)
term.write("["..options[i].."]")
term.setBackgroundColor(colors.white)
term.write(" ")
else
term.setCursorPos(range[i].s + ofC + ofsX - 1,ofsY + 3)
term.write(" "..options[i].." ")
end
end
printC(ofsX+2,ofsY+2,colors.black,colors.lightGray,string.rep(" ",boxW-4))
end
drawBox()
term.setCursorPos(ofsX+2,ofsY+2)
local co = coroutine.create(function() return readMOD(nil,nil,boxW - 4) end)
while true do
local event = {os.pullEvent()}
if event[1] == "key" or event[1] == "char" then
if event[2] == 28 then
local test,data = coroutine.resume(co,"return")
return data
else
coroutine.resume(co,unpack(event))
end
elseif event[1] == "mouse_click" then
if event[4] == ofsY + 3 then
for i = 1,#options do
if event[3] >= range[i].s + ofC + ofsX - 1 and event[3] <= range[i].f + ofC + ofsX then
if options[i] == "ok" then
local test,data = coroutine.resume(co,"return")
return data
elseif options[i] == "cancel" then
return false
end
end
end
end
end
end
end
local function dialogBox(title,message,options, h, w)
term.setCursorBlink(false)
local selected = 1
title = title or ""
message = message or ""
options = options or {}
local boxW,boxH = (w or 26), (h or 3)
local termX,termY = term.getSize()
local ofsX,ofsY = math.ceil((termX/2) - (boxW/2)) , math.ceil((termY/2) - (boxH/2)) -- offset from top left
local space = 0
local range = {}
for i = 1,#options do
range[i] = {s = space,f = space + string.len(options[i])}
space = space + string.len(options[i])+3
end
local ofC = math.ceil((boxW/2)) - math.ceil((space/2))
local function drawBox()
printC(ofsX,ofsY,dialogTitle.txt,dialogTitle.back," "..title..string.rep(" ",boxW-#title-5).."_[]")
term.setBackgroundColor(colors.red)
term.setTextColor(colors.white)
term.write("X")
printC(ofsX,ofsY+1,dialogWindo.txt,dialogWindo.back,string.sub(" "..message..string.rep(" ",boxW),1,boxW))
term.setCursorPos(ofsX,ofsY+2)
term.write(string.rep(" ",boxW))
term.setCursorPos(ofsX,ofsY+3)
term.write(string.rep(" ",boxW))
for i = 1,#options do
if i == selected then
printC(range[i].s + ofC + ofsX - 1,ofsY + 3,"black","lightGray","["..options[i].."]")
term.setBackgroundColor(dialogWindo.back)
term.setTextColor(dialogWindo.txt)
term.write(" ")
else
term.setCursorPos(range[i].s + ofC + ofsX - 1,ofsY + 3)
term.write(" "..options[i].." ")
end
end
term.setCursorPos(ofsX + ofC + space,ofsY + 3)
term.write(string.rep(" ",boxW - (ofC + space)))
term.setBackgroundColor(colors.black)
term.setTextColor(colors.white)
end
while true do
drawBox()
event = {os.pullEvent()}
if event[1] == "key" then
if event[2] == 203 then -- left
selected = selected - 1
if selected < 1 then
selected = #options
end
elseif event[2] == 205 then -- right
selected = selected + 1
if selected > #options then
selected = 1
end
elseif event[2] == 28 then -- enter
return selected , options[selected]
end
elseif event[1] == "mouse_click" then
if bugTest then term.write("M "..event[2].." X "..event[3].." Y "..event[4].." ") end
if event[2] == 1 then
if event[4] == ofsY + 3 then
for i = 1,#options do
if event[3] >= range[i].s + ofC + ofsX - 1 and event[3] <= range[i].f + ofC + ofsX then
return i , options[i]
end
end
end
end
end
end
end
local flag = true
local fSlash = "/"
local path = {dir:match("[^/]+")}
local function stringPath() -- compacted this a lot
return fSlash..table.concat(path,fSlash)
end
local function osRunSpaces(sFileLocation,...) -- getRunningProgram() ["shell"] = shell
clear()
if os.newThread then
os.newThread(false,...)
else
local fProg,probblem = loadfile(sFileLocation)
if fProg then
local tEnv = {["shell"] = {}}
setmetatable(tEnv.shell,{ __index = shell})
tEnv.shell.getRunningProgram = function()
return sFileLocation
end
setmetatable(tEnv,{ __index = _G})
setfenv(fProg,tEnv)
local test,probblem = pcall(fProg,...)
if not test then
print(probblem)
dialogBox("ERROR",tostring(probblem),{"ok"},3,30)
else
return true
end
else
print(probblem)
dialogBox("ERROR",tostring(probblem),{"ok"},3,30)
end
end
end
local function rClickMenu(title,tList,tItem,posX,posY)
term.setCursorBlink(false)
local BoxTitle = title
local choices = {}
local termX,termY = term.getSize()
local offX,offY
local width = #BoxTitle + 2
local hight
for k,v in pairs(tList) do
if v ~= nil then
table.insert(choices,k)
end
if width < #k + 2 then
width = #k + 2
end
end
if #choices == 0 then
return
end
hight = #choices + 1
table.sort(choices)
offX,offY = math.ceil((termX/2) - (width/2)),math.ceil((termY/2) - (hight/2))
if posX and posY then -- offX,offY = posX,posY
if posX >= termX - width - 1 then
offX = termX - width - 1
else
offX = posX
end
if posY >= termY - hight then
offY = termY - hight
else
offY = posY
end
end
local function reDrawer()
printC(offX,offY,rcmTitle.txt,rcmTitle.back," "..BoxTitle..string.rep(" ",width - #BoxTitle - 1))
for i = 1,#choices do
printC(offX,offY + i,rcmList.txt,rcmList.back," "..choices[i]..string.rep(" ",width - #choices[i] - 1))
end
end
while true do
reDrawer()
local event = {os.pullEvent()}
if event[1] == "mouse_click" then
if event[2] == 1 then -- event[3] = x event[4] = y
if event[4] > offY and event[4] < hight + offY and event[3] >= offX and event[3] < width + offX then
--dialogBox("ERROR:",type(tList[choices[event[4] - offY]]),{"ok"})
if type(tList[choices[event[4] - offY]]) == "function" then
return tList[choices[event[4] - offY]](tItem)
elseif type(tList[choices[event[4] - offY]]) == "table" then
return rClickMenu("Options",tList[choices[event[4] - offY]],tItem,event[3],event[4])
elseif type(tList[choices[event[4] - offY]]) == "string" then
return osRunSpaces(
unpack(
fixArgs(
tList[choices[event[4] - offY]].." \""..stringPath()..fSlash..tItem.n.."\""
)
)
)
else
dialogBox("ERROR:","somthing up with new rMenu",{"ok"})
end
else
return
end
elseif event[2] == 2 then
return
end
end
end
end
local function preferences()
local tItem = {
{txt = "Title Bar",it = titleBar},
{txt = "Address Bar",it = addressBar},
{txt = "Item Windo", it = itemWindo},
{txt = "Title Right Click Title",it = rcmTitle},
{txt = "Right Click Menu",it = rcmList},
{txt = "Title Dialog Box",it = dialogTitle},
{txt = "Dialog Box",it = dialogWindo},
{txt = "Scroll Bar",it = scrollCol}
}
local topL,topR = 13,5
local width,hight = 23,6
local bottomL,bottomR = topL + width,topR + hight
local listOffset = 0
local sel = 1
local otherSel = 1
local otherItems = {}
if tItem[sel] then
for k,v in pairs(tItem[sel].it) do
table.insert(otherItems,{txt = k,it = v})
end
end
local function draw()
printC(topL,topR,titleBar.txt,titleBar.back,string.sub(" Preferences "..string.rep(" ",width),1,width))
for i = 0,12,4 do
for a = 1,4 do
--printC(topL + (a*12)-12 ,topR + ((i+4)/4),4,2^(a+i-1)," "..tostring(2^(a+i-1)))
printC(topL + a-1 ,topR + ((i+4)/4),4,2^(a+i-1)," ")
end
end
local sSel = " "
for i = 1,hight - 2 do
if i == sel - listOffset then
sSel = ">"
end
if tItem[i+listOffset] then
printC(topL + 4 ,topR + i,colors.black,colors.white,string.sub(sSel..tItem[i+listOffset].txt..string.rep(" ",width),1,width - 4))
else
printC(topL + 4 ,topR + i,colors.black,colors.white,sSel..string.rep(" ",width-5))
end
if i == sel - listOffset then
sSel = " "
end
end
term.setCursorPos(topL,topR + hight - 1)
local loop = 1
local length = 0
for i = 1,#otherItems do
if otherSel == i then
sSel = ">"
end
if colors.black == otherItems[i].it or colors.gray == otherItems[i].it then
term.setTextColor(colors.white)
else
term.setTextColor(colors.black)
end
term.setBackgroundColor(otherItems[i].it)
term.write(sSel..tostring(otherItems[i].txt).." ")
length = length + #otherItems[i].txt + 2
if otherSel == i then
sSel = " "
end
loop = loop+1
end
term.setBackgroundColor(colors.white)
term.write(string.rep(" ",width - length))
end
while true do
draw()
local event = {os.pullEvent()}
if event[1] == "mouse_click" and event[2] == 1 then
if inBouwndry(event[3],event[4],topL,topR,width,hight) then
local inSideX,inSideY = event[3] - topL,event[4] - topR
if inBouwndry(inSideX+1,inSideY,1,1,4,4) and tItem[sel] then
--[[
term.setCursorPos(1,1)
term.setBackgroundColor(2^(inSideX + ((inSideY*4)-4)))
print(2^(inSideX + ((inSideY*4)-4))," ",inSideX + ((inSideY*4)-4)," ")
]]--
tItem[sel]["it"][otherItems[otherSel].txt] = (2^(inSideX + ((inSideY*4)-4)))
end
end
elseif event[1] == "key" then
if event[2] == 200 then
sel = sel - 1
elseif event[2] == 208 then
sel = sel + 1
elseif event[2] == 203 then
otherSel = otherSel - 1
elseif event[2] == 205 then
otherSel = otherSel + 1
elseif event[2] == 28 then
if dialogBox("Confirm","Save prefrences?",{"Yes","No"}) == 1 then
saveCFG(true)
end
return
end
end
if sel < 1 then
sel = 1
elseif sel > #tItem then
sel = #tItem
end
if sel > listOffset + hight - 2 then
listOffset = listOffset + 1
elseif sel - listOffset < 1 then
listOffset = listOffset - 1
end
otherItems = {}
if tItem[sel] then
for k,v in pairs(tItem[sel].it) do
table.insert(otherItems,{txt = k,it = v})
end
end
if otherSel < 1 then
otherSel = 1
elseif otherSel > #otherItems then
otherSel = #otherItems
end
if bugTest then
term.setBackgroundColor(colors.black)
term.setTextColor(colors.white)
term.setCursorPos(1,1)
term.clearLine()
term.write("sel "..sel.." offset "..listOffset)
end
end
end
local function fileSelect(mode) -- save_file open_file browse < not yet implemented
local title = sTitle.." "..ver
local bRun = true
local clipboard = nil
local cut = false
local termX,termY = term.getSize()
local offsetX,offsetY = 1,1
local hight,width = math.ceil(termY-2),math.ceil(termX-2)
local oldHight,oldWidth
-- offsets
local boxOffX,boxOffY = offsetX,offsetY + 2
local boxH,boxW = hight - 2 ,width - 2
local barX,barY = offsetX + 1,offsetY + 2
local barH,barW = 1,width - 1
local tbarX,tbarY = offsetX + 1,offsetY + 1
local tbarH,tbarW = 1,width - 1
local exitX,exitY = offsetX + width - 1 ,offsetY + 1
local pading = string.rep(" ",boxW)
local list
local listOff = 0
local sPath
local tItemList = {}
local function newList()
listOff = 0
flag = true
tItemList = {{n = "..", id = "back"}} -- adds a back item at top of list
sPath = stringPath()
local folders = {}
local files = {}
local disks = {}
if not fs.exists(sPath) then
path = {}
sPath = stringPath()
dialogBox("ERROR:","Path no longer exists",{"ok"})
end
local test,list = pcall(fs.list,sPath) -- stopes fs.list crash
if list == nil then
list = {}
dialogBox("ERROR : ","fs.list crashed",{"ok"})
end
if #path == 0 then
for i,v in pairs(rs.getSides()) do
if disk.isPresent(v) then
if disk.hasData(v) then
table.insert(tItemList,{n = disk.getMountPath(v), id = "disk",s = v})
disks[disk.getMountPath(v)] = true
elseif disk.hasAudio(v) then
table.insert(tItemList,{n = disk.getAudioTitle(v), id = "audio",s = v})
end
end
end
end
for i,v in pairs(list) do
if fs.isDir(sPath..fSlash..v) then
table.insert(folders,v)
else
table.insert(files,v)
end
end
table.sort(folders)
table.sort(files)
for i,v in pairs(folders) do
if disks[v] == nil then
table.insert(tItemList,{n = v, id = "folder"})
end
end
for i,v in pairs(files) do
table.insert(tItemList,{n = v, id = "file"})
end
end
local function paste()
if cut then
local s, m = pcall(
function()
fs.move(clipboard[1]..fSlash..clipboard[2], stringPath()..fSlash..clipboard[2])
cut = false
clipboard = nil
end)
if not s then
dialogBox("Error", (m or "Couldn't move"), {"ok"}, 4, 30)
end
if bugTest then
local x, y = term.getCursorPos()
term.setCursorPos(1, ({term.getSize()})[2])
write("from "..clipboard[1]..fSlash..clipboard[2].." to "..stringPath()..fSlash..clipboard[2])
end
else
local s, m = pcall(function()
if fs.exists(stringPath()..fSlash..clipboard[2]) then
fs.copy(clipboard[1]..fSlash..clipboard[2], stringPath()..fSlash.."copy-"..clipboard[2])
else
fs.copy(clipboard[1]..fSlash..clipboard[2], stringPath()..fSlash..clipboard[2])
end
end)
if not s then
dialogBox("Error", (m or "Couldn't copy"), {"ok"}, 4, 30)
end
if bugTest then
local x, y = term.getCursorPos()
term.setCursorPos(1, ({term.getSize()})[2])
write("from "..clipboard[1]..fSlash..clipboard[2].." to "..stringPath()..fSlash..clipboard[2])
end
end
newList()
end
-- this section bellow handles the right click menu
local tmenu = {
disk = {
["Open"] = function(tItem)
table.insert(path,tItem.n)
newList()
end,
["Copy"] = function(tItem)
clipboard = {stringPath(), tItem.n}
cut = false
end,
["Eject"] = function(tItem)
if dialogBox("Confirm","Eject "..fSlash..tItem.n.." "..tItem.s,{"yes","no"}) == 1 then
disk.eject(tItem.s)
newList()
end
end,
["ID label"] = function(tItem)
dialogBox("ID label",disk.getDiskID(tItem.s).." "..tostring(disk.getLabel(tItem.s)),{"ok"})
end,
["Set label"] = function(tItem)
local name = InputBox("Label?")
if name then
disk.setLabel(tItem.s,name)
end
end,
["Clear label"] = function(tItem)
if dialogBox("Confirm","Cleal Label from "..tItem.s,{"yes","no"}) == 1 then
disk.setLabel(tItem.s)
end
end
},
folder = {
["Open"] = function(temp)
table.insert(path,temp.n)
newList()
end,
["Copy"] = function(tItem)
clipboard = {stringPath(), tItem.n}
cut = false
end,
["Cut"] = function(tItem)
clipboard = {stringPath(), tItem.n}
cut = true
end,
["Delete"] = function(tItem)
if dialogBox("Confirm","Delete "..tItem.id.." "..tItem.n,{"yes","no"}) == 1 then
if fs.isReadOnly(stringPath()..fSlash..tItem.n) then
dialogBox("ERROR",tItem.id.." Is read Only",{"ok"})
else
fs.delete(stringPath()..fSlash..tItem.n)
newList()
end
end
end,
["Rename"] = function(tItem)
local sName = InputBox("New Name")
if type(sName) == "string" and sName ~= "" then
local s, m = pcall(function()
fs.move(stringPath()..fSlash..tItem.n,stringPath()..fSlash..sName)
end)
if not s then
dialogBox("Error", (m or "Rename failed"), {"ok"})
end
end
newList()
end
},
file = {
["Run"] = {
["Run"] = function(tItem)
osRunSpaces(stringPath()..fSlash..tItem.n)
end,
["Run CMD"] = function(tItem)
local cmd = InputBox("Commands")
if cmd then
osRunSpaces(stringPath()..fSlash..tItem.n,unpack(fixArgs(cmd)))
end
end,
},
["Open With"] = customLaunch,
["Rename"] = function(tItem)
local sName = InputBox("New Name")
if type(sName) == "string" and sName ~= "" then
local s, m = pcall(function()
fs.move(stringPath()..fSlash..tItem.n,stringPath()..fSlash..sName)
end)
if not s then
dialogBox("Error", (m or "Rename failed"), {"ok"})
end
end
newList()
end,
["Delete"] = function(tItem)
if dialogBox("Confirm","Delete "..tItem.id.." "..tItem.n,{"yes","no"}) == 1 then
if fs.isReadOnly(stringPath()..fSlash..tItem.n) then
dialogBox("ERROR",tItem.id.." Is read Only",{"ok"})
else
fs.delete(stringPath()..fSlash..tItem.n)
newList()
end
end
end,
["Cut"] = function(tItem)
clipboard = {stringPath(), tItem.n}
cut = true
end,
["Copy"] = function(tItem)
clipboard = {stringPath(), tItem.n}
cut = false
end
},
audio = {
["Play"] = 1,
["Eject"] = 1
},
back = {
},
blank = { -- tmenu.blank.Paste =
["Paste"] = nil,
["New File"] = function()
local name = InputBox()
if name then
if fs.exists(stringPath()..fSlash..name) then
dialogBox("ERROR","Name exists",{"ok"})
else
local file = fs.open(stringPath()..fSlash..name,"w")
if file then
file.write("")
file.close()
newList()
else
dialogBox("ERROR","File not created",{"ok"})
end
end
end
end,
["New Folder"] = function()
local name = InputBox()
if name then
if fs.exists(stringPath()..fSlash..name) then
dialogBox("ERROR","Name exists",{"ok"})
else
if pcall(fs.makeDir,stringPath()..fSlash..name) then
newList()
else
dialogBox("ERROR","Access Denied",{"ok"})
end
end
end
end,
["Preferences"] = preferences
},
}
-- end right click menu
local function scrollBar(posX,posY)
if posX == boxOffX+boxW+1 and posY > boxOffY and posY <= boxOffY+boxH then
if #tItemList > boxH then
if posY == boxOffY + 1 then
listOff = 0
elseif posY == boxOffY+boxH then
listOff = #tItemList + 1 - boxH
else
listOff = math.ceil((posY - boxOffY - 1 )*(((#tItemList - boxH+2)/boxH)))
end
flag = true
end
end
end
newList()
while bRun do
if flag then
flag = false
-- clear
if oldHight ~= hight and oldWidth ~= width then
term.setBackgroundColor(colors.black)
term.clear()
oldHight,oldWidth = hight,width
end
-- draw top title bar
local b = tbarW - #title -2
if b < 0 then
b = 0
end
printC(tbarX,tbarY,titleBar.txt,titleBar.back,string.sub(" "..title,1,tbarW)..string.rep(" ",b))
term.setTextColor(colors.white)
term.setBackgroundColor(colors.red)
term.write("X")
-- draw location bar
local a = barW - #sPath - 1
if a < 0 then
a = 0
end
local tmppath = sPath
if shell and shell.getDisplayName then
tmppath = shell.getDisplayName(sPath)
--dialogBox("yay")
else
--dialogBox("moop")
end
tmppath = tmppath or sPath
local a = barW - #tmppath - 1
if a < 0 then
a = 0
end
printC(barX,barY,addressBar.txt,addressBar.back,string.sub(" "..tmppath,1,barW)..string.rep(" ",a))
-- draw scroll bar
if #tItemList > boxH then
term.setBackgroundColor(scrollCol.back)
for i = 1,boxH do
term.setCursorPos(boxOffX+boxW+1,i + boxOffY)
local scroll = math.floor( boxH* (listOff/(#tItemList-boxH+2)) )+1
if i == scroll then
term.setBackgroundColor(scrollCol.button)
term.write(" ")
term.setBackgroundColor(scrollCol.back)
else
term.write(" ")
end
end
else
term.setBackgroundColor(scrollCol.off)
for i = 1,boxH do
term.setCursorPos(boxOffX+boxW+1,i + boxOffY)
term.write(" ")
end
end
-- draw main section
for i = 1,boxH do -- listOff
local sel = i+listOff
if tItemList[sel] then
printC(1+boxOffX,i+boxOffY,(tIcons[tItemList[sel].id].tCol or itemWindo.txt),(tIcons[tItemList[sel].id].bCol or itemWindo.back),( tIcons[tItemList[sel].id].txt or " "))
printC(4+boxOffX,i+boxOffY,itemWindo.txt,itemWindo.back,string.sub(" "..tItemList[sel].n..pading,1,boxW-3))
else
printC(1+boxOffX,i+boxOffY,itemWindo.txt,itemWindo.back,pading)
end
end
if bugTest then
printC(1,1,"black","white",listOff.." "..boxOffY.." "..boxH)
end
end
-- react to events
local event = {os.pullEvent()}
if event[1] == "mouse_click" then
if inBouwndry(event[3],event[4],boxOffX+1,boxOffY+1,boxW,boxH) then
local selected = tItemList[event[4]+listOff-boxOffY]
if selected and inBouwndry(event[3],event[4],boxOffX+1,event[4],#selected.n + 4,1) then
if event[2] == 1 then -- left mouse
if selected.id == "back" then
table.remove(path,#path)
newList()
elseif selected.id == "folder" or selected.id == "disk" then
table.insert(path,selected.n)
newList()
elseif selected.id == "file" then
if dialogBox("Run file ?",selected.n,{"yes","no"}) == 1 then
osRunSpaces(stringPath()..fSlash..selected.n)
end
flag = true
end
elseif event[2] == 2 then -- right mouse
rClickMenu("Options",tmenu[selected.id],selected,event[3],event[4])
flag = true
end
elseif event[2] == 2 then -- right clicking not on object
if clipboard then
tmenu.blank.Paste = paste
else
tmenu.blank.Paste = nil
end
rClickMenu("Options",tmenu["blank"],selected,event[3],event[4])
flag = true
end
elseif event[2] == 1 and event[3] == exitX and event[4] == exitY then
if dialogBox("Confirm","Exit application",{"yes","no"}) == 1 then
bRun = false
end
flag = true
elseif event[2] == 1 then
scrollBar(event[3],event[4])
end
elseif event[1] == "mouse_scroll" then -- flag this needs new math
local old = listOff
listOff = listOff + event[2]
if listOff < 0 then
listOff = 0
end
if #tItemList + 1 - boxH > 0 and listOff > #tItemList + 1 - boxH then
listOff = #tItemList + 1 - boxH
elseif listOff > 0 and #tItemList + 1 - boxH < 0 then
listOff = 0
end
if listOff ~= old then
flag = true
end
elseif event[1] == "mouse_drag" then -- scroll bar
scrollBar(event[3],event[4])
elseif event[1] == "disk" or event[1] == "disk_eject" then
newList()
elseif event[1] == "window_resize" then
termX,termY = term.getSize()
offsetX,offsetY = 1,1
hight,width = math.ceil(termY-2),math.ceil(termX-2)
boxOffX,boxOffY = offsetX,offsetY + 2
boxH,boxW = hight - 2 ,width - 2
barX,barY = offsetX + 1,offsetY + 2
barH,barW = 1,width - 1
tbarX,tbarY = offsetX + 1,offsetY + 1
tbarH,tbarW = 1,width - 1
exitX,exitY = offsetX + width - 1 ,offsetY + 1
pading = string.rep(" ",boxW)
flag = true
elseif event[1] == "redraw" then
flag = true
end
end
end
local function main()
if term.isColor() then
clear()
fileSelect()
clear()
else
error("Not an Advanced Computer (gold) ")
end
end
local trash = (norun or main())