|
@ -1,15 +1,43 @@ |
|
|
#!/usr/bin/env python |
|
|
#!/usr/bin/env python |
|
|
|
|
|
# coding: utf-8 |
|
|
|
|
|
# vim: set noet ts=4 tw=0: |
|
|
|
|
|
from __future__ import unicode_literals, print_function, absolute_import, division |
|
|
|
|
|
|
|
|
import os |
|
|
import os |
|
|
import sys |
|
|
import sys |
|
|
import getopt |
|
|
import getopt |
|
|
import gtk |
|
|
try: |
|
|
|
|
|
import gtk |
|
|
|
|
|
pygtk=True |
|
|
|
|
|
except ImportError: |
|
|
|
|
|
from gi.repository import Gtk |
|
|
|
|
|
pygtk=False |
|
|
import xdg.DesktopEntry as dentry |
|
|
import xdg.DesktopEntry as dentry |
|
|
import xdg.Exceptions as exc |
|
|
import xdg.Exceptions as exc |
|
|
import xdg.BaseDirectory as bd |
|
|
import xdg.BaseDirectory as bd |
|
|
import ConfigParser |
|
|
import ConfigParser |
|
|
from operator import attrgetter |
|
|
from operator import attrgetter |
|
|
|
|
|
|
|
|
|
|
|
def gtk_icon_theme_get_default(): |
|
|
|
|
|
if pygtk: |
|
|
|
|
|
return gtk.icon_theme_get_default() |
|
|
|
|
|
else: |
|
|
|
|
|
return Gtk.IconTheme.get_default() |
|
|
|
|
|
def gtk_lookup_icon(icon_theme, icon_name, size, no_svg=False, force_svg=False, use_builtin=False, generic_fallback=False, force_size=False): |
|
|
|
|
|
flags = None |
|
|
|
|
|
if pygtk: |
|
|
|
|
|
if no_svg: flags = gtk.ICON_LOOKUP_NO_SVG |
|
|
|
|
|
elif force_svg: flags = gtk.ICON_LOOKUP_FORCE_SVG |
|
|
|
|
|
if use_builtin: flags &= gtk.ICON_LOOKUP_FORCE_SVG |
|
|
|
|
|
else: |
|
|
|
|
|
if no_svg: flags = Gtk.IconLookupFlags.NO_SVG |
|
|
|
|
|
elif force_svg: flags = Gtk.IconLookupFlags.FORCE_SVG |
|
|
|
|
|
if use_builtin: flags &= Gtk.IconLookupFlags.USE_BUILTIN |
|
|
|
|
|
if generic_fallback: flags &= Gtk.IconLookupFlags.GENERIC_FALLBACK |
|
|
|
|
|
if force_size: flags &= Gtk.IconLookupFlags.FORCE_SIZE |
|
|
|
|
|
return icon_theme.lookup_icon(icon_name, size, flags) |
|
|
|
|
|
pass |
|
|
|
|
|
|
|
|
seticon = False |
|
|
seticon = False |
|
|
desktop = False |
|
|
desktop = False |
|
|
submenu = True |
|
|
submenu = True |
|
@ -107,19 +135,20 @@ def main(argv): |
|
|
sys.exit(2) |
|
|
sys.exit(2) |
|
|
|
|
|
|
|
|
def usage(): |
|
|
def usage(): |
|
|
print 'USAGE:', os.path.basename(sys.argv[0]), '[OPTIONS]' |
|
|
print("""\ |
|
|
print |
|
|
USAGE: {app} [OPTIONS] |
|
|
print 'OPTIONS:' |
|
|
|
|
|
print ' -f, --format the output format to use. Valid options are fluxbox, icewm, windowmaker and pekwm' |
|
|
OPTIONS: |
|
|
print ' -i, --icons enable support for icons in the menus. Only works with fluxbox, icewm' |
|
|
-f, --format the output format to use. Valid options are fluxbox, icewm, windowmaker and pekwm |
|
|
print ' -n, --no-submenu do not create a submenu. Does not work with windowmaker' |
|
|
-i, --icons enable support for icons in the menus. Only works with fluxbox, icewm |
|
|
print ' --pekwm-dynamic generate dynamic menus for pekwm' |
|
|
-n, --no-submenu do not create a submenu. Does not work with windowmaker |
|
|
print ' -h, --help show this help message' |
|
|
--pekwm-dynamic generate dynamic menus for pekwm |
|
|
print ' You have to specify the output format using the -f switch.' |
|
|
-h, --help show this help message |
|
|
print |
|
|
You have to specify the output format using the -f switch. |
|
|
print 'EXAMPLES:' |
|
|
|
|
|
print ' xdgmenumaker -f windowmaker' |
|
|
EXAMPLES: |
|
|
print ' xdgmenumaker -i -f fluxbox' |
|
|
xdgmenumaker -f windowmaker |
|
|
|
|
|
xdgmenumaker -i -f fluxbox""".format(app=os.path.basename(sys.argv[0]))) |
|
|
|
|
|
|
|
|
class MenuEntry: |
|
|
class MenuEntry: |
|
|
def __init__(self, category, name, icon, command, path): |
|
|
def __init__(self, category, name, icon, command, path): |
|
@ -147,8 +176,8 @@ def icon_full_path(icon): |
|
|
icon = icon.replace('.svg', '') |
|
|
icon = icon.replace('.svg', '') |
|
|
elif icon.endswith('.xpm'): |
|
|
elif icon.endswith('.xpm'): |
|
|
icon = icon.replace('.xpm', '') |
|
|
icon = icon.replace('.xpm', '') |
|
|
icon_theme = gtk.icon_theme_get_default() |
|
|
icon_theme = gtk_icon_theme_get_default() |
|
|
icon = icon_theme.lookup_icon(icon, 16, gtk.ICON_LOOKUP_NO_SVG) |
|
|
icon = gtk_lookup_icon(icon_theme, icon, 16, no_svg=True) |
|
|
if icon: |
|
|
if icon: |
|
|
icon = icon.get_filename() |
|
|
icon = icon.get_filename() |
|
|
return icon |
|
|
return icon |
|
@ -316,11 +345,11 @@ def fluxboxmenu(): |
|
|
if seticon == True: |
|
|
if seticon == True: |
|
|
app_icon = icon_full_path(applications_icon) |
|
|
app_icon = icon_full_path(applications_icon) |
|
|
if app_icon is None: |
|
|
if app_icon is None: |
|
|
print '[submenu] ('+applications+')' |
|
|
print('[submenu] ({app})'.format(app=applications)) |
|
|
else: |
|
|
else: |
|
|
print '[submenu] ('+applications+') <'+app_icon+'>' |
|
|
print('[submenu] ({app}) <{icon}>'.format(app=applications, icon=app_icon)) |
|
|
else: |
|
|
else: |
|
|
print '[submenu] ('+applications+')' |
|
|
print('[submenu] ({app})'.format(app=applications)) |
|
|
else: |
|
|
else: |
|
|
spacing = '' |
|
|
spacing = '' |
|
|
for i in menu(): |
|
|
for i in menu(): |
|
@ -329,11 +358,11 @@ def fluxboxmenu(): |
|
|
cat_icon = category_icon(category) |
|
|
cat_icon = category_icon(category) |
|
|
cat_icon = icon_full_path(cat_icon) |
|
|
cat_icon = icon_full_path(cat_icon) |
|
|
if cat_icon: |
|
|
if cat_icon: |
|
|
print spacing+'[submenu] ('+category+') <'+cat_icon+'>' |
|
|
print('{spc}[submenu] ({cat}) <{icon}>'.format(spc=spacing, cat=category, icon=cat_icon)) |
|
|
else: |
|
|
else: |
|
|
print spacing+'[submenu] ('+category+')' |
|
|
print('{spc}[submenu] ({cat})'.format(spc=spacing, cat=category)) |
|
|
else: |
|
|
else: |
|
|
print spacing+'[submenu] ('+category+')' |
|
|
print('{spc}[submenu] ({cat})'.format(spc=spacing, cat=category)) |
|
|
for j in i[1]: |
|
|
for j in i[1]: |
|
|
# closing parentheses need to be escaped, otherwise they are |
|
|
# closing parentheses need to be escaped, otherwise they are |
|
|
# cropped out, along with everything that comes after them |
|
|
# cropped out, along with everything that comes after them |
|
@ -344,24 +373,24 @@ def fluxboxmenu(): |
|
|
if path is not None: |
|
|
if path is not None: |
|
|
command = 'cd '+path+' ; '+command |
|
|
command = 'cd '+path+' ; '+command |
|
|
if icon is None: |
|
|
if icon is None: |
|
|
print spacing+' [exec] ('+name+') {'+command+'}' |
|
|
print('{spc} [exec] ({name}) {{{cmd}}}'.format(spc=spacing, name=name, cmd=commnd)) |
|
|
else: |
|
|
else: |
|
|
print spacing+' [exec] ('+name+') {'+command+'} <'+icon+'>' |
|
|
print('{spc} [exec] ({name}) {{{cmd}}} <{icon}>'.format(spc=spacing, name=name, cmd=commnd, icon=icon)) |
|
|
print spacing+'[end] # ('+category+')' |
|
|
print('{spc}[end] # ({cat})'.format(spc=spacing, cat=category)) |
|
|
if submenu is True: |
|
|
if submenu is True: |
|
|
print '[end] # ('+applications+')' |
|
|
print('[end] # ({app})'.format(app=applications)) |
|
|
|
|
|
|
|
|
def windowmakermenu(): |
|
|
def windowmakermenu(): |
|
|
print '"'+applications+'" MENU' |
|
|
print('"{app}" MENU'.format(app=applications)) |
|
|
for i in menu(): |
|
|
for i in menu(): |
|
|
category = i[0] |
|
|
category = i[0] |
|
|
print ' "'+category+'" MENU' |
|
|
print(' "{cat}" MENU'.format(cat=category)) |
|
|
for j in i[1]: |
|
|
for j in i[1]: |
|
|
name = j[0] |
|
|
name = j[0] |
|
|
command = j[2] |
|
|
command = j[2] |
|
|
print ' "'+name+'" EXEC '+command |
|
|
print(' "{name}" EXEC {cmd}'.format(name=name, cmd=command)) |
|
|
print ' "'+category+'" END' |
|
|
print(' "{cat}" END'.format(cat=category)) |
|
|
print '"'+applications+'" END' |
|
|
print('"{app}" END'.format(app=applications)) |
|
|
|
|
|
|
|
|
def icewmmenu(): |
|
|
def icewmmenu(): |
|
|
global seticon |
|
|
global seticon |
|
@ -372,9 +401,9 @@ def icewmmenu(): |
|
|
app_icon = icon_full_path(applications_icon) |
|
|
app_icon = icon_full_path(applications_icon) |
|
|
if app_icon is None: |
|
|
if app_icon is None: |
|
|
app_icon = "_none_" |
|
|
app_icon = "_none_" |
|
|
print 'menu "'+applications+'" '+app_icon+' {' |
|
|
print('menu "{app}" {icon} {{'.format(app=applications, icon=app_icon)) |
|
|
else: |
|
|
else: |
|
|
print 'menu "'+applications+'" _none_ {' |
|
|
print('menu "{app}" _none_ {{'.format(app=applications)) |
|
|
else: |
|
|
else: |
|
|
spacing = '' |
|
|
spacing = '' |
|
|
for i in menu(): |
|
|
for i in menu(): |
|
@ -382,27 +411,27 @@ def icewmmenu(): |
|
|
cat_icon = category_icon(category) |
|
|
cat_icon = category_icon(category) |
|
|
cat_icon = icon_full_path(cat_icon) |
|
|
cat_icon = icon_full_path(cat_icon) |
|
|
if seticon is True and cat_icon is not None: |
|
|
if seticon is True and cat_icon is not None: |
|
|
print spacing+'menu "'+category+'" '+cat_icon+' {' |
|
|
print('{spc}menu "{cat}" {icon} {{'.format(spc=spacing, cat=category, icon=cat_icon)) |
|
|
else: |
|
|
else: |
|
|
print spacing+'menu "'+category+'" _none_ {' |
|
|
print('{spc}menu "{cat}" _none_ {{'.format(spc=spacing, cat=category)) |
|
|
for j in i[1]: |
|
|
for j in i[1]: |
|
|
name = j[0] |
|
|
name = j[0] |
|
|
icon = j[1] |
|
|
icon = j[1] |
|
|
command = j[2] |
|
|
command = j[2] |
|
|
if seticon is True and icon is not None: |
|
|
if seticon is True and icon is not None: |
|
|
print spacing+' prog "'+name+'" '+icon+' '+command |
|
|
print('{spc} prog "{name}" {icon} {cmd}'.format(spc=spacing, name=name, icon=icon, cmd=command)) |
|
|
else: |
|
|
else: |
|
|
print spacing+' prog "'+name+'" _none_ '+command |
|
|
print('{spc} prog "{name}" _none_ {cmd}'.format(spc=spacing, name=name, cmd=command)) |
|
|
print spacing+'}' |
|
|
print(spacing + '}') |
|
|
if submenu is True: |
|
|
if submenu is True: |
|
|
print '}' |
|
|
print('}') |
|
|
|
|
|
|
|
|
def pekwmmenu(): |
|
|
def pekwmmenu(): |
|
|
global seticon |
|
|
global seticon |
|
|
global submenu |
|
|
global submenu |
|
|
global pekwmdynamic |
|
|
global pekwmdynamic |
|
|
if pekwmdynamic is True: |
|
|
if pekwmdynamic is True: |
|
|
print "Dynamic {" |
|
|
print("Dynamic {") |
|
|
dspacing = ' ' |
|
|
dspacing = ' ' |
|
|
else: |
|
|
else: |
|
|
dspacing = '' |
|
|
dspacing = '' |
|
@ -410,9 +439,9 @@ def pekwmmenu(): |
|
|
spacing = ' ' |
|
|
spacing = ' ' |
|
|
if seticon == True: |
|
|
if seticon == True: |
|
|
app_icon = icon_full_path(applications_icon) |
|
|
app_icon = icon_full_path(applications_icon) |
|
|
print dspacing+'Submenu = "'+applications+'" { Icon = "'+app_icon+'"' |
|
|
print('{dspc}Submenu = "{app}" {{ Icon = "{icon}"'.format(dspc=dspacing, app=applications, icon=app_icon)) |
|
|
else: |
|
|
else: |
|
|
print dspacing+'Submenu = "'+applications+'" {' |
|
|
print('{dspc}Submenu = "{app}" {{'.format(dspc=dspacing, app=applications)) |
|
|
else: |
|
|
else: |
|
|
spacing = '' |
|
|
spacing = '' |
|
|
for i in menu(): |
|
|
for i in menu(): |
|
@ -420,9 +449,9 @@ def pekwmmenu(): |
|
|
cat_icon = category_icon(category) |
|
|
cat_icon = category_icon(category) |
|
|
cat_icon = icon_full_path(cat_icon) |
|
|
cat_icon = icon_full_path(cat_icon) |
|
|
if seticon is True and cat_icon is not None: |
|
|
if seticon is True and cat_icon is not None: |
|
|
print dspacing+spacing+'Submenu = "'+category+'" { Icon = "'+cat_icon+'"' |
|
|
print('{dspc}{spc}Submenu = "{cat}" {{ Icon = "{icon}"'.format(dspc=dspacing, spc=spacing, cat=category, icon=cat_icon)) |
|
|
else: |
|
|
else: |
|
|
print dspacing+spacing+'Submenu = "'+category+'" {' |
|
|
print('{dspc}{spc}Submenu = "{cat}" {{'.format(dspc=dspacing, spc=spacing, cat=category)) |
|
|
for j in i[1]: |
|
|
for j in i[1]: |
|
|
name = j[0] |
|
|
name = j[0] |
|
|
icon = j[1] |
|
|
icon = j[1] |
|
@ -438,14 +467,14 @@ def pekwmmenu(): |
|
|
# path does not exist |
|
|
# path does not exist |
|
|
command = 'cd '+path+' && '+command+' || '+command |
|
|
command = 'cd '+path+' && '+command+' || '+command |
|
|
if seticon is True and icon is not None: |
|
|
if seticon is True and icon is not None: |
|
|
print dspacing+spacing+' Entry = "'+name+'" { Icon = "'+icon+'"; Actions = "Exec '+command+' &" }' |
|
|
print('{dspc}{spc} Entry = "{name}" {{ Icon = "{icon}"; Actions = "Exec {cmd} &" }}'.format(dspc=dspacing, spc=spacing, name=name, icon=icon, cmd=command)) |
|
|
else: |
|
|
else: |
|
|
print dspacing+spacing+' Entry = "'+name+'" { Actions = "Exec '+command+' &" }' |
|
|
print('{dspc}{spc} Entry = "{name}" {{ Actions = "Exec {cmd} &" }}'.format(dspc=dspacing, spc=spacing, name=name, cmd=command)) |
|
|
print dspacing+spacing+'}' |
|
|
print(dspacing + spacing + '}') |
|
|
if submenu is True: |
|
|
if submenu is True: |
|
|
print dspacing+'}' |
|
|
print(dspacing+'}') |
|
|
if pekwmdynamic is True: |
|
|
if pekwmdynamic is True: |
|
|
print "}" |
|
|
print("}") |
|
|
|
|
|
|
|
|
if __name__ == "__main__": |
|
|
if __name__ == "__main__": |
|
|
main(sys.argv[1:]) |
|
|
main(sys.argv[1:]) |
|
|