diff --git a/frontend/ui/menusorter.lua b/frontend/ui/menusorter.lua index b7066d3f7..8d7f0ae3e 100644 --- a/frontend/ui/menusorter.lua +++ b/frontend/ui/menusorter.lua @@ -156,12 +156,15 @@ function MenuSorter:sort(item_table, order) -- remove top level reference before orphan handling item_table["KOMenu:menu_buttons"] = nil - --attach orphans based on menu_hint + + -- attach orphans based on sorting_hint, or with a NEW prefix in the first menu if none found for k,v in pairs(item_table) do + local sorting_hint = v.sorting_hint + -- normally there should be menu text but check to be sure if v.text and v.new ~= true then v.id = k - v.text = self.orphaned_prefix .. v.text + if not sorting_hint then v.text = self.orphaned_prefix .. v.text end -- prevent text being prepended to item on menu reload, i.e., on switching between reader and filemanager v.new = true -- deal with orphaned submenus @@ -172,7 +175,13 @@ function MenuSorter:sort(item_table, order) end end end - table.insert(menu_table["KOMenu:menu_buttons"][1], v) + if sorting_hint then + local sorting_hint_menu = self:findById(menu_table["KOMenu:menu_buttons"], sorting_hint) + sorting_hint_menu = sorting_hint_menu.sub_item_table or sorting_hint_menu + table.insert(sorting_hint_menu, v) + else + table.insert(menu_table["KOMenu:menu_buttons"][1], v) + end end return menu_table["KOMenu:menu_buttons"] end @@ -193,10 +202,13 @@ function MenuSorter:findById(tbl, needle_id) local k, v k, v = next(items, nil) while k do - if v.id == needle_id then + local id_match = v.id == needle_id + local sub_table = v.sub_item_table or type(v) == "table" and v + + if id_match then return v - elseif v.sub_item_table then - for _,item in pairs(v.sub_item_table) do + elseif sub_table then + for _,item in pairs(sub_table) do if type(item) == "table" and item.id then table.insert(items, item) end diff --git a/plugins/hello.koplugin/main.lua b/plugins/hello.koplugin/main.lua index 3a1e11499..9f8699dac 100644 --- a/plugins/hello.koplugin/main.lua +++ b/plugins/hello.koplugin/main.lua @@ -20,6 +20,9 @@ end function Hello:addToMainMenu(menu_items) menu_items.hello_world = { text = _("Hello World"), + -- in which menu this should be appended + sorting_hint = "more_plugins", + -- a callback when tapping callback = function() UIManager:show(InfoMessage:new{ text = _("Hello, plugin world"), diff --git a/spec/unit/menusorter_spec.lua b/spec/unit/menusorter_spec.lua index 005df02f1..19f2a1722 100644 --- a/spec/unit/menusorter_spec.lua +++ b/spec/unit/menusorter_spec.lua @@ -1,8 +1,10 @@ describe("MenuSorter module", function() local MenuSorter + local equals setup(function() require("commonrequire") MenuSorter = require("ui/menusorter") + equals = require("util").tableEquals end) it("should put menu items in the defined order", function() @@ -80,6 +82,79 @@ describe("MenuSorter module", function() assert.is_true(string.sub(menu_item.text,1,string.len(MenuSorter.orphaned_prefix))==MenuSorter.orphaned_prefix) end end) + it("should put orphans with sorting_hint in the right menu", function() + local menu_items = { + ["KOMenu:menu_buttons"] = {}, + main = {text="Main"}, + search = {text="Search", sorting_hint="tools",}, + tools = {text="Tools"}, + setting = {text="Settings"}, + submenu = {text="Submenu"}, + submenu_item1 = {text="Submenu item 1", sorting_hint="submenu",}, + submenu_item2 = {text="Submenu item 2"}, + } + local order = { + ["KOMenu:menu_buttons"] = { + "setting", + }, + tools = {}, + setting = { + "tools", + "submenu" + }, + submenu = { + "submenu_item2", + }, + } + + local test_menu = MenuSorter:sort(menu_items, order) + local result_menu = { + [1] = { + [1] = { + ["id"] = "tools", + ["sub_item_table"] = { + [1] = { + ["sorting_hint"] = "tools", + ["new"] = true, + ["id"] = "search", + ["text"] = "Search" + }, + ["text"] = "Tools", + ["id"] = "tools" + }, + ["text"] = "Tools" + }, + [2] = { + ["id"] = "submenu", + ["sub_item_table"] = { + [1] = { + ["id"] = "submenu_item2", + ["text"] = "Submenu item 2" + }, + [2] = { + ["sorting_hint"] = "submenu", + ["new"] = true, + ["id"] = "submenu_item1", + ["text"] = "Submenu item 1" + }, + ["text"] = "Submenu", + ["id"] = "submenu" + }, + ["text"] = "Submenu" + }, + [3] = { + ["new"] = true, + ["text"] = "NEW: Main", + ["id"] = "main" + }, + ["id"] = "setting", + ["text"] = "Settings" + }, + ["id"] = "KOMenu:menu_buttons" + } + + assert.is_true( equals(result_menu, test_menu) ) + end) it("should display submenu of orphaned submenu", function() local menu_items = { ["KOMenu:menu_buttons"] = {},