Refactored to use strictly locals

pull/334/head
HW 11 years ago
parent 8efdff65d3
commit ef111b99c6

@ -1,9 +1,19 @@
require "ui/widget/filechooser"
require "apps/filemanager/fmhistory"
require "apps/filemanager/fmmenu"
local InputContainer = require("ui/widget/container/inputcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local TextWidget = require("ui/widget/textwidget")
local FileChooser = require("ui/widget/filechooser")
local VerticalGroup = require("ui/widget/verticalgroup")
local Font = require("ui/font")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
local UIManager = require("ui/uimanager")
local Event = require("ui/event")
local DocumentRegistry = require("document/documentregistry")
local FileManagerMenu = require("apps/filemanager/filemanagermenu")
local FileManagerHistory = require("apps/filemanager/filemanagerhistory")
local _ = require("gettext")
FileManager = InputContainer:extend{
local FileManager = InputContainer:extend{
title = _("FileManager"),
width = Screen:getWidth(),
height = Screen:getHeight(),
@ -90,3 +100,5 @@ function FileManager:onClose()
end
return true
end
return FileManager

@ -1,4 +1,10 @@
FileManagerHistory = InputContainer:extend{
local InputContainer = require("ui/widget/container/inputcontainer")
local Screen = require("ui/screen")
local UIManager = require("ui/uimanager")
local DocSettings = require("docsettings")
local _ = require("gettext")
local FileManagerHistory = InputContainer:extend{
hist_menu_title = _("History"),
}
@ -70,4 +76,4 @@ function FileManagerHistory:updateItemTable()
end
end
return FileManagerHistory

@ -1,7 +1,15 @@
require "ui/widget/menu"
require "ui/widget/touchmenu"
FileManagerMenu = InputContainer:extend{
local CenterContainer = require("ui/widget/container/centercontainer")
local TouchMenu = require("ui/widget/touchmenu")
local ReaderFrontLight = require("ui/reader/readerfrontlight")
local InputContainer = require("ui/widget/container/inputcontainer")
local UIManager = require("ui/uimanager")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
local _ = require("gettext")
local FileManagerMenu = InputContainer:extend{
tab_item_table = nil,
registered_widgets = {},
}
@ -132,3 +140,4 @@ function FileManagerMenu:registerToMainMenu(widget)
table.insert(self.registered_widgets, widget)
end
return FileManagerMenu

@ -1,26 +1,7 @@
--[[
Inheritable abstraction for cache items
--]]
CacheItem = {
size = 64, -- some reasonable default for simple Lua values / small tables
}
function CacheItem:new(o)
o = o or {}
setmetatable(o, self)
self.__index = self
return o
end
function CacheItem:onFree()
end
--[[
A global LRU cache
]]--
Cache = {
local Cache = {
-- cache configuration:
max_memsize = DGLOBAL_CACHE_SIZE,
-- cache state:
@ -89,3 +70,5 @@ function Cache:clear()
self.cache_order = {}
self.current_memsize = 0
end
return Cache

@ -0,0 +1,19 @@
--[[
Inheritable abstraction for cache items
--]]
local CacheItem = {
size = 64, -- some reasonable default for simple Lua values / small tables
}
function CacheItem:new(o)
o = o or {}
setmetatable(o, self)
self.__index = self
return o
end
function CacheItem:onFree()
end
return CacheItem

@ -1,10 +1,32 @@
require "settings" -- for dump method
local DocSettings = require("docsettings") -- for dump method
Dbg = {
local Dbg = {
is_on = false,
ev_log = nil,
}
local Dbg_mt = {}
local function LvDEBUG(lv, ...)
local line = ""
for i,v in ipairs({...}) do
if type(v) == "table" then
line = line .. " " .. DocSettings:dump(v, lv)
else
line = line .. " " .. tostring(v)
end
end
print("#"..line)
end
local function DEBUGBT()
DEBUG(debug.traceback())
end
function Dbg_mt.__call(dbg, ...)
LvDEBUG(math.huge, ...)
end
function Dbg:turnOn()
self.is_on = true
@ -20,22 +42,6 @@ function Dbg:logEv(ev)
self.ev_log:flush()
end
function DEBUG(...)
LvDEBUG(math.huge, ...)
end
setmetatable(Dbg, Dbg_mt)
function LvDEBUG(lv, ...)
local line = ""
for i,v in ipairs({...}) do
if type(v) == "table" then
line = line .. " " .. dump(v, lv)
else
line = line .. " " .. tostring(v)
end
end
print("#"..line)
end
function DEBUGBT()
DEBUG(debug.traceback())
end
return Dbg

@ -1,4 +1,5 @@
DocSettings = {}
local DocSettings = {}
-- lfs
function DocSettings:getHistoryPath(fullpath)
local i = #fullpath - 1
@ -67,9 +68,9 @@ function DocSettings:delSetting(key)
self.data[key] = nil
end
function dump(data, max_lv)
function DocSettings:dump(data, max_lv)
local out = {}
DocSettings:_serialize(data, out, 0, max_lv)
self:_serialize(data, out, 0, max_lv)
return table.concat(out)
end
@ -129,3 +130,5 @@ end
function DocSettings:close()
self:flush()
end
return DocSettings

@ -1,8 +1,10 @@
require "ui/geometry"
require "ui/reader/readerconfig"
require "ui/data/creoptions"
local Geom = require("ui/geometry")
local CreOptions = require("ui/data/creoptions")
local Document = require("document/document")
local Configurable = require("ui/reader/configurable")
-- TBD: DrawContext
CreDocument = Document:new{
local CreDocument = Document:new{
-- this is defined in kpvcrlib/crengine/crengine/include/lvdocview.h
SCROLL_VIEW_MODE = 0,
PAGE_VIEW_MODE = 1,
@ -248,16 +250,20 @@ function CreDocument:setVisiblePageCount(new_count)
self._document:setVisiblePageCount(new_count)
end
DocumentRegistry:addProvider("txt", "application/txt", CreDocument)
DocumentRegistry:addProvider("epub", "application/epub", CreDocument)
DocumentRegistry:addProvider("html", "application/html", CreDocument)
DocumentRegistry:addProvider("htm", "application/htm", CreDocument)
DocumentRegistry:addProvider("zip", "application/zip", CreDocument)
DocumentRegistry:addProvider("rtf", "application/rtf", CreDocument)
DocumentRegistry:addProvider("mobi", "application/mobi", CreDocument)
DocumentRegistry:addProvider("prc", "application/prc", CreDocument)
DocumentRegistry:addProvider("azw", "application/azw", CreDocument)
DocumentRegistry:addProvider("chm", "application/chm", CreDocument)
DocumentRegistry:addProvider("pdb", "application/pdb", CreDocument)
DocumentRegistry:addProvider("doc", "application/doc", CreDocument)
DocumentRegistry:addProvider("tcr", "application/tcr", CreDocument)
function CreDocument:register(registry)
registry:addProvider("txt", "application/txt", self)
registry:addProvider("epub", "application/epub", self)
registry:addProvider("html", "application/html", self)
registry:addProvider("htm", "application/htm", self)
registry:addProvider("zip", "application/zip", self)
registry:addProvider("rtf", "application/rtf", self)
registry:addProvider("mobi", "application/mobi", self)
registry:addProvider("prc", "application/prc", self)
registry:addProvider("azw", "application/azw", self)
registry:addProvider("chm", "application/chm", self)
registry:addProvider("pdb", "application/pdb", self)
registry:addProvider("doc", "application/doc", self)
registry:addProvider("tcr", "application/tcr", self)
end
return CreDocument

@ -1,10 +1,13 @@
require "cache"
require "ui/geometry"
require "ui/reader/readerconfig"
require "ui/data/koptoptions"
require "document/koptinterface"
DjvuDocument = Document:new{
local Geom = require("ui/geometry")
local Cache = require("cache")
local CacheItem = require("cacheitem")
local KoptOptions = require("ui/data/koptoptions")
local KoptInterface = require("document/koptinterface")
local Document = require("document/document")
local Configurable = require("ui/reader/configurable")
-- TBD: DrawContext
local DjvuDocument = Document:new{
_document = false,
-- libdjvulibre manages its own additional cache, default value is hard written in c module.
djvulibre_cache_size = nil,
@ -14,6 +17,16 @@ DjvuDocument = Document:new{
koptinterface = KoptInterface,
}
-- check DjVu magic string to validate
local function validDjvuFile(filename)
f = io.open(filename, "r")
if not f then return false end
local magic = f:read(8)
f:close()
if not magic or magic ~= "AT&TFORM" then return false end
return true
end
function DjvuDocument:init()
self.configurable:loadDefaults(self.options)
if not validDjvuFile(self.file) then
@ -33,16 +46,6 @@ function DjvuDocument:init()
self:_readMetadata()
end
-- check DjVu magic string to validate
function validDjvuFile(filename)
f = io.open(filename, "r")
if not f then return false end
local magic = f:read(8)
f:close()
if not magic or magic ~= "AT&TFORM" then return false end
return true
end
function DjvuDocument:invertTextYAxel(pageno, text_table)
local _, height = self.doc:getOriginalPageSize(pageno)
for _,text in pairs(text_table) do
@ -105,4 +108,8 @@ function DjvuDocument:drawPage(target, x, y, rect, pageno, zoom, rotation, gamma
return self.koptinterface:drawPage(self, target, x, y, rect, pageno, zoom, rotation, gamma, render_mode)
end
DocumentRegistry:addProvider("djvu", "application/djvu", DjvuDocument)
function DjvuDocument:register(registry)
registry:addProvider("djvu", "application/djvu", self)
end
return DjvuDocument

@ -1,46 +1,12 @@
require "../math"
--[[
This is a registry for document providers
]]--
DocumentRegistry = {
providers = { }
}
function DocumentRegistry:addProvider(extension, mimetype, provider)
table.insert(self.providers, { extension = extension, mimetype = mimetype, provider = provider })
end
function DocumentRegistry:getProvider(file)
-- TODO: some implementation based on mime types?
local extension = string.lower(string.match(file, ".+%.([^.]+)") or "")
for _, provider in ipairs(self.providers) do
if extension == provider.extension then
return provider.provider
end
end
end
function DocumentRegistry:openDocument(file)
local provider = self:getProvider(file)
if provider ~= nil then
return provider:new{file = file}
end
end
TileCacheItem = CacheItem:new{}
function TileCacheItem:onFree()
if self.bb.free then
DEBUG("free blitbuffer", self.bb)
self.bb:free()
end
end
local Cache = require("cache")
local CacheItem = require("cacheitem")
local TileCacheItem = require("document/tilecacheitem")
local Geom = require("ui/geometry")
--[[
This is an abstract interface to a document
]]--
Document = {
local Document = {
-- file name
file = nil,
@ -304,8 +270,4 @@ function Document:getPageText(pageno)
return text
end
-- load implementations:
require "document/pdfdocument"
require "document/djvudocument"
require "document/credocument"
return Document

@ -0,0 +1,35 @@
--[[
This is a registry for document providers
]]--
local DocumentRegistry = {
providers = { }
}
function DocumentRegistry:addProvider(extension, mimetype, provider)
table.insert(self.providers, { extension = extension, mimetype = mimetype, provider = provider })
end
function DocumentRegistry:getProvider(file)
-- TODO: some implementation based on mime types?
local extension = string.lower(string.match(file, ".+%.([^.]+)") or "")
for _, provider in ipairs(self.providers) do
if extension == provider.extension then
return provider.provider
end
end
end
function DocumentRegistry:openDocument(file)
local provider = self:getProvider(file)
if provider ~= nil then
return provider:new{file = file}
end
end
-- load implementations:
require("document/pdfdocument"):register(DocumentRegistry)
require("document/djvudocument"):register(DocumentRegistry)
require("document/credocument"):register(DocumentRegistry)
return DocumentRegistry

@ -1,11 +1,10 @@
require "dbg"
require "cache"
require "ui/geometry"
require "ui/device"
require "ui/screen"
require "ui/reader/readerconfig"
KoptInterface = {
local Document = require("document/document")
local Cache = require("cache")
local CacheItem = require("cacheitem")
local Screen = require("ui/screen")
-- TBD: KOPTContext
local KoptInterface = {
ocrengine = "ocrengine",
tessocr_data = "data",
ocr_lang = "eng",
@ -15,7 +14,7 @@ KoptInterface = {
screen_dpi = Screen:getDPI(),
}
ContextCacheItem = CacheItem:new{}
local ContextCacheItem = CacheItem:new{}
function ContextCacheItem:onFree()
if self.kctx.free then
@ -24,7 +23,7 @@ function ContextCacheItem:onFree()
end
end
OCREngine = CacheItem:new{}
local OCREngine = CacheItem:new{}
function OCREngine:onFree()
if self.ocrengine.freeOCR then
@ -811,3 +810,5 @@ function KoptInterface:logMemoryUsage(pageno)
log_file:close()
end
end
return KoptInterface

@ -1,10 +1,12 @@
require "cache"
require "ui/geometry"
require "ui/reader/readerconfig"
require "ui/data/koptoptions"
require "document/koptinterface"
PdfDocument = Document:new{
local Cache = require("cache")
local CacheItem = require("cacheitem")
local KoptOptions = require("ui/data/koptoptions")
local KoptInterface = require("document/koptinterface")
local Document = require("document/document")
local Configurable = require("ui/reader/configurable")
-- TBD: DrawContext
local PdfDocument = Document:new{
_document = false,
-- muPDF manages its own additional cache
mupdf_cache_size = 5 * 1024 * 1024,
@ -111,5 +113,9 @@ function PdfDocument:drawPage(target, x, y, rect, pageno, zoom, rotation, gamma,
return self.koptinterface:drawPage(self, target, x, y, rect, pageno, zoom, rotation, gamma, render_mode)
end
DocumentRegistry:addProvider("pdf", "application/pdf", PdfDocument)
DocumentRegistry:addProvider("cbz", "application/cbz", PdfDocument)
function PdfDocument:register(registry)
registry:addProvider("pdf", "application/pdf", self)
registry:addProvider("cbz", "application/cbz", self)
end
return PdfDocument

@ -0,0 +1,12 @@
local CacheItem = require("cacheitem")
local TileCacheItem = CacheItem:new{}
function TileCacheItem:onFree()
if self.bb.free then
DEBUG("free blitbuffer", self.bb)
self.bb:free()
end
end
return TileCacheItem

@ -1,11 +1,16 @@
lua_gettext.init("./i18n", "koreader")
local GetText = {}
local GetText_mt = {}
function _(string)
function GetText_mt.__call(gettext, string)
return lua_gettext.translate(string)
end
function gettextChangeLang(new_lang)
function GetText.changeLang(new_lang)
lua_gettext.change_lang(new_lang)
end
setmetatable(GetText, GetText_mt)
return GetText

@ -2,7 +2,9 @@
Simple math helper function
]]--
function math.roundAwayFromZero(num)
local Math = {}
function Math.roundAwayFromZero(num)
if num > 0 then
return math.ceil(num)
else
@ -10,11 +12,11 @@ function math.roundAwayFromZero(num)
end
end
function math.round(num)
function Math.round(num)
return math.floor(num + 0.5)
end
function math.oddEven(number)
function Math.oddEven(number)
if number % 2 == 1 then
return "odd"
else
@ -22,7 +24,7 @@ function math.oddEven(number)
end
end
function tmin_max(tab, func, op)
local function tmin_max(tab, func, op)
if #tab == 0 then return nil, nil end
local index, value = 1, tab[1]
for i = 2, #tab do
@ -47,7 +49,7 @@ end
Return the minimum element of a table.
The optional argument func specifies a one-argument ordering function.
]]--
function math.tmin(tab, func)
function Math.tmin(tab, func)
return tmin_max(tab, func, "min")
end
@ -55,6 +57,8 @@ end
Return the maximum element of a table.
The optional argument func specifies a one-argument ordering function.
]]--
function math.tmax(tab, func)
function Math.tmax(tab, func)
return tmin_max(tab, func, "max")
end
return Math

@ -1,5 +1,7 @@
require "ui/screen"
require "ui/data/strings"
local Screen = require("ui/screen")
local S = require("ui/data/strings")
local _ = require("gettext")
-- add multiply operator to Aa dict
local Aa = setmetatable({"Aa"}, {
@ -12,15 +14,15 @@ local Aa = setmetatable({"Aa"}, {
end
})
CreOptions = {
local CreOptions = {
prefix = 'copt',
{
icon = "resources/icons/appbar.transform.rotate.right.large.png",
options = {
{
name = "screen_mode",
name_text = SCREEN_MODE_STR,
toggle = {PORTRAIT_STR, LANDSCAPE_STR},
name_text = S.SCREEN_MODE,
toggle = {S.PORTRAIT, S.LANDSCAPE},
args = {"portrait", "landscape"},
default_arg = "portrait",
current_func = function() return Screen:getScreenMode() end,
@ -33,16 +35,16 @@ CreOptions = {
options = {
{
name = "line_spacing",
name_text = LINE_SPACING_STR,
item_text = {DECREASE_STR, INCREASE_STR},
name_text = S.LINE_SPACING,
item_text = {S.DECREASE, S.INCREASE},
args = {"decrease", "increase"},
default_arg = nil,
event = "ChangeLineSpace",
},
{
name = "page_margins",
name_text = PAGE_MARGIN_STR,
toggle = {SMALL_STR, MEDIUM_STR, LARGE_STR},
name_text = S.PAGE_MARGIN,
toggle = {S.SMALL, S.MEDIUM, S.LARGE},
values = {
{6, 5, 2, 5},
{15, 10, 10, 10},
@ -79,8 +81,8 @@ CreOptions = {
options = {
{
name = "font_weight",
name_text = FONT_WEIGHT_STR,
item_text = {TOGGLE_BOLD_STR},
name_text = S.FONT_WEIGHT,
item_text = {S.TOGGLE_BOLD},
-- args is indeed not used, we put here just to keep the
-- UI happy.
args = {1},
@ -89,8 +91,8 @@ CreOptions = {
},
{
name = "font_gamma",
name_text = GAMMA_STR,
item_text = {DECREASE_STR, INCREASE_STR},
name_text = S.GAMMA,
item_text = {S.DECREASE, S.INCREASE},
args = {"decrease", "increase"},
default_arg = nil,
event = "ChangeFontGamma",
@ -102,8 +104,8 @@ CreOptions = {
options = {
{
name = "view_mode",
name_text = VIEW_MODE_STR,
toggle = {VIEW_SCROLL_STR, VIEW_PAGE_STR},
name_text = S.VIEW_MODE,
toggle = {S.VIEW_SCROLL, S.VIEW_PAGE},
values = {1, 0},
default_value = 0,
args = {"scroll", "page"},
@ -112,8 +114,8 @@ CreOptions = {
},
{
name = "embedded_css",
name_text = EMBEDDED_STYLE_STR,
toggle = {ON_STR, OFF_STR},
name_text = S.EMBEDDED_STYLE,
toggle = {S.ON, S.OFF},
values = {1, 0},
default_value = 1,
args = {true, false},
@ -123,3 +125,5 @@ CreOptions = {
},
},
}
return CreOptions

@ -1,15 +1,17 @@
require "ui/screen"
require "ui/data/strings"
local Screen = require("ui/screen")
local S = require("ui/data/strings")
KoptOptions = {
local _ = require("gettext")
local KoptOptions = {
prefix = 'kopt',
{
icon = "resources/icons/appbar.transform.rotate.right.large.png",
options = {
{
name = "screen_mode",
name_text = SCREEN_MODE_STR,
toggle = {PORTRAIT_STR, LANDSCAPE_STR},
name_text = S.SCREEN_MODE,
toggle = {S.PORTRAIT, S.LANDSCAPE},
alternate = false,
args = {"portrait", "landscape"},
default_arg = "portrait",
@ -23,9 +25,9 @@ KoptOptions = {
options = {
{
name = "trim_page",
name_text = PAGE_CROP_STR,
name_text = S.PAGE_CROP,
width = 225,
toggle = {MANUAL_STR, AUTO_STR, SEMIAUTO_STR},
toggle = {S.MANUAL, S.AUTO, S.SEMIAUTO},
alternate = false,
values = {0, 1, 2},
default_value = DKOPTREADER_CONFIG_TRIM_PAGE,
@ -39,8 +41,8 @@ KoptOptions = {
options = {
{
name = "full_screen",
name_text = FULL_SCREEN_STR,
toggle = {ON_STR, OFF_STR},
name_text = S.FULL_SCREEN,
toggle = {S.ON, S.OFF},
values = {1, 0},
default_value = DFULL_SCREEN,
event = "SetFullScreen",
@ -48,8 +50,8 @@ KoptOptions = {
},
{
name = "page_scroll",
name_text = SCROLL_MODE_STR,
toggle = {ON_STR, OFF_STR},
name_text = S.SCROLL_MODE,
toggle = {S.ON, S.OFF},
values = {1, 0},
default_value = DSCROLL_MODE,
event = "ToggleScrollMode",
@ -57,22 +59,22 @@ KoptOptions = {
},
{
name = "page_margin",
name_text = PAGE_MARGIN_STR,
toggle = {SMALL_STR, MEDIUM_STR, LARGE_STR},
name_text = S.PAGE_MARGIN,
toggle = {S.SMALL, S.MEDIUM, S.LARGE},
values = {0.05, 0.10, 0.15},
default_value = DKOPTREADER_CONFIG_PAGE_MARGIN,
event = "MarginUpdate",
},
{
name = "line_spacing",
name_text = LINE_SPACING_STR,
toggle = {SMALL_STR, MEDIUM_STR, LARGE_STR},
name_text = S.LINE_SPACING,
toggle = {S.SMALL, S.MEDIUM, S.LARGE},
values = {1.0, 1.2, 1.4},
default_value = DKOPTREADER_CONFIG_LINE_SPACING,
},
{
name = "max_columns",
name_text = COLUMNS_STR,
name_text = S.COLUMNS,
item_icons = {
"resources/icons/appbar.column.one.png",
"resources/icons/appbar.column.two.png",
@ -83,7 +85,7 @@ KoptOptions = {
},
{
name = "justification",
name_text = TEXT_ALIGN_STR,
name_text = S.TEXT_ALIGN,
item_icons = {
"resources/icons/appbar.align.auto.png",
"resources/icons/appbar.align.left.png",
@ -112,8 +114,8 @@ KoptOptions = {
},
{
name = "font_fine_tune",
name_text = FONTSIZE_FINE_TUNING_STR,
toggle = {DECREASE_STR, INCREASE_STR},
name_text = S.FONTSIZE_FINE_TUNING,
toggle = {S.DECREASE, S.INCREASE},
values = {-0.05, 0.05},
default_value = 0.05,
event = "FineTuningFontSize",
@ -128,9 +130,9 @@ KoptOptions = {
options = {
{
name = "contrast",
name_text = CONTRAST_STR,
name_text = S.CONTRAST,
name_align_right = 0.2,
item_text = {LIGHTEST_STR , LIGHTER_STR, DEFAULT_STR, DARKER_STR, DARKEST_STR},
item_text = {S.LIGHTEST , S.LIGHTER, S.DEFAULT, S.DARKER, S.DARKEST},
item_font_size = 18,
item_align_center = 0.8,
values = {2.0, 1.5, 1.0, 0.5, 0.2},
@ -146,7 +148,7 @@ KoptOptions = {
{
name = "text_wrap",
name_text = _("Reflow"),
toggle = {ON_STR, OFF_STR},
toggle = {S.ON, S.OFF},
values = {1, 0},
default_value = DKOPTREADER_CONFIG_TEXT_WRAP,
events = {
@ -163,7 +165,7 @@ KoptOptions = {
},
{
name="doc_language",
name_text = DOC_LANG_STR,
name_text = S.DOC_LANG,
toggle = DKOPTREADER_CONFIG_DOC_LANGS_TEXT,
values = DKOPTREADER_CONFIG_DOC_LANGS_CODE,
default_value = DKOPTREADER_CONFIG_DOC_DEFAULT_LANG_CODE,
@ -172,45 +174,45 @@ KoptOptions = {
},
{
name="screen_rotation",
name_text = VERTICAL_TEXT_STR,
toggle = {ON_STR, OFF_STR},
name_text = S.VERTICAL_TEXT,
toggle = {S.ON, S.OFF},
values = {90, 0},
default_value = 0,
},
{
name = "word_spacing",
name_text = WORD_GAP_STR,
toggle = {SMALL_STR, MEDIUM_STR, LARGE_STR},
name_text = S.WORD_GAP,
toggle = {S.SMALL, S.MEDIUM, S.LARGE},
values = DKOPTREADER_CONFIG_WORD_SAPCINGS,
default_value = DKOPTREADER_CONFIG_DEFAULT_WORD_SAPCING,
},
{
name = "defect_size",
name_text = DEFECT_SIZE_STR,
toggle = {SMALL_STR, MEDIUM_STR, LARGE_STR},
name_text = S.DEFECT_SIZE,
toggle = {S.SMALL, S.MEDIUM, S.LARGE},
values = {1.0, 3.0, 5.0},
default_value = DKOPTREADER_CONFIG_DEFECT_SIZE,
event = "DefectSizeUpdate",
},
{
name = "quality",
name_text = RENDER_QUALITY_STR,
toggle = {LOW_STR, DEFAULT_STR, HIGH_STR},
name_text = S.RENDER_QUALITY,
toggle = {S.LOW, S.DEFAULT, S.HIGH},
values={0.5, 1.0, 1.5},
default_value = DKOPTREADER_CONFIG_RENDER_QUALITY,
},
{
name = "auto_straighten",
name_text = AUTO_STRAIGHTEN_STR,
toggle = {ZERO_DEG_STR, FIVE_DEG_STR, TEN_DEG_STR},
name_text = S.AUTO_STRAIGHTEN,
toggle = {S.ZERO_DEG, S.FIVE_DEG, S.TEN_DEG},
values = {0, 5, 10},
default_value = DKOPTREADER_CONFIG_AUTO_STRAIGHTEN,
default_value = S.DKOPTREADER_CONFIG_AUTOAIGHTEN,
show = false,
},
{
name = "detect_indent",
name_text = INDENTATION_STR,
toggle = {ON_STR, OFF_STR},
name_text = S.INDENTATION,
toggle = {S.ON, S.OFF},
values = {1, 0},
default_value = DKOPTREADER_CONFIG_DETECT_INDENT,
show = false,
@ -218,3 +220,5 @@ KoptOptions = {
}
},
}
return KoptOptions

@ -1,49 +1,54 @@
local _ = require("gettext")
SCREEN_MODE_STR = _("Screen Mode")
PAGE_CROP_STR = _("Page Crop")
FULL_SCREEN_STR = _("Full Screen")
SCROLL_MODE_STR = _("Scroll Mode")
PAGE_MARGIN_STR = _("Page Margin")
LINE_SPACING_STR = _("Line Spacing")
COLUMNS_STR = _("Columns")
TEXT_ALIGN_STR = _("Text Align")
FONTSIZE_FINE_TUNING_STR = _("Fine Tuning")
CONTRAST_STR = _("Contrast")
REFLOW_STR = _("Reflow")
DOC_LANG_STR = _("Document Language")
VERTICAL_TEXT_STR = _("Vertical Text")
WORD_GAP_STR = _("Word Gap")
DEFECT_SIZE_STR = _("Defect Size")
RENDER_QUALITY_STR = _("Render Quality")
AUTO_STRAIGHTEN_STR = _("Auto Straighten")
INDENTATION_STR = _("Indentation")
FONT_WEIGHT_STR = _("Font weight")
GAMMA_STR = _("Gamma")
VIEW_MODE_STR = _("View mode")
EMBEDDED_STYLE_STR = _("Embedded style")
local S = {}
ON_STR = _("on")
OFF_STR = _("off")
AUTO_STR = _("auto")
MANUAL_STR = _("manual")
SEMIAUTO_STR = _("semi-auto")
SMALL_STR = _("small")
MEDIUM_STR = _("medium")
LARGE_STR = _("large")
DECREASE_STR = _("decrease")
INCREASE_STR = _("increase")
LIGHTEST_STR = _("lightest")
LIGHTER_STR = _("lighter")
DEFAULT_STR = _("default")
DARKER_STR = _("darker")
DARKEST_STR = _("darkest")
LOW_STR = _("low")
HIGH_STR = _("high")
ZERO_DEG_STR = _("0 deg")
FIVE_DEG_STR = _("5 deg")
TEN_DEG_STR = _("10 deg")
PORTRAIT_STR = _("portrait")
LANDSCAPE_STR = _("landscape")
TOGGLE_BOLD_STR = _("toggle bold")
VIEW_SCROLL_STR = _("scroll")
VIEW_PAGE_STR = _("page")
S.SCREEN_MODE = _("Screen Mode")
S.PAGE_CROP = _("Page Crop")
S.FULL_SCREEN = _("Full Screen")
S.SCROLL_MODE = _("Scroll Mode")
S.PAGE_MARGIN = _("Page Margin")
S.LINE_SPACING = _("Line Spacing")
S.COLUMNS = _("Columns")
S.TEXT_ALIGN = _("Text Align")
S.FONTSIZE_FINE_TUNING = _("Fine Tuning")
S.CONTRAST = _("Contrast")
S.REFLOW = _("Reflow")
S.DOC_LANG = _("Document Language")
S.VERTICAL_TEXT = _("Vertical Text")
S.WORD_GAP = _("Word Gap")
S.DEFECT_SIZE = _("Defect Size")
S.RENDER_QUALITY = _("Render Quality")
S.AUTO_STRAIGHTEN = _("Auto Straighten")
S.INDENTATION = _("Indentation")
S.FONT_WEIGHT = _("Font weight")
S.GAMMA = _("Gamma")
S.VIEW_MODE = _("View mode")
S.EMBEDDED_STYLE = _("Embedded style")
S.ON = _("on")
S.OFF = _("off")
S.AUTO = _("auto")
S.MANUAL = _("manual")
S.SEMIAUTO = _("semi-auto")
S.SMALL = _("small")
S.MEDIUM = _("medium")
S.LARGE = _("large")
S.DECREASE = _("decrease")
S.INCREASE = _("increase")
S.LIGHTEST = _("lightest")
S.LIGHTER = _("lighter")
S.DEFAULT = _("default")
S.DARKER = _("darker")
S.DARKEST = _("darkest")
S.LOW = _("low")
S.HIGH = _("high")
S.ZERO_DEG = _("0 deg")
S.FIVE_DEG = _("5 deg")
S.TEN_DEG = _("10 deg")
S.PORTRAIT = _("portrait")
S.LANDSCAPE = _("landscape")
S.TOGGLE_BOLD = _("toggle bold")
S.VIEW_SCROLL = _("scroll")
S.VIEW_PAGE = _("page")
return S

@ -1,4 +1,12 @@
Device = {
local KindleFrontLight = require("ui/device/kindlefrontlight")
local KoboFrontLight = require("ui/device/kobofrontlight")
local BaseFrontLight = require("ui/device/basefrontlight")
-- Screen
-- util
-- lfs
local Device = {
screen_saver_mode = false,
charging_mode = false,
survive_screen_saver = false,
@ -8,25 +16,6 @@ Device = {
frontlight = nil,
}
BaseFrontLight = {
min = 1, max = 10,
intensity = nil,
}
KindleFrontLight = {
min = 0, max = 24,
kpw_fl = "/sys/devices/system/fl_tps6116x/fl_tps6116x0/fl_intensity",
intensity = nil,
lipc_handle = nil,
}
KoboFrontLight = {
min = 1, max = 100,
intensity = 20,
restore_settings = true,
fl = nil,
}
function Device:getModel()
if self.model then return self.model end
if util.isEmulated() then
@ -219,58 +208,4 @@ function Device:getFrontlight()
return self.frontlight
end
function BaseFrontLight:init() end
function BaseFrontLight:toggle() end
function BaseFrontLight:setIntensityHW() end
function BaseFrontLight:setIntensity(intensity)
intensity = intensity < self.min and self.min or intensity
intensity = intensity > self.max and self.max or intensity
self.intensity = intensity
self:setIntensityHW()
end
function KindleFrontLight:init()
require "liblipclua"
self.lipc_handle = lipc.init("com.github.koreader")
if self.lipc_handle then
self.intensity = self.lipc_handle:get_int_property("com.lab126.powerd", "flIntensity")
end
end
function KindleFrontLight:toggle()
local f = io.open(self.kpw_fl, "r")
local sysint = tonumber(f:read("*all"):match("%d+"))
f:close()
if sysint == 0 then
self:setIntensity(self.intensity)
else
os.execute("echo -n 0 > " .. self.kpw_fl)
end
end
KindleFrontLight.setIntensity = BaseFrontLight.setIntensity
function KindleFrontLight:setIntensityHW()
if self.lipc_handle ~= nil then
self.lipc_handle:set_int_property("com.lab126.powerd", "flIntensity", self.intensity)
end
end
function KoboFrontLight:init()
self.fl = kobolight.open()
end
function KoboFrontLight:toggle()
if self.fl ~= nil then
self.fl:toggle()
end
end
KoboFrontLight.setIntensity = BaseFrontLight.setIntensity
function KoboFrontLight:setIntensityHW()
if self.fl ~= nil then
self.fl:setBrightness(self.intensity)
end
end
return Device

@ -0,0 +1,17 @@
local BaseFrontLight = {
min = 1, max = 10,
intensity = nil,
}
function BaseFrontLight:init() end
function BaseFrontLight:toggle() end
function BaseFrontLight:setIntensityHW() end
function BaseFrontLight:setIntensity(intensity)
intensity = intensity < self.min and self.min or intensity
intensity = intensity > self.max and self.max or intensity
self.intensity = intensity
self:setIntensityHW()
end
return BaseFrontLight

@ -0,0 +1,38 @@
local BaseFrontLight = require("ui/device/basefrontlight")
-- liblipclua, see require below
local KindleFrontLight = {
min = 0, max = 24,
kpw_fl = "/sys/devices/system/fl_tps6116x/fl_tps6116x0/fl_intensity",
intensity = nil,
lipc_handle = nil,
}
function KindleFrontLight:init()
require "liblipclua"
self.lipc_handle = lipc.init("com.github.koreader")
if self.lipc_handle then
self.intensity = self.lipc_handle:get_int_property("com.lab126.powerd", "flIntensity")
end
end
function KindleFrontLight:toggle()
local f = io.open(self.kpw_fl, "r")
local sysint = tonumber(f:read("*all"):match("%d+"))
f:close()
if sysint == 0 then
self:setIntensity(self.intensity)
else
os.execute("echo -n 0 > " .. self.kpw_fl)
end
end
KindleFrontLight.setIntensity = BaseFrontLight.setIntensity
function KindleFrontLight:setIntensityHW()
if self.lipc_handle ~= nil then
self.lipc_handle:set_int_property("com.lab126.powerd", "flIntensity", self.intensity)
end
end
return KindleFrontLight

@ -0,0 +1,28 @@
local BaseFrontLight = require("ui/device/basefrontlight")
local KoboFrontLight = {
min = 1, max = 100,
intensity = 20,
restore_settings = true,
fl = nil,
}
function KoboFrontLight:init()
self.fl = kobolight.open()
end
function KoboFrontLight:toggle()
if self.fl ~= nil then
self.fl:toggle()
end
end
KoboFrontLight.setIntensity = BaseFrontLight.setIntensity
function KoboFrontLight:setIntensityHW()
if self.fl ~= nil then
self.fl:setBrightness(self.intensity)
end
end
return KoboFrontLight

@ -7,7 +7,7 @@ In order to see how event propagation works and how to make
widgets event-aware see the implementation in WidgetContainer
below.
]]
Event = {}
local Event = {}
function Event:new(name, ...)
local o = {
@ -18,3 +18,5 @@ function Event:new(name, ...)
self.__index = self
return o
end
return Event

@ -1,6 +1,7 @@
require "dbg" -- for DEBUG()
local Screen = require("ui/screen")
Font = {
local Font = {
fontmap = {
-- default font for menu contents
cfont = "freefont/FreeSerif.ttf",
@ -50,7 +51,7 @@ function Font:getFace(font, size)
font = self.cfont
end
local size = scaleByDPI(size)
local size = Screen:scaleByDPI(size)
local face = self.faces[font..size]
-- build face if not found
@ -98,3 +99,5 @@ function Font:update()
self.faces = {}
clearGlyphCache()
end
return Font

@ -9,7 +9,7 @@ some behaviour is defined for dimensions { w = ..., h = ... }
just use it on simple tables that have x, y and/or w, h
or define your own types using this as a metatable
]]--
Geom = {
local Geom = {
x = 0,
y = 0,
w = 0,
@ -305,3 +305,5 @@ function Geom:center()
w = 0, h = 0,
}
end
return Geom

@ -1,46 +1,6 @@
require "ui/geometry"
GestureRange = {
ges = nil,
-- spatial range limits the gesture emitting position
range = nil,
-- temproal range limits the gesture emitting rate
rate = nil,
-- span limits of this gesture
scale = nil,
}
function GestureRange:new(o)
local o = o or {}
setmetatable(o, self)
self.__index = self
return o
end
function GestureRange:match(gs)
if gs.ges ~= self.ges then
return false
end
if self.range then
if not self.range:contains(gs.pos) then
return false
end
end
if self.rate then
local last_time = self.last_time or TimeVal:new{}
if gs.time - last_time > TimeVal:new{usec = 1000000 / self.rate} then
self.last_time = gs.time
else
return false
end
end
if self.scale then
if self.scale[1] > gs.span or self.scale[2] < gs.span then
return false
end
end
return true
end
local Geom = require("ui/geometry")
local TimeVal = require("ui/timeval")
local Screen = require("ui/screen")
--[[
Current detectable gestures:
@ -80,7 +40,9 @@ GestureDetector:feedEvent(tev) will return a detection result when you
feed a touch release event to it.
--]]
GestureDetector = {
local GestureDetector = {
-- must be initialized with the Input singleton class
input = nil,
-- all the time parameters are in us
DOUBLE_TAP_INTERVAL = 300 * 1000,
TWO_FINGER_TAP_DURATION = 300 * 1000,
@ -351,9 +313,9 @@ function GestureDetector:handleDoubleTap(tev)
-- deadline should be calculated by adding current tap time and the interval
local deadline = cur_tap.timev + TimeVal:new{
sec = 0,
usec = not Input.disable_double_tap and self.DOUBLE_TAP_INTERVAL or 0,
usec = not self.input.disable_double_tap and self.DOUBLE_TAP_INTERVAL or 0,
}
Input:setTimeout(function()
self.input:setTimeout(function()
DEBUG("in tap timer", self.last_taps[slot] ~= nil)
-- double tap will set last_tap to nil so if it is not, then
-- user must only tapped once
@ -379,7 +341,7 @@ function GestureDetector:handleNonTap(tev)
local deadline = tev.timev + TimeVal:new{
sec = 0, usec = self.HOLD_INTERVAL
}
Input:setTimeout(function()
self.input:setTimeout(function()
if self.states[slot] == self.tapState then
-- timer set in tapState, so we switch to hold
DEBUG("hold gesture detected in slot", slot)
@ -680,3 +642,5 @@ function GestureDetector:adjustGesCoordinate(ges)
end
return ges
end
return GestureDetector

@ -0,0 +1,45 @@
-- TimeVal
local GestureRange = {
ges = nil,
-- spatial range limits the gesture emitting position
range = nil,
-- temproal range limits the gesture emitting rate
rate = nil,
-- span limits of this gesture
scale = nil,
}
function GestureRange:new(o)
local o = o or {}
setmetatable(o, self)
self.__index = self
return o
end
function GestureRange:match(gs)
if gs.ges ~= self.ges then
return false
end
if self.range then
if not self.range:contains(gs.pos) then
return false
end
end
if self.rate then
local last_time = self.last_time or TimeVal:new{}
if gs.time - last_time > TimeVal:new{usec = 1000000 / self.rate} then
self.last_time = gs.time
else
return false
end
end
if self.scale then
if self.scale[1] > gs.span or self.scale[2] < gs.span then
return false
end
end
return true
end
return GestureRange

@ -1,181 +0,0 @@
--[[
Draw a border
@x: start position in x axis
@y: start position in y axis
@w: width of the border
@h: height of the border
@bw: line width of the border
@c: color for loading bar
@r: radius of for border's corner (nil or 0 means right corner border)
--]]
function blitbuffer.paintBorder(bb, x, y, w, h, bw, c, r)
x, y = math.ceil(x), math.ceil(y)
h, w = math.ceil(h), math.ceil(w)
if not r or r == 0 then
bb:paintRect(x, y, w, bw, c)
bb:paintRect(x, y+h-bw, w, bw, c)
bb:paintRect(x, y+bw, bw, h - 2*bw, c)
bb:paintRect(x+w-bw, y+bw, bw, h - 2*bw, c)
else
if h < 2*r then r = math.floor(h/2) end
if w < 2*r then r = math.floor(w/2) end
bb:paintRoundedCorner(x, y, w, h, bw, r, c)
bb:paintRect(r+x, y, w-2*r, bw, c)
bb:paintRect(r+x, y+h-bw, w-2*r, bw, c)
bb:paintRect(x, r+y, bw, h-2*r, c)
bb:paintRect(x+w-bw, r+y, bw, h-2*r, c)
end
end
--[[
Fill a rounded corner rectangular area
@x: start position in x axis
@y: start position in y axis
@w: width of the area
@h: height of the area
@c: color used to fill the area
@r: radius of for four corners
--]]
function blitbuffer.paintRoundedRect(bb, x, y, w, h, c, r)
x, y = math.ceil(x), math.ceil(y)
h, w = math.ceil(h), math.ceil(w)
if not r or r == 0 then
bb:paintRect(x, y, w, h, c)
else
if h < 2*r then r = math.floor(h/2) end
if w < 2*r then r = math.floor(w/2) end
bb:paintBorder(x, y, w, h, r, c, r)
bb:paintRect(x+r, y+r, w-2*r, h-2*r, c)
end
end
--[[
Draw a progress bar according to following args:
@x: start position in x axis
@y: start position in y axis
@w: width for progress bar
@h: height for progress bar
@load_m_w: width margin for loading bar
@load_m_h: height margin for loading bar
@load_percent: progress in percent
@c: color for loading bar
--]]
function blitbuffer.progressBar(bb, x, y, w, h,
load_m_w, load_m_h, load_percent, c)
if load_m_h*2 > h then
load_m_h = h/2
end
bb:paintBorder(x, y, w, h, 2, 15)
bb:paintRect(x+load_m_w, y+load_m_h,
(w-2*load_m_w)*load_percent, (h-2*load_m_h), c)
end
------------------------------------------------
-- Start of Cursor class
------------------------------------------------
Cursor = {
x_pos = 0,
y_pos = 0,
--color = 15,
h = 10,
w = nil,
line_w = nil,
is_cleared = true,
}
function Cursor:new(o)
o = o or {}
o.x_pos = o.x_pos or self.x_pos
o.y_pos = o.y_pos or self.y_pos
o.line_width_factor = o.line_width_factor or 10
setmetatable(o, self)
self.__index = self
o:setHeight(o.h or self.h)
return o
end
function Cursor:setHeight(h)
self.h = h
self.w = self.h / 3
self.line_w = math.floor(self.h / self.line_width_factor)
end
function Cursor:_draw(x, y)
local up_down_width = math.floor(self.line_w / 2)
local body_h = self.h - (up_down_width * 2)
-- paint upper horizontal line
fb.bb:invertRect(x, y, self.w, up_down_width)
-- paint middle vertical line
fb.bb:invertRect(x + (self.w / 2) - up_down_width, y + up_down_width,
self.line_w, body_h)
-- paint lower horizontal line
fb.bb:invertRect(x, y + body_h + up_down_width, self.w, up_down_width)
end
function Cursor:draw()
if self.is_cleared then
self.is_cleared = false
self:_draw(self.x_pos, self.y_pos)
end
end
function Cursor:clear()
if not self.is_cleared then
self.is_cleared = true
self:_draw(self.x_pos, self.y_pos)
end
end
function Cursor:move(x_off, y_off)
self.x_pos = self.x_pos + x_off
self.y_pos = self.y_pos + y_off
end
function Cursor:moveHorizontal(x_off)
self.x_pos = self.x_pos + x_off
end
function Cursor:moveVertical(x_off)
self.y_pos = self.y_pos + y_off
end
function Cursor:moveAndDraw(x_off, y_off)
self:clear()
self:move(x_off, y_off)
self:draw()
end
function Cursor:moveTo(x_pos, y_pos)
self.x_pos = x_pos
self.y_pos = y_pos
end
function Cursor:moveToAndDraw(x_pos, y_pos)
self:clear()
self.x_pos = x_pos
self.y_pos = y_pos
self:draw()
end
function Cursor:moveHorizontalAndDraw(x_off)
self:clear()
self:move(x_off, 0)
self:draw()
end
function Cursor:moveVerticalAndDraw(y_off)
self:clear()
self:move(0, y_off)
self:draw()
end

@ -1,41 +1,42 @@
require "ui/event"
require "ui/device"
require "ui/time"
require "ui/gesturedetector"
require "ui/geometry"
local Device = require("ui/device")
local GestureDetector = require("ui/gesturedetector")
local Event = require("ui/event")
local TimeVal = require("ui/timeval")
local Screen = require("ui/screen")
local Dbg = require("dbg")
-- constants from <linux/input.h>
EV_SYN = 0
EV_KEY = 1
EV_ABS = 3
local EV_SYN = 0
local EV_KEY = 1
local EV_ABS = 3
-- key press event values (KEY.value)
EVENT_VALUE_KEY_PRESS = 1
EVENT_VALUE_KEY_REPEAT = 2
EVENT_VALUE_KEY_RELEASE = 0
local EVENT_VALUE_KEY_PRESS = 1
local EVENT_VALUE_KEY_REPEAT = 2
local EVENT_VALUE_KEY_RELEASE = 0
-- Synchronization events (SYN.code).
SYN_REPORT = 0
SYN_CONFIG = 1
SYN_MT_REPORT = 2
local SYN_REPORT = 0
local SYN_CONFIG = 1
local SYN_MT_REPORT = 2
-- For single-touch events (ABS.code).
ABS_X = 00
ABS_Y = 01
ABS_PRESSURE = 24
local ABS_X = 00
local ABS_Y = 01
local ABS_PRESSURE = 24
-- For multi-touch events (ABS.code).
ABS_MT_SLOT = 47
ABS_MT_POSITION_X = 53
ABS_MT_POSITION_Y = 54
ABS_MT_TRACKING_ID = 57
ABS_MT_PRESSURE = 58
local ABS_MT_SLOT = 47
local ABS_MT_POSITION_X = 53
local ABS_MT_POSITION_Y = 54
local ABS_MT_TRACKING_ID = 57
local ABS_MT_PRESSURE = 58
--[[
an interface for key presses
]]
Key = {}
local Key = {}
function Key:new(key, modifiers)
local o = { key = key, modifiers = modifiers }
@ -124,7 +125,7 @@ end
--[[
an interface to get input events
]]
Input = {
local Input = {
event_map = {},
modifiers = {},
rotation_map = {
@ -133,7 +134,6 @@ Input = {
[2] = { Up = "Down", Right = "Left", Down = "Up", Left = "Right" },
[3] = { Up = "Left", Right = "Up", Down = "Right", Left = "Down" }
},
rotation = 0,
timer_callbacks = {},
disable_double_tap = DGESDETECT_DISABLE_DOUBLE_TAP,
}
@ -255,9 +255,6 @@ function Input:initTouchState()
end
function Input:init()
-- Screen module must have been initilized by now.
self.rotation = Screen:getRotationMode()
if Device:hasKeyboard() then
self:initKeyMap()
end
@ -414,8 +411,8 @@ function Input:handleKeyBoardEv(ev)
end
-- take device rotation into account
if self.rotation_map[self.rotation][keycode] then
keycode = self.rotation_map[self.rotation][keycode]
if self.rotation_map[Screen:getRotationMode()][keycode] then
keycode = self.rotation_map[Screen:getRotationMode()][keycode]
end
if keycode == "IntoSS" or keycode == "OutOfSS"
@ -661,3 +658,9 @@ function Input:sequenceToString(sequence)
end
return table.concat(keystring)
end
-- initialize the GestureDectector
-- so it can modify our (Input) state
GestureDetector.input = Input
return Input

@ -0,0 +1,49 @@
local Configurable = {}
function Configurable:hash(sep)
local hash = ""
local excluded = {multi_threads = true,}
for key,value in pairs(self) do
if type(value) == "number" or type(value) == "string"
and not excluded[key] then
hash = hash..sep..value
end
end
return hash
end
function Configurable:loadDefaults(config_options)
for i=1,#config_options do
local options = config_options[i].options
for j=1,#config_options[i].options do
local key = config_options[i].options[j].name
self[key] = config_options[i].options[j].default_value
if not self[key] then
self[key] = config_options[i].options[j].default_arg
end
end
end
end
function Configurable:loadSettings(settings, prefix)
for key,value in pairs(self) do
if type(value) == "number" or type(value) == "string"
or type(value) == "table" then
local saved_value = settings:readSetting(prefix..key)
self[key] = (saved_value == nil) and self[key] or saved_value
--Debug("Configurable:loadSettings", "key", key, "saved value", saved_value,"Configurable.key", self[key])
end
end
--Debug("loaded config:", dump(Configurable))
end
function Configurable:saveSettings(settings, prefix)
for key,value in pairs(self) do
if type(value) == "number" or type(value) == "string"
or type(value) == "table" then
settings:saveSetting(prefix..key, value)
end
end
end
return Configurable

@ -1,6 +1,8 @@
require "ui/device"
local EventListener = require("ui/widget/eventlistener")
local Device = require("ui/device")
-- lipc
ReaderActivityIndicator = EventListener:new{}
local ReaderActivityIndicator = EventListener:new{}
function ReaderActivityIndicator:init()
local dev_mod = Device:getModel()
@ -41,3 +43,5 @@ function ReaderActivityIndicator:onStopActivityIndicator()
end
return true
end
return ReaderActivityIndicator

@ -1,6 +1,15 @@
require "ui/widget/notification"
ReaderBookmark = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local Menu = require("ui/widget/menu")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
local UIManager = require("ui/uimanager")
local Event = require("ui/event")
local _ = require("gettext")
local ReaderBookmark = InputContainer:new{
bm_menu_title = _("Bookmarks"),
bookmarks = nil,
}
@ -170,3 +179,5 @@ function ReaderBookmark:toggleBookmark(pn_or_xp)
end
self:addBookmark(pn_or_xp)
end
return ReaderBookmark

@ -1,54 +1,14 @@
require "ui/widget/config"
Configurable = {}
function Configurable:hash(sep)
local hash = ""
local excluded = {multi_threads = true,}
for key,value in pairs(self) do
if type(value) == "number" or type(value) == "string"
and not excluded[key] then
hash = hash..sep..value
end
end
return hash
end
function Configurable:loadDefaults(config_options)
for i=1,#config_options do
local options = config_options[i].options
for j=1,#config_options[i].options do
local key = config_options[i].options[j].name
self[key] = config_options[i].options[j].default_value
if not self[key] then
self[key] = config_options[i].options[j].default_arg
end
end
end
end
function Configurable:loadSettings(settings, prefix)
for key,value in pairs(self) do
if type(value) == "number" or type(value) == "string"
or type(value) == "table" then
local saved_value = settings:readSetting(prefix..key)
self[key] = (saved_value == nil) and self[key] or saved_value
--Debug("Configurable:loadSettings", "key", key, "saved value", saved_value,"Configurable.key", self[key])
end
end
--Debug("loaded config:", dump(Configurable))
end
function Configurable:saveSettings(settings, prefix)
for key,value in pairs(self) do
if type(value) == "number" or type(value) == "string"
or type(value) == "table" then
settings:saveSetting(prefix..key, value)
end
end
end
ReaderConfig = InputContainer:new{
local ConfigDialog = require("ui/widget/configdialog")
local InputContainer = require("ui/widget/container/inputcontainer")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
local Event = require("ui/event")
local UIManager = require("ui/uimanager")
local _ = require("gettext")
local ReaderConfig = InputContainer:new{
last_panel_index = 1,
}
@ -130,3 +90,5 @@ function ReaderConfig:onCloseDocument()
self.configurable:saveSettings(self.ui.doc_settings, self.options.prefix.."_")
self.ui.doc_settings:saveSetting("config_panel_index", self.last_panel_index)
end
return ReaderConfig

@ -1,5 +1,6 @@
local EventListener = require("ui/widget/eventlistener")
ReaderCoptListener = EventListener:new{}
local ReaderCoptListener = EventListener:new{}
function ReaderCoptListener:onReadSettings(config)
local embedded_css = config:readSetting("copt_embedded_css")
@ -37,3 +38,5 @@ function ReaderCoptListener:onReadSettings(config)
end)
end
end
return ReaderCoptListener

@ -1,13 +1,22 @@
require "ui/widget/group"
require "ui/widget/bbox"
require "ui/widget/button"
local InputContainer = require("ui/widget/container/inputcontainer")
local UIManager = require("ui/uimanager")
local Geom = require("ui/geometry")
local Event = require("ui/event")
local Screen = require("ui/screen")
local LeftContainer = require("ui/widget/container/leftcontainer")
local RightContainer = require("ui/widget/container/rightcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local VerticalGroup = require("ui/widget/verticalgroup")
local HorizontalGroup = require("ui/widget/horizontalgroup")
local Button = require("ui/widget/button")
local _ = require("gettext")
PageCropDialog = VerticalGroup:new{
local PageCropDialog = VerticalGroup:new{
ok_text = "OK",
cancel_text = "Cancel",
ok_callback = function() end,
cancel_callback = function() end,
button_width = math.floor(scaleByDPI(70)),
button_width = math.floor(Screen:scaleByDPI(70)),
}
function PageCropDialog:init()
@ -49,7 +58,7 @@ function PageCropDialog:init()
}
end
ReaderCropping = InputContainer:new{}
local ReaderCropping = InputContainer:new{}
function ReaderCropping:onPageCrop(mode)
if mode == "auto" then return end
@ -147,3 +156,5 @@ end
function ReaderCropping:onCloseDocument()
self.ui.doc_settings:saveSetting("bbox", self.document.bbox)
end
return ReaderCropping

@ -1,11 +1,9 @@
require "ui/device"
require "ui/widget/dict"
local EventListener = require("ui/widget/eventlistener")
local UIManager = require("ui/uimanager")
local DictQuickLookup = require("ui/widget/dictquicklookup")
local JSON = require("JSON")
ReaderDictionary = EventListener:new{}
function ReaderDictionary:init()
JSON = require("JSON")
end
local ReaderDictionary = EventListener:new{}
function ReaderDictionary:onLookupWord(word)
self:stardictLookup(word)
@ -38,7 +36,7 @@ function ReaderDictionary:showDict(results)
dialog = self.dialog,
results = results,
dictionary = self.default_dictionary,
width = Screen:getWidth() - scaleByDPI(120),
width = Screen:getWidth() - screen:scaleByDPI(120),
height = Screen:getHeight()*0.43,
})
end
@ -56,3 +54,5 @@ end
function ReaderDictionary:onCloseDocument()
self.ui.doc_settings:saveSetting("default_dictionary", self.default_dictionary)
end
return ReaderDictionary

@ -1,6 +1,9 @@
require "ui/widget/image"
local RightContainer = require("ui/widget/container/rightcontainer")
local ImageWidget = require("ui/widget/imagewidget")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
ReaderDogear = RightContainer:new{}
local ReaderDogear = RightContainer:new{}
function ReaderDogear:init()
local widget = ImageWidget:new{
@ -15,3 +18,5 @@ function ReaderDogear:onSetDogearVisibility(visible)
self.view.dogear_visible = visible
return true
end
return ReaderDogear

@ -1,5 +1,9 @@
local LeftContainer = require("ui/widget/container/leftcontainer")
local ImageWidget = require("ui/widget/imagewidget")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
ReaderFlipping = LeftContainer:new{
local ReaderFlipping = LeftContainer:new{
orig_reflow_mode = 0,
}
@ -24,3 +28,5 @@ function ReaderFlipping:onSetFlippingMode(flipping_mode)
end
return true
end
return ReaderFlipping

@ -1,4 +1,10 @@
ReaderFont = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local Device = require("ui/device")
local Screen = require("ui/screen")
local UIManager = require("ui/uimanager")
local _ = require("gettext")
local ReaderFont = InputContainer:new{
font_face = nil,
font_size = nil,
line_space_percent = nil,
@ -231,3 +237,5 @@ function ReaderFont:addToMainMenu(tab_item_table)
sub_item_table = self.face_table,
})
end
return ReaderFont

@ -1,6 +1,16 @@
require "ui/widget/progress"
local InputContainer = require("ui/widget/container/inputcontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local RightContainer = require("ui/widget/container/rightcontainer")
local BottomContainer = require("ui/widget/container/bottomcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local ProgressWidget = require("ui/widget/progresswidget")
local TextWidget = require("ui/widget/textwidget")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
local Font = require("ui/font")
local HorizontalGroup = require("ui/widget/horizontalgroup")
ReaderFooter = InputContainer:new{
local ReaderFooter = InputContainer:new{
pageno = nil,
pages = nil,
progress_percentage = 0.0,
@ -24,16 +34,16 @@ function ReaderFooter:init()
}
local _, text_height = self.progress_text:getSize()
local horizontal_group = HorizontalGroup:new{}
local bar_containner = RightContainer:new{
local bar_container = RightContainer:new{
dimen = Geom:new{w = Screen:getWidth()*self.bar_width, h = self.height},
self.progress_bar,
}
local text_containner = CenterContainer:new{
local text_container = CenterContainer:new{
dimen = Geom:new{w = Screen:getWidth()*self.text_width, h = self.height},
self.progress_text,
}
table.insert(horizontal_group, bar_containner)
table.insert(horizontal_group, text_containner)
table.insert(horizontal_group, bar_container)
table.insert(horizontal_group, text_container)
self[1] = BottomContainer:new{
dimen = Screen:getSize(),
FrameContainer:new{
@ -63,3 +73,5 @@ function ReaderFooter:onPageUpdate(pageno)
self.pages = self.view.document.info.number_of_pages
self:updateFooter()
end
return ReaderFooter

@ -1,8 +1,11 @@
require "ui/widget/container"
require "ui/widget/inputdialog"
require "ui/device"
local InputContainer = require("ui/widget/container/inputcontainer")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local _ = require("gettext")
ReaderFrontLight = InputContainer:new{
local ReaderFrontLight = InputContainer:new{
steps = {0,1,2,3,4,5,6,7,8,9,10},
}
@ -111,3 +114,5 @@ function ReaderFrontLight:fldialIntensity()
Device:getFrontlight():setIntensity(number)
end
end
return ReaderFrontLight

@ -1,8 +1,11 @@
require "ui/widget/container"
require "ui/widget/inputdialog"
local InputContainer = require("ui/widget/container/inputcontainer")
local InputDialog = require("ui/widget/inputdialog")
local UIManager = require("ui/uimanager")
local Screen = require("ui/screen")
local Event = require("ui/event")
local _ = require("gettext")
ReaderGoto = InputContainer:new{
local ReaderGoto = InputContainer:new{
goto_menu_title = _("Go To"),
goto_dialog_title = _("Go to Page or Location"),
}
@ -77,3 +80,5 @@ function ReaderGoto:gotoLocation()
-- TODO: implement go to location
self:close()
end
return ReaderGoto

@ -1,6 +1,11 @@
require "ui/widget/buttontable"
local InputContainer = require("ui/widget/container/inputcontainer")
local GestureRange = require("ui/gesturerange")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
local Device = require("ui/device")
local _ = require("gettext")
ReaderHighlight = InputContainer:new{}
local ReaderHighlight = InputContainer:new{}
function ReaderHighlight:init()
if Device:hasKeyboard() then
@ -353,3 +358,5 @@ end
function ReaderHighlight:editHighlight()
DEBUG("edit highlight")
end
return ReaderHighlight

@ -1,5 +1,6 @@
local EventListener = require("ui/widget/eventlistener")
ReaderHinting = EventListener:new{
local ReaderHinting = EventListener:new{
hinting_states = {}
}
@ -32,3 +33,5 @@ function ReaderHinting:onRestoreHinting()
self.view.hinting = table.remove(self.hinting_states)
return true
end
return ReaderHinting

@ -1,5 +1,9 @@
local InputContainer = require("ui/widget/container/inputcontainer")
local UIManager = require("ui/uimanager")
local InfoMessage = require("ui/widget/infomessage")
local _ = require("gettext")
ReaderHyphenation = InputContainer:new{
local ReaderHyphenation = InputContainer:new{
hyph_menu_title = _("Hyphenation"),
hyph_table = nil,
cur_hyph_idx = nil,
@ -36,3 +40,5 @@ function ReaderHyphenation:addToMainMenu(tab_item_table)
sub_item_table = self.hyph_table,
})
end
return ReaderHyphenation

@ -1,5 +1,7 @@
local EventListener = require("ui/widget/eventlistener")
local Event = require("ui/event")
ReaderKoptListener = EventListener:new{}
local ReaderKoptListener = EventListener:new{}
function ReaderKoptListener:setZoomMode(zoom_mode)
if self.document.configurable.text_wrap == 1 then
@ -58,3 +60,5 @@ function ReaderKoptListener:onDocLangUpdate(lang)
self.document.configurable.word_spacing = DKOPTREADER_CONFIG_WORD_SAPCINGS[3]
end
end
return ReaderKoptListener

@ -1,7 +1,15 @@
require "ui/widget/menu"
require "ui/widget/touchmenu"
ReaderMenu = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local TouchMenu = require("ui/widget/touchmenu")
local UIManager = require("ui/uimanager")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local Geom = require("ui/geometry")
local Event = require("ui/event")
local Screen = require("ui/screen")
local _ = require("gettext")
local ReaderMenu = InputContainer:new{
tab_item_table = nil,
registered_widgets = {},
}
@ -133,3 +141,4 @@ function ReaderMenu:registerToMainMenu(widget)
table.insert(self.registered_widgets, widget)
end
return ReaderMenu

@ -1,12 +1,20 @@
require "math"
ReaderPaging = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
local Input = require("ui/input")
local GestureRange = require("ui/gesturerange")
local Device = require("ui/device")
local Event = require("ui/event")
local UIManager = require("ui/uimanager")
local Math = require("optmath")
local ReaderPaging = InputContainer:new{
current_page = 0,
number_of_pages = 0,
visible_area = nil,
page_area = nil,
show_overlap_enable = DSHOWOVERLAP,
overlap = scaleByDPI(20),
overlap = Screen:scaleByDPI(20),
flip_steps = {0,1,2,5,10,20,50,100}
}
@ -569,10 +577,10 @@ function ReaderPaging:onGotoPageRel(diff)
-- adjust offset to help with page turn decision
-- we dont take overlap into account here yet, otherwise new_va will
-- always intersect with page_area
x_pan_off = math.roundAwayFromZero(x_pan_off)
y_pan_off = math.roundAwayFromZero(y_pan_off)
new_va.x = math.roundAwayFromZero(self.visible_area.x+x_pan_off)
new_va.y = math.roundAwayFromZero(self.visible_area.y+y_pan_off)
x_pan_off = Math.roundAwayFromZero(x_pan_off)
y_pan_off = Math.roundAwayFromZero(y_pan_off)
new_va.x = Math.roundAwayFromZero(self.visible_area.x+x_pan_off)
new_va.y = Math.roundAwayFromZero(self.visible_area.y+y_pan_off)
if new_va:notIntersectWith(self.page_area) then
-- view area out of page area, do a page turn
@ -604,8 +612,8 @@ function ReaderPaging:onGotoPageRel(diff)
y_pan_off = y_pan_off + self.overlap
end
-- we have to calculate again to count into overlap
new_va.x = math.roundAwayFromZero(self.visible_area.x+x_pan_off)
new_va.y = math.roundAwayFromZero(self.visible_area.y+y_pan_off)
new_va.x = Math.roundAwayFromZero(self.visible_area.x+x_pan_off)
new_va.y = Math.roundAwayFromZero(self.visible_area.y+y_pan_off)
end
-- fit new view area into page area
new_va:offsetWithin(self.page_area, 0, 0)
@ -676,3 +684,5 @@ function ReaderPaging:onGotoPage(number)
self:gotoPage(number)
return true
end
return ReaderPaging

@ -1,4 +1,8 @@
ReaderPanning = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local Device = require("ui/device")
local _ = require("gettext")
local ReaderPanning = InputContainer:new{
-- defaults
panning_steps = {
normal = 50,
@ -42,3 +46,5 @@ function ReaderPanning:onPanning(args, key)
dy * self.panning_steps.normal * self.dimen.h / 100)
return true
end
return ReaderPanning

@ -1,6 +1,12 @@
require "ui/reader/readerpanning"
local InputContainer = require("ui/widget/container/inputcontainer")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
local Input = require("ui/input")
local GestureRange = require("ui/gesturerange")
local ReaderPanning = require("ui/reader/readerpanning")
local _ = require("gettext")
ReaderRolling = InputContainer:new{
local ReaderRolling = InputContainer:new{
old_doc_height = nil,
old_page = nil,
current_pos = 0,
@ -325,4 +331,4 @@ function ReaderRolling:gotoPercent(new_percent)
self:gotoPos(new_percent * self.doc_height / 10000)
end
return ReaderRolling

@ -1,4 +1,11 @@
ReaderRotation = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local _ = require("gettext")
local ReaderRotation = InputContainer:new{
ROTATE_ANGLE_THRESHOLD = 15,
current_rotation = 0
}
@ -66,3 +73,5 @@ function ReaderRotation:onTwoFingerPanRelease(arg, ges)
self.rotate_angle = nil
end
end
return ReaderRotation

@ -1,5 +1,9 @@
local InputContainer = require("ui/widget/container/inputcontainer")
local Screen = require("ui/screen")
local GestureRange = require("ui/gesturerange")
local UIManager = require("ui/uimanager")
ReaderScreenshot = InputContainer:new{}
local ReaderScreenshot = InputContainer:new{}
function ReaderScreenshot:init()
local diagonal = math.sqrt(
@ -10,7 +14,7 @@ function ReaderScreenshot:init()
Screenshot = {
GestureRange:new{
ges = "two_finger_tap",
scale = {diagonal - scaleByDPI(100), diagonal},
scale = {diagonal - Screen:scaleByDPI(100), diagonal},
rate = 1.0,
}
},
@ -23,3 +27,4 @@ function ReaderScreenshot:onScreenshot()
return true
end
return ReaderScreenshot

@ -1,4 +1,12 @@
ReaderToc = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local Menu = require("ui/widget/menu")
local Screen = require("ui/screen")
local Device = require("ui/device")
local UIManager = require("ui/uimanager")
local _ = require("gettext")
local ReaderToc = InputContainer:new{
toc = nil,
toc_menu_title = _("Table of contents"),
}
@ -113,3 +121,5 @@ function ReaderToc:addToMainMenu(tab_item_table)
end,
})
end
return ReaderToc

@ -1,4 +1,8 @@
ReaderTypeset = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local _ = require("gettext")
-- lfs
local ReaderTypeset = InputContainer:new{
css_menu_title = _("Set render style"),
css = nil,
internal_css = true,
@ -106,4 +110,4 @@ function ReaderTypeset:addToMainMenu(tab_item_table)
})
end
return ReaderTypeset

@ -1,9 +1,13 @@
require "ui/widget/group"
require "ui/reader/readerflip"
require "ui/reader/readerfooter"
require "ui/reader/readerdogear"
ReaderView = OverlapGroup:new{
local OverlapGroup = require("ui/widget/overlapgroup")
local Screen = require("ui/screen")
local ReaderFlipping = require("ui/reader/readerflipping")
local ReaderFooter = require("ui/reader/readerfooter")
local ReaderDogear = require("ui/reader/readerdogear")
local Geom = require("ui/geometry")
local Event = require("ui/event")
local UIManager = require("ui/uimanager")
local ReaderView = OverlapGroup:new{
document = nil,
-- single page state
@ -32,8 +36,8 @@ ReaderView = OverlapGroup:new{
page_states = {},
scroll_mode = "vertical",
page_gap = {
width = scaleByDPI(8),
height = scaleByDPI(8),
width = Screen:scaleByDPI(8),
height = Screen:scaleByDPI(8),
color = 8,
},
-- DjVu page rendering mode (used in djvu.c:drawPage())
@ -571,3 +575,5 @@ function ReaderView:onCloseDocument()
self.ui.doc_settings:saveSetting("gamma", self.state.gamma)
self.ui.doc_settings:saveSetting("highlight", self.highlight.saved)
end
return ReaderView

@ -1,4 +1,13 @@
ReaderZooming = InputContainer:new{
local InputContainer = require("ui/widget/container/inputcontainer")
local Device = require("ui/device")
local Input = require("ui/input")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
local GestureRange = require("ui/gesturerange")
local Event = require("ui/event")
local _ = require("gettext")
local ReaderZooming = InputContainer:new{
zoom = 1.0,
-- default to nil so we can trigger ZoomModeUpdate events on start up
zoom_mode = nil,
@ -262,3 +271,5 @@ function ReaderZooming:addToMainMenu(tab_item_table)
})
end
end
return ReaderZooming

@ -1,26 +1,34 @@
require "ui/reader/readerview"
require "ui/reader/readerzooming"
require "ui/reader/readerpanning"
require "ui/reader/readerrotation"
require "ui/reader/readerpaging"
require "ui/reader/readerrolling"
require "ui/reader/readertoc"
require "ui/reader/readerbookmark"
require "ui/reader/readerfont"
require "ui/reader/readertypeset"
require "ui/reader/readermenu"
require "ui/reader/readergoto"
require "ui/reader/readerconfig"
require "ui/reader/readercropping"
require "ui/reader/readerkopt"
require "ui/reader/readercopt"
require "ui/reader/readerhinting"
require "ui/reader/readerhighlight"
require "ui/reader/readerscreenshot"
require "ui/reader/readerfrontlight"
require "ui/reader/readerdictionary"
require "ui/reader/readerhyphenation"
require "ui/reader/readeractivityindicator"
local InputContainer = require("ui/widget/container/inputcontainer")
local Geom = require("ui/geometry")
local Device = require("ui/device")
local DocSettings = require("docsettings")
local Event = require("ui/event")
local UIManager = require("ui/uimanager")
local _ = require("gettext")
local ReaderView = require("ui/reader/readerview")
local ReaderZooming = require("ui/reader/readerzooming")
local ReaderPanning = require("ui/reader/readerpanning")
local ReaderRotation = require("ui/reader/readerrotation")
local ReaderPaging = require("ui/reader/readerpaging")
local ReaderRolling = require("ui/reader/readerrolling")
local ReaderToc = require("ui/reader/readertoc")
local ReaderBookmark = require("ui/reader/readerbookmark")
local ReaderFont = require("ui/reader/readerfont")
local ReaderTypeset = require("ui/reader/readertypeset")
local ReaderMenu = require("ui/reader/readermenu")
local ReaderGoto = require("ui/reader/readergoto")
local ReaderConfig = require("ui/reader/readerconfig")
local ReaderCropping = require("ui/reader/readercropping")
local ReaderKoptListener = require("ui/reader/readerkoptlistener")
local ReaderCoptListener = require("ui/reader/readercoptlistener")
local ReaderHinting = require("ui/reader/readerhinting")
local ReaderHighlight = require("ui/reader/readerhighlight")
local ReaderScreenshot = require("ui/reader/readerscreenshot")
local ReaderFrontLight = require("ui/reader/readerfrontlight")
local ReaderDictionary = require("ui/reader/readerdictionary")
local ReaderHyphenation = require("ui/reader/readerhyphenation")
local ReaderActivityIndicator = require("ui/reader/readeractivityindicator")
--[[
This is an abstraction for a reader interface
@ -28,7 +36,7 @@ This is an abstraction for a reader interface
it works using data gathered from a document interface
]]--
ReaderUI = InputContainer:new{
local ReaderUI = InputContainer:new{
key_events = {
Close = { { "Home" },
doc = _("close document"), event = "Close" },
@ -278,3 +286,4 @@ function ReaderUI:onClose()
return true
end
return ReaderUI

@ -1,10 +1,12 @@
require "cache"
local Cache = require("cache")
local CacheItem = require("cacheitem")
--[[
TODO: all these functions should probably be methods on Face objects
]]--
local RenderText = {}
GlyphCache = Cache:new{
local GlyphCache = Cache:new{
max_memsize = 512*1024,
current_memsize = 0,
cache = {},
@ -56,7 +58,7 @@ local function utf8Chars(input)
return read_next_glyph, input, 1
end
function getGlyph(face, charcode, bgcolor, fgcolor)
function RenderText:getGlyph(face, charcode, bgcolor, fgcolor)
if bgcolor == nil then bgcolor = 0.0 end
if fgcolor == nil then fgcolor = 1.0 end
local hash = "glyph|"..face.hash.."|"..charcode.."|"..bgcolor.."|"..fgcolor
@ -87,13 +89,13 @@ function getGlyph(face, charcode, bgcolor, fgcolor)
return rendered_glyph
end
function getSubTextByWidth(text, face, width, kerning)
function RenderText:getSubTextByWidth(text, face, width, kerning)
local pen_x = 0
local prevcharcode = 0
local char_list = {}
for _, charcode, uchar in utf8Chars(text) do
if pen_x < width then
local glyph = getGlyph(face, charcode)
local glyph = self:getGlyph(face, charcode)
if kerning and prevcharcode then
local kern = face.ftface:getKerning(prevcharcode, charcode)
pen_x = pen_x + kern
@ -110,7 +112,7 @@ function getSubTextByWidth(text, face, width, kerning)
return table.concat(char_list)
end
function sizeUtf8Text(x, width, face, text, kerning)
function RenderText:sizeUtf8Text(x, width, face, text, kerning)
if not text then
DEBUG("sizeUtf8Text called without text");
return
@ -124,7 +126,7 @@ function sizeUtf8Text(x, width, face, text, kerning)
local prevcharcode = 0
for _, charcode, uchar in utf8Chars(text) do
if pen_x < (width - x) then
local glyph = getGlyph(face, charcode)
local glyph = self:getGlyph(face, charcode)
if kerning and (prevcharcode ~= 0) then
pen_x = pen_x + (face.ftface):getKerning(prevcharcode, charcode)
end
@ -138,7 +140,7 @@ function sizeUtf8Text(x, width, face, text, kerning)
return { x = pen_x, y_top = pen_y_top, y_bottom = pen_y_bottom}
end
function renderUtf8Text(buffer, x, y, face, text, kerning, bgcolor, fgcolor)
function RenderText:renderUtf8Text(buffer, x, y, face, text, kerning, bgcolor, fgcolor)
if not text then
DEBUG("renderUtf8Text called without text");
return 0
@ -151,7 +153,7 @@ function renderUtf8Text(buffer, x, y, face, text, kerning, bgcolor, fgcolor)
local buffer_width = buffer:getWidth()
for _, charcode, uchar in utf8Chars(text) do
if pen_x < buffer_width then
local glyph = getGlyph(face, charcode, bgcolor, fgcolor)
local glyph = self:getGlyph(face, charcode, bgcolor, fgcolor)
if kerning and (prevcharcode ~= 0) then
pen_x = pen_x + face.ftface:getKerning(prevcharcode, charcode)
end
@ -167,3 +169,5 @@ function renderUtf8Text(buffer, x, y, face, text, kerning, bgcolor, fgcolor)
return pen_x
end
return RenderText

@ -1,19 +1,8 @@
--[[
Copyright (C) 2011 Hans-Werner Hilse <hilse@web.de>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
local Device = require("ui/device")
local Geom = require("ui/geometry")
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
]]--
-- Blitbuffer
-- einkfb
--[[
Codes for rotation modes:
@ -39,7 +28,7 @@ Codes for rotation modes:
--]]
Screen = {
local Screen = {
width = 0,
height = 0,
native_rotation_mode = nil,
@ -138,16 +127,6 @@ function Screen:rescaleByDPI(px)
return math.ceil(px * 167/self:getDPI())
end
-- make a shortcut to Screen:scaleByDPI
function scaleByDPI(px)
return Screen:scaleByDPI(px)
end
-- make a shortcut to Screen:rescaleByDPI
function rescaleByDPI(px)
return Screen:rescaleByDPI(px)
end
function Screen:getPitch()
return self.fb:getPitch()
end
@ -181,8 +160,6 @@ function Screen:setRotationMode(mode)
self.cur_rotation_mode = mode
self.bb:free()
self.bb = Blitbuffer.new(self.width, self.height, self.width/2)
-- update mode for input module
Input.rotation = mode
end
function Screen:setScreenMode(mode)
@ -229,3 +206,5 @@ function Screen:restoreFromBB(bb)
DEBUG("Got nil bb in restoreFromSavedBB!")
end
end
return Screen

@ -1,4 +1,4 @@
TimeVal = {
local TimeVal = {
sec = 0,
usec = 0,
}
@ -100,3 +100,5 @@ function TimeVal:now()
local sec, usec = util.gettime()
return TimeVal:new{sec = sec, usec = usec}
end
return TimeVal

@ -1,28 +1,25 @@
require "ui/geometry"
require "ui/device"
require "ui/inputevent"
require "ui/widget/container"
require "ui/screen"
require "debug"
require "gettext"
local Device = require("ui/device")
local Screen = require("ui/screen")
local Input = require("ui/input")
local Event = require("ui/event")
-- initialize output module, this must be initialized before Input
Screen:init()
-- initialize the input handling
Input:init()
WAVEFORM_MODE_INIT = 0x0 -- Screen goes to white (clears)
WAVEFORM_MODE_DU = 0x1 -- Grey->white/grey->black
WAVEFORM_MODE_GC16 = 0x2 -- High fidelity (flashing)
WAVEFORM_MODE_GC4 = WAVEFORM_MODE_GC16 -- For compatibility
WAVEFORM_MODE_GC16_FAST = 0x3 -- Medium fidelity
WAVEFORM_MODE_A2 = 0x4 -- Faster but even lower fidelity
WAVEFORM_MODE_GL16 = 0x5 -- High fidelity from white transition
WAVEFORM_MODE_GL16_FAST = 0x6 -- Medium fidelity from white transition
WAVEFORM_MODE_AUTO = 0x101
local WAVEFORM_MODE_INIT = 0x0 -- Screen goes to white (clears)
local WAVEFORM_MODE_DU = 0x1 -- Grey->white/grey->black
local WAVEFORM_MODE_GC16 = 0x2 -- High fidelity (flashing)
local WAVEFORM_MODE_GC4 = WAVEFORM_MODE_GC16 -- For compatibility
local WAVEFORM_MODE_GC16_FAST = 0x3 -- Medium fidelity
local WAVEFORM_MODE_A2 = 0x4 -- Faster but even lower fidelity
local WAVEFORM_MODE_GL16 = 0x5 -- High fidelity from white transition
local WAVEFORM_MODE_GL16_FAST = 0x6 -- Medium fidelity from white transition
local WAVEFORM_MODE_AUTO = 0x101
-- there is only one instance of this
UIManager = {
local UIManager = {
-- change this to set refresh type for next refresh
-- defaults to 1 initially and will be set to 1 after each refresh
default_refresh_type = 1,
@ -296,12 +293,12 @@ function UIManager:run()
Device:getFrontlight():toggle()
elseif (input_event == "Power" and not Device.screen_saver_mode) or
input_event == "Suspend" then
UIManager:show(InfoMessage:new{
self:show(InfoMessage:new{
text = _("Standby"),
timeout = 1,
})
Device:prepareSuspend()
UIManager:scheduleIn(0.5, function() Device:Suspend() end)
self:scheduleIn(0.5, function() Device:Suspend() end)
elseif (input_event == "Power" and Device.screen_saver_mode) or
input_event == "Resume" then
Device:Resume()
@ -311,3 +308,5 @@ function UIManager:run()
end
end
end
return UIManager

@ -1,10 +1,9 @@
require "math"
require "ui/widget/container"
local InputContainer = require("ui/widget/container/inputcontainer")
--[[
BBoxWidget shows a bbox for page cropping
]]
BBoxWidget = InputContainer:new{
local BBoxWidget = InputContainer:new{
page_bbox = nil,
screen_bbox = nil,
linesize = 2,
@ -212,3 +211,5 @@ function BBoxWidget:onConfirmAdjust(arg, ges)
end
return true
end
return BBoxWidget

@ -1,10 +1,18 @@
require "ui/widget/image"
require "ui/widget/container"
local InputContainer = require("ui/widget/container/inputcontainer")
local TextWidget = require("ui/widget/textwidget")
local ImageWidget = require("ui/widget/imagewidget")
local Font = require("ui/font")
local Geom = require("ui/geometry")
local GestureRange = require("ui/gesturerange")
local FrameContainer = require("ui/widget/container/framecontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local Device = require("ui/device")
local _ = require("gettext")
--[[
a button widget that shows text or a icon and handles callback when tapped
--]]
Button = InputContainer:new{
local Button = InputContainer:new{
text = nil, -- mandatory
icon = nil,
preselect = false,
@ -134,3 +142,5 @@ function Button:onTapSelect()
end
return true
end
return Button

@ -1,7 +1,12 @@
require "ui/widget/base"
require "ui/widget/line"
local VerticalGroup = require("ui/widget/verticalgroup")
local HorizontalGroup = require("ui/widget/horizontalgroup")
local VerticalSpan = require("ui/widget/verticalspan")
local LineWidget = require("ui/widget/linewidget")
local Button = require("ui/widget/button")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
ButtonTable = VerticalGroup:new{
local ButtonTable = VerticalGroup:new{
width = Screen:getWidth(),
buttons = {
{
@ -9,8 +14,8 @@ ButtonTable = VerticalGroup:new{
{text="Cancel", enabled=false, callback=nil},
},
},
sep_width = scaleByDPI(1),
padding = scaleByDPI(2),
sep_width = Screen:scaleByDPI(1),
padding = Screen:scaleByDPI(2),
zero_sep = false,
button_font_face = "cfont",
@ -59,7 +64,7 @@ function ButtonTable:init()
end
function ButtonTable:addHorizontalSep()
table.insert(self, VerticalSpan:new{ width = scaleByDPI(2) })
table.insert(self, VerticalSpan:new{ width = Screen:scaleByDPI(2) })
table.insert(self, LineWidget:new{
background = 8,
dimen = Geom:new{
@ -67,5 +72,7 @@ function ButtonTable:addHorizontalSep()
h = self.sep_width,
}
})
table.insert(self, VerticalSpan:new{ width = scaleByDPI(2) })
table.insert(self, VerticalSpan:new{ width = Screen:scaleByDPI(2) })
end
return ButtonTable

@ -1,7 +1,28 @@
require "ui/widget/container"
require "ui/widget/toggleswitch"
MenuBarItem = InputContainer:new{}
local InputContainer = require("ui/widget/container/inputcontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local RightContainer = require("ui/widget/container/rightcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local BottomContainer = require("ui/widget/container/bottomcontainer")
local UnderlineContainer = require("ui/widget/container/underlinecontainer")
local ImageWidget = require("ui/widget/imagewidget")
local TextWidget = require("ui/widget/textwidget")
local FixedTextWidget = require("ui/widget/fixedtextwidget")
local ToggleSwitch = require("ui/widget/toggleswitch")
local Font = require("ui/font")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local UIManager = require("ui/uimanager")
local RectSpan = require("ui/widget/rectspan")
local HorizontalSpan = require("ui/widget/horizontalspan")
local HorizontalGroup = require("ui/widget/horizontalgroup")
local VerticalSpan = require("ui/widget/verticalspan")
local VerticalGroup = require("ui/widget/verticalgroup")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
local Event = require("ui/event")
local _ = require("gettext")
local MenuBarItem = InputContainer:new{}
function MenuBarItem:init()
self.dimen = self[1]:getSize()
-- we need this table per-instance, so we declare it here
@ -40,7 +61,7 @@ function MenuBarItem:invert(invert)
UIManager:setDirty(self.config, "full")
end
OptionTextItem = InputContainer:new{}
local OptionTextItem = InputContainer:new{}
function OptionTextItem:init()
local text_widget = self[1]
@ -96,7 +117,7 @@ function OptionTextItem:onTapSelect()
return true
end
OptionIconItem = InputContainer:new{}
local OptionIconItem = InputContainer:new{}
function OptionIconItem:init()
self.dimen = self.icon:getSize()
self[1] = UnderlineContainer:new{
@ -138,19 +159,7 @@ function OptionIconItem:onTapSelect()
return true
end
--[[
Dummy Widget that reserves vertical and horizontal space
]]
RectSpan = Widget:new{
width = 0,
hright = 0,
}
function RectSpan:getSize()
return {w = self.width, h = self.height}
end
ConfigOption = CenterContainer:new{}
local ConfigOption = CenterContainer:new{}
function ConfigOption:init()
local default_name_font_size = 20
local default_item_font_size = 16
@ -159,7 +168,7 @@ function ConfigOption:init()
local default_option_padding = 15
local vertical_group = VerticalGroup:new{}
table.insert(vertical_group, VerticalSpan:new{
width = scaleByDPI(default_option_padding),
width = Screen:scaleByDPI(default_option_padding),
})
for c = 1, #self.options do
if self.options[c].show ~= false then
@ -169,9 +178,9 @@ function ConfigOption:init()
local name_font_size = self.options[c].name_font_size and self.options[c].name_font_size or default_name_font_size
local item_font_face = self.options[c].item_font_face and self.options[c].item_font_face or "cfont"
local item_font_size = self.options[c].item_font_size and self.options[c].item_font_size or default_item_font_size
local option_height = scaleByDPI(self.options[c].height and self.options[c].height or default_option_height)
local option_height = Screen:scaleByDPI(self.options[c].height and self.options[c].height or default_option_height)
local items_spacing = HorizontalSpan:new{
width = scaleByDPI(self.options[c].spacing and self.options[c].spacing or default_items_spacing)
width = Screen:scaleByDPI(self.options[c].spacing and self.options[c].spacing or default_items_spacing)
}
local horizontal_group = HorizontalGroup:new{}
if self.options[c].name_text then
@ -325,7 +334,7 @@ function ConfigOption:init()
if self.options[c].toggle then
local switch = ToggleSwitch:new{
width = scaleByDPI(self.options[c].width or 216),
width = Screen:scaleByDPI(self.options[c].width or 216),
name = self.options[c].name,
toggle = self.options[c].toggle,
alternate = self.options[c].alternate,
@ -350,7 +359,7 @@ function ConfigOption:init()
self.dimen = vertical_group:getSize()
end
ConfigPanel = FrameContainer:new{ background = 0, bordersize = 0, }
local ConfigPanel = FrameContainer:new{ background = 0, bordersize = 0, }
function ConfigPanel:init()
local config_options = self.config_dialog.config_options
local default_option = config_options.default_options and config_options.default_options
@ -363,7 +372,7 @@ function ConfigPanel:init()
table.insert(self, panel)
end
MenuBar = FrameContainer:new{ background = 0, }
local MenuBar = FrameContainer:new{ background = 0, }
function MenuBar:init()
local config_options = self.config_dialog.config_options
local menu_items = {}
@ -419,7 +428,7 @@ Widget that displays config menubar and config panel
--]]
ConfigDialog = InputContainer:new{
local ConfigDialog = InputContainer:new{
--is_borderless = false,
panel_index = 1,
}
@ -521,3 +530,5 @@ function ConfigDialog:onTapCloseMenu(arg, ges_ev)
return true
end
end
return ConfigDialog

@ -1,11 +1,14 @@
require "ui/widget/container"
require "ui/widget/focusmanager"
require "ui/widget/button"
local CenterContainer = require("ui/widget/container/centercontainer")
local FrameContainer = require("ui/widget/container/centercontainer")
local FocusManager = require("ui/widget/focusmanager")
local Button = require("ui/widget/button")
-- screen
--[[
Widget that shows a message and OK/Cancel buttons
]]
ConfirmBox = FocusManager:new{
local ConfirmBox = FocusManager:new{
text = _("no text"),
width = nil,
ok_text = _("OK"),
@ -88,3 +91,4 @@ function ConfirmBox:onSelect()
return true
end
return ConfirmBox

@ -1,326 +0,0 @@
require "ui/widget/base"
--[[
WidgetContainer is a container for another Widget
--]]
WidgetContainer = Widget:new()
function WidgetContainer:init()
if not self.dimen then
self.dimen = Geom:new{}
end
end
function WidgetContainer:getSize()
if self.dimen then
-- fixed size
return self.dimen
elseif self[1] then
-- return size of first child widget
return self[1]:getSize()
else
return Geom:new{ w = 0, h = 0 }
end
end
--[[
delete all child widgets
--]]
function WidgetContainer:clear()
while table.remove(self) do end
end
function WidgetContainer:paintTo(bb, x, y)
-- default to pass request to first child widget
if self[1] then
return self[1]:paintTo(bb, x, y)
end
end
function WidgetContainer:propagateEvent(event)
-- propagate to children
for _, widget in ipairs(self) do
if widget:handleEvent(event) then
-- stop propagating when an event handler returns true
return true
end
end
return false
end
--[[
Containers will pass events to children or react on them themselves
--]]
function WidgetContainer:handleEvent(event)
if not self:propagateEvent(event) then
-- call our own standard event handler
return Widget.handleEvent(self, event)
else
return true
end
end
function WidgetContainer:free()
for _, widget in ipairs(self) do
if widget.free then widget:free() end
end
end
--[[
BottomContainer contains its content (1 widget) at the bottom of its own
dimensions
--]]
BottomContainer = WidgetContainer:new()
function BottomContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
self[1]:paintTo(bb,
x + math.floor((self.dimen.w - contentSize.w)/2),
y + (self.dimen.h - contentSize.h))
end
--[[
CenterContainer centers its content (1 widget) within its own dimensions
--]]
CenterContainer = WidgetContainer:new()
function CenterContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
local x_pos = x
local y_pos = y
if self.ignore ~= "height" then
y_pos = y + math.floor((self.dimen.h - contentSize.h)/2)
end
if self.ignore ~= "width" then
x_pos = x + math.floor((self.dimen.w - contentSize.w)/2)
end
self[1]:paintTo(bb, x_pos, y_pos)
end
--[[
LeftContainer aligns its content (1 widget) at the left of its own dimensions
--]]
LeftContainer = WidgetContainer:new()
function LeftContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
self[1]:paintTo(bb, x , y + math.floor((self.dimen.h - contentSize.h)/2))
end
--[[
RightContainer aligns its content (1 widget) at the right of its own dimensions
--]]
RightContainer = WidgetContainer:new()
function RightContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
self[1]:paintTo(bb,
x + (self.dimen.w - contentSize.w),
y + math.floor((self.dimen.h - contentSize.h)/2))
end
--[[
A FrameContainer is some graphics content (1 widget) that is surrounded by a
frame
--]]
FrameContainer = WidgetContainer:new{
background = nil,
color = 15,
margin = 0,
radius = 0,
bordersize = 2,
padding = 5,
width = nil,
height = nil,
invert = false,
}
function FrameContainer:getSize()
local content_size = self[1]:getSize()
return Geom:new{
w = content_size.w + ( self.margin + self.bordersize + self.padding ) * 2,
h = content_size.h + ( self.margin + self.bordersize + self.padding ) * 2
}
end
function FrameContainer:paintTo(bb, x, y)
local my_size = self:getSize()
self.dimen = Geom:new{
x = x, y = y,
w = my_size.w,
h = my_size.h
}
local container_width = self.width or my_size.w
local container_height = self.height or my_size.h
--@TODO get rid of margin here? 13.03 2013 (houqp)
if self.background then
bb:paintRoundedRect(x, y, container_width, container_height,
self.background, self.radius)
end
if self.bordersize > 0 then
bb:paintBorder(x + self.margin, y + self.margin,
container_width - self.margin * 2,
container_height - self.margin * 2,
self.bordersize, self.color, self.radius)
end
if self[1] then
self[1]:paintTo(bb,
x + self.margin + self.bordersize + self.padding,
y + self.margin + self.bordersize + self.padding)
end
if self.invert then
bb:invertRect(x + self.bordersize, y + self.bordersize,
container_width - 2*self.bordersize,
container_height - 2*self.bordersize)
end
end
--[[
an UnderlineContainer is a WidgetContainer that is able to paint
a line under its child node
--]]
UnderlineContainer = WidgetContainer:new{
linesize = 2,
padding = 1,
color = 0,
vertical_align = "top",
}
function UnderlineContainer:getSize()
return self:getContentSize()
end
function UnderlineContainer:getContentSize()
local contentSize = self[1]:getSize()
return Geom:new{
w = contentSize.w,
h = contentSize.h + self.linesize + self.padding
}
end
function UnderlineContainer:paintTo(bb, x, y)
local container_size = self:getSize()
local content_size = self:getContentSize()
local p_y = y
if self.vertical_align == "center" then
p_y = math.floor((container_size.h - content_size.h) / 2) + y
elseif self.vertical_align == "bottom" then
p_y = (container_size.h - content_size.h) + y
end
self[1]:paintTo(bb, x, p_y)
bb:paintRect(x, y + container_size.h - self.linesize,
container_size.w, self.linesize, self.color)
end
--[[
an InputContainer is an WidgetContainer that handles input events
an example for a key_event is this:
PanBy20 = {
{ "Shift", Input.group.Cursor },
seqtext = "Shift+Cursor",
doc = "pan by 20px",
event = "Pan", args = 20, is_inactive = true,
},
PanNormal = {
{ Input.group.Cursor },
seqtext = "Cursor",
doc = "pan by 10 px", event = "Pan", args = 10,
},
Quit = { {"Home"} },
it is suggested to reference configurable sequences from another table
and store that table as configuration setting
--]]
InputContainer = WidgetContainer:new{
vertical_align = "top",
}
function InputContainer:_init()
-- we need to do deep copy here
local new_key_events = {}
if self.key_events then
for k,v in pairs(self.key_events) do
new_key_events[k] = v
end
end
self.key_events = new_key_events
local new_ges_events = {}
if self.ges_events then
for k,v in pairs(self.ges_events) do
new_ges_events[k] = v
end
end
self.ges_events = new_ges_events
if not self.dimen then
self.dimen = Geom:new{}
end
end
function InputContainer:paintTo(bb, x, y)
self.dimen.x = x
self.dimen.y = y
if self[1] then
if self.vertical_align == "center" then
local content_size = self[1]:getSize()
self[1]:paintTo(bb, x, y + math.floor((self.dimen.h - content_size.h)/2))
else
self[1]:paintTo(bb, x, y)
end
end
end
--[[
the following handler handles keypresses and checks if they lead to a command.
if this is the case, we retransmit another event within ourselves
--]]
function InputContainer:onKeyPress(key)
for name, seq in pairs(self.key_events) do
if not seq.is_inactive then
for _, oneseq in ipairs(seq) do
if key:match(oneseq) then
local eventname = seq.event or name
return self:handleEvent(Event:new(eventname, seq.args, key))
end
end
end
end
end
function InputContainer:onGesture(ev)
for name, gsseq in pairs(self.ges_events) do
for _, gs_range in ipairs(gsseq) do
--DEBUG("gs_range", gs_range)
if gs_range:match(ev) then
local eventname = gsseq.event or name
return self:handleEvent(Event:new(eventname, gsseq.args, ev))
end
end
end
end

@ -0,0 +1,20 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
--[[
BottomContainer contains its content (1 widget) at the bottom of its own
dimensions
--]]
local BottomContainer = WidgetContainer:new()
function BottomContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
self[1]:paintTo(bb,
x + math.floor((self.dimen.w - contentSize.w)/2),
y + (self.dimen.h - contentSize.h))
end
return BottomContainer

@ -0,0 +1,25 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
--[[
CenterContainer centers its content (1 widget) within its own dimensions
--]]
local CenterContainer = WidgetContainer:new()
function CenterContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
local x_pos = x
local y_pos = y
if self.ignore ~= "height" then
y_pos = y + math.floor((self.dimen.h - contentSize.h)/2)
end
if self.ignore ~= "width" then
x_pos = x + math.floor((self.dimen.w - contentSize.w)/2)
end
self[1]:paintTo(bb, x_pos, y_pos)
end
return CenterContainer

@ -0,0 +1,61 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
local Geom = require("ui/geometry")
--[[
A FrameContainer is some graphics content (1 widget) that is surrounded by a
frame
--]]
local FrameContainer = WidgetContainer:new{
background = nil,
color = 15,
margin = 0,
radius = 0,
bordersize = 2,
padding = 5,
width = nil,
height = nil,
invert = false,
}
function FrameContainer:getSize()
local content_size = self[1]:getSize()
return Geom:new{
w = content_size.w + ( self.margin + self.bordersize + self.padding ) * 2,
h = content_size.h + ( self.margin + self.bordersize + self.padding ) * 2
}
end
function FrameContainer:paintTo(bb, x, y)
local my_size = self:getSize()
self.dimen = Geom:new{
x = x, y = y,
w = my_size.w,
h = my_size.h
}
local container_width = self.width or my_size.w
local container_height = self.height or my_size.h
--@TODO get rid of margin here? 13.03 2013 (houqp)
if self.background then
bb:paintRoundedRect(x, y, container_width, container_height,
self.background, self.radius)
end
if self.bordersize > 0 then
bb:paintBorder(x + self.margin, y + self.margin,
container_width - self.margin * 2,
container_height - self.margin * 2,
self.bordersize, self.color, self.radius)
end
if self[1] then
self[1]:paintTo(bb,
x + self.margin + self.bordersize + self.padding,
y + self.margin + self.bordersize + self.padding)
end
if self.invert then
bb:invertRect(x + self.bordersize, y + self.bordersize,
container_width - 2*self.bordersize,
container_height - 2*self.bordersize)
end
end
return FrameContainer

@ -0,0 +1,94 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
local Event = require("ui/event")
--[[
an InputContainer is an WidgetContainer that handles input events
an example for a key_event is this:
PanBy20 = {
{ "Shift", Input.group.Cursor },
seqtext = "Shift+Cursor",
doc = "pan by 20px",
event = "Pan", args = 20, is_inactive = true,
},
PanNormal = {
{ Input.group.Cursor },
seqtext = "Cursor",
doc = "pan by 10 px", event = "Pan", args = 10,
},
Quit = { {"Home"} },
it is suggested to reference configurable sequences from another table
and store that table as configuration setting
--]]
local InputContainer = WidgetContainer:new{
vertical_align = "top",
}
function InputContainer:_init()
-- we need to do deep copy here
local new_key_events = {}
if self.key_events then
for k,v in pairs(self.key_events) do
new_key_events[k] = v
end
end
self.key_events = new_key_events
local new_ges_events = {}
if self.ges_events then
for k,v in pairs(self.ges_events) do
new_ges_events[k] = v
end
end
self.ges_events = new_ges_events
if not self.dimen then
self.dimen = Geom:new{}
end
end
function InputContainer:paintTo(bb, x, y)
self.dimen.x = x
self.dimen.y = y
if self[1] then
if self.vertical_align == "center" then
local content_size = self[1]:getSize()
self[1]:paintTo(bb, x, y + math.floor((self.dimen.h - content_size.h)/2))
else
self[1]:paintTo(bb, x, y)
end
end
end
--[[
the following handler handles keypresses and checks if they lead to a command.
if this is the case, we retransmit another event within ourselves
--]]
function InputContainer:onKeyPress(key)
for name, seq in pairs(self.key_events) do
if not seq.is_inactive then
for _, oneseq in ipairs(seq) do
if key:match(oneseq) then
local eventname = seq.event or name
return self:handleEvent(Event:new(eventname, seq.args, key))
end
end
end
end
end
function InputContainer:onGesture(ev)
for name, gsseq in pairs(self.ges_events) do
for _, gs_range in ipairs(gsseq) do
--DEBUG("gs_range", gs_range)
if gs_range:match(ev) then
local eventname = gsseq.event or name
return self:handleEvent(Event:new(eventname, gsseq.args, ev))
end
end
end
end
return InputContainer

@ -0,0 +1,17 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
--[[
LeftContainer aligns its content (1 widget) at the left of its own dimensions
--]]
local LeftContainer = WidgetContainer:new()
function LeftContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
self[1]:paintTo(bb, x , y + math.floor((self.dimen.h - contentSize.h)/2))
end
return LeftContainer

@ -0,0 +1,19 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
--[[
RightContainer aligns its content (1 widget) at the right of its own dimensions
--]]
local RightContainer = WidgetContainer:new()
function RightContainer:paintTo(bb, x, y)
local contentSize = self[1]:getSize()
if contentSize.w > self.dimen.w or contentSize.h > self.dimen.h then
-- throw error? paint to scrap buffer and blit partially?
-- for now, we ignore this
end
self[1]:paintTo(bb,
x + (self.dimen.w - contentSize.w),
y + math.floor((self.dimen.h - contentSize.h)/2))
end
return RightContainer

@ -0,0 +1,42 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
local Geom = require("ui/geometry")
--[[
an UnderlineContainer is a WidgetContainer that is able to paint
a line under its child node
--]]
local UnderlineContainer = WidgetContainer:new{
linesize = 2,
padding = 1,
color = 0,
vertical_align = "top",
}
function UnderlineContainer:getSize()
return self:getContentSize()
end
function UnderlineContainer:getContentSize()
local contentSize = self[1]:getSize()
return Geom:new{
w = contentSize.w,
h = contentSize.h + self.linesize + self.padding
}
end
function UnderlineContainer:paintTo(bb, x, y)
local container_size = self:getSize()
local content_size = self:getContentSize()
local p_y = y
if self.vertical_align == "center" then
p_y = math.floor((container_size.h - content_size.h) / 2) + y
elseif self.vertical_align == "bottom" then
p_y = (container_size.h - content_size.h) + y
end
self[1]:paintTo(bb, x, p_y)
bb:paintRect(x, y + container_size.h - self.linesize,
container_size.w, self.linesize, self.color)
end
return UnderlineContainer

@ -0,0 +1,70 @@
local Geom = require("ui/geometry")
local Widget = require("ui/widget/widget")
--[[
WidgetContainer is a container for another Widget
--]]
local WidgetContainer = Widget:new()
function WidgetContainer:init()
if not self.dimen then
self.dimen = Geom:new{}
end
end
function WidgetContainer:getSize()
if self.dimen then
-- fixed size
return self.dimen
elseif self[1] then
-- return size of first child widget
return self[1]:getSize()
else
return Geom:new{ w = 0, h = 0 }
end
end
--[[
delete all child widgets
--]]
function WidgetContainer:clear()
while table.remove(self) do end
end
function WidgetContainer:paintTo(bb, x, y)
-- default to pass request to first child widget
if self[1] then
return self[1]:paintTo(bb, x, y)
end
end
function WidgetContainer:propagateEvent(event)
-- propagate to children
for _, widget in ipairs(self) do
if widget:handleEvent(event) then
-- stop propagating when an event handler returns true
return true
end
end
return false
end
--[[
Containers will pass events to children or react on them themselves
--]]
function WidgetContainer:handleEvent(event)
if not self:propagateEvent(event) then
-- call our own standard event handler
return Widget.handleEvent(self, event)
else
return true
end
end
function WidgetContainer:free()
for _, widget in ipairs(self) do
if widget.free then widget:free() end
end
end
return WidgetContainer

@ -1,10 +1,19 @@
require "ui/widget/container"
require "ui/widget/buttontable"
local InputContainer = require("ui/widget/container/inputcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local TextWidget = require("ui/widget/textwidget")
local TextBoxWidget = require("ui/widget/textboxwidget")
local ScrollTextWidget = require("ui/widget/scrolltextwidget")
local LineWidget = require("ui/widget/linewidget")
local Screen = require("ui/screen")
local GestureRange = require("ui/gesturerange")
local Geom = require("ui/geometry")
local Font = require("ui/font")
--[[
Display quick lookup word definition
]]
DictQuickLookup = InputContainer:new{
local DictQuickLookup = InputContainer:new{
results = nil,
lookupword = nil,
dictionary = nil,
@ -16,13 +25,13 @@ DictQuickLookup = InputContainer:new{
width = nil,
height = nil,
title_padding = scaleByDPI(5),
title_margin = scaleByDPI(2),
word_padding = scaleByDPI(2),
word_margin = scaleByDPI(2),
definition_padding = scaleByDPI(2),
definition_margin = scaleByDPI(2),
button_padding = scaleByDPI(14),
title_padding = Screen:scaleByDPI(5),
title_margin = Screen:scaleByDPI(2),
word_padding = Screen:scaleByDPI(2),
word_margin = Screen:scaleByDPI(2),
definition_padding = Screen:scaleByDPI(2),
definition_margin = Screen:scaleByDPI(2),
button_padding = Screen:scaleByDPI(14),
}
function DictQuickLookup:init()
@ -133,7 +142,7 @@ function DictQuickLookup:update()
--background = 8,
dimen = Geom:new{
w = button_table:getSize().w + self.button_padding,
h = scaleByDPI(2),
h = Screen:scaleByDPI(2),
}
}
@ -260,3 +269,5 @@ function DictQuickLookup:onTapCloseDict(arg, ges_ev)
end
return true
end
return DictQuickLookup

@ -0,0 +1,24 @@
--[[
The EventListener is an interface that handles events
EventListeners have a rudimentary event handler/dispatcher that
will call a method "onEventName" for an event with name
"EventName"
--]]
local EventListener = {}
function EventListener:new(o)
local o = o or {}
setmetatable(o, self)
self.__index = self
if o.init then o:init() end
return o
end
function EventListener:handleEvent(event)
if self[event.handler] then
return self[event.handler](self, unpack(event.args))
end
end
return EventListener

@ -1,6 +1,9 @@
require "ui/widget/menu"
local Menu = require("ui/widget/menu")
local Screen = require("ui/screen")
local UIManager = require("ui/uimanager")
-- lfs
FileChooser = Menu:extend{
local FileChooser = Menu:extend{
height = Screen:getHeight(),
width = Screen:getWidth(),
no_title = true,
@ -73,3 +76,5 @@ function FileChooser:onFileSelect(file)
UIManager:close(self)
return true
end
return FileChooser

@ -0,0 +1,29 @@
local TextWidget = require("ui/widget/textwidget")
local RenderText = require("ui/rendertext")
local Geom = require("ui/geometry")
local Screen = require("ui/screen")
--[[
FixedTextWidget
--]]
local FixedTextWidget = TextWidget:new{}
function FixedTextWidget:getSize()
local tsize = RenderText:sizeUtf8Text(0, Screen:getWidth(), self.face, self.text, true)
if not tsize then
return Geom:new{}
end
self._length = tsize.x
self._height = self.face.size
return Geom:new{
w = self._length,
h = self._height,
}
end
function FixedTextWidget:paintTo(bb, x, y)
RenderText:renderUtf8Text(bb, x, y+self._height, self.face, self.text,
true, self.bgcolor, self.fgcolor)
end
return FixedTextWidget

@ -1,3 +1,6 @@
local InputContainer = require("ui/widget/container/inputcontainer")
-- UIManager
--[[
Wrapper Widget that manages focus for a whole dialog
@ -21,7 +24,7 @@ reach either <okbutton> or <cancelbutton>.
but notice that this does _not_ do the layout for you,
it rather defines an abstract layout.
]]
FocusManager = InputContainer:new{
local FocusManager = InputContainer:new{
selected = nil, -- defaults to x=1, y=1
layout = nil, -- mandatory
movement_allowed = { x = true, y = true }
@ -93,3 +96,5 @@ function FocusManager:onWrapLast()
self.selected.y = 1
return true
end
return FocusManager

@ -1,172 +0,0 @@
require "ui/widget/container"
--[[
A Layout widget that puts objects besides each others
--]]
HorizontalGroup = WidgetContainer:new{
align = "center",
_size = nil,
}
function HorizontalGroup:getSize()
if not self._size then
self._size = { w = 0, h = 0 }
self._offsets = { }
for i, widget in ipairs(self) do
local w_size = widget:getSize()
self._offsets[i] = {
x = self._size.w,
y = w_size.h
}
self._size.w = self._size.w + w_size.w
if w_size.h > self._size.h then
self._size.h = w_size.h
end
end
end
return self._size
end
function HorizontalGroup:paintTo(bb, x, y)
local size = self:getSize()
for i, widget in ipairs(self) do
if self.align == "center" then
widget:paintTo(bb,
x + self._offsets[i].x,
y + math.floor((size.h - self._offsets[i].y) / 2))
elseif self.align == "top" then
widget:paintTo(bb, x + self._offsets[i].x, y)
elseif self.align == "bottom" then
widget:paintTo(bb, x + self._offsets[i].x, y + size.h - self._offsets[i].y)
end
end
end
function HorizontalGroup:clear()
self:free()
WidgetContainer.clear(self)
end
function HorizontalGroup:resetLayout()
self._size = nil
self._offsets = {}
end
function HorizontalGroup:free()
self:resetLayout()
WidgetContainer.free(self)
end
--[[
A Layout widget that puts objects under each other
--]]
VerticalGroup = WidgetContainer:new{
align = "center",
_size = nil,
_offsets = {}
}
function VerticalGroup:getSize()
if not self._size then
self._size = { w = 0, h = 0 }
self._offsets = { }
for i, widget in ipairs(self) do
local w_size = widget:getSize()
self._offsets[i] = {
x = w_size.w,
y = self._size.h,
}
self._size.h = self._size.h + w_size.h
if w_size.w > self._size.w then
self._size.w = w_size.w
end
end
end
return self._size
end
function VerticalGroup:paintTo(bb, x, y)
local size = self:getSize()
for i, widget in ipairs(self) do
if self.align == "center" then
widget:paintTo(bb,
x + math.floor((size.w - self._offsets[i].x) / 2),
y + self._offsets[i].y)
elseif self.align == "left" then
widget:paintTo(bb, x, y + self._offsets[i].y)
elseif self.align == "right" then
widget:paintTo(bb,
x + size.w - self._offsets[i].x,
y + self._offsets[i].y)
end
end
end
function VerticalGroup:clear()
self:free()
WidgetContainer.clear(self)
end
function VerticalGroup:resetLayout()
self._size = nil
self._offsets = {}
end
function VerticalGroup:free()
self:resetLayout()
WidgetContainer.free(self)
end
--[[
A Layout widget that puts objects above each other
--]]
OverlapGroup = WidgetContainer:new{
_size = nil,
}
function OverlapGroup:getSize()
if not self._size then
self._size = {w = 0, h = 0}
self._offsets = { x = math.huge, y = math.huge }
for i, widget in ipairs(self) do
local w_size = widget:getSize()
if self._size.h < w_size.h then
self._size.h = w_size.h
end
if self._size.w < w_size.w then
self._size.w = w_size.w
end
end
end
if self.dimen.w then
self._size.w = self.dimen.w
end
if self.dimen.h then
self._size.h = self.dimen.h
end
return self._size
end
function OverlapGroup:paintTo(bb, x, y)
local size = self:getSize()
for i, wget in ipairs(self) do
local wget_size = wget:getSize()
if wget.align == "right" then
wget:paintTo(bb, x+size.w-wget_size.w, y)
elseif wget.align == "center" then
wget:paintTo(bb, x+math.floor((size.w-wget_size.w)/2), y)
else
-- default to left
wget:paintTo(bb, x, y)
end
end
end

@ -0,0 +1,61 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
--[[
A Layout widget that puts objects besides each others
--]]
local HorizontalGroup = WidgetContainer:new{
align = "center",
_size = nil,
}
function HorizontalGroup:getSize()
if not self._size then
self._size = { w = 0, h = 0 }
self._offsets = { }
for i, widget in ipairs(self) do
local w_size = widget:getSize()
self._offsets[i] = {
x = self._size.w,
y = w_size.h
}
self._size.w = self._size.w + w_size.w
if w_size.h > self._size.h then
self._size.h = w_size.h
end
end
end
return self._size
end
function HorizontalGroup:paintTo(bb, x, y)
local size = self:getSize()
for i, widget in ipairs(self) do
if self.align == "center" then
widget:paintTo(bb,
x + self._offsets[i].x,
y + math.floor((size.h - self._offsets[i].y) / 2))
elseif self.align == "top" then
widget:paintTo(bb, x + self._offsets[i].x, y)
elseif self.align == "bottom" then
widget:paintTo(bb, x + self._offsets[i].x, y + size.h - self._offsets[i].y)
end
end
end
function HorizontalGroup:clear()
self:free()
WidgetContainer.clear(self)
end
function HorizontalGroup:resetLayout()
self._size = nil
self._offsets = {}
end
function HorizontalGroup:free()
self:resetLayout()
WidgetContainer.free(self)
end
return HorizontalGroup

@ -0,0 +1,14 @@
local Widget = require("ui/widget/widget")
--[[
Dummy Widget that reserves horizontal space
--]]
local HorizontalSpan = Widget:new{
width = 0,
}
function HorizontalSpan:getSize()
return {w = self.width, h = 0}
end
return HorizontalSpan

@ -1,11 +1,12 @@
require "ui/widget/container"
require "ui/widget/image"
local InputContainer = require("ui/widget/container/inputcontainer")
local ImageWidget = require("ui/widget/imagewidget")
local GestureRange = require("ui/gesturerange")
local UIManager = require("ui/uimanager")
--[[
Button with a big icon image! Designed for touch device
--]]
IconButton = InputContainer:new{
local IconButton = InputContainer:new{
icon_file = "resources/info-confirm.png",
dimen = nil,
-- show_parent is used for UIManager:setDirty, so we can trigger repaint
@ -53,3 +54,4 @@ function IconButton:onSetDimensions(new_dimen)
self.dimen = new_dimen
end
return IconButton

@ -1,9 +1,11 @@
require "ui/widget/base"
local Widget = require("ui/widget/widget")
local Geom = require("ui/geometry")
-- Image
--[[
ImageWidget shows an image from a file
--]]
ImageWidget = Widget:new{
local ImageWidget = Widget:new{
file = nil,
invert = nil,
dim = nil,
@ -51,4 +53,4 @@ function ImageWidget:free()
end
end
return ImageWidget

@ -1,11 +1,20 @@
require "ui/widget/container"
local InputContainer = require("ui/widget/container/inputcontainer")
local Font = require("ui/font")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local FrameContainer = require("ui/widget/container/framecontainer")
local HorizontalGroup = require("ui/widget/horizontalgroup")
local ImageWidget = require("ui/widget/imagewidget")
local TextBoxWidget = require("ui/widget/textboxwidget")
local HorizontalSpan = require("ui/widget/horizontalspan")
local UIManager = require("ui/uimanager")
--[[
Widget that displays an informational message
it vanishes on key press or after a given timeout
]]
InfoMessage = InputContainer:new{
local InfoMessage = InputContainer:new{
face = Font:getFace("infofont", 25),
text = "",
timeout = nil, -- in seconds
@ -69,3 +78,5 @@ function InfoMessage:onTapClose()
UIManager:close(self)
return true
end
return InfoMessage

@ -1,7 +1,17 @@
require "ui/widget/container"
require "ui/widget/inputtext"
local InputContainer = require("ui/widget/container/inputcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local ButtonTable = require("ui/widget/buttontable")
local TextWidget = require("ui/widget/textwidget")
local LineWidget = require("ui/widget/linewidget")
local InputText = require("ui/widget/inputtext")
local VerticalGroup = require("ui/widget/verticalgroup")
local Font = require("ui/font")
local Geom = require("ui/geometry")
local UIManager = require("ui/uimanager")
local Screen = require("ui/screen")
InputDialog = InputContainer:new{
local InputDialog = InputContainer:new{
title = "",
input = "",
input_hint = "",
@ -14,11 +24,11 @@ InputDialog = InputContainer:new{
title_face = Font:getFace("tfont", 22),
input_face = Font:getFace("cfont", 20),
title_padding = scaleByDPI(5),
title_margin = scaleByDPI(2),
input_padding = scaleByDPI(10),
input_margin = scaleByDPI(10),
button_padding = scaleByDPI(14),
title_padding = Screen:scaleByDPI(5),
title_margin = Screen:scaleByDPI(2),
input_padding = Screen:scaleByDPI(10),
input_margin = Screen:scaleByDPI(10),
button_padding = Screen:scaleByDPI(14),
}
function InputDialog:init()
@ -52,7 +62,7 @@ function InputDialog:init()
--background = 8,
dimen = Geom:new{
w = button_table:getSize().w + self.button_padding,
h = scaleByDPI(2),
h = Screen:scaleByDPI(2),
}
}
@ -107,3 +117,5 @@ end
function InputDialog:onClose()
self.input:onCloseKeyboard()
end
return InputDialog

@ -1,9 +1,13 @@
require "ui/graphics"
require "ui/widget/text"
require "ui/widget/keyboard"
require "ui/widget/container"
local InputContainer = require("ui/widget/container/inputcontainer")
local ScrollTextWidget = require("ui/widget/scrolltextwidget")
local TextBoxWidget = require("ui/widget/textboxwidget")
local FrameContainer = require("ui/widget/container/framecontainer")
local VirtualKeyboard = require("ui/widget/virtualkeyboard")
local Font = require("ui/font")
local Screen = require("ui/screen")
local UIManager = require("ui/uimanager")
InputText = InputContainer:new{
local InputText = InputContainer:new{
text = "",
hint = "demo hint",
charlist = {}, -- table to store input string
@ -144,3 +148,5 @@ function InputText:CharlistToString()
end
return s
end
return InputText

@ -1,6 +1,6 @@
require "ui/widget/base"
local Widget = require("ui/widget/widget")
LineWidget = Widget:new{
local LineWidget = Widget:new{
style = "solid",
background = 15,
dimen = nil,
@ -29,3 +29,5 @@ function LineWidget:paintTo(bb, x, y)
end
end
end
return LineWidget

@ -1,16 +1,30 @@
require "ui/widget/container"
require "ui/widget/focusmanager"
require "ui/widget/infomessage"
require "ui/widget/button"
require "ui/widget/text"
require "ui/widget/group"
require "ui/widget/span"
require "ui/font"
local InputContainer = require("ui/widget/container/inputcontainer")
local WidgetContainer = require("ui/widget/container/widgetcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local BottomContainer = require("ui/widget/container/bottomcontainer")
local UnderlineContainer = require("ui/widget/container/underlinecontainer")
local HorizontalSpan = require("ui/widget/horizontalspan")
local FocusManager = require("ui/widget/focusmanager")
local TextWidget = require("ui/widget/textwidget")
local OverlapGroup = require("ui/widget/overlapgroup")
local VerticalGroup = require("ui/widget/verticalgroup")
local HorizontalGroup = require("ui/widget/horizontalgroup")
local Button = require("ui/widget/button")
local GestureRange = require("ui/gesturerange")
local Font = require("ui/font")
local Geom = require("ui/geometry")
local Device = require("ui/device")
local Screen = require("ui/screen")
local Input = require("ui/input")
local UIManager = require("ui/uimanager")
local RenderText = require("ui/rendertext")
local _ = require("gettext")
--[[
Widget that displays a shortcut icon for menu item
--]]
ItemShortCutIcon = WidgetContainer:new{
local ItemShortCutIcon = WidgetContainer:new{
dimen = Geom:new{ w = 22, h = 22 },
key = nil,
bordersize = 2,
@ -60,7 +74,7 @@ end
NOTICE:
@menu entry must be provided in order to close the menu
--]]
MenuCloseButton = InputContainer:new{
local MenuCloseButton = InputContainer:new{
align = "right",
menu = nil,
dimen = Geom:new{},
@ -92,7 +106,7 @@ end
--[[
Widget that displays an item for menu
--]]
MenuItem = InputContainer:new{
local MenuItem = InputContainer:new{
text = nil,
show_parent = nil,
detail = nil,
@ -132,7 +146,7 @@ function MenuItem:init()
}
end
w = sizeUtf8Text(0, self.dimen.w, self.face, self.text, true).x
w = RenderText:sizeUtf8Text(0, self.dimen.w, self.face, self.text, true).x
if w >= self.content_width then
if Device:isTouchDevice() then
else
@ -141,8 +155,8 @@ function MenuItem:init()
}
end
indicator = " >>"
indicator_w = sizeUtf8Text(0, self.dimen.w, self.face, indicator, true).x
self.text = getSubTextByWidth(self.text, self.face,
indicator_w = RenderText:sizeUtf8Text(0, self.dimen.w, self.face, indicator, true).x
self.text = RenderText:getSubTextByWidth(self.text, self.face,
self.content_width - indicator_w, true) .. indicator
end
@ -211,7 +225,7 @@ end
--[[
Widget that displays menu
--]]
Menu = FocusManager:new{
local Menu = FocusManager:new{
show_parent = nil,
-- face for displaying item contents
cface = Font:getFace("cfont", 22),
@ -611,3 +625,5 @@ function Menu:onSwipe(arg, ges_ev)
self:onPrevPage()
end
end
return Menu

@ -1,9 +1,16 @@
require "ui/widget/container"
local InputContainer = require("ui/widget/container/inputcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local TextBoxWidget = require("ui/widget/textboxwidget")
local Font = require("ui/font")
local Geom = require("ui/geometry")
local Device = require("ui/device")
local UIManager = require("ui/uimanager")
--[[
Widget that displays a tiny notification on top of screen
--]]
Notification = InputContainer:new{
local Notification = InputContainer:new{
face = Font:getFace("infofont", 20),
text = "Null Message",
timeout = nil,
@ -50,3 +57,4 @@ function Notification:onAnyKeyPressed()
return true
end
return Notification

@ -0,0 +1,51 @@
local WidgetContainer = require("ui/widget/container/widgetcontainer")
--[[
A Layout widget that puts objects above each other
--]]
local OverlapGroup = WidgetContainer:new{
_size = nil,
}
function OverlapGroup:getSize()
if not self._size then
self._size = {w = 0, h = 0}
self._offsets = { x = math.huge, y = math.huge }
for i, widget in ipairs(self) do
local w_size = widget:getSize()
if self._size.h < w_size.h then
self._size.h = w_size.h
end
if self._size.w < w_size.w then
self._size.w = w_size.w
end
end
end
if self.dimen.w then
self._size.w = self.dimen.w
end
if self.dimen.h then
self._size.h = self.dimen.h
end
return self._size
end
function OverlapGroup:paintTo(bb, x, y)
local size = self:getSize()
for i, wget in ipairs(self) do
local wget_size = wget:getSize()
if wget.align == "right" then
wget:paintTo(bb, x+size.w-wget_size.w, y)
elseif wget.align == "center" then
wget:paintTo(bb, x+math.floor((size.w-wget_size.w)/2), y)
else
-- default to left
wget:paintTo(bb, x, y)
end
end
end
return OverlapGroup

@ -1,10 +1,9 @@
require "ui/widget/base"
local Widget = require("ui/widget/widget")
--[[
ProgressWidget shows a progress bar
--]]
ProgressWidget = Widget:new{
local ProgressWidget = Widget:new{
width = nil,
height = nil,
margin_h = 3,
@ -35,5 +34,4 @@ function ProgressWidget:setPercentage(percentage)
self.percentage = percentage
end
return ProgressWidget

@ -0,0 +1,15 @@
local Widget = require("ui/widget/widget")
--[[
Dummy Widget that reserves vertical and horizontal space
]]
local RectSpan = Widget:new{
width = 0,
hright = 0,
}
function RectSpan:getSize()
return {w = self.width, h = self.height}
end
return RectSpan

@ -0,0 +1,80 @@
local InputContainer = require("ui/widget/container/inputcontainer")
local TextBoxWidget = require("ui/widget/textboxwidget")
local VerticalScrollBar = require("ui/widget/verticalscrollbar")
local Geom = require("ui/geometry")
local GestureRange = require("ui/gesturerange")
local UIManager = require("ui/uimanager")
local Screen = require("ui/screen")
--[[
Text widget with vertical scroll bar
--]]
local ScrollTextWidget = InputContainer:new{
text = nil,
face = nil,
bgcolor = 0.0, -- [0.0, 1.0]
fgcolor = 1.0, -- [0.0, 1.0]
width = 400,
height = 20,
scroll_bar_width = Screen:scaleByDPI(6),
text_scroll_span = Screen:scaleByDPI(6),
dialog = nil,
}
function ScrollTextWidget:init()
self.text_widget = TextBoxWidget:new{
text = self.text,
face = self.face,
bgcolor = self.bgcolor,
fgcolor = self.fgcolor,
width = self.width - self.scroll_bar_width - self.text_scroll_span,
height = self.height
}
local visible_line_count = self.text_widget:getVisLineCount()
local total_line_count = self.text_widget:getAllLineCount()
self.v_scroll_bar = VerticalScrollBar:new{
enable = visible_line_count < total_line_count,
low = 0,
high = visible_line_count/total_line_count,
width = Screen:scaleByDPI(6),
height = self.height,
}
local horizontal_group = HorizontalGroup:new{}
table.insert(horizontal_group, self.text_widget)
table.insert(horizontal_group, HorizontalSpan:new{width = Screen:scaleByDPI(6)})
table.insert(horizontal_group, self.v_scroll_bar)
self[1] = horizontal_group
self.dimen = Geom:new(self[1]:getSize())
if Device:isTouchDevice() then
self.ges_events = {
Swipe = {
GestureRange:new{
ges = "swipe",
range = self.dimen,
},
},
}
end
end
function ScrollTextWidget:updateScrollBar(text)
local virtual_line_num = text:getVirtualLineNum()
local visible_line_count = text:getVisLineCount()
local all_line_count = text:getAllLineCount()
self.v_scroll_bar:set(
(virtual_line_num - 1) / all_line_count,
(virtual_line_num - 1 + visible_line_count) / all_line_count
)
end
function ScrollTextWidget:onSwipe(arg, ges)
if ges.direction == "north" then
self.text_widget:scrollDown()
self:updateScrollBar(self.text_widget)
elseif ges.direction == "south" then
self.text_widget:scrollUp()
self:updateScrollBar(self.text_widget)
end
UIManager:setDirty(self.dialog, "partial")
return true
end

@ -1,27 +0,0 @@
require "ui/widget/base"
--[[
Dummy Widget that reserves horizontal space
--]]
HorizontalSpan = Widget:new{
width = 0,
}
function HorizontalSpan:getSize()
return {w = self.width, h = 0}
end
--[[
Dummy Widget that reserves vertical space
--]]
VerticalSpan = Widget:new{
width = 0,
}
function VerticalSpan:getSize()
return {w = 0, h = self.width}
end

@ -1,65 +1,14 @@
require "ui/rendertext"
require "ui/widget/base"
require "ui/widget/scrollbar"
local Widget = require("ui/widget/widget")
local RenderText = require("ui/rendertext")
local Screen = require("ui/screen")
local Geom = require("ui/geometry")
--[[
A TextWidget puts a string on a single line
--]]
TextWidget = Widget:new{
text = nil,
face = nil,
bgcolor = 0.0, -- [0.0, 1.0]
fgcolor = 1.0, -- [0.0, 1.0]
_bb = nil,
_length = 0,
_height = 0,
_maxlength = 1200,
}
--function TextWidget:_render()
--local h = self.face.size * 1.3
--self._bb = Blitbuffer.new(self._maxlength, h)
--self._length = renderUtf8Text(self._bb, 0, h*0.8, self.face, self.text, self.color)
--end
function TextWidget:getSize()
--if not self._bb then
--self:_render()
--end
--return { w = self._length, h = self._bb:getHeight() }
local tsize = sizeUtf8Text(0, Screen:getWidth(), self.face, self.text, true)
if not tsize then
return Geom:new{}
end
self._length = tsize.x
self._height = self.face.size * 1.5
return Geom:new{
w = self._length,
h = self._height,
}
end
function TextWidget:paintTo(bb, x, y)
--if not self._bb then
--self:_render()
--end
--bb:blitFrom(self._bb, x, y, 0, 0, self._length, self._bb:getHeight())
--@TODO Don't use kerning for monospaced fonts. (houqp)
renderUtf8Text(bb, x, y+self._height*0.7, self.face, self.text,
true, self.bgcolor, self.fgcolor)
end
function TextWidget:free()
if self._bb then
self._bb:free()
self._bb = nil
end
end
-- TODO: rename string:gsplit definition
--[[
A TextWidget that handles long text wrapping
--]]
TextBoxWidget = Widget:new{
local TextBoxWidget = Widget:new{
text = nil,
face = nil,
bgcolor = 0.0, -- [0.0, 1.0]
@ -157,7 +106,7 @@ function TextBoxWidget:_getVerticalList(alg)
for w in word:gsplit("%p+", true) do
local word_box = {}
word_box.word = w
word_box.width = sizeUtf8Text(0, Screen:getWidth(), self.face, w, true).x
word_box.width = RenderText:sizeUtf8Text(0, Screen:getWidth(), self.face, w, true).x
table.insert(h_list, word_box)
end
end
@ -245,7 +194,7 @@ end
function TextBoxWidget:_render(v_list)
local font_height = self.face.size
local line_height_px = self.line_height * font_height
local space_w = sizeUtf8Text(0, Screen:getWidth(), self.face, " ", true).x
local space_w = RenderText:sizeUtf8Text(0, Screen:getWidth(), self.face, " ", true).x
local h = (font_height + line_height_px) * #v_list
self._bb = Blitbuffer.new(self.width, h)
local y = font_height
@ -255,7 +204,7 @@ function TextBoxWidget:_render(v_list)
for _,w in ipairs(l) do
--@TODO Don't use kerning for monospaced fonts. (houqp)
-- refert to cb25029dddc42693cc7aaefbe47e9bd3b7e1a750 in master tree
renderUtf8Text(self._bb, pen_x, y, self.face, w.word, true,
RenderText:renderUtf8Text(self._bb, pen_x, y, self.face, w.word, true,
self.bgcolor, self.fgcolor)
pen_x = pen_x + w.width
end
@ -312,97 +261,4 @@ function TextBoxWidget:free()
end
end
--[[
FixedTextWidget
--]]
FixedTextWidget = TextWidget:new{}
function FixedTextWidget:getSize()
local tsize = sizeUtf8Text(0, Screen:getWidth(), self.face, self.text, true)
if not tsize then
return Geom:new{}
end
self._length = tsize.x
self._height = self.face.size
return Geom:new{
w = self._length,
h = self._height,
}
end
function FixedTextWidget:paintTo(bb, x, y)
renderUtf8Text(bb, x, y+self._height, self.face, self.text,
true, self.bgcolor, self.fgcolor)
end
--[[
Text widget with vertical scroll bar
--]]
ScrollTextWidget = InputContainer:new{
text = nil,
face = nil,
bgcolor = 0.0, -- [0.0, 1.0]
fgcolor = 1.0, -- [0.0, 1.0]
width = 400,
height = 20,
scroll_bar_width = scaleByDPI(6),
text_scroll_span = scaleByDPI(6),
dialog = nil,
}
function ScrollTextWidget:init()
self.text_widget = TextBoxWidget:new{
text = self.text,
face = self.face,
bgcolor = self.bgcolor,
fgcolor = self.fgcolor,
width = self.width - self.scroll_bar_width - self.text_scroll_span,
height = self.height
}
local visible_line_count = self.text_widget:getVisLineCount()
local total_line_count = self.text_widget:getAllLineCount()
self.v_scroll_bar = VerticalScrollBar:new{
enable = visible_line_count < total_line_count,
low = 0,
high = visible_line_count/total_line_count,
width = scaleByDPI(6),
height = self.height,
}
local horizontal_group = HorizontalGroup:new{}
table.insert(horizontal_group, self.text_widget)
table.insert(horizontal_group, HorizontalSpan:new{width = scaleByDPI(6)})
table.insert(horizontal_group, self.v_scroll_bar)
self[1] = horizontal_group
self.dimen = Geom:new(self[1]:getSize())
if Device:isTouchDevice() then
self.ges_events = {
Swipe = {
GestureRange:new{
ges = "swipe",
range = self.dimen,
},
},
}
end
end
function ScrollTextWidget:updateScrollBar(text)
local virtual_line_num = text:getVirtualLineNum()
local visible_line_count = text:getVisLineCount()
local all_line_count = text:getAllLineCount()
self.v_scroll_bar:set(
(virtual_line_num - 1) / all_line_count,
(virtual_line_num - 1 + visible_line_count) / all_line_count
)
end
function ScrollTextWidget:onSwipe(arg, ges)
if ges.direction == "north" then
self.text_widget:scrollDown()
self:updateScrollBar(self.text_widget)
elseif ges.direction == "south" then
self.text_widget:scrollUp()
self:updateScrollBar(self.text_widget)
end
UIManager:setDirty(self.dialog, "partial")
return true
end
return TextBoxWidget

@ -0,0 +1,60 @@
local Widget = require("ui/widget/widget")
local Screen = require("ui/screen")
local RenderText = require("ui/rendertext")
local Geom = require("ui/geometry")
--[[
A TextWidget puts a string on a single line
--]]
local TextWidget = Widget:new{
text = nil,
face = nil,
bgcolor = 0.0, -- [0.0, 1.0]
fgcolor = 1.0, -- [0.0, 1.0]
_bb = nil,
_length = 0,
_height = 0,
_maxlength = 1200,
}
--function TextWidget:_render()
--local h = self.face.size * 1.3
--self._bb = Blitbuffer.new(self._maxlength, h)
--self._length = RenderText:renderUtf8Text(self._bb, 0, h*0.8, self.face, self.text, self.color)
--end
function TextWidget:getSize()
--if not self._bb then
--self:_render()
--end
--return { w = self._length, h = self._bb:getHeight() }
local tsize = RenderText:sizeUtf8Text(0, Screen:getWidth(), self.face, self.text, true)
if not tsize then
return Geom:new{}
end
self._length = tsize.x
self._height = self.face.size * 1.5
return Geom:new{
w = self._length,
h = self._height,
}
end
function TextWidget:paintTo(bb, x, y)
--if not self._bb then
--self:_render()
--end
--bb:blitFrom(self._bb, x, y, 0, 0, self._length, self._bb:getHeight())
--@TODO Don't use kerning for monospaced fonts. (houqp)
RenderText:renderUtf8Text(bb, x, y+self._height*0.7, self.face, self.text,
true, self.bgcolor, self.fgcolor)
end
function TextWidget:free()
if self._bb then
self._bb:free()
self._bb = nil
end
end
return TextWidget

@ -1,16 +1,29 @@
local TextWidget = require("ui/widget/textwidget")
local InputContainer = require("ui/widget/container/inputcontainer")
local FrameContainer = require("ui/widget/container/framecontainer")
local CenterContainer = require("ui/widget/container/centercontainer")
local HorizontalGroup = require("ui/widget/horizontalgroup")
local Font = require("ui/font")
local Geom = require("ui/geometry")
local RenderText = require("ui/rendertext")
local UIManager = require("ui/uimanager")
local Screen = require("ui/screen")
local Device = require("ui/device")
local GestureRange = require("ui/gesturerange")
local _ = require("gettext")
ToggleLabel = TextWidget:new{
local ToggleLabel = TextWidget:new{
bgcolor = 0,
fgcolor = 1,
}
function ToggleLabel:paintTo(bb, x, y)
renderUtf8Text(bb, x, y+self._height*0.75, self.face, self.text, true, self.bgcolor, self.fgcolor)
RenderText:renderUtf8Text(bb, x, y+self._height*0.75, self.face, self.text, true, self.bgcolor, self.fgcolor)
end
ToggleSwitch = InputContainer:new{
width = scaleByDPI(216),
height = scaleByDPI(30),
local ToggleSwitch = InputContainer:new{
width = Screen:scaleByDPI(216),
height = Screen:scaleByDPI(30),
bgcolor = 0, -- unfoused item color
fgcolor = 7, -- focused item color
}
@ -123,3 +136,4 @@ function ToggleSwitch:onTapSelect(arg, gev)
UIManager.repaint_all = true
end
return ToggleSwitch

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save