From 53f083f51669f2768995fb532a5224f0bf01a525 Mon Sep 17 00:00:00 2001 From: poire-z Date: Sun, 1 Oct 2017 19:23:06 +0200 Subject: [PATCH] Allow for toggling color rendering New menu item in Screen submenu. hasColorScreen enabled for SDL device. --- frontend/apps/reader/modules/readerpaging.lua | 4 +++ .../apps/reader/modules/readerrolling.lua | 4 +++ frontend/device/generic/device.lua | 4 ++- frontend/device/sdl/device.lua | 1 + frontend/document/credocument.lua | 23 +++++++++--- frontend/document/djvudocument.lua | 1 + frontend/document/document.lua | 35 ++++++++++++++----- frontend/document/pdfdocument.lua | 19 ++++++++-- frontend/document/picdocument.lua | 4 ++- .../elements/common_settings_menu_table.lua | 10 ++++-- .../ui/elements/screen_color_menu_table.lua | 14 ++++++++ 11 files changed, 100 insertions(+), 19 deletions(-) create mode 100644 frontend/ui/elements/screen_color_menu_table.lua diff --git a/frontend/apps/reader/modules/readerpaging.lua b/frontend/apps/reader/modules/readerpaging.lua index b57e99f80..745dd4274 100644 --- a/frontend/apps/reader/modules/readerpaging.lua +++ b/frontend/apps/reader/modules/readerpaging.lua @@ -219,6 +219,10 @@ function ReaderPaging:addToMainMenu(menu_items) } end +function ReaderPaging:onColorRenderingUpdate() + self.ui.document:updateColorRendering() +end + --[[ Set reading position on certain page Page position is a fractional number ranging from 0 to 1, indicating the read diff --git a/frontend/apps/reader/modules/readerrolling.lua b/frontend/apps/reader/modules/readerrolling.lua index 6ac540ee0..3c72e65df 100644 --- a/frontend/apps/reader/modules/readerrolling.lua +++ b/frontend/apps/reader/modules/readerrolling.lua @@ -530,6 +530,10 @@ function ReaderRolling:onChangeScreenMode(mode) self:onUpdatePos() end +function ReaderRolling:onColorRenderingUpdate() + self.ui.document:updateColorRendering() +end + --[[ PosUpdate event is used to signal other widgets that pos has been changed. --]] diff --git a/frontend/device/generic/device.lua b/frontend/device/generic/device.lua index 9c913d3ec..576483343 100644 --- a/frontend/device/generic/device.lua +++ b/frontend/device/generic/device.lua @@ -24,6 +24,7 @@ local Device = { isTouchDevice = no, hasFrontlight = no, needsTouchScreenProbe = no, + hasColorScreen = no, -- use these only as a last resort. We should abstract the functionality -- and have device dependent implementations in the corresponting @@ -57,9 +58,10 @@ function Device:init() error("screen/framebuffer must be implemented") end + self.screen.isColorScreen = self.hasColorScreen self.screen.isColorEnabled = function() if G_reader_settings:has("color_rendering") then return G_reader_settings:isTrue("color_rendering") end - return self.screen.color + return self.screen.isColorScreen() end local is_eink = G_reader_settings:readSetting("eink") diff --git a/frontend/device/sdl/device.lua b/frontend/device/sdl/device.lua index e786f2cca..0e26b0da2 100644 --- a/frontend/device/sdl/device.lua +++ b/frontend/device/sdl/device.lua @@ -14,6 +14,7 @@ local Device = Generic:new{ hasFrontlight = yes, isTouchDevice = yes, needsScreenRefreshAfterResume = no, + hasColorScreen = yes, } if os.getenv("DISABLE_TOUCH") == "1" then diff --git a/frontend/document/credocument.lua b/frontend/document/credocument.lua index 772a29310..6fc331afa 100644 --- a/frontend/document/credocument.lua +++ b/frontend/document/credocument.lua @@ -73,6 +73,7 @@ function CreDocument:engineInit() end function CreDocument:init() + self:updateColorRendering() self:engineInit() self.configurable:loadDefaults(self.options) @@ -137,6 +138,20 @@ end function CreDocument:close() Document.close(self) + if self.buffer then + self.buffer:free() + self.buffer = nil + end +end + +function CreDocument:updateColorRendering() + Document.updateColorRendering(self) -- will set self.render_color + -- Delete current buffer, a new one will be created according + -- to self.render_color + if self.buffer then + self.buffer:free() + self.buffer = nil + end end function CreDocument:getPageCount() @@ -239,15 +254,15 @@ function CreDocument:drawCurrentView(target, x, y, rect, pos) self.buffer:free() self.buffer = nil end - local color = Screen:isColorEnabled() if not self.buffer then + -- Note about color rendering: -- If we use TYPE_BBRGB32 (and LVColorDrawBuf drawBuf(..., 32) in cre.cpp), -- we get inverted Red and Blue in the blitbuffer (could be that -- crengine/src/lvdrawbuf.cpp treats our 32bits not as RGBA). -- But it is all fine if we use TYPE_BBRGB16. - self.buffer = Blitbuffer.new(rect.w, rect.h, color and Blitbuffer.TYPE_BBRGB16 or nil) + self.buffer = Blitbuffer.new(rect.w, rect.h, self.render_color and Blitbuffer.TYPE_BBRGB16 or nil) end - self._document:drawCurrentPage(self.buffer, color) + self._document:drawCurrentPage(self.buffer, self.render_color) target:blitFrom(self.buffer, x, y, 0, 0, rect.w, rect.h) end @@ -307,7 +322,7 @@ function CreDocument:getLinkFromPosition(pos) return self._document:getLinkFromPosition(pos.x, pos.y) end -function Document:gotoPos(pos) +function CreDocument:gotoPos(pos) logger.dbg("CreDocument: goto position", pos) self._document:gotoPos(pos) end diff --git a/frontend/document/djvudocument.lua b/frontend/document/djvudocument.lua index 540478c3b..1ccb90f4e 100644 --- a/frontend/document/djvudocument.lua +++ b/frontend/document/djvudocument.lua @@ -24,6 +24,7 @@ local function validDjvuFile(filename) end function DjvuDocument:init() + self:updateColorRendering() local djvu = require("libs/libkoreader-djvu") self.koptinterface = require("document/koptinterface") self.configurable:loadDefaults(self.options) diff --git a/frontend/document/document.lua b/frontend/document/document.lua index 4758dd609..ae2c65166 100644 --- a/frontend/document/document.lua +++ b/frontend/document/document.lua @@ -72,6 +72,10 @@ function Document:_init() author = "", date = "" } + + -- Should be updated by a call to Document.updateColorRendering(self) + -- in subclasses + self.render_color = false end -- override this method to open a document @@ -269,14 +273,30 @@ function Document:findText() return nil end -function Document:getFullPageHash(pageno, zoom, rotation, gamma, render_mode) +function Document:updateColorRendering() + if self.is_color_capable and Screen:isColorEnabled() then + self.render_color = true + else + self.render_color = false + end +end + +function Document:preRenderPage() + return nil +end + +function Document:postRenderPage() + return nil +end + +function Document:getFullPageHash(pageno, zoom, rotation, gamma, render_mode, color) return "renderpg|"..self.file.."|"..self.mod_time.."|"..pageno.."|" - ..zoom.."|"..rotation.."|"..gamma.."|"..render_mode + ..zoom.."|"..rotation.."|"..gamma.."|"..render_mode..(color and "|color" or "") end function Document:renderPage(pageno, rect, zoom, rotation, gamma, render_mode) local hash_excerpt - local hash = self:getFullPageHash(pageno, zoom, rotation, gamma, render_mode) + local hash = self:getFullPageHash(pageno, zoom, rotation, gamma, render_mode, self.render_color) local tile = Cache:check(hash, TileCacheItem) if not tile then hash_excerpt = hash.."|"..tostring(rect) @@ -284,6 +304,8 @@ function Document:renderPage(pageno, rect, zoom, rotation, gamma, render_mode) end if tile then return tile end + self:preRenderPage() + local page_size = self:getPageDimensions(pageno, zoom, rotation) -- this will be the size we actually render local size = page_size @@ -303,16 +325,12 @@ function Document:renderPage(pageno, rect, zoom, rotation, gamma, render_mode) end -- prepare cache item with contained blitbuffer - local bbtype = nil -- use Blitbuffer default greyscale type - if self.is_color_capable and Screen:isColorEnabled() then - bbtype = Blitbuffer.TYPE_BBRGB32 - end tile = TileCacheItem:new{ persistent = true, size = size.w * size.h + 64, -- estimation excerpt = size, pageno = pageno, - bb = Blitbuffer.new(size.w, size.h, bbtype) + bb = Blitbuffer.new(size.w, size.h, self.render_color and Blitbuffer.TYPE_BBRGB32 or nil) } -- create a draw context @@ -339,6 +357,7 @@ function Document:renderPage(pageno, rect, zoom, rotation, gamma, render_mode) page:close() Cache:insert(hash, tile) + self:postRenderPage() return tile end diff --git a/frontend/document/pdfdocument.lua b/frontend/document/pdfdocument.lua index 8113f65e3..03f122065 100644 --- a/frontend/document/pdfdocument.lua +++ b/frontend/document/pdfdocument.lua @@ -3,9 +3,9 @@ local CacheItem = require("cacheitem") local Document = require("document/document") local DrawContext = require("ffi/drawcontext") local KoptOptions = require("ui/data/koptoptions") -local Screen = require("device").screen local logger = require("logger") local util = require("util") +local pdf = nil local PdfDocument = Document:new{ _document = false, @@ -16,8 +16,13 @@ local PdfDocument = Document:new{ } function PdfDocument:init() - local pdf = require("ffi/mupdf") - pdf.color = Screen:isColorEnabled() + if not pdf then pdf = require("ffi/mupdf") end + -- mupdf.color has to stay false for kopt to work correctly + -- and be accurate (including its job about showing highlight + -- boxes). We will turn it on and off in PdfDocument:preRenderPage() + -- and :postRenderPage() when mupdf is called without kopt involved. + pdf.color = false + self:updateColorRendering() self.koptinterface = require("document/koptinterface") self.configurable:loadDefaults(self.options) local ok @@ -39,6 +44,14 @@ function PdfDocument:init() -- end end +function PdfDocument:preRenderPage() + pdf.color = self.render_color +end + +function PdfDocument:postRenderPage() + pdf.color = false +end + function PdfDocument:unlock(password) if not self._document:authenticatePassword(password) then return false diff --git a/frontend/document/picdocument.lua b/frontend/document/picdocument.lua index c8509fe82..e41fef4f2 100644 --- a/frontend/document/picdocument.lua +++ b/frontend/document/picdocument.lua @@ -10,8 +10,10 @@ local PicDocument = Document:new{ } function PicDocument:init() + self:updateColorRendering() if not pic then pic = require("ffi/pic") end - pic.color = Screen:isColorEnabled() + -- pic.color needs to be true before opening document to allow toggling color + pic.color = Screen.isColorScreen() local ok ok, self._document = pcall(pic.openDocument, self.file) if not ok then diff --git a/frontend/ui/elements/common_settings_menu_table.lua b/frontend/ui/elements/common_settings_menu_table.lua index 55ece1303..dd7194955 100644 --- a/frontend/ui/elements/common_settings_menu_table.lua +++ b/frontend/ui/elements/common_settings_menu_table.lua @@ -107,13 +107,19 @@ common_settings.screen = { text = _("Screen"), sub_item_table = { require("ui/elements/screen_dpi_menu_table"), + require("ui/elements/refresh_menu_table"), require("ui/elements/screen_eink_opt_menu_table"), + require("ui/elements/menu_activate"), require("ui/elements/screen_disable_double_tap_table"), - require("ui/elements/refresh_menu_table"), require("ui/elements/flash_keyboard"), - require("ui/elements/menu_activate"), }, } +if Screen.isColorScreen() then + table.insert(common_settings.screen.sub_item_table, 4, require("ui/elements/screen_color_menu_table")) + common_settings.screen.sub_item_table[4].separator = true +else + common_settings.screen.sub_item_table[3].separator = true +end if Device:isAndroid() then table.insert(common_settings.screen.sub_item_table, require("ui/elements/screen_fullscreen_menu_table")) end diff --git a/frontend/ui/elements/screen_color_menu_table.lua b/frontend/ui/elements/screen_color_menu_table.lua new file mode 100644 index 000000000..d2b4a9105 --- /dev/null +++ b/frontend/ui/elements/screen_color_menu_table.lua @@ -0,0 +1,14 @@ +local Event = require("ui/event") +local Screen = require("device").screen +local UIManager = require("ui/uimanager") +local _ = require("gettext") + +return { + text = _("Color rendering"), + enabled_func = Screen.isColorScreen, + checked_func = Screen.isColorEnabled, + callback = function() + G_reader_settings:flipNilOrTrue("color_rendering") + UIManager:broadcastEvent(Event:new("ColorRenderingUpdate")) + end +}