gimp r26336 - in branches/soc-2008-python: . plug-ins/pygimp plug-ins/pygimp/plug-ins
- From: larsc svn gnome org
- To: svn-commits-list gnome org
- Subject: gimp r26336 - in branches/soc-2008-python: . plug-ins/pygimp plug-ins/pygimp/plug-ins
- Date: Tue, 29 Jul 2008 19:33:35 +0000 (UTC)
Author: larsc
Date: Tue Jul 29 19:33:35 2008
New Revision: 26336
URL: http://svn.gnome.org/viewvc/gimp?rev=26336&view=rev
Log:
2008-07-29 Lars-Peter Clausen <lars metafoo de>
* plug-ins/pygimp/gimpfu.py: Refactored the interactive mode code. Moved all
widget code to a new subclass of gimp.Dialog.
Added support to specifiy a custom layout for plugins.
* plug-ins/pygimp/plug-ins/sphere.py: Added testcode for the new layout
parameter of register.
Modified:
branches/soc-2008-python/ChangeLog
branches/soc-2008-python/plug-ins/pygimp/gimpfu.py
branches/soc-2008-python/plug-ins/pygimp/plug-ins/sphere.py
Modified: branches/soc-2008-python/plug-ins/pygimp/gimpfu.py
==============================================================================
--- branches/soc-2008-python/plug-ins/pygimp/gimpfu.py (original)
+++ branches/soc-2008-python/plug-ins/pygimp/gimpfu.py Tue Jul 29 19:33:35 2008
@@ -69,7 +69,7 @@
consists of the translation domain and the directory where the translations
are installed.
'''
-
+import gtk
import string as _string
import gimp
from gimp.enums import *
@@ -97,7 +97,6 @@
#PF_STRINGARRAY = int(PDB_STRINGARRAY)
PF_COLOR = int(PDB_COLOR)
PF_COLOUR = PF_COLOR
-PF_REGION = int(PDB_REGION)
PF_DISPLAY = int(PDB_DISPLAY)
PF_IMAGE = int(PDB_IMAGE)
PF_LAYER = int(PDB_LAYER)
@@ -127,6 +126,12 @@
PF_DIRNAME = 1012
PF_OPTION = 1013
+LAY_EXPANDER = 0
+LAY_GROUP = 1
+LAY_TABLE = 2
+LAY_FIELD = 3
+LAY_PREVIEW = 4
+
_type_mapping = {
PF_INT8 : PDB_INT8,
PF_INT16 : PDB_INT16,
@@ -139,7 +144,6 @@
#PF_FLOATARRAY : PDB_FLOATARRAY,
#PF_STRINGARRAY : PDB_STRINGARRAY,
PF_COLOR : PDB_COLOR,
- PF_REGION : PDB_REGION,
PF_DISPLAY : PDB_DISPLAY,
PF_IMAGE : PDB_IMAGE,
PF_LAYER : PDB_LAYER,
@@ -176,7 +180,6 @@
#PF_FLOATARRAY : list,
#PF_STRINGARRAY : list,
PF_COLOR : gimp.color.RGB,
- PF_REGION : int,
PF_DISPLAY : gimp.Display,
PF_IMAGE : gimp.Image,
PF_LAYER : gimp.Layer,
@@ -201,11 +204,455 @@
PF_OPTION : int,
}
+class EntryValueError(Exception):
+ pass
+
+
+class ScriptFuDialog(gimp.ui.Dialog):
+
+ def __init__(self, proc_name, params, defaults, domain, blurb, layout):
+ gimp.ui.Dialog.__init__(self, proc_name, 'python-fu', None, 0, None,
+ proc_name, (gtk.STOCK_CANCEL,
+ gtk.RESPONSE_CANCEL, gtk.STOCK_OK,
+ gtk.RESPONSE_OK))
+
+
+ self.proc_name = proc_name
+ self.params = params
+ self.field_widgets = []
+ self.params_by_name = {}
+
+ for i in range(len(params)):
+ self.params_by_name[params[i][1]] = (params[i][0], params[i][2],
+ defaults[i]) + tuple(params[i][4:])
+
+
+
+ self.tooltips = gtk.Tooltips()
+
+ self.set_alternative_button_order((gtk.RESPONSE_OK, gtk.RESPONSE_CANCEL))
+ self.set_transient()
+ vbox = gtk.VBox(False, 12)
+ vbox.set_border_width(12)
+ self.vbox.pack_start(vbox)
+ vbox.show()
+
+ if blurb:
+ if domain:
+ try:
+ (domain, locale_dir) = domain
+ trans = gettext.translation(domain, locale_dir, fallback=True)
+ except ValueError:
+ trans = gettext.translation(domain, fallback=True)
+ blurb = trans.ugettext(blurb)
+ box = gimp.ui.HintBox(blurb)
+ vbox.pack_start(box, expand=False)
+ box.show()
+
+ if layout:
+ table = self.process_layout(layout)
+ else:
+ table = gtk.Table(len(params), 2, False)
+ table.set_row_spacings(6)
+ table.set_col_spacings(6)
+
+ row = 0
+
+ for param in params:
+ label, widget = self.create_field(param[1])
+ table.attach(label, 0, 1, row, row+1, xoptions=gtk.FILL)
+ table.attach(widget, 1, 2, row, row+1, yoptions=0)
+ row += 1
+ vbox.pack_start(table, expand=False)
+ table.show()
+
+ progress_vbox = gtk.VBox(False, 6)
+ vbox.pack_end(progress_vbox, expand=False)
+ progress_vbox.show()
+
+ progress = gimp.ui.ProgressBar()
+ progress_vbox.pack_start(progress)
+ progress.show()
+
+ # progress_label = gtk.Label()
+ # progress_label.set_alignment(0.0, 0.5)
+ # progress_label.set_ellipsize(pango.ELLIPSIZE_MIDDLE)
+
+ # attrs = pango.AttrList()
+ # attrs.insert(pango.AttrStyle(pango.STYLE_ITALIC, 0, -1))
+ # progress_label.set_attributes(attrs)
+
+ # progress_vbox.pack_start(progress_label)
+ # progress_label.show()
+
+
+ self.tooltips.enable()
+ self.connect("response", self.response)
+
+ def response(self, dialog, id):
+ if id == gtk.RESPONSE_OK:
+ self.set_response_sensitive(gtk.RESPONSE_OK, False)
+ self.set_response_sensitive(gtk.RESPONSE_CANCEL, False)
+
+ params = []
+
+ try:
+ for wid in self.field_widgets:
+ params.append(wid.get_value())
+ except EntryValueError:
+ self.warning_dialog(dialog, _("Invalid input for '%s'") % wid.desc)
+ else:
+ try:
+ self.result = self.run_script(params)
+ except Exception:
+ self.set_response_sensitive(gtk.RESPONSE_CANCEL, True)
+ self.error_dialog()
+ raise
+
+ gtk.main_quit()
+
+
+ def warning_dialog(self, primary, secondary=None):
+ dlg = gtk.MessageDialog(self, gtk.DIALOG_DESTROY_WITH_PARENT,
+ gtk.MESSAGE_WARNING, gtk.BUTTONS_CLOSE,
+ primary)
+ if secondary:
+ dlg.format_secondary_text(secondary)
+ dlg.run()
+ dlg.destroy()
+
+ def error_dialog(self):
+ import sys, traceback
+
+ exc_str = exc_only_str = _('Missing exception information')
+
+ try:
+ etype, value, tb = sys.exc_info()
+ exc_str = ''.join(traceback.format_exception(etype, value, tb))
+ exc_only_str = ''.join(traceback.format_exception_only(etype, value))
+ finally:
+ etype = value = tb = None
+
+ title = _("An error occured running %s") % self.proc_name
+ dlg = gtk.MessageDialog(self, gtk.DIALOG_DESTROY_WITH_PARENT,
+ gtk.MESSAGE_ERROR, gtk.BUTTONS_CLOSE,
+ title)
+ dlg.format_secondary_text(exc_only_str)
+
+ alignment = gtk.Alignment(0.0, 0.0, 1.0, 1.0)
+ alignment.set_padding(0, 0, 12, 12)
+ dlg.vbox.pack_start(alignment)
+ alignment.show()
+
+ expander = gtk.Expander(_("_More Information"));
+ expander.set_use_underline(True)
+ expander.set_spacing(6)
+ alignment.add(expander)
+ expander.show()
+
+ scrolled = gtk.ScrolledWindow()
+ scrolled.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
+ scrolled.set_size_request(-1, 200)
+ expander.add(scrolled)
+ scrolled.show()
+
+
+ label = gtk.Label(exc_str)
+ label.set_alignment(0.0, 0.0)
+ label.set_padding(6, 6)
+ label.set_selectable(True)
+ scrolled.add_with_viewport(label)
+ label.show()
+
+ def response(widget, id):
+ widget.destroy()
+
+ dlg.connect("response", response)
+ dlg.set_resizable(True)
+ dlg.show()
+
+ def create_field(self, name):
+ # define a mapping of param types to edit objects ...
+ class StringEntry(gtk.Entry):
+ def __init__(self, default=''):
+ gtk.Entry.__init__(self)
+ self.set_text(str(default))
+
+ def get_value(self):
+ return self.get_text()
+
+ class TextEntry(gtk.ScrolledWindow):
+ def __init__ (self, default=''):
+ gtk.ScrolledWindow.__init__(self)
+ self.set_shadow_type(gtk.SHADOW_IN)
+
+ self.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
+ self.set_size_request(100, -1)
+
+ self.view = gtk.TextView()
+ self.add(self.view)
+ self.view.show()
+
+ self.buffer = self.view.get_buffer()
+
+ self.set_value(str(default))
+
+ def set_value(self, text):
+ self.buffer.set_text(text)
+
+ def get_value(self):
+ return self.buffer.get_text(self.buffer.get_start_iter(),
+ self.buffer.get_end_iter())
+
+ class IntEntry(StringEntry):
+ def get_value(self):
+ try:
+ return int(self.get_text())
+ except ValueError, e:
+ raise EntryValueError, e.args
+
+ class FloatEntry(StringEntry):
+ def get_value(self):
+ try:
+ return float(self.get_text())
+ except ValueError, e:
+ raise EntryValueError, e.args
+
+ #class ArrayEntry(StringEntry):
+ # def get_value(self):
+ # return eval(self.get_text(), {}, {})
+
+ class SliderEntry(gtk.HScale):
+ # bounds is (upper, lower, step)
+ def __init__(self, default=0.0, bounds=(0.0, 100.0, 5.0)):
+ self.adj = gtk.Adjustment(default, bounds[0],
+ bounds[1], bounds[2],
+ bounds[2], 0.0)
+ gtk.HScale.__init__(self, self.adj)
+
+ def get_value(self):
+ return self.adj.value
+
+ class SpinnerEntry(gtk.SpinButton):
+ # bounds is (upper, lower, step)
+ def __init__(self, default=0.0, bounds=(0.0, 100.0, 5.0)):
+ self.adj = gtk.Adjustment(default, bounds[0],
+ bounds[1], bounds[2],
+ bounds[2], 0.0)
+ gtk.SpinButton.__init__(self, self.adj, 1, 0)
+
+ def get_value(self):
+ try:
+ return int(self.get_text())
+ except ValueError, e:
+ raise EntryValueError, e.args
+
+ class ToggleEntry(gtk.ToggleButton):
+ def __init__(self, default=0):
+ gtk.ToggleButton.__init__(self)
+
+ self.label = gtk.Label(_("No"))
+ self.add(self.label)
+ self.label.show()
+
+ self.connect("toggled", self.changed)
+
+ self.set_active(default)
+
+ def changed(self, tog):
+ if tog.get_active():
+ self.label.set_text(_("Yes"))
+ else:
+ self.label.set_text(_("No"))
+
+ def get_value(self):
+ return self.get_active()
+
+ class RadioEntry(gtk.VBox):
+ def __init__(self, default=0, items=((_("Yes"), 1), (_("No"), 0))):
+ gtk.VBox.__init__(self, homogeneous=False, spacing=2)
+
+ button = None
+
+ for (label, value) in items:
+ button = gtk.RadioButton(button, label)
+ self.pack_start(button)
+ button.show()
+
+ button.connect("toggled", self.changed, value)
+
+ if value == default:
+ button.set_active(True)
+ self.active_value = value
+
+ def changed(self, radio, value):
+ if radio.get_active():
+ self.active_value = value
+
+ def get_value(self):
+ return self.active_value
+
+ class ComboEntry(gtk.ComboBox):
+ def __init__(self, default=0, items=()):
+ store = gtk.ListStore(str)
+ for item in items:
+ store.append([item])
+
+ gtk.ComboBox.__init__(self, model=store)
+
+ cell = gtk.CellRendererText()
+ self.pack_start(cell)
+ self.set_attributes(cell, text=0)
+
+ self.set_active(default)
+
+ def get_value(self):
+ return self.get_active()
+
+ def FileSelector(default=''):
+ if default and default.endswith('/'):
+ selector = DirnameSelector
+ if default == '/': default = ''
+ else:
+ selector = FilenameSelector
+ return selector(default)
+
+ class FilenameSelector(gtk.FileChooserButton):
+ def __init__(self, default='', save_mode=False):
+ gtk.FileChooserButton.__init__(self,
+ _("Python-Fu File Selection"))
+ self.set_action(gtk.FILE_CHOOSER_ACTION_OPEN)
+ if default:
+ self.set_filename(default)
+
+ def get_value(self):
+ return self.get_filename()
+
+ class DirnameSelector(gtk.FileChooserButton):
+ def __init__(self, default=''):
+ gtk.FileChooserButton.__init__(self,
+ _("Python-Fu Folder Selection"))
+ self.set_action(gtk.FILE_CHOOSER_ACTION_SELECT_FOLDER)
+ if default:
+ self.set_filename(default)
+
+ def get_value(self):
+ return self.get_filename()
+
+ _edit_mapping = {
+ PF_INT8 : IntEntry,
+ PF_INT16 : IntEntry,
+ PF_INT32 : IntEntry,
+ PF_FLOAT : FloatEntry,
+ PF_STRING : StringEntry,
+ #PF_INT8ARRAY : ArrayEntry,
+ #PF_INT16ARRAY : ArrayEntry,
+ #PF_INT32ARRAY : ArrayEntry,
+ #PF_FLOATARRAY : ArrayEntry,
+ #PF_STRINGARRAY : ArrayEntry,
+ PF_COLOR : gimp.ui.ColorSelector,
+ PF_IMAGE : gimp.ui.ImageSelector,
+ PF_LAYER : gimp.ui.LayerSelector,
+ PF_CHANNEL : gimp.ui.ChannelSelector,
+ PF_DRAWABLE : gimp.ui.DrawableSelector,
+ PF_VECTORS : gimp.ui.VectorsSelector,
+
+ PF_TOGGLE : ToggleEntry,
+ PF_SLIDER : SliderEntry,
+ PF_SPINNER : SpinnerEntry,
+ PF_RADIO : RadioEntry,
+ PF_OPTION : ComboEntry,
+
+ PF_FONT : gimp.ui.FontSelector,
+ PF_FILE : FileSelector,
+ PF_FILENAME : FilenameSelector,
+ PF_DIRNAME : DirnameSelector,
+ PF_BRUSH : gimp.ui.BrushSelector,
+ PF_PATTERN : gimp.ui.PatternSelector,
+ PF_GRADIENT : gimp.ui.GradientSelector,
+ PF_PALETTE : gimp.ui.PaletteSelector,
+ PF_TEXT : TextEntry
+ }
+
+ param = self.params_by_name[name]
+ label = gtk.Label(param[1])
+ label.set_use_underline(True)
+ label.set_alignment(0.0, 0.5)
+ label.show()
+
+ widget = _edit_mapping[param[0]](*param[2:])
+
+ label.set_mnemonic_widget(widget)
+
+ if param[0] != PF_TEXT:
+ self.tooltips.set_tip(widget, param[1], None)
+ else:
+ #Attach tip to TextView, not to ScrolledWindow
+ self.tooltips.set_tip(widget.view, param[1], None)
+ widget.show()
+
+ widget.desc = param[1]
+ self.field_widgets.append(widget)
+
+ return (label, widget)
+
+ def create_expander(self, label, children):
+ expander = gtk.Expander(label)
+ expander.add(self.process_layout(children))
+ expander.show()
+ return expander
+
+ def create_group(self, label, children):
+ group = gtk.Frame(label)
+ table = self.process_layout(children)
+ table.set_border_width(6)
+ group.add(table)
+ group.show()
+ return group
+
+ def create_table(self, children):
+ return self.process_layout(children)
+
+ def create_preview(self, type = None):
+ return gimp.ui.ZoomPreview()
+
+ def process_layout(self, layout):
+
+ table = gtk.Table(len(layout), 2, False)
+ table.set_row_spacings(6)
+ table.set_col_spacings(6)
+ table.show()
+
+ mappings = {LAY_EXPANDER: self.create_expander,
+ LAY_GROUP: self.create_group,
+ LAY_TABLE: self.create_table,
+ LAY_PREVIEW: self.create_preview,
+ LAY_FIELD: self.create_field}
+
+ row = 0
+ for item in layout:
+ func = mappings[item[0]]
+ result = func(*item[1:])
+ if isinstance(result, tuple):
+ table.attach(result[0], 0, 1, row, row+1, xoptions=gtk.FILL)
+ table.attach(result[1], 1, 2, row, row+1, yoptions=0)
+ else:
+ table.attach(result, 0, 2, row, row+1, xoptions=gtk.FILL)
+ row += 1
+
+ return table
+
+
+
+
+
+
_registered_plugins_ = {}
def register(proc_name, blurb, help, author, copyright, date, label,
imagetypes, params, results, function,
- menu=None, domain=None, on_query=None, on_run=None):
+ menu=None, domain=None, on_query=None, on_run=None,
+ layout=None):
'''This is called to register a new plug-in.'''
# First perform some sanity checks on the data
@@ -281,14 +728,14 @@
date, label, imagetypes,
plugin_type, params, results,
function, menu, domain,
- on_query, on_run)
+ on_query, on_run, layout)
def _query():
for plugin in _registered_plugins_.keys():
(blurb, help, author, copyright, date,
label, imagetypes, plugin_type,
params, results, function, menu, domain,
- on_query, on_run) = _registered_plugins_[plugin]
+ on_query, on_run, layout) = _registered_plugins_[plugin]
def make_params(params):
return [(_type_mapping[x[0]],
@@ -319,10 +766,7 @@
on_query()
def _get_defaults(proc_name):
- (blurb, help, author, copyright, date,
- label, imagetypes, plugin_type,
- params, results, function, menu, domain,
- on_query, on_run) = _registered_plugins_[proc_name]
+ params = _registered_plugins_[proc_name][8]
key = "python-fu-save--" + proc_name
@@ -333,7 +777,6 @@
return [x[3] for x in params]
def _set_defaults(proc_name, defaults):
-
key = "python-fu-save--" + proc_name
gimp.shelf.shelf[key] = defaults
@@ -341,12 +784,15 @@
(blurb, help, author, copyright, date,
label, imagetypes, plugin_type,
params, results, function, menu, domain,
- on_query, on_run) = _registered_plugins_[proc_name]
+ on_query, on_run, layout) = _registered_plugins_[proc_name]
+
+ if on_run:
+ on_run()
def run_script(run_params):
params = start_params + tuple(run_params)
_set_defaults(proc_name, params)
- return apply(function, params)
+ return function(*params)
params = params[len(start_params):]
@@ -354,394 +800,13 @@
if len(params) == 0:
return run_script([])
- import pygtk
- pygtk.require('2.0')
-
- import gtk
-# import pango
-
defaults = _get_defaults(proc_name)
defaults = defaults[len(start_params):]
- class EntryValueError(Exception):
- pass
-
- def warning_dialog(parent, primary, secondary=None):
- dlg = gtk.MessageDialog(parent, gtk.DIALOG_DESTROY_WITH_PARENT,
- gtk.MESSAGE_WARNING, gtk.BUTTONS_CLOSE,
- primary)
- if secondary:
- dlg.format_secondary_text(secondary)
- dlg.run()
- dlg.destroy()
-
- def error_dialog(parent, proc_name):
- import sys, traceback
-
- exc_str = exc_only_str = _('Missing exception information')
-
- try:
- etype, value, tb = sys.exc_info()
- exc_str = ''.join(traceback.format_exception(etype, value, tb))
- exc_only_str = ''.join(traceback.format_exception_only(etype, value))
- finally:
- etype = value = tb = None
-
- title = _("An error occured running %s") % proc_name
- dlg = gtk.MessageDialog(parent, gtk.DIALOG_DESTROY_WITH_PARENT,
- gtk.MESSAGE_ERROR, gtk.BUTTONS_CLOSE,
- title)
- dlg.format_secondary_text(exc_only_str)
-
- alignment = gtk.Alignment(0.0, 0.0, 1.0, 1.0)
- alignment.set_padding(0, 0, 12, 12)
- dlg.vbox.pack_start(alignment)
- alignment.show()
-
- expander = gtk.Expander(_("_More Information"));
- expander.set_use_underline(True)
- expander.set_spacing(6)
- alignment.add(expander)
- expander.show()
-
- scrolled = gtk.ScrolledWindow()
- scrolled.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
- scrolled.set_size_request(-1, 200)
- expander.add(scrolled)
- scrolled.show()
-
-
- label = gtk.Label(exc_str)
- label.set_alignment(0.0, 0.0)
- label.set_padding(6, 6)
- label.set_selectable(True)
- scrolled.add_with_viewport(label)
- label.show()
-
- def response(widget, id):
- widget.destroy()
-
- dlg.connect("response", response)
- dlg.set_resizable(True)
- dlg.show()
-
- # define a mapping of param types to edit objects ...
- class StringEntry(gtk.Entry):
- def __init__(self, default=''):
- gtk.Entry.__init__(self)
- self.set_text(str(default))
-
- def get_value(self):
- return self.get_text()
-
- class TextEntry(gtk.ScrolledWindow):
- def __init__ (self, default=''):
- gtk.ScrolledWindow.__init__(self)
- self.set_shadow_type(gtk.SHADOW_IN)
-
- self.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
- self.set_size_request(100, -1)
-
- self.view = gtk.TextView()
- self.add(self.view)
- self.view.show()
-
- self.buffer = self.view.get_buffer()
-
- self.set_value(str(default))
-
- def set_value(self, text):
- self.buffer.set_text(text)
-
- def get_value(self):
- return self.buffer.get_text(self.buffer.get_start_iter(),
- self.buffer.get_end_iter())
-
- class IntEntry(StringEntry):
- def get_value(self):
- try:
- return int(self.get_text())
- except ValueError, e:
- raise EntryValueError, e.args
-
- class FloatEntry(StringEntry):
- def get_value(self):
- try:
- return float(self.get_text())
- except ValueError, e:
- raise EntryValueError, e.args
-
-# class ArrayEntry(StringEntry):
-# def get_value(self):
-# return eval(self.get_text(), {}, {})
-
- class SliderEntry(gtk.HScale):
- # bounds is (upper, lower, step)
- def __init__(self, default=0, bounds=(0, 100, 5)):
- self.adj = gtk.Adjustment(default, bounds[0],
- bounds[1], bounds[2],
- bounds[2], 0)
- gtk.HScale.__init__(self, self.adj)
-
- def get_value(self):
- return self.adj.value
-
- class SpinnerEntry(gtk.SpinButton):
- # bounds is (upper, lower, step)
- def __init__(self, default=0, bounds=(0, 100, 5)):
- self.adj = gtk.Adjustment(default, bounds[0],
- bounds[1], bounds[2],
- bounds[2], 0)
- gtk.SpinButton.__init__(self, self.adj, 1, 0)
-
- def get_value(self):
- try:
- return int(self.get_text())
- except ValueError, e:
- raise EntryValueError, e.args
-
- class ToggleEntry(gtk.ToggleButton):
- def __init__(self, default=0):
- gtk.ToggleButton.__init__(self)
-
- self.label = gtk.Label(_("No"))
- self.add(self.label)
- self.label.show()
-
- self.connect("toggled", self.changed)
-
- self.set_active(default)
-
- def changed(self, tog):
- if tog.get_active():
- self.label.set_text(_("Yes"))
- else:
- self.label.set_text(_("No"))
-
- def get_value(self):
- return self.get_active()
-
- class RadioEntry(gtk.VBox):
- def __init__(self, default=0, items=((_("Yes"), 1), (_("No"), 0))):
- gtk.VBox.__init__(self, homogeneous=False, spacing=2)
-
- button = None
-
- for (label, value) in items:
- button = gtk.RadioButton(button, label)
- self.pack_start(button)
- button.show()
-
- button.connect("toggled", self.changed, value)
-
- if value == default:
- button.set_active(True)
- self.active_value = value
-
- def changed(self, radio, value):
- if radio.get_active():
- self.active_value = value
-
- def get_value(self):
- return self.active_value
-
- class ComboEntry(gtk.ComboBox):
- def __init__(self, default=0, items=()):
- store = gtk.ListStore(str)
- for item in items:
- store.append([item])
-
- gtk.ComboBox.__init__(self, model=store)
-
- cell = gtk.CellRendererText()
- self.pack_start(cell)
- self.set_attributes(cell, text=0)
-
- self.set_active(default)
-
- def get_value(self):
- return self.get_active()
-
- def FileSelector(default=''):
- if default and default.endswith('/'):
- selector = DirnameSelector
- if default == '/': default = ''
- else:
- selector = FilenameSelector
- return selector(default)
-
- class FilenameSelector(gtk.FileChooserButton):
- def __init__(self, default='', save_mode=False):
- gtk.FileChooserButton.__init__(self,
- _("Python-Fu File Selection"))
- self.set_action(gtk.FILE_CHOOSER_ACTION_OPEN)
- if default:
- self.set_filename(default)
-
- def get_value(self):
- return self.get_filename()
-
- class DirnameSelector(gtk.FileChooserButton):
- def __init__(self, default=''):
- gtk.FileChooserButton.__init__(self,
- _("Python-Fu Folder Selection"))
- self.set_action(gtk.FILE_CHOOSER_ACTION_SELECT_FOLDER)
- if default:
- self.set_filename(default)
-
- def get_value(self):
- return self.get_filename()
-
- _edit_mapping = {
- PF_INT8 : IntEntry,
- PF_INT16 : IntEntry,
- PF_INT32 : IntEntry,
- PF_FLOAT : FloatEntry,
- PF_STRING : StringEntry,
- #PF_INT8ARRAY : ArrayEntry,
- #PF_INT16ARRAY : ArrayEntry,
- #PF_INT32ARRAY : ArrayEntry,
- #PF_FLOATARRAY : ArrayEntry,
- #PF_STRINGARRAY : ArrayEntry,
- PF_COLOR : gimp.ui.ColorSelector,
- PF_REGION : IntEntry, # should handle differently ...
- PF_IMAGE : gimp.ui.ImageSelector,
- PF_LAYER : gimp.ui.LayerSelector,
- PF_CHANNEL : gimp.ui.ChannelSelector,
- PF_DRAWABLE : gimp.ui.DrawableSelector,
- PF_VECTORS : gimp.ui.VectorsSelector,
-
- PF_TOGGLE : ToggleEntry,
- PF_SLIDER : SliderEntry,
- PF_SPINNER : SpinnerEntry,
- PF_RADIO : RadioEntry,
- PF_OPTION : ComboEntry,
-
- PF_FONT : gimp.ui.FontSelector,
- PF_FILE : FileSelector,
- PF_FILENAME : FilenameSelector,
- PF_DIRNAME : DirnameSelector,
- PF_BRUSH : gimp.ui.BrushSelector,
- PF_PATTERN : gimp.ui.PatternSelector,
- PF_GRADIENT : gimp.ui.GradientSelector,
- PF_PALETTE : gimp.ui.PaletteSelector,
- PF_TEXT : TextEntry
- }
-
- if on_run:
- on_run()
-
- tooltips = gtk.Tooltips()
-
- dialog = gimp.ui.Dialog(proc_name, 'python-fu', None, 0, None, proc_name,
- (gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
- gtk.STOCK_OK, gtk.RESPONSE_OK))
-
- dialog.set_alternative_button_order((gtk.RESPONSE_OK, gtk.RESPONSE_CANCEL))
-
- dialog.set_transient()
-
- vbox = gtk.VBox(False, 12)
- vbox.set_border_width(12)
- dialog.vbox.pack_start(vbox)
- vbox.show()
-
- if blurb:
- if domain:
- try:
- (domain, locale_dir) = domain
- trans = gettext.translation(domain, locale_dir, fallback=True)
- except ValueError:
- trans = gettext.translation(domain, fallback=True)
- blurb = trans.ugettext(blurb)
- box = gimp.ui.HintBox(blurb)
- vbox.pack_start(box, expand=False)
- box.show()
-
- table = gtk.Table(len(params), 2, False)
- table.set_row_spacings(6)
- table.set_col_spacings(6)
- vbox.pack_start(table, expand=False)
- table.show()
-
- def response(dlg, id):
- if id == gtk.RESPONSE_OK:
- dlg.set_response_sensitive(gtk.RESPONSE_OK, False)
- dlg.set_response_sensitive(gtk.RESPONSE_CANCEL, False)
-
- params = []
-
- try:
- for wid in edit_wids:
- params.append(wid.get_value())
- except EntryValueError:
- warning_dialog(dialog, _("Invalid input for '%s'") % wid.desc)
- else:
- try:
- dialog.res = run_script(params)
- except Exception:
- dlg.set_response_sensitive(gtk.RESPONSE_CANCEL, True)
- error_dialog(dialog, proc_name)
- raise
-
- gtk.main_quit()
-
- dialog.connect("response", response)
-
- edit_wids = []
- for i in range(len(params)):
- pf_type = params[i][0]
- name = params[i][1]
- desc = params[i][2]
- def_val = defaults[i]
-
- label = gtk.Label(desc)
- label.set_use_underline(True)
- label.set_alignment(0.0, 0.5)
- table.attach(label, 1, 2, i, i+1, xoptions=gtk.FILL)
- label.show()
-
- if pf_type in (PF_SPINNER, PF_SLIDER, PF_RADIO, PF_OPTION):
- wid = _edit_mapping[pf_type](def_val, params[i][4])
- else:
- wid = _edit_mapping[pf_type](def_val)
-
- label.set_mnemonic_widget(wid)
-
- table.attach(wid, 2,3, i,i+1, yoptions=0)
-
- if pf_type != PF_TEXT:
- tooltips.set_tip(wid, desc, None)
- else:
- #Attach tip to TextView, not to ScrolledWindow
- tooltips.set_tip(wid.view, desc, None)
- wid.show()
-
- wid.desc = desc
- edit_wids.append(wid)
-
- progress_vbox = gtk.VBox(False, 6)
- vbox.pack_end(progress_vbox, expand=False)
- progress_vbox.show()
-
- progress = gimp.ui.ProgressBar()
- progress_vbox.pack_start(progress)
- progress.show()
-
-# progress_label = gtk.Label()
-# progress_label.set_alignment(0.0, 0.5)
-# progress_label.set_ellipsize(pango.ELLIPSIZE_MIDDLE)
-
-# attrs = pango.AttrList()
-# attrs.insert(pango.AttrStyle(pango.STYLE_ITALIC, 0, -1))
-# progress_label.set_attributes(attrs)
-
-# progress_vbox.pack_start(progress_label)
-# progress_label.show()
-
- tooltips.enable()
+ dialog = ScriptFuDialog(proc_name, params, defaults, domain, blurb, layout)
+ # FIXME: This is really ugly!
+ dialog.run_script = run_script
dialog.show()
-
gtk.main()
if hasattr(dialog, 'res'):
@@ -757,7 +822,7 @@
func = _registered_plugins_[proc_name][10]
if run_mode == RUN_NONINTERACTIVE:
- return apply(func, params[1:])
+ return func(params[1:])
script_params = _registered_plugins_[proc_name][8]
@@ -787,7 +852,7 @@
except CancelError:
return
else:
- res = apply(func, params[1:])
+ res = func(*params[1:])
gimp.displays_flush()
Modified: branches/soc-2008-python/plug-ins/pygimp/plug-ins/sphere.py
==============================================================================
--- branches/soc-2008-python/plug-ins/pygimp/plug-ins/sphere.py (original)
+++ branches/soc-2008-python/plug-ins/pygimp/plug-ins/sphere.py Tue Jul 29 19:33:35 2008
@@ -101,12 +101,20 @@
(PF_INT, "radius", "Radius for sphere", 100),
(PF_SLIDER, "light", "Light angle", 45, (0,360,1)),
(PF_TOGGLE, "shadow", "Shadow?", 1),
- (PF_RADIO, "foo", "Test", "foo", (("Foo", "foo"), ("Bar", "bar"))),
+ (PF_RADIO, "foo", "Test 123", "foo", (("Foo", "foo"), ("Bar", "bar"))),
(PF_COLOR, "bg-color", "Background", (1.0, 1.0, 1.0)),
(PF_COLOR, "sphere-color", "Sphere", "orange")
],
[],
sphere,
- menu="<Image>/Filters/Languages/Python-Fu/Test")
+ menu="<Image>/Filters/Languages/Python-Fu/Test",
+ layout=((LAY_FIELD, "radius"),
+ (LAY_FIELD, "light"),
+ (LAY_EXPANDER, "Test expander", ((LAY_FIELD, "shadow"),
+ (LAY_FIELD, "foo"))),
+ (LAY_GROUP, "Test group", ((LAY_FIELD, "bg-color"),
+ (LAY_FIELD, "sphere-color")))
+ )
+ )
main()
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]