diff options
Diffstat (limited to 'grc/gui')
-rw-r--r-- | grc/gui/ActionHandler.py | 9 | ||||
-rw-r--r-- | grc/gui/Actions.py | 5 | ||||
-rw-r--r-- | grc/gui/Bars.py | 124 | ||||
-rw-r--r-- | grc/gui/MainWindow.py | 10 | ||||
-rw-r--r-- | grc/gui/Preferences.py | 35 |
5 files changed, 139 insertions, 44 deletions
diff --git a/grc/gui/ActionHandler.py b/grc/gui/ActionHandler.py index a2c48a7c52..ebf701553d 100644 --- a/grc/gui/ActionHandler.py +++ b/grc/gui/ActionHandler.py @@ -480,10 +480,14 @@ class ActionHandler: self.get_flow_graph()._options_block.get_param('generate_options').set_value(args[0]) self.get_flow_graph().update() elif action == Actions.FLOW_GRAPH_OPEN: - file_paths = OpenFlowGraphFileDialog(self.get_page().get_file_path()).run() + file_paths = args if args else OpenFlowGraphFileDialog(self.get_page().get_file_path()).run() if file_paths: #open a new page for each file, show only the first for i,file_path in enumerate(file_paths): self.main_window.new_page(file_path, show=(i==0)) + Preferences.files_recent_add(file_path) + self.main_window.tool_bar.refresh_submenus() + self.main_window.menu_bar.refresh_submenus() + elif action == Actions.FLOW_GRAPH_OPEN_QSS_THEME: file_paths = OpenQSSFileDialog(GR_PREFIX + '/share/gnuradio/themes/').run() if file_paths: @@ -513,6 +517,9 @@ class ActionHandler: if file_path is not None: self.get_page().set_file_path(file_path) Actions.FLOW_GRAPH_SAVE() + Preferences.files_recent_add(file_path) + self.main_window.tool_bar.refresh_submenus() + self.main_window.menu_bar.refresh_submenus() elif action == Actions.FLOW_GRAPH_SCREEN_CAPTURE: file_path = SaveImageFileDialog(self.get_page().get_file_path()).run() if file_path is not None: diff --git a/grc/gui/Actions.py b/grc/gui/Actions.py index c3ae6c971f..d646722df1 100644 --- a/grc/gui/Actions.py +++ b/grc/gui/Actions.py @@ -183,6 +183,11 @@ FLOW_GRAPH_OPEN = Action( stock_id=gtk.STOCK_OPEN, keypresses=(gtk.keysyms.o, gtk.gdk.CONTROL_MASK), ) +FLOW_GRAPH_OPEN_RECENT = Action( + label='Open _Recent', + tooltip='Open a recently used flow graph', + stock_id=gtk.STOCK_OPEN, +) FLOW_GRAPH_SAVE = Action( label='_Save', tooltip='Save the current flow graph', diff --git a/grc/gui/Bars.py b/grc/gui/Bars.py index 2ab5b2a712..8a04b1c8f7 100644 --- a/grc/gui/Bars.py +++ b/grc/gui/Bars.py @@ -1,5 +1,5 @@ """ -Copyright 2007, 2008, 2009 Free Software Foundation, Inc. +Copyright 2007, 2008, 2009, 2015 Free Software Foundation, Inc. This file is part of GNU Radio GNU Radio Companion is free software; you can redistribute it and/or @@ -26,8 +26,8 @@ from . import Actions # The list of actions for the toolbar. TOOLBAR_LIST = ( - Actions.FLOW_GRAPH_NEW, - Actions.FLOW_GRAPH_OPEN, + (Actions.FLOW_GRAPH_NEW, 'flow_graph_new'), + (Actions.FLOW_GRAPH_OPEN, 'flow_graph_recent'), Actions.FLOW_GRAPH_SAVE, Actions.FLOW_GRAPH_CLOSE, None, @@ -64,6 +64,7 @@ MENU_BAR_LIST = ( (gtk.Action('File', '_File', None, None), [ 'flow_graph_new', Actions.FLOW_GRAPH_OPEN, + 'flow_graph_recent', None, Actions.FLOW_GRAPH_SAVE, Actions.FLOW_GRAPH_SAVE_AS, @@ -155,24 +156,90 @@ CONTEXT_MENU_LIST = [ ] -class Toolbar(gtk.Toolbar): +class SubMenuCreator(object): + + def __init__(self, generate_modes, action_handler_callback): + self.generate_modes = generate_modes + self.action_handler_callback = action_handler_callback + self.submenus = [] + + def create_submenu(self, action_tuple, item): + func = getattr(self, '_fill_' + action_tuple[1] + "_submenu") + self.submenus.append((action_tuple[0], func, item)) + self.refresh_submenus() + + def refresh_submenus(self): + for action, func, item in self.submenus: + try: + item.set_property("menu", func(action)) + except TypeError: + item.set_property("submenu", func(action)) + item.set_property('sensitive', True) + + def callback_adaptor(self, item, action_key): + action, key = action_key + self.action_handler_callback(action, key) + + def _fill_flow_graph_new_submenu(self, action): + """Sub menu to create flow-graph with pre-set generate mode""" + menu = gtk.Menu() + for key, name, default in self.generate_modes: + if default: + item = Actions.FLOW_GRAPH_NEW.create_menu_item() + item.set_label(name) + else: + item = gtk.MenuItem(name) + item.connect('activate', self.callback_adaptor, (action, key)) + menu.append(item) + menu.show_all() + return menu + + def _fill_flow_graph_recent_submenu(self, action): + """menu showing recent flow-graphs""" + import Preferences + menu = gtk.Menu() + recent_files = Preferences.files_recent() + if len(recent_files) > 0: + for i, file_name in enumerate(recent_files): + item = gtk.MenuItem("%d. %s" % (i+1, file_name)) + item.connect('activate', self.callback_adaptor, + (action, file_name)) + menu.append(item) + menu.show_all() + return menu + return None + + +class Toolbar(gtk.Toolbar, SubMenuCreator): """The gtk toolbar with actions added from the toolbar list.""" - def __init__(self): + def __init__(self, generate_modes, action_handler_callback): """ Parse the list of action names in the toolbar list. - Look up the action for each name in the action list and add it to the toolbar. + Look up the action for each name in the action list and add it to the + toolbar. """ gtk.Toolbar.__init__(self) self.set_style(gtk.TOOLBAR_ICONS) + SubMenuCreator.__init__(self, generate_modes, action_handler_callback) + for action in TOOLBAR_LIST: - if action: # add a tool item + if isinstance(action, tuple) and isinstance(action[1], str): + # create a button with a sub-menu + action[0].set_tool_item_type(gtk.MenuToolButton) + item = action[0].create_tool_item() + self.create_submenu(action, item) + self.refresh_submenus() + + elif action is None: + item = gtk.SeparatorToolItem() + + else: + action.set_tool_item_type(gtk.ToolButton) item = action.create_tool_item() # this reset of the tooltip property is required # (after creating the tool item) for the tooltip to show action.set_property('tooltip', action.get_property('tooltip')) - else: - item = gtk.SeparatorToolItem() self.add(item) @@ -202,42 +269,37 @@ class MenuHelperMixin(object): return main -class MenuBar(gtk.MenuBar, MenuHelperMixin): +class MenuBar(gtk.MenuBar, MenuHelperMixin, SubMenuCreator): """The gtk menu bar with actions added from the menu bar list.""" def __init__(self, generate_modes, action_handler_callback): """ Parse the list of submenus from the menubar list. For each submenu, get a list of action names. - Look up the action for each name in the action list and add it to the submenu. - Add the submenu to the menu bar. + Look up the action for each name in the action list and add it to the + submenu. Add the submenu to the menu bar. """ gtk.MenuBar.__init__(self) - self.generate_modes = generate_modes - self.action_handler_callback = action_handler_callback + SubMenuCreator.__init__(self, generate_modes, action_handler_callback) for main_action, actions in MENU_BAR_LIST: self.append(self._make_sub_menu(main_action, actions)) def create_flow_graph_new(self): - """Sub menu to create flow-graph with pre-set generate mode""" - - def callback_adaptor(item, key): - """Sets original FLOW_GRAPH_NEW action as source""" - self.action_handler_callback(Actions.FLOW_GRAPH_NEW, key) - - sub_menu = gtk.Menu() - for key, name, default in self.generate_modes: - if default: - item = Actions.FLOW_GRAPH_NEW.create_menu_item() - item.set_label(name) - else: - item = gtk.MenuItem(name) - item.connect('activate', callback_adaptor, key) - sub_menu.append(item) - sub_menu.show_all() main = gtk.ImageMenuItem(gtk.STOCK_NEW) main.set_label(Actions.FLOW_GRAPH_NEW.get_label()) - main.set_submenu(sub_menu) + func = self._fill_flow_graph_new_submenu + self.submenus.append((Actions.FLOW_GRAPH_NEW, func, main)) + self.refresh_submenus() + return main + + def create_flow_graph_recent(self): + main = gtk.ImageMenuItem(gtk.STOCK_OPEN) + main.set_label(Actions.FLOW_GRAPH_OPEN_RECENT.get_label()) + func = self._fill_flow_graph_recent_submenu + self.submenus.append((Actions.FLOW_GRAPH_OPEN, func, main)) + self.refresh_submenus() + if main.get_submenu() is None: + main.set_property('sensitive', False) return main diff --git a/grc/gui/MainWindow.py b/grc/gui/MainWindow.py index f658a85062..08cef11639 100644 --- a/grc/gui/MainWindow.py +++ b/grc/gui/MainWindow.py @@ -76,6 +76,8 @@ class MainWindow(gtk.Window): generate_modes = [ (o.get_key(), o.get_name(), o.get_key() == generate_mode_default) for o in gen_opts.get_options()] + # load preferences + Preferences.load(platform) #setup window gtk.Window.__init__(self, gtk.WINDOW_TOPLEVEL) vbox = gtk.VBox() @@ -83,9 +85,10 @@ class MainWindow(gtk.Window): self.add(vbox) #create the menu bar and toolbar self.add_accel_group(Actions.get_accel_group()) - menu_bar = Bars.MenuBar(generate_modes, action_handler_callback) - vbox.pack_start(menu_bar, False) - vbox.pack_start(Bars.Toolbar(), False) + self.menu_bar = Bars.MenuBar(generate_modes, action_handler_callback) + vbox.pack_start(self.menu_bar, False) + self.tool_bar = Bars.Toolbar(generate_modes, action_handler_callback ) + vbox.pack_start(self.tool_bar, False) vbox.pack_start(self.hpaned) #create the notebook self.notebook = gtk.Notebook() @@ -110,7 +113,6 @@ class MainWindow(gtk.Window): self.reports_scrolled_window.set_size_request(-1, DEFAULT_REPORTS_WINDOW_WIDTH) self.flow_graph_vpaned.pack2(self.reports_scrolled_window, False) #dont allow resize #load preferences and show the main window - Preferences.load(platform) self.resize(*Preferences.main_window_size()) self.flow_graph_vpaned.set_position(Preferences.reports_window_position()) self.hpaned.set_position(Preferences.blocks_window_position()) diff --git a/grc/gui/Preferences.py b/grc/gui/Preferences.py index a5a7fa91b5..54dab38282 100644 --- a/grc/gui/Preferences.py +++ b/grc/gui/Preferences.py @@ -41,8 +41,11 @@ def load(platform): global _platform _platform = platform # create sections - _config_parser.add_section('main') - _config_parser.add_section('files_open') + for section in ['main', 'files_open', 'files_recent']: + try: + _config_parser.add_section(section) + except Exception, e: + print e try: _config_parser.read(_platform.get_prefs_file()) except Exception as err: @@ -91,21 +94,37 @@ def file_open(filename=None): return entry('file_open', filename, default='') -def files_open(files=None): +def files_lists(key, files=None): if files is not None: - _config_parser.remove_section('files_open') # clear section - _config_parser.add_section('files_open') + _config_parser.remove_section(key) # clear section + _config_parser.add_section(key) for i, filename in enumerate(files): - _config_parser.set('files_open', 'file_open_%d' % i, filename) + _config_parser.set(key, '%s_%d' % (key, i), filename) else: try: - files = [value for name, value in _config_parser.items('files_open') - if name.startswith('file_open_')] + files = [value for name, value in _config_parser.items(key) + if name.startswith('%s_' % key)] except ConfigParser.Error: files = [] return files +def files_open(files=None): + return files_lists('files_open', files) + +def files_recent(files=None): + return files_lists('files_recent', files) + +def files_recent_add(file_name): + import os + # double check file_name + if os.path.exists(file_name): + recent_files = files_recent() + if file_name in recent_files: + recent_files.remove(file_name) # attempt removal + recent_files.insert(0, file_name) # insert at start + files_recent(recent_files[:10]) # keep up to 10 files + def reports_window_position(pos=None): return entry('reports_window_position', pos, default=-1) or 1 |