diff --git a/defaults.lua b/defaults.lua index 41f5b40bd..4e19dd417 100644 --- a/defaults.lua +++ b/defaults.lua @@ -34,13 +34,20 @@ DKOPTREADER_CONFIG_DETECT_INDENT = 1 -- 1 = enable, 0 = disable DKOPTREADER_CONFIG_DEFECT_SIZE = 1.0 -- range from 0.0 to 3.0 DKOPTREADER_CONFIG_PAGE_MARGIN = 0.10 -- range from 0.0 to 1.0 DKOPTREADER_CONFIG_LINE_SPACING = 1.2 -- range from 0.5 to 2.0 -DKOPTREADER_CONFIG_WORD_SAPCING = 0.15 -- range from 0.05 to 0.5 DKOPTREADER_CONFIG_RENDER_QUALITY = 0.8 -- range from 0.5 to 1.0 DKOPTREADER_CONFIG_AUTO_STRAIGHTEN = 0 -- range from 0 to 10 DKOPTREADER_CONFIG_JUSTIFICATION = -1 -- -1 = auto, 0 = left, 1 = center, 2 = right, 3 = full DKOPTREADER_CONFIG_MAX_COLUMNS = 2 -- range from 1 to 4 DKOPTREADER_CONFIG_CONTRAST = 1.0 -- range from 0.2 to 2.0 +-- word spacing for reflow +DKOPTREADER_CONFIG_WORD_SAPCINGS = {0.05, 0.15, 0.375} -- range from 0.05 to 0.5 +DKOPTREADER_CONFIG_DEFAULT_WORD_SAPCING = 0.15 -- range from 0.05 to 0.5 +-- document languages for OCR +DKOPTREADER_CONFIG_DOC_LANGS_TEXT = {"English", "Chinese_S", "Chinese_T"} +DKOPTREADER_CONFIG_DOC_LANGS_CODE = {"eng", "chi_sim", "chi_tra"} -- ISO 639-3 language string, +DKOPTREADER_CONFIG_DOC_DEFAULT_LANG_CODE = "eng" -- and make sure you have corresponding training data + -- #################################################################### -- following features are not supported right now diff --git a/frontend/document/koptinterface.lua b/frontend/document/koptinterface.lua index 21ed28622..50422d185 100644 --- a/frontend/document/koptinterface.lua +++ b/frontend/document/koptinterface.lua @@ -62,6 +62,7 @@ function KoptInterface:createContext(doc, pageno, bbox) kc:setDefectSize(doc.configurable.defect_size) kc:setLineSpacing(doc.configurable.line_spacing) kc:setWordSpacing(doc.configurable.word_spacing) + kc:setLanguage(doc.configurable.doc_language) kc:setBBox(bbox.x0, bbox.y0, bbox.x1, bbox.y1) if Dbg.is_on then kc:setDebug() end return kc @@ -75,9 +76,11 @@ function KoptInterface:getContextHash(doc, pageno, bbox) end function KoptInterface:getAutoBBox(doc, pageno) + local native_size = Document.getNativePageDimensions(doc, pageno) local bbox = { x0 = 0, y0 = 0, - x1 = 0, y1 = 0, + x1 = native_size.w, + y1 = native_size.h, } local context_hash = self:getContextHash(doc, pageno, bbox) local hash = "autobbox|"..context_hash @@ -129,6 +132,13 @@ function KoptInterface:getReflewTextBoxes(doc, pageno) local cached = Cache:check(kctx_hash) if cached then local kc = self:waitForContext(cached.kctx) + --kc:setDebug() + local lang = doc.configurable.doc_language + if lang == "chi_sim" or lang == "chi_tra" or + lang == "jpn" or lang == "kor" then + kc:setCJKChar() + end + kc:setLanguage(lang) local fullwidth, fullheight = kc:getPageDim() local boxes = kc:getWordBoxes(0, 0, fullwidth, fullheight) Cache:insert(hash, CacheItem:new{ rfpgboxes = boxes }) @@ -146,6 +156,12 @@ function KoptInterface:getTextBoxes(doc, pageno) local kc_hash = "kctx|"..doc.file.."|"..pageno local kc = KOPTContext.new() kc:setDebug() + local lang = doc.configurable.doc_language + if lang == "chi_sim" or lang == "chi_tra" or + lang == "jpn" or lang == "kor" then + kc:setCJKChar() + end + kc:setLanguage(lang) local page = doc._document:openPage(pageno) page:getPagePix(kc) local fullwidth, fullheight = kc:getPageDim() @@ -167,6 +183,7 @@ function KoptInterface:getReflewOCRWord(doc, pageno, rect) local dummy = KOPTContext.new() Cache:insert(ocrengine, OCREngine:new{ ocrengine = dummy }) end + self.ocr_lang = doc.configurable.doc_language local bbox = doc:getPageBBox(pageno) local context_hash = self:getContextHash(doc, pageno, bbox) local hash = "rfocrword|"..context_hash..rect.x..rect.y..rect.w..rect.h @@ -197,6 +214,7 @@ function KoptInterface:getOCRWord(doc, pageno, rect) local dummy = KOPTContext.new() Cache:insert(ocrengine, OCREngine:new{ ocrengine = dummy }) end + self.ocr_lang = doc.configurable.doc_language local hash = "ocrword|"..doc.file.."|"..pageno..rect.x..rect.y..rect.w..rect.h local cached = Cache:check(hash) if not cached then diff --git a/frontend/ui/data/koptoptions.lua b/frontend/ui/data/koptoptions.lua index 1656f70d6..db93869ff 100644 --- a/frontend/ui/data/koptoptions.lua +++ b/frontend/ui/data/koptoptions.lua @@ -160,6 +160,15 @@ KoptOptions = { }, } }, + { + name="doc_language", + name_text = DOC_LANG_STR, + toggle = DKOPTREADER_CONFIG_DOC_LANGS_TEXT, + values = DKOPTREADER_CONFIG_DOC_LANGS_CODE, + default_value = DKOPTREADER_CONFIG_DOC_DEFAULT_LANG_CODE, + event = "DocLangUpdate", + args = DKOPTREADER_CONFIG_DOC_LANGS_CODE, + }, { name="screen_rotation", name_text = VERTICAL_TEXT_STR, @@ -171,8 +180,8 @@ KoptOptions = { name = "word_spacing", name_text = WORD_GAP_STR, toggle = {SMALL_STR, MEDIUM_STR, LARGE_STR}, - values = {0.05, 0.15, 0.375}, - default_value = DKOPTREADER_CONFIG_WORD_SAPCING, + values = DKOPTREADER_CONFIG_WORD_SAPCINGS, + default_value = DKOPTREADER_CONFIG_DEFAULT_WORD_SAPCING, }, { name = "defect_size", @@ -195,6 +204,7 @@ KoptOptions = { toggle = {ZERO_DEG_STR, FIVE_DEG_STR, TEN_DEG_STR}, values = {0, 5, 10}, default_value = DKOPTREADER_CONFIG_AUTO_STRAIGHTEN, + show = false, }, { name = "detect_indent", diff --git a/frontend/ui/data/strings.lua b/frontend/ui/data/strings.lua index 9036ed419..08e52b5cc 100644 --- a/frontend/ui/data/strings.lua +++ b/frontend/ui/data/strings.lua @@ -10,6 +10,7 @@ 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") diff --git a/frontend/ui/reader/readerconfig.lua b/frontend/ui/reader/readerconfig.lua index 8d0a3c67a..ec243b140 100644 --- a/frontend/ui/reader/readerconfig.lua +++ b/frontend/ui/reader/readerconfig.lua @@ -6,7 +6,8 @@ function Configurable:hash(sep) local hash = "" local excluded = {multi_threads = true,} for key,value in pairs(self) do - if type(value) == "number" and not excluded[key] then + if type(value) == "number" or type(value) == "string" + and not excluded[key] then hash = hash..sep..value end end @@ -28,8 +29,9 @@ end function Configurable:loadSettings(settings, prefix) for key,value in pairs(self) do - if type(value) == "number" or type(value) == "table" then - saved_value = settings:readSetting(prefix..key) + 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 @@ -39,7 +41,8 @@ end function Configurable:saveSettings(settings, prefix) for key,value in pairs(self) do - if type(value) == "number" or type(value) == "table" then + if type(value) == "number" or type(value) == "string" + or type(value) == "table" then settings:saveSetting(prefix..key, value) end end diff --git a/frontend/ui/reader/readerhighlight.lua b/frontend/ui/reader/readerhighlight.lua index 75c3e5695..95f99c71c 100644 --- a/frontend/ui/reader/readerhighlight.lua +++ b/frontend/ui/reader/readerhighlight.lua @@ -165,22 +165,42 @@ function ReaderHighlight:onHoldPan(arg, ges) end end +function ReaderHighlight:lookup(selected_word) + -- if we extracted text directly + if selected_word.word then + self.ui:handleEvent(Event:new("LookupWord", selected_word.word)) + -- or we will do OCR + else + local word_box = selected_word.box + --word_box.x = word_box.x - math.floor(word_box.h * 0.1) + --word_box.y = word_box.y - math.floor(word_box.h * 0.2) + --word_box.w = word_box.w + math.floor(word_box.h * 0.2) + --word_box.h = word_box.h + math.floor(word_box.h * 0.4) + local word = self.ui.document:getOCRWord(self.hold_pos.page, word_box) + DEBUG("OCRed word:", word) + self.ui:handleEvent(Event:new("LookupWord", word)) + end +end + +function ReaderHighlight:translate(selected_text) + if selected_text.text ~= "" then + self.ui:handleEvent(Event:new("LookupWord", selected_text.text)) + -- or we will do OCR + else + local text_box = selected_text.boxes[1] + --text_box.x = text_box.x - math.floor(text_box.h * 0.1) + text_box.y = text_box.y - math.floor(text_box.h * 0.2) + --text_box.w = text_box.w + math.floor(text_box.h * 0.2) + text_box.h = text_box.h + math.floor(text_box.h * 0.4) + local text = self.ui.document:getOCRWord(self.hold_pos.page, text_box) + DEBUG("OCRed text:", text) + self.ui:handleEvent(Event:new("LookupWord", text)) + end +end + function ReaderHighlight:onHoldRelease(arg, ges) if self.selected_word then - -- if we extracted text directly - if self.selected_word.word then - self.ui:handleEvent(Event:new("LookupWord", self.selected_word.word)) - -- or we will do OCR - else - local word_box = self.selected_word.box - word_box.x = word_box.x - math.floor(word_box.h * 0.1) - word_box.y = word_box.y - math.floor(word_box.h * 0.2) - word_box.w = word_box.w + math.floor(word_box.h * 0.2) - word_box.h = word_box.h + math.floor(word_box.h * 0.4) - local word = self.ui.document:getOCRWord(self.hold_pos.page, word_box) - DEBUG("OCRed word:", word) - self.ui:handleEvent(Event:new("LookupWord", word)) - end + self:lookup(self.selected_word) self.selected_word = nil elseif self.selected_text then DEBUG("show highlight dialog") @@ -206,6 +226,14 @@ function ReaderHighlight:onHoldRelease(arg, ges) }, }, { + { + text = _("Translate"), + callback = function() + self:translate(self.selected_text) + UIManager:close(self.highlight_dialog) + self.ui:handleEvent(Event:new("Tap")) + end, + }, { text = _("Share"), enabled = false, @@ -215,6 +243,8 @@ function ReaderHighlight:onHoldRelease(arg, ges) self.ui:handleEvent(Event:new("Tap")) end, }, + }, + { { text = _("More"), enabled = false, diff --git a/frontend/ui/reader/readerkopt.lua b/frontend/ui/reader/readerkopt.lua index 479f65fda..f52e92d4f 100644 --- a/frontend/ui/reader/readerkopt.lua +++ b/frontend/ui/reader/readerkopt.lua @@ -49,3 +49,12 @@ function ReaderKoptListener:onZoomUpdate(zoom) end end +-- misc koptoption handler +function ReaderKoptListener:onDocLangUpdate(lang) + if lang == "chi_sim" or lang == "chi_tra" or + lang == "jpn" or lang == "kor" then + self.document.configurable.word_spacing = DKOPTREADER_CONFIG_WORD_SAPCINGS[1] + else + self.document.configurable.word_spacing = DKOPTREADER_CONFIG_WORD_SAPCINGS[3] + end +end diff --git a/frontend/ui/widget/config.lua b/frontend/ui/widget/config.lua index 7c80350b2..aaa26d2ae 100644 --- a/frontend/ui/widget/config.lua +++ b/frontend/ui/widget/config.lua @@ -204,6 +204,16 @@ function ConfigOption:init() end -- make current index according to configurable table local current_item = nil + local function value_diff(val1, val2, name) + if type(val1) ~= type(val2) then + error("different data types in option", name) + end + if type(val1) == "number" then + return math.abs(val1 - val2) + elseif type(val1) == "string" then + return val1 == val2 and 0 or 1 + end + end if self.options[c].name then if self.options[c].values then -- check if current value is stored in configurable or calculated in runtime @@ -211,18 +221,18 @@ function ConfigOption:init() or self.config.configurable[self.options[c].name] local min_diff = nil if type(val) == "table" then - min_diff = math.abs(val[1] - self.options[c].values[1][1]) + min_diff = value_diff(val[1], self.options[c].values[1][1]) else - min_diff = math.abs(val - self.options[c].values[1]) + min_diff = value_diff(val, self.options[c].values[1]) end local diff = nil for index, val_ in pairs(self.options[c].values) do local diff = nil if type(val) == "table" then - diff = math.abs(val[1] - val_[1]) + diff = value_diff(val[1], val_[1]) else - diff = math.abs(val - val_) + diff = value_diff(val, val_) end if val == val_ then current_item = index @@ -492,6 +502,7 @@ end function ConfigDialog:onConfigEvent(option_event, option_arg) --DEBUG("config option event", option_event, option_arg) self.ui:handleEvent(Event:new(option_event, option_arg)) + self:onShowConfigPanel(self.panel_index) end function ConfigDialog:closeDialog() diff --git a/koreader-base b/koreader-base index 7de326340..d45c0ac4b 160000 --- a/koreader-base +++ b/koreader-base @@ -1 +1 @@ -Subproject commit 7de326340ee639c79957f5c4e80c47116c0849eb +Subproject commit d45c0ac4b1f4801e193d0bc9a6c3759989dec7c2