You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
koreader/frontend/ui/widget/pathchooser.lua

190 lines
6.4 KiB
Lua

local BD = require("ui/bidi")
local ButtonDialog = require("ui/widget/buttondialog")
local Device = require("device")
local FileChooser = require("ui/widget/filechooser")
local UIManager = require("ui/uimanager")
local ffiutil = require("ffi/util")
local lfs = require("libs/libkoreader-lfs")
local util = require("util")
local _ = require("gettext")
local N_ = _.ngettext
local T = ffiutil.template
local PathChooser = FileChooser:extend{
title = true, -- or a string
-- if let to true, a generic title will be set in init()
no_title = false,
is_popout = false,
covers_fullscreen = true, -- set it to false if you set is_popout = true
is_borderless = true,
select_directory = true, -- allow selecting directories
select_file = true, -- allow selecting files
show_files = true, -- show files, even if select_file=false
-- (directories are always shown, to allow navigation)
detailed_file_info = true, -- show size and last mod time in Select message (if select_file=true only)
}
function PathChooser:init()
if self.title == true then -- default title depending on options
if self.select_directory and not self.select_file then
self.title = _("Long-press to choose a folder")
elseif not self.select_directory and self.select_file then
self.title = _("Long-press to choose a file")
else
self.title = _("Long-press to choose")
end
end
if not self.show_files then
self.file_filter = function() return false end -- filter out regular files
end
if self.file_filter then
self.show_unsupported = false -- honour file_filter
end
if self.select_directory then
-- Let FileChooser display "Long-press to choose current folder"
self.show_current_dir_for_hold = true
end
self.title_bar_left_icon = "home"
self.onLeftButtonTap = function()
self:goHome()
end
self.onLeftButtonHold = function()
self:showPlusMenu()
end
FileChooser.init(self)
end
function PathChooser:onMenuSelect(item)
local path = item.path
if path:sub(-2, -1) == "/." then -- with show_current_dir_for_hold
if not Device:isTouchDevice() and self.select_directory then -- let non-touch device can select the folder
return self:onMenuHold(item)
end
-- Don't navigate to same directory
return true
end
path = ffiutil.realpath(path)
if not path then
-- If starting in a no-more existing directory, allow
-- not getting stuck in it
self:changeToPath("/")
return true
end
local attr = lfs.attributes(path)
if not attr then
-- Same as above
self:changeToPath("/")
return true
end
if attr.mode ~= "directory" then
if not Device:isTouchDevice() and self.select_file then -- let non-touch device can select the file
return self:onMenuHold(item)
end
-- Do nothing if Tap on other than directories
return true
end
-- Let this method check permissions and if we can list
-- this directory: we should get at least one item: ".."
local sub_table = self:genItemTableFromPath(path)
if #sub_table > 0 then
self:changeToPath(path)
end
return true
end
function PathChooser:onMenuHold(item)
local path = item.path
if path:sub(-2, -1) == "/." then -- with show_current_dir_for_hold
path = path:sub(1, -3)
end
path = ffiutil.realpath(path)
if not path then
return true
end
local attr = lfs.attributes(path)
if not attr then
return true
end
if attr.mode == "file" and not self.select_file then
return true
end
if attr.mode == "directory" and not self.select_directory then
return true
end
local title
if attr.mode == "file" then
title = _("Choose this file?") .. "\n\n" .. BD.filepath(path) .. "\n"
if self.detailed_file_info then
local filesize = util.getFormattedSize(attr.size)
local lastmod = os.date("%Y-%m-%d %H:%M", attr.modification)
title = title .. "\n" .. T(N_("File size: 1 byte", "File size: %1 bytes", attr.size), filesize) ..
"\n" .. T(_("Last modified: %1"), lastmod) .. "\n"
end
elseif attr.mode == "directory" then
title = _("Choose this folder?") .. "\n\n" .. BD.dirpath(path) .. "\n"
else -- just in case we get something else
title = _("Choose this path?") .. "\n\n" .. BD.path(path) .. "\n"
end
local onConfirm = self.onConfirm
self.button_dialog = ButtonDialog:new{
title = title,
buttons = {
{
{
text = _("Cancel"),
callback = function()
UIManager:close(self.button_dialog)
end,
},
{
text = _("Choose"),
callback = function()
if onConfirm then
onConfirm(path)
end
UIManager:close(self.button_dialog)
UIManager:close(self)
end,
},
},
},
}
UIManager:show(self.button_dialog)
return true
end
function PathChooser:showPlusMenu()
local button_dialog
button_dialog = ButtonDialog:new{
buttons = {
{
{
text = _("Folder shortcuts"),
callback = function()
UIManager:close(button_dialog)
local FileManagerShortcuts = require("apps/filemanager/filemanagershortcuts")
local select_callback = function(path)
self:changeToPath(path)
end
FileManagerShortcuts:onShowFolderShortcutsDialog(select_callback)
end,
},
},
{
{
text = _("New folder"),
callback = function()
UIManager:close(button_dialog)
local FileManager = require("apps/filemanager/filemanager")
FileManager.file_chooser = self
FileManager:createFolder()
end,
},
},
},
}
UIManager:show(button_dialog)
end
return PathChooser