def _create_properties(self): """Populate a frame with a list of all editable properties""" # To mantain container options: self._container_options = {} # Layout Options editors self._rcbag = {} # bag for row/column prop editors # main options frame self._fprop = fprop = ttk.Labelframe(self._sframe.innerframe, text=_('Options:'), padding=4) fprop.grid(row=0, sticky='nswe') # Layout selector label = ttk.Label(fprop, text=_('Manager:')) label.grid(row=0, column=0, sticky=tk.EW, pady=2) self.layout_selector = combo = LayoutManagerPropertyEditor(fprop) combo.parameters(state='readonly', values=self.managers) combo.grid(row=0, column=1, sticky=tk.EW, pady=2) combo.bind('<<PropertyChanged>>', self._layout_manager_changed) self._allowed_managers = self.managers.keys() # Separator w = ttk.Separator(fprop, orient='horizontal') w.grid(row=1, column=0, columnspan=2, sticky='ew', pady=4) # Other Layout properties label_tpl = "{0}:" row = 2 col = 0 self._groups = (('00', properties.MANAGER_PROPERTIES, properties.LAYOUT_OPTIONS), ) for gcode, plist, propdescr in self._groups: for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._fprop, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) label.tooltip = create_tooltip(label, '?') widget = self._create_editor(self._fprop, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) # container layout editor self._cleditor = ContainerLayoutEditor(self._sframe.innerframe) self._cleditor.grid(row=1, sticky='nswe', pady='5 0')
def _ask_manager_change(self, old_manager, new_manager): title = _('Change Manager') msg = _('Change manager from {0} to {1}?') msg = msg.format(old_manager, new_manager) detail = _('All container widgets will be updated.') user_accepts_change = messagebox.askokcancel( title, msg, detail=detail, parent=self.layout_selector.winfo_toplevel()) if user_accepts_change: topack = '<<LayoutEditorContainerManagerToPack>>' togrid = '<<LayoutEditorContainerManagerToGrid>>' event_name = togrid if new_manager == 'grid' else topack self._sframe.event_generate(event_name)
def _create_properties(self): """Populate a frame with a list of all editable properties""" self._frame = f = ttk.Labelframe(self._sframe.innerframe, text=_('Widget properties')) f.configure(padding=4) f.grid(sticky='nswe') label_tpl = "{0}:" row = 0 col = 0 groups = ( ('00', _('Required'), properties.WIDGET_REQUIRED_OPTIONS, properties.REQUIRED_OPTIONS), ('01', _('Standard'), properties.WIDGET_STANDARD_OPTIONS, properties.TK_WIDGET_OPTIONS), ('02', _('Specific'), properties.WIDGET_SPECIFIC_OPTIONS, properties.TK_WIDGET_OPTIONS), ('03', _('Custom'), properties.WIDGET_CUSTOM_OPTIONS, properties.CUSTOM_OPTIONS), ) for gcode, gname, plist, propdescr in groups: padding = '0 0 0 5' if row == 0 else '0 5 0 5' label = ttk.Label(self._frame, text=gname, font='TkDefaultFont 10 bold', padding=padding, foreground='#000059') label.grid(row=row, column=0, sticky='we', columnspan=2) row += 1 for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._frame, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) label.tooltip = create_tooltip(label, '?') widget = self._create_editor(self._frame, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) logger.debug('Created property: %s-%s', gname, name) # add validator for widget id if gcode == '00' and name == 'id': widget.set_unique_cb(self._id_validator)
def _create_ui(self): self._lbl_callback = _('Callback:') self._plabel = w = ttk.Label(self, text=self._lbl_callback, font='TkSmallCaptionFont') w.grid(row=0, column=0, sticky='nswe') self._cbname = w = EntryPropertyEditor(self) w.grid(row=0, column=1, sticky='nswe') w.bind('<<PropertyChanged>>', self._on_variable_changed) # type label: w = ttk.Label(self, text='Type:', font='TkSmallCaptionFont') w.grid(row=1, column=0, sticky='nsew') # type combo cmdtypes = ( (CB_TYPES.SIMPLE, _('Simple')), (CB_TYPES.WITH_WID, _('Send widget ID')), ) self._cmdtype = w = ChoiceByKeyPropertyEditor(self) w.parameters(values=cmdtypes) w.bind('<<PropertyChanged>>', self._on_variable_changed) w.grid(row=1, column=1, sticky='nswe') self.columnconfigure(1, weight=1)
def _create_properties(self): """Populate a frame with a list of all editable properties""" self._frame = f = ttk.Labelframe(self._sframe.innerframe, text=_('Widget properties')) f.grid(sticky='nswe') label_tpl = "{0}:" row = 0 col = 0 groups = ( ('00', _('Required'), properties.WIDGET_REQUIRED_OPTIONS, properties.REQUIRED_OPTIONS), ('01', _('Standard'), properties.WIDGET_STANDARD_OPTIONS, properties.TK_WIDGET_OPTIONS), ('02', _('Specific'), properties.WIDGET_SPECIFIC_OPTIONS, properties.TK_WIDGET_OPTIONS), ('03', _('Custom'), properties.WIDGET_CUSTOM_OPTIONS, properties.CUSTOM_OPTIONS), ) for gcode, gname, plist, propdescr in groups: padding = '0 0 0 5' if row == 0 else '0 5 0 5' label = ttk.Label(self._frame, text=gname, font='TkDefaultFont 10 bold', padding=padding, foreground='#000059') label.grid(row=row, column=0, sticky='we', columnspan=2) row += 1 for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._frame, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) widget = self._create_editor(self._frame, name, kwdata) widget.grid(row=row, column=col+1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode+name] = (label, widget) logger.debug('Created property: {0}-{1}'.format(gname,name))
def _create_ui(self): self._cbname = w = EntryPropertyEditor(self) w.grid(row=0, column=0, sticky='nswe', columnspan=2) w.bind('<<PropertyChanged>>', self._on_variable_changed) self._arg_var = var = tk.StringVar(self, '') self._argd = w = EntryPropertyEditor(self) w.parameters(state='readonly', textvariable=var) w.grid(row=1, column=0, sticky='nswe') self._mb = w = ttk.Menubutton(self, text='Args') w.grid(row=1, column=1, sticky='nswe') olist = ( ('%d', _('Type of action.')), ('%i', _('Index of character string to be inserted/deleted.')), ('%P', _("The new/current value of the entry.")), ('%s', _('The current value of entry prior to editing.')), ('%S', _('The text string being inserted/deleted.')), ('%v', _('The current value of the -validate option.')), ('%V', _('The validation condition that triggered the callback.')), ('%W', _('The name of the entry widget.')), ) options = OrderedDict(olist) self._vars = {k: tk.BooleanVar(self) for k in options.keys()} self._menu = m = tk.Menu(self._mb, tearoff=False) m.add_command(label=_('Select all'), command=self._on_select_all) m.add_command(label=_('Clear'), command=self._on_clear) m.add_separator() for key, txt in options.items(): txt = '{0} {1}'.format(key, txt) m.add_checkbutton(label=txt, variable=self._vars[key], command=self._on_update_args) self._mb['menu'] = m self.columnconfigure(0, weight=1)
def _create_properties(self): """Populate a frame with a list of all editable properties""" self._rcbag = {} # bag for row/column prop editors self._fgrid = f = ttk.Labelframe(self._sframe.innerframe, text=_('Grid options:'), padding=5) f.grid(sticky='nswe') # hack to resize correctly when properties are hidden label = ttk.Label(f) label.grid() label_tpl = "{0}:" row = 0 col = 0 groups = (('00', properties.GRID_PROPERTIES, properties.LAYOUT_OPTIONS), ) for gcode, plist, propdescr in groups: for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._fgrid, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) widget = self._create_editor(self._fgrid, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) # Grid row/col properties #labels gcode = '01' self._fgrc = fgrc = ttk.LabelFrame(self._sframe.innerframe, text=_('Grid row/column options:'), padding=5) fgrc.grid(row=1, column=0, sticky=tk.NSEW, pady='10 0') #hack to resize correctly when properties are hidden label = ttk.Label(fgrc) label.grid() row = col = 0 icol = 1 headers = [] for pname in properties.GRID_RC_PROPERTIES: label = ttk.Label(fgrc, text=pname) label.grid(row=row, column=icol) headers.append(label) icol += 1 self._internal = {'grc_headers': headers} # name_format = '{}_{}_{}' # {row/column}_{number}_{name} MAX_RC = 50 #rowconfig row += 1 trow_label = _('Row {0}:') tcol_label = _('Column {0}:') for index in range(0, MAX_RC): labeltext = trow_label.format(index) label = ttk.Label(fgrc, text=labeltext) label.grid(row=row, column=0) labeltext = tcol_label.format(index) labelc = ttk.Label(fgrc, text=labeltext) labelc.grid(row=row + MAX_RC, column=0, sticky=tk.E, pady=2) icol = 1 for pname in properties.GRID_RC_PROPERTIES: kwdata = properties.LAYOUT_OPTIONS[pname] alias = name_format.format('row', index, pname) widget = self._create_editor(fgrc, alias, kwdata) widget.grid(row=row, column=icol, pady=2) self._rcbag[alias] = (label, widget) alias = name_format.format('column', index, pname) widget = self._create_editor(fgrc, alias, kwdata) widget.grid(row=row + MAX_RC, column=icol, pady=2) self._rcbag[alias] = (labelc, widget) icol += 1 row += 1
def _create_properties(self): """Populate a frame with a list of all editable properties""" self._rcbag = {} # bag for row/column prop editors self._fgrid = f = ttk.Labelframe(self._sframe.innerframe, text=_("Grid options:"), padding=5) f.grid(sticky="nswe") # hack to resize correctly when properties are hidden label = ttk.Label(f) label.grid() label_tpl = "{0}:" row = 0 col = 0 groups = (("00", properties.GRID_PROPERTIES, properties.LAYOUT_OPTIONS),) for gcode, plist, propdescr in groups: for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._fgrid, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) widget = self._create_editor(self._fgrid, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) # Grid row/col properties # labels gcode = "01" self._fgrc = fgrc = ttk.LabelFrame(self._sframe.innerframe, text=_("Grid row/column options:"), padding=5) fgrc.grid(row=1, column=0, sticky=tk.NSEW, pady="10 0") # hack to resize correctly when properties are hidden label = ttk.Label(fgrc) label.grid() row = col = 0 icol = 1 headers = [] for pname in properties.GRID_RC_PROPERTIES: label = ttk.Label(fgrc, text=pname) label.grid(row=row, column=icol) headers.append(label) icol += 1 self._internal = {"grc_headers": headers} # name_format = "{}_{}_{}" # {row/column}_{number}_{name} MAX_RC = 50 # rowconfig row += 1 trow_label = _("Row {0}:") tcol_label = _("Column {0}:") for index in range(0, MAX_RC): labeltext = trow_label.format(index) label = ttk.Label(fgrc, text=labeltext) label.grid(row=row, column=0) labeltext = tcol_label.format(index) labelc = ttk.Label(fgrc, text=labeltext) labelc.grid(row=row + MAX_RC, column=0, sticky=tk.E, pady=2) icol = 1 for pname in properties.GRID_RC_PROPERTIES: kwdata = properties.LAYOUT_OPTIONS[pname] alias = name_format.format("row", index, pname) widget = self._create_editor(fgrc, alias, kwdata) widget.grid(row=row, column=icol, pady=2) self._rcbag[alias] = (label, widget) alias = name_format.format("column", index, pname) widget = self._create_editor(fgrc, alias, kwdata) widget.grid(row=row + MAX_RC, column=icol, pady=2) self._rcbag[alias] = (labelc, widget) icol += 1 row += 1
class LayoutEditor(PropertiesEditor): managers_keys = ('grid', 'pack', 'place') managers_labels = (_('Grid'), _('Pack'), _('Place')) managers = dict(zip(managers_keys, managers_labels)) def _create_properties(self): """Populate a frame with a list of all editable properties""" # To mantain container options: self._container_options = {} # Layout Options editors self._rcbag = {} # bag for row/column prop editors # main options frame self._fprop = fprop = ttk.Labelframe(self._sframe.innerframe, text=_('Options:'), padding=4) fprop.grid(row=0, sticky='nswe') # Layout selector label = ttk.Label(fprop, text=_('Manager:')) label.grid(row=0, column=0, sticky=tk.EW, pady=2) self.layout_selector = combo = LayoutManagerPropertyEditor(fprop) combo.parameters(state='readonly', values=self.managers) combo.grid(row=0, column=1, sticky=tk.EW, pady=2) combo.bind('<<PropertyChanged>>', self._layout_manager_changed) self._allowed_managers = self.managers.keys() # Separator w = ttk.Separator(fprop, orient='horizontal') w.grid(row=1, column=0, columnspan=2, sticky='ew', pady=4) # Other Layout properties label_tpl = "{0}:" row = 2 col = 0 self._groups = (('00', properties.MANAGER_PROPERTIES, properties.LAYOUT_OPTIONS), ) for gcode, plist, propdescr in self._groups: for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._fprop, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) label.tooltip = create_tooltip(label, '?') widget = self._create_editor(self._fprop, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) # container layout editor self._cleditor = ContainerLayoutEditor(self._sframe.innerframe) self._cleditor.grid(row=1, sticky='nswe', pady='5 0') def edit(self, wdescr, manager_options, container_options=None): self._current = wdescr # need to save the container info when updating the view. # this function is called again in _layout_manager_changed if container_options is not None: self._container_options = container_options wclass = wdescr.classname #class_descr = CLASS_MAP[wclass].builder max_children = CLASS_MAP[wclass].builder.maxchildren max_children = 0 if max_children is None else max_children is_container = CLASS_MAP[wclass].builder.container layout_required = CLASS_MAP[wclass].builder.layout_required allow_container_layout = CLASS_MAP[wclass].builder.container_layout show_layout = layout_required # manager selector manager = wdescr.manager manager_prop = properties.GRID_PROPERTIES if manager == 'pack': manager_prop = properties.PACK_PROPERTIES elif manager == 'place': manager_prop = properties.PLACE_PROPERTIES if show_layout: self._fprop.grid() self._allowed_managers = manager_options self.layout_selector.edit(manager) # layout properties for gcode, proplist, gproperties in self._groups: for name in proplist: propdescr = gproperties[name] label, widget = self._propbag[gcode + name] if show_layout and name in manager_prop: self.update_editor(label, widget, wdescr, name, propdescr) label.grid() widget.grid() else: label.grid_remove() widget.grid_remove() else: self._fprop.grid_remove() # determine if show container layout options has_children = self._container_options.get('has_children', False) children_grid_dim = self._container_options.get('grid_dim', None) if is_container and allow_container_layout and has_children: self._cleditor.grid() cmanager = wdescr.container_manager self._cleditor.edit(wdescr, cmanager, children_grid_dim) else: self._cleditor.grid_remove() self._sframe.reposition() def _layout_manager_changed(self, event=None): if self._current is None: # I'm not editing anything return old_manager = self._current.manager new_manager = self.layout_selector.value needs_container_change = (new_manager not in self._allowed_managers) if needs_container_change: self.layout_selector.edit(old_manager) def cb(f=old_manager, t=new_manager): return self._ask_manager_change(f, t) self._sframe.after_idle(cb) else: self._current.manager = new_manager self.edit(self._current, self._allowed_managers) def _ask_manager_change(self, old_manager, new_manager): title = _('Change Manager') msg = _('Change manager from {0} to {1}?') msg = msg.format(old_manager, new_manager) detail = _('All container widgets will be updated.') user_accepts_change = messagebox.askokcancel( title, msg, detail=detail, parent=self.layout_selector.winfo_toplevel()) if user_accepts_change: topack = '<<LayoutEditorContainerManagerToPack>>' togrid = '<<LayoutEditorContainerManagerToGrid>>' event_name = togrid if new_manager == 'grid' else topack self._sframe.event_generate(event_name) def _on_property_changed(self, name, editor): value = editor.value # Save new value and update the preview self._current.layout_property(name, value) def update_editor(self, label, editor, wdescr, pname, propdescr): pdescr = propdescr.copy() manager = wdescr.manager if manager in pdescr: pdescr = dict(pdescr, **pdescr[manager]) label.tooltip.text = pdescr.get('help', None) params = pdescr.get('params', {}) editor.parameters(**params) default = pdescr.get('default', '') value = wdescr.layout_property(pname) if not value and default: value = default editor.edit(value) def hide_all(self): super(LayoutEditor, self).hide_all() self._fprop.grid_remove() self._cleditor.grid_remove()
# encoding: utf-8 # translator marker from pygubudesigner.i18n import translator as _ tooltip_help = { 'class': _('Object class name.'), 'id': _('Object unique identifier.'), 'accelerator': _('Specifies a string to display at the right side of the menu entry.'), 'activerelief': _('Specifies the relief to use when displaying the element that is active, if any.' ), 'activestyle': _('Specifies the style in which to draw the active element.'), 'activebackground': _('Specifies background color to use when drawing active elements.'), 'activeborderwidth': _('Specifies a non-negative value indicating the width of the 3-D border drawn around active elements.' ), 'activeforeground': _('Specifies foreground color to use when drawing active elements.'), 'after': None, 'anchor': _('Specifies how the information in the widget is positioned relative to the inner margins.' ), 'aspect': _('Specifies a non-negative integer value indicating desired aspect ratio for the text. The aspect ratio is specified as 100*width/height. 100 means the text should be as wide as it is tall, 200 means the text should be twice as wide as it is tall, 50 means the text should be twice as tall as it is wide, and so on.'
def _create_properties(self): """Populate a frame with a list of all editable properties""" # Layout selector self._fselector = fm = ttk.Frame(self._sframe.innerframe) label = ttk.Label(fm, text='Manager:') label.pack(side='left') self.layout_selector = combo = LayoutManagerPropertyEditor(fm) combo.parameters(state='readonly', values=self.managers) combo.pack(side='left', expand=True) combo.bind('<<PropertyChanged>>', self._layout_manager_changed) self._allowed_managers = self.managers.keys() fm.grid(row=0, sticky='w') # Layout Options editors self._rcbag = {} # bag for row/column prop editors # main options frame self._fprop = f = ttk.Labelframe(self._sframe.innerframe, text=_('Options:'), padding=4) f.grid(row=1, sticky='nswe') # hack to resize correctly when properties are hidden label = ttk.Frame(f) label.grid() label_tpl = "{0}:" row = 0 col = 0 groups = (('00', properties.MANAGER_PROPERTIES, properties.LAYOUT_OPTIONS), ) for gcode, plist, propdescr in groups: for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._fprop, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) widget = self._create_editor(self._fprop, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) # Grid row properties self._fgr_label = _("Grid row '{0}' options:") self._fgr = fgr = ttk.LabelFrame(self._sframe.innerframe, text=self._fgr_label, padding=5) fgr.grid(row=2, column=0, sticky=tk.NSEW, pady='10 0') name_format = 'row_{0}' # row_{name} row = 0 label_tpl = "{0}:" for pname in properties.GRID_RC_PROPERTIES: kwdata = properties.LAYOUT_OPTIONS[pname] alias = name_format.format(pname) labeltext = label_tpl.format(pname) label = ttk.Label(fgr, text=labeltext, anchor=tk.W) label.grid(row=row, column=0, sticky=tk.EW, pady=2) widget = self._create_editor(fgr, alias, kwdata) widget.grid(row=row, column=1, sticky=tk.EW, pady=2) self._rcbag[alias] = (label, widget) row = row + 1 fgr.columnconfigure(1, weight=1) # Grid column properties self._fgc_label = _("Grid column '{0}' options:") self._fgc = fgc = ttk.LabelFrame(self._sframe.innerframe, text=self._fgc_label, padding=5) fgc.grid(row=3, column=0, sticky=tk.NSEW, pady='10 0') name_format = 'col_{0}' # row_{name} row = 0 label_tpl = "{0}:" for pname in properties.GRID_RC_PROPERTIES: kwdata = properties.LAYOUT_OPTIONS[pname] alias = name_format.format(pname) labeltext = label_tpl.format(pname) label = ttk.Label(fgc, text=labeltext, anchor=tk.W) label.grid(row=row, column=0, sticky=tk.EW, pady=2) widget = self._create_editor(fgc, alias, kwdata) widget.grid(row=row, column=1, sticky=tk.EW, pady=2) self._rcbag[alias] = (label, widget) row = row + 1 fgc.columnconfigure(1, weight=1)
class LayoutEditor(PropertiesEditor): managers_keys = ('grid', 'pack', 'place') managers_labels = (_('Grid'), _('Pack'), _('Place')) managers = dict(zip(managers_keys, managers_labels)) def _create_properties(self): """Populate a frame with a list of all editable properties""" # Layout selector self._fselector = fm = ttk.Frame(self._sframe.innerframe) label = ttk.Label(fm, text='Manager:') label.pack(side='left') self.layout_selector = combo = LayoutManagerPropertyEditor(fm) combo.parameters(state='readonly', values=self.managers) combo.pack(side='left', expand=True) combo.bind('<<PropertyChanged>>', self._layout_manager_changed) self._allowed_managers = self.managers.keys() fm.grid(row=0, sticky='w') # Layout Options editors self._rcbag = {} # bag for row/column prop editors # main options frame self._fprop = f = ttk.Labelframe(self._sframe.innerframe, text=_('Options:'), padding=4) f.grid(row=1, sticky='nswe') # hack to resize correctly when properties are hidden label = ttk.Frame(f) label.grid() label_tpl = "{0}:" row = 0 col = 0 groups = (('00', properties.MANAGER_PROPERTIES, properties.LAYOUT_OPTIONS), ) for gcode, plist, propdescr in groups: for name in plist: kwdata = propdescr[name] labeltext = label_tpl.format(name) label = ttk.Label(self._fprop, text=labeltext, anchor=tk.W) label.grid(row=row, column=col, sticky=tk.EW, pady=2) widget = self._create_editor(self._fprop, name, kwdata) widget.grid(row=row, column=col + 1, sticky=tk.EW, pady=2) row += 1 self._propbag[gcode + name] = (label, widget) # Grid row properties self._fgr_label = _("Grid row '{0}' options:") self._fgr = fgr = ttk.LabelFrame(self._sframe.innerframe, text=self._fgr_label, padding=5) fgr.grid(row=2, column=0, sticky=tk.NSEW, pady='10 0') name_format = 'row_{0}' # row_{name} row = 0 label_tpl = "{0}:" for pname in properties.GRID_RC_PROPERTIES: kwdata = properties.LAYOUT_OPTIONS[pname] alias = name_format.format(pname) labeltext = label_tpl.format(pname) label = ttk.Label(fgr, text=labeltext, anchor=tk.W) label.grid(row=row, column=0, sticky=tk.EW, pady=2) widget = self._create_editor(fgr, alias, kwdata) widget.grid(row=row, column=1, sticky=tk.EW, pady=2) self._rcbag[alias] = (label, widget) row = row + 1 fgr.columnconfigure(1, weight=1) # Grid column properties self._fgc_label = _("Grid column '{0}' options:") self._fgc = fgc = ttk.LabelFrame(self._sframe.innerframe, text=self._fgc_label, padding=5) fgc.grid(row=3, column=0, sticky=tk.NSEW, pady='10 0') name_format = 'col_{0}' # row_{name} row = 0 label_tpl = "{0}:" for pname in properties.GRID_RC_PROPERTIES: kwdata = properties.LAYOUT_OPTIONS[pname] alias = name_format.format(pname) labeltext = label_tpl.format(pname) label = ttk.Label(fgc, text=labeltext, anchor=tk.W) label.grid(row=row, column=0, sticky=tk.EW, pady=2) widget = self._create_editor(fgc, alias, kwdata) widget.grid(row=row, column=1, sticky=tk.EW, pady=2) self._rcbag[alias] = (label, widget) row = row + 1 fgc.columnconfigure(1, weight=1) def edit(self, wdescr, manager_options): self._current = wdescr wclass = wdescr.classname #class_descr = CLASS_MAP[wclass].builder max_children = CLASS_MAP[wclass].builder.maxchildren max_children = 0 if max_children is None else max_children is_container = CLASS_MAP[wclass].builder.container layout_required = CLASS_MAP[wclass].builder.layout_required show_layout = layout_required self._fprop.grid() self._fselector.grid() # manager selector manager = wdescr.manager manager_prop = properties.GRID_PROPERTIES if manager == 'pack': manager_prop = properties.PACK_PROPERTIES elif manager == 'place': manager_prop = properties.PLACE_PROPERTIES if show_layout: self._allowed_managers = manager_options self.layout_selector.edit(manager) self.layout_selector.pack() else: self.layout_selector.pack_forget() #layout properties groups = (('00', properties.MANAGER_PROPERTIES, properties.LAYOUT_OPTIONS), ) for gcode, proplist, gproperties in groups: for name in proplist: propdescr = gproperties[name] label, widget = self._propbag[gcode + name] if show_layout and name in manager_prop: self.update_editor(widget, wdescr, name, propdescr) label.grid() widget.grid() else: label.grid_remove() widget.grid_remove() # determine if show grid r/c properties show_grid_rc = (manager == 'grid' and layout_required) if show_grid_rc: rownum = wdescr.layout_property('row') colnum = wdescr.layout_property('column') label = self._fgr_label.format(rownum) self._fgr.config(text=label) label = self._fgc_label.format(colnum) self._fgc.config(text=label) target = self._current for key in self._rcbag: rowcol, name = self.identify_gridrc_property(key) propdescr = properties.LAYOUT_OPTIONS[name] number = colnum if rowcol == 'col' else rownum label, widget = self._rcbag[key] self.update_rc_editor(rowcol, number, widget, target, name, propdescr) self._fgr.grid() self._fgc.grid() else: self._fgr.grid_remove() self._fgc.grid_remove() self._sframe.reposition() def _layout_manager_changed(self, event=None): if self._current is None: # I'm not editing anything return old_manager = self._current.manager new_manager = self.layout_selector.value needs_container_change = (new_manager not in self._allowed_managers) if needs_container_change: self.layout_selector.edit(old_manager) cb = lambda f=old_manager, t=new_manager: self._ask_manager_change( f, t) self._fselector.after_idle(cb) else: self._current.manager = new_manager self.edit(self._current, self._allowed_managers) def _ask_manager_change(self, old_manager, new_manager): title = _('Change Manager') msg = _('Change manager from {0} to {1}?') msg = msg.format(old_manager, new_manager) detail = _('All container widgets will be updated.') user_accepts_change = messagebox.askokcancel( title, msg, detail=detail, parent=self.layout_selector.winfo_toplevel()) if user_accepts_change: topack = '<<LayoutEditorContainerManagerToPack>>' togrid = '<<LayoutEditorContainerManagerToGrid>>' event_name = togrid if new_manager == 'grid' else topack self._fselector.event_generate(event_name) def _on_property_changed(self, name, editor): value = editor.value if name in properties.MANAGER_PROPERTIES: self._current.layout_property(name, value) else: # asume that is a grid row/col property rowcol, pname = self.identify_gridrc_property(name) number = self._current.layout_property('row') if rowcol == 'col': number = self._current.layout_property('column') target = self._current target.gridrc_property(rowcol, number, pname, value) editor.event_generate('<<LayoutEditorGridRCChanged>>') def identify_gridrc_property(self, alias): return alias.split('_') def update_editor(self, editor, wdescr, pname, propdescr): pdescr = propdescr.copy() manager = wdescr.manager if manager in pdescr: pdescr = dict(pdescr, **pdescr[manager]) params = pdescr.get('params', {}) editor.parameters(**params) default = pdescr.get('default', '') value = wdescr.layout_property(pname) if not value and default: value = default editor.edit(value) def update_rc_editor(self, type_, index, editor, wdescr, pname, propdescr): pdescr = propdescr.copy() classname = wdescr.classname if classname in pdescr: pdescr = dict(pdescr, **pdescr[classname]) params = pdescr.get('params', {}) editor.parameters(**params) default = pdescr.get('default', '') value = '' value = wdescr.gridrc_property(type_, str(index), pname) if not value and default: value = default editor.edit(value) def hide_all(self): super(LayoutEditor, self).hide_all() self._fselector.grid_remove() self._fprop.grid_remove() self._fgr.grid_remove() self._fgc.grid_remove()