def __init__(self): ''' Constructor ''' cellRendererText = CellRendererText() treeViewColumn = TreeViewColumn() treeViewColumn.pack_start(cellRendererText) treeView = TreeView() treeView.append_column(treeViewColumn) scrolledWindow = ScrolledWindow() scrolledWindow.add(treeView) btnAdd_Alternative = Button() btnDel_Alternative = Button() hButtonBox = HButtonBox() hButtonBox.pack_start(btnAdd_Alternative) hButtonBox.pack_start(btnDel_Alternative) vBox = VBox() vBox.pack_start(scrolledWindow) vBox.pack_start(hButtonBox) self.add(vBox)
def __init__(self): Window.__init__(self) self.model = ListStore(str, str) self.aboutWindow = None self.helper = Helper(None) self.set_title('Gnome Custom Shortcuts') self.set_icon_from_file(join(data_path, 'icon.svg')) self.set_border_width(5) self.set_size_request(400, 400) list = TreeView() list.append_column(TreeViewColumn('')) list.append_column(TreeViewColumn('Command')) list.append_column(TreeViewColumn('Shortcut')) closeButton = Button(None, STOCK_CLOSE) aboutButton = Button(None, STOCK_ABOUT) buttonsBox = HButtonBox() buttonsBox.pack_start(aboutButton, False, False, 0) buttonsBox.pack_start(Label(''), True, True, 0) buttonsBox.pack_start(closeButton, False, False, 0) box = VBox(False, 5) box.pack_start(list, True, True, 0) box.pack_start(buttonsBox, False, False, 0) self.connect('destroy', main_quit, None) closeButton.connect('clicked', main_quit, None) aboutButton.connect('clicked', self.show_about, None) self.add(box) self.show_all()
def __init__(self, objectives, new): Expander.__init__(self) self.connect("enter-notify-event", self.onEnterNotifyEvent) self.connect("leave-notify-event", self.onLeaveNotifyEvent) vBox = VBox() self.add(vBox) # Data model self.model = ListStore(str, float) # Title bar hBox = HBox() self.set_property("label-widget", hBox) self.title = Label() hBox.pack_start(self.title) # Alternatives treeView = TreeView(self.model) # treeView.set_headers_visible(False) vBox.pack_start(treeView) listStore_objectives = ListStore(str) for name in objectives: listStore_objectives.append((name, )) def combo_changed(_, path, text, model): model[path][0] = text cellRenderer = CellRendererCombo() cellRenderer.connect("edited", combo_changed, self.model) cellRenderer.set_property("text-column", 0) cellRenderer.set_property("editable", True) cellRenderer.set_property("has-entry", True) cellRenderer.set_property("model", listStore_objectives) treeViewColumn = TreeViewColumn("Alternative", cellRenderer, text=0) # treeViewColumn = TreeViewColumn(None,cellRenderer,text=0) treeView.append_column(treeViewColumn) def spin_changed(_, path, value, model): model[path][1] = float(value.replace(",", ".")) cellRenderer = CellRendererSpin() cellRenderer.connect("edited", spin_changed, self.model) cellRenderer.set_property("adjustment", Adjustment(1, 0, 100, 1, 10, 0)) cellRenderer.set_property("editable", True) cellRenderer.set_property("digits", 2) treeViewColumn = TreeViewColumn(None, cellRenderer, text=1) treeView.append_column(treeViewColumn) # Add/remove alternative button box # hButtonBox = HButtonBox() # vBox.pack_start(hButtonBox, False) # Add alternative button = Button("gtk-add") button.connect("clicked", self.on_btnAdd_Alternative_clicked) button.set_use_stock(True) # hButtonBox.pack_start(button) vBox.pack_start(button, False) # # Remove alternative # button = Button("gtk-remove") # button.connect("clicked",self.on_btnDel_Alternative_clicked) # button.set_use_stock(True) # hButtonBox.pack_start(button) # Expand the requeriment and add an alternative if it's new if new: self.set_expanded(True) self.model.append((None, 1.0)) # Show requeriment self.show_all() # Delete requeriment button (default is hidden) self.imgRemove = Image() self.imgRemove.connect("button-press-event", self.onDelRequeriment) self.imgRemove.set_from_stock("gtk-cancel", ICON_SIZE_MENU) hBox.pack_start(self.imgRemove)
def __on_plugin_directories_button_click(self, button): """Present a dialog to the user for selecting extra plugin directories and process the request.""" dia = Dialog('Plugin Directories', None, DIALOG_MODAL, (STOCK_OK, RESPONSE_OK, STOCK_CANCEL, RESPONSE_CANCEL ) ) dia.resize(500, 300) dia.vbox.set_spacing(8) # Setup the tree view of plugin directories. model = ListStore(str) # each row contains a single string tv = TreeView(model) cell = CellRendererText() column = TreeViewColumn('Directory', cell, text = 0) tv.append_column(column) dia.vbox.pack_start(tv) # Populate the tree view. plugin_directories = \ get_plugins_directories_from_config(self.config, self.config_path) for plugin_directory in plugin_directories: row = (plugin_directory,) model.append(row) modify_box = HBox(spacing = 8) # Setup the remove directory button. remove_button = Button('Remove') remove_button.set_sensitive(False) # no directory selected initially remove_button.connect('clicked', self.__on_remove, tv) modify_box.pack_end(remove_button, expand = False) tv.connect('cursor-changed', self.__on_select, remove_button) # Setup the add directory button. add_button = Button('Add') add_button.connect('clicked', self.__on_add, tv) modify_box.pack_end(add_button, expand = False) dia.vbox.pack_start(modify_box, expand = False) # Setup the "already included directories" label. included_label = Label('Plugins in the PYTHONPATH are already ' + 'available to BoKeep.') # Use a horizontal box to left-justify the label. For some reason, # the label's set_justification property doesn't work for me. label_box = HBox() label_box.pack_start(included_label, expand = False) dia.vbox.pack_start(label_box, expand = False) dia.show_all() dia_result = dia.run() if dia_result == RESPONSE_OK: # Remove the old plugin directories from the program's path. plugin_directories = \ get_plugins_directories_from_config(self.config, self.config_path) for plugin_directory in plugin_directories: path.remove(plugin_directory) # Get the new plugin directories from the dialog. plugin_directories = [] for row in model: plugin_directory = row[0] plugin_directories.append(plugin_directory) # Update the BoKeep PYTHONPATH so that new plugins can be loaded and # populate the list of possible new plugins. for plugin_directory in plugin_directories: path.append(plugin_directory) self.__populate_possible_plugins() # Save the new plugin directories in the configuration file. set_plugin_directories_in_config(self.config, self.config_path, plugin_directories) dia.destroy()
class BoKeepConfigDialog(object): """GUI for configuring BoKeep.""" config_path = None config = None def __init__(self, db_path, db_access_method, config_path, config, error_msg=None): self.config_path = config_path self.config = config load_glade_file_get_widgets_and_connect_signals( get_main_window_glade_file(), "bokeep_config_dialog", self, self) self.selection_change_lock = True self.state = BoKeepConfigGuiState( error_msg, self.__force_config_on_newly_created_plugin) self.books_tv = TreeView(self.state.book_liststore) self.books_tv.append_column( TreeViewColumn("Book", CellRendererText(), text=0 ) ) self.books_tv.get_selection().connect( "changed", self.on_book_selection_change) self.books_window.add(self.books_tv) self.books_tv.show() self.plugins_tv = TreeView(self.state.frontend_plugin_liststore) self.plugins_tv.append_column( TreeViewColumn("Plugin", CellRendererText(), text=0) ) crt = CellRendererToggle() crt.set_radio(False) self.plugins_tv.append_column( TreeViewColumn("Enabled", crt, active=1) ) self.plugins_window.add(self.plugins_tv) self.plugins_tv.show() self.plugin_directories_button.connect('clicked', self.__on_plugin_directories_button_click) self.__populate_possible_plugins() self.db_path_label.set_text(db_path) if db_path != None: self.do_action(DB_ENTRY_CHANGE, (db_path, db_access_method)) self.do_action(DB_PATH_CHANGE) if db_access_method == ZODB_CONFIG_FILESTORAGE: self.filestorage_radio.set_active(True) elif db_access_method == ZODB_CONFIG_ZCONFIG: self.zconfig_radio.set_active(True) if error_msg == None: error_msg = "" self.message_label.set_label(error_msg) self.set_sensitivities() self.selection_change_lock = False self.backend_entry_lock = False def __populate_possible_plugins(self): """Populates the GUI with the possible front and backend plugins.""" available_plugin_liststore = ListStore(str) for plugin_name in get_available_frontend_plugins(): available_plugin_liststore.append([plugin_name]) self.plugin_add_entry_combo.set_model(available_plugin_liststore) self.plugin_add_entry_combo.set_text_column(0) available_backend_plugin_liststore = ListStore(str) for backend_plugin_name in get_available_backend_plugins(): available_backend_plugin_liststore.append([backend_plugin_name]) self.backend_plugin_entry_combo.set_model(available_backend_plugin_liststore) self.backend_plugin_entry_combo.set_text_column(0) def do_action(self, action, arg=None): """Passes on an action to BoKeepConfigGuiState and gui is then updated after to reflect the effects of that action by examining where that state machine is at after the action. """ try: self.state.do_action(action, arg) except FrontendPluginImportError, err: backend_plugin_entry = self.backend_plugin_entry_combo.child backend_plugin_name = backend_plugin_entry.get_text() if backend_plugin_name in err.plugin_names: self.backend_plugin_entry_combo.child.set_text( self.state.data[BOOK].get_backend_plugin_name() ) err.plugin_names.remove(backend_plugin_name) frontend_plugins = {} for name, enabled in self.state.frontend_plugin_liststore: frontend_plugins[name] = (name, enabled) for err_plugin_name in err.plugin_names: del frontend_plugins[err_plugin_name] self.state.frontend_plugin_liststore.clear() for valid_plugin_name, enabled in frontend_plugins.values(): self.state.frontend_plugin_liststore.append((valid_plugin_name, enabled)) error_dialog = MessageDialog(self.bokeep_config_dialog, DIALOG_MODAL, MESSAGE_ERROR, BUTTONS_OK, str(err)) error_dialog.run() error_dialog.destroy() # raises last exception that had been caught, in above # except clause, err raise
def create_editable_type_defined_listview_and_model( field_list, new_row_func, parralell_list, change_register, readonly=False, insert_pre_hook=null_function, insert_post_hook=null_function, change_pre_hook=null_function, change_post_hook=null_function, del_pre_hook=null_function, del_post_hook=null_function): vbox = VBox() tv = TreeView() model = ListStore( * chain((display_fieldtype_transform(fieldtype) for fieldname, fieldtype in field_list), (store_fieldtype_transform(fieldtype) for fieldname, fieldtype in field_list) ) # chain ) # ListStore # it is important to do this fill of the liststore # with the existing items first prior to adding event handlers # (row-changed, row-inserted, row-deleted) that # look for changes and keep the two lists in sync for list_row in parralell_list: model.append( tuple(transform_list_row_into_twice_repeated_row_for_model( list_row, field_list) ) ) # append if not readonly: model.connect("row-changed", row_changed_handler, parralell_list, change_register, field_list, change_pre_hook, change_post_hook, ) model.connect("row-inserted", row_inserted_handler, parralell_list, change_register, insert_pre_hook, insert_post_hook ) model.connect("row-deleted", row_deleted_handler, parralell_list, change_register, del_pre_hook, del_post_hook) for i, (fieldname, fieldtype) in enumerate(field_list): def setup_edited_handler_for_renderer_to_original_model(cell_renderer): cell_renderer.connect( 'edited', cell_edited_update_original_modelhandler, model, i, field_list[i][FIELD_TYPE]) return cell_renderer if fieldtype == date: cell_renderer = \ setup_edited_handler_for_renderer_to_original_model( CellRendererDate() ) elif type(fieldtype) == tuple: cell_renderer = CellRendererCombo() cell_renderer.set_property("has-entry", fieldtype[COMBO_TYPE_HAS_ENTRY_FIELD]) combo_liststore = ListStore( str, store_fieldtype_transform(fieldtype) ) for combo_string, combo_value in \ combobox_list_strings_and_values_iteration(fieldtype): combo_liststore.append( (combo_string, combo_value) ) cell_renderer.set_property("model", combo_liststore) cell_renderer.set_property("text-column", 0) if fieldtype[COMBO_TYPE_HAS_ENTRY_FIELD]: setup_edited_handler_for_renderer_to_original_model( cell_renderer) else: lookup_dict = dict( combobox_list_strings_and_values_iteration(fieldtype) ) cell_renderer.connect( 'edited', combo_cell_edited_update_original_modelhandler, model, i, lookup_dict) elif type(fieldtype) == dict and fieldtype['type'] == file: cell_renderer = CellRendererFile( fieldtype['file_type'] if 'file_type' in fieldtype else FILE_CHOOSER_ACTION_OPEN ) setup_edited_handler_for_renderer_to_original_model(cell_renderer) else: cell_renderer = \ setup_edited_handler_for_renderer_to_original_model( CellRendererText() ) if not readonly: cell_renderer.set_property("editable", True) cell_renderer.set_property("editable-set", True) tvc = TreeViewColumn(fieldname, cell_renderer, text=i) tv.append_column(tvc) vbox.pack_start(tv) tv.set_model(model) hbox = HBox() buttons = [ pack_in_stock_but_and_ret(start_stock_button(code), hbox) for code in (STOCK_ADD, STOCK_DELETE) ] if readonly: for button in buttons: button.set_property("sensitive", False) else: buttons[0].connect( "clicked", editable_listview_add_button_clicked_handler, model, new_row_func, field_list ) buttons[1].connect( "clicked", editable_listview_del_button_clicked_handler, tv ) vbox.pack_start(hbox, expand=False) return model, tv, vbox