awesome/lib/menubar/menu_gen.lua
Kazunobu Kuriyama 9ae945c931 Enhance menubar icon path lookup
The way of icon path lookup for `menubar` is enhanced so that it is
based on a theme-oriented way as described in the specification:

  Icon Theme Specification, Ver. 0.12
  http://standards.freedesktop.org/icon-theme-spec/icon-theme-spec-latest.html

To accomplish this:

 * Add the two new files `icon_theme.lua` and `index_theme.lua`.

   The former implements an icon lookup algorithm suggested in the URL
   above.  The latter implements a helper object to parse the cache file
   `index.theme` of which data is used by the former.

 * Modify `menu_gen.lua` to use the new algorithm.

   - The implementation of `lookup_category_icons` is changed
     accordingly.
   - The values of the field `all_categories.icon_name` are changed file
     names to icon names, i.e., file extensions which are used to
     indicate image file formats are removed.

 * Add the new file `icon_theme_spec.lua` for a unit test for checking
   if `icon_theme.lua` together with `index_theme.lua` works as
   expected.
2015-09-26 11:45:38 +09:00

129 lines
5 KiB
Lua

---------------------------------------------------------------------------
--- Menu generation module for menubar
--
-- @author Antonio Terceiro
-- @copyright 2009, 2011-2012 Antonio Terceiro, Alexander Yakushev
-- @release @AWESOME_VERSION@
-- @module menubar.menu_gen
---------------------------------------------------------------------------
-- Grab environment
local utils = require("menubar.utils")
local icon_theme = require("menubar.icon_theme")
local pairs = pairs
local ipairs = ipairs
local string = string
local table = table
local menu_gen = {}
-- Options section
local data_dir = os.getenv("XDG_DATA_HOME")
if not data_dir then
data_dir = os.getenv("HOME") .. '/.local/share/'
end
--- Specifies all directories where menubar should look for .desktop
-- files. The search is not recursive.
menu_gen.all_menu_dirs = { data_dir .. 'applications/', '/usr/share/applications/', '/usr/local/share/applications/' }
--- Specify the mapping of .desktop Categories section to the
-- categories in the menubar. If "use" flag is set to false then any of
-- the applications that fall only to this category will not be shown.
menu_gen.all_categories = {
multimedia = { app_type = "AudioVideo", name = "Multimedia",
icon_name = "applications-multimedia", use = true },
development = { app_type = "Development", name = "Development",
icon_name = "applications-development", use = true },
education = { app_type = "Education", name = "Education",
icon_name = "applications-science", use = true },
games = { app_type = "Game", name = "Games",
icon_name = "applications-games", use = true },
graphics = { app_type = "Graphics", name = "Graphics",
icon_name = "applications-graphics", use = true },
office = { app_type = "Office", name = "Office",
icon_name = "applications-office", use = true },
internet = { app_type = "Network", name = "Internet",
icon_name = "applications-internet", use = true },
settings = { app_type = "Settings", name = "Settings",
icon_name = "applications-utilities", use = true },
tools = { app_type = "System", name = "System Tools",
icon_name = "applications-system", use = true },
utility = { app_type = "Utility", name = "Accessories",
icon_name = "applications-accessories", use = true }
}
--- Find icons for category entries.
function menu_gen.lookup_category_icons()
for _, v in pairs(menu_gen.all_categories) do
v.icon = icon_theme():find_icon_path(v.icon_name)
end
end
--- Get category key name and whether it is used by its app_type.
-- @param app_type Application category as written in .desktop file.
-- @return category key name in all_categories, whether the category is used
local function get_category_name_and_usage_by_type(app_type)
for k, v in pairs(menu_gen.all_categories) do
if app_type == v.app_type then
return k, v.use
end
end
end
--- Remove CR\LF newline from the end of the string.
-- @param s string to trim
local function trim(s)
if not s then return end
if string.byte(s, #s) == 13 then
return string.sub(s, 1, #s - 1)
end
return s
end
--- Generate an array of all visible menu entries.
-- @return all menu entries.
function menu_gen.generate()
-- Update icons for category entries
menu_gen.lookup_category_icons()
local result = {}
for _, dir in ipairs(menu_gen.all_menu_dirs) do
local entries = utils.parse_dir(dir)
for _, program in ipairs(entries) do
-- Check whether to include program in the menu
if program.show and program.Name and program.cmdline then
local target_category = nil
-- Check if the program falls at least to one of the
-- usable categories. Set target_category to be the id
-- of the first category it finds.
if program.categories then
for _, category in pairs(program.categories) do
local cat_key, cat_use =
get_category_name_and_usage_by_type(category)
if cat_key and cat_use then
target_category = cat_key
break
end
end
end
if target_category then
local name = trim(program.Name) or ""
local cmdline = trim(program.cmdline) or ""
local icon = utils.lookup_icon(trim(program.icon_path)) or nil
table.insert(result, { name = name,
cmdline = cmdline,
icon = icon,
category = target_category })
end
end
end
end
return result
end
return menu_gen
-- vim: filetype=lua:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:textwidth=80