diff --git a/app/dialogs/preferences-dialog.c b/app/dialogs/preferences-dialog.c index f6d69e71a9..09207ab09b 100644 --- a/app/dialogs/preferences-dialog.c +++ b/app/dialogs/preferences-dialog.c @@ -2150,8 +2150,7 @@ prefs_dialog_new (Gimp *gimp, /* Tool Editor */ vbox2 = prefs_frame_new (_("Tools Configuration"), GTK_CONTAINER (vbox), TRUE); - tool_editor = gimp_tool_editor_new (gimp->tool_info_list, gimp->user_context, - gimp_tools_get_default_order (gimp), + tool_editor = gimp_tool_editor_new (gimp->tool_item_list, gimp->user_context, GIMP_VIEW_SIZE_SMALL, 1); gtk_box_pack_start (GTK_BOX (vbox2), tool_editor, TRUE, TRUE, 0); diff --git a/app/tools/gimp-tools.c b/app/tools/gimp-tools.c index 55c0b6e30c..891ac6a5c0 100644 --- a/app/tools/gimp-tools.c +++ b/app/tools/gimp-tools.c @@ -197,9 +197,7 @@ gimp_tools_init (Gimp *gimp) gimp_operation_tool_register }; - GList *default_order = NULL; - GList *list; - gint i; + gint i; g_return_if_fail (GIMP_IS_GIMP (gimp)); @@ -217,20 +215,6 @@ gimp_tools_init (Gimp *gimp) gimp_tool_options_manager_init (gimp); tool_manager_init (gimp); - - for (list = gimp_get_tool_info_iter (gimp); - list; - list = g_list_next (list)) - { - const gchar *identifier = gimp_object_get_name (list->data); - - default_order = g_list_prepend (default_order, g_strdup (identifier)); - } - - default_order = g_list_reverse (default_order); - - g_object_set_data (G_OBJECT (gimp), - "gimp-tools-default-order", default_order); } void @@ -633,15 +617,6 @@ gimp_tools_reset (Gimp *gimp, gimp_container_thaw (container); } -GList * -gimp_tools_get_default_order (Gimp *gimp) -{ - g_return_val_if_fail (GIMP_IS_GIMP (gimp), NULL); - - return g_object_get_data (G_OBJECT (gimp), - "gimp-tools-default-order"); -} - /* private functions */ @@ -748,9 +723,6 @@ gimp_tools_register (GType tool_type, if (tool_type == GIMP_TYPE_OPERATION_TOOL) tool_info->hidden = TRUE; - g_object_set_data (G_OBJECT (tool_info), "gimp-tool-default-visible", - GINT_TO_POINTER (visible)); - g_object_set_data (G_OBJECT (tool_info), "gimp-tool-options-gui-func", options_gui_func); diff --git a/app/tools/gimp-tools.h b/app/tools/gimp-tools.h index d718b168c5..5be61c3e12 100644 --- a/app/tools/gimp-tools.h +++ b/app/tools/gimp-tools.h @@ -19,29 +19,27 @@ #define __GIMP_TOOLS_H__ -void gimp_tools_init (Gimp *gimp); -void gimp_tools_exit (Gimp *gimp); +void gimp_tools_init (Gimp *gimp); +void gimp_tools_exit (Gimp *gimp); -void gimp_tools_restore (Gimp *gimp); -void gimp_tools_save (Gimp *gimp, - gboolean save_tool_options, - gboolean always_save); +void gimp_tools_restore (Gimp *gimp); +void gimp_tools_save (Gimp *gimp, + gboolean save_tool_options, + gboolean always_save); -gboolean gimp_tools_clear (Gimp *gimp, - GError **error); +gboolean gimp_tools_clear (Gimp *gimp, + GError **error); -gboolean gimp_tools_serialize (Gimp *gimp, - GimpContainer *container, - GimpConfigWriter *writer); -gboolean gimp_tools_deserialize (Gimp *gimp, - GimpContainer *container, - GScanner *scanner); +gboolean gimp_tools_serialize (Gimp *gimp, + GimpContainer *container, + GimpConfigWriter *writer); +gboolean gimp_tools_deserialize (Gimp *gimp, + GimpContainer *container, + GScanner *scanner); -void gimp_tools_reset (Gimp *gimp, - GimpContainer *container, - gboolean user_toolrc); - -GList * gimp_tools_get_default_order (Gimp *gimp); +void gimp_tools_reset (Gimp *gimp, + GimpContainer *container, + gboolean user_toolrc); #endif /* __GIMP_TOOLS_H__ */ diff --git a/app/widgets/gimpdnd.c b/app/widgets/gimpdnd.c index 22b2051afb..7be8622130 100644 --- a/app/widgets/gimpdnd.c +++ b/app/widgets/gimpdnd.c @@ -42,7 +42,7 @@ #include "core/gimppalette.h" #include "core/gimppattern.h" #include "core/gimptemplate.h" -#include "core/gimptoolinfo.h" +#include "core/gimptoolitem.h" #include "text/gimpfont.h" @@ -98,168 +98,168 @@ struct _GimpDndDataDef }; -static GtkWidget * gimp_dnd_get_viewable_icon (GtkWidget *widget, - GdkDragContext *context, - GCallback get_viewable_func, - gpointer get_viewable_data); -static GtkWidget * gimp_dnd_get_component_icon (GtkWidget *widget, - GdkDragContext *context, - GCallback get_comp_func, - gpointer get_comp_data); -static GtkWidget * gimp_dnd_get_color_icon (GtkWidget *widget, - GdkDragContext *context, - GCallback get_color_func, - gpointer get_color_data); +static GtkWidget * gimp_dnd_get_viewable_icon (GtkWidget *widget, + GdkDragContext *context, + GCallback get_viewable_func, + gpointer get_viewable_data); +static GtkWidget * gimp_dnd_get_component_icon (GtkWidget *widget, + GdkDragContext *context, + GCallback get_comp_func, + gpointer get_comp_data); +static GtkWidget * gimp_dnd_get_color_icon (GtkWidget *widget, + GdkDragContext *context, + GCallback get_color_func, + gpointer get_color_data); -static void gimp_dnd_get_uri_list_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_uri_list_func, - gpointer get_uri_list_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_uri_list_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_uri_list_func, - gpointer set_uri_list_data, - GtkSelectionData *selection); +static void gimp_dnd_get_uri_list_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_uri_list_func, + gpointer get_uri_list_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_uri_list_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_uri_list_func, + gpointer set_uri_list_data, + GtkSelectionData *selection); -static void gimp_dnd_get_xds_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_image_func, - gpointer get_image_data, - GtkSelectionData *selection); +static void gimp_dnd_get_xds_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_image_func, + gpointer get_image_data, + GtkSelectionData *selection); -static void gimp_dnd_get_color_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_color_func, - gpointer get_color_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_color_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_color_func, - gpointer set_color_data, - GtkSelectionData *selection); +static void gimp_dnd_get_color_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_color_func, + gpointer get_color_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_color_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_color_func, + gpointer set_color_data, + GtkSelectionData *selection); -static void gimp_dnd_get_stream_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_stream_func, - gpointer get_stream_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_stream_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_stream_func, - gpointer set_stream_data, - GtkSelectionData *selection); +static void gimp_dnd_get_stream_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_stream_func, + gpointer get_stream_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_stream_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_stream_func, + gpointer set_stream_data, + GtkSelectionData *selection); -static void gimp_dnd_get_pixbuf_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_pixbuf_func, - gpointer get_pixbuf_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_pixbuf_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_pixbuf_func, - gpointer set_pixbuf_data, - GtkSelectionData *selection); -static void gimp_dnd_get_component_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_comp_func, - gpointer get_comp_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_component_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_comp_func, - gpointer set_comp_data, - GtkSelectionData *selection); +static void gimp_dnd_get_pixbuf_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_pixbuf_func, + gpointer get_pixbuf_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_pixbuf_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_pixbuf_func, + gpointer set_pixbuf_data, + GtkSelectionData *selection); +static void gimp_dnd_get_component_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_comp_func, + gpointer get_comp_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_component_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_comp_func, + gpointer set_comp_data, + GtkSelectionData *selection); -static void gimp_dnd_get_image_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_image_func, - gpointer get_image_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_image_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_image_func, - gpointer set_image_data, - GtkSelectionData *selection); +static void gimp_dnd_get_image_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_image_func, + gpointer get_image_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_image_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_image_func, + gpointer set_image_data, + GtkSelectionData *selection); -static void gimp_dnd_get_item_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_item_func, - gpointer get_item_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_item_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_item_func, - gpointer set_item_data, - GtkSelectionData *selection); +static void gimp_dnd_get_item_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_item_func, + gpointer get_item_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_item_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_item_func, + gpointer set_item_data, + GtkSelectionData *selection); -static void gimp_dnd_get_object_data (GtkWidget *widget, - GdkDragContext *context, - GCallback get_object_func, - gpointer get_object_data, - GtkSelectionData *selection); +static void gimp_dnd_get_object_data (GtkWidget *widget, + GdkDragContext *context, + GCallback get_object_func, + gpointer get_object_data, + GtkSelectionData *selection); -static gboolean gimp_dnd_set_brush_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_brush_func, - gpointer set_brush_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_pattern_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_pattern_func, - gpointer set_pattern_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_gradient_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_gradient_func, - gpointer set_gradient_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_palette_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_palette_func, - gpointer set_palette_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_font_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_font_func, - gpointer set_font_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_buffer_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_buffer_func, - gpointer set_buffer_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_imagefile_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_imagefile_func, - gpointer set_imagefile_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_template_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_template_func, - gpointer set_template_data, - GtkSelectionData *selection); -static gboolean gimp_dnd_set_tool_info_data (GtkWidget *widget, - gint x, - gint y, - GCallback set_tool_info_func, - gpointer set_tool_info_data, - GtkSelectionData *selection); +static gboolean gimp_dnd_set_brush_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_brush_func, + gpointer set_brush_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_pattern_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_pattern_func, + gpointer set_pattern_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_gradient_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_gradient_func, + gpointer set_gradient_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_palette_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_palette_func, + gpointer set_palette_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_font_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_font_func, + gpointer set_font_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_buffer_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_buffer_func, + gpointer set_buffer_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_imagefile_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_imagefile_func, + gpointer set_imagefile_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_template_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_template_func, + gpointer set_template_data, + GtkSelectionData *selection); +static gboolean gimp_dnd_set_tool_item_data (GtkWidget *widget, + gint x, + gint y, + GCallback set_tool_item_func, + gpointer set_tool_item_data, + GtkSelectionData *selection); @@ -585,17 +585,17 @@ static const GimpDndDataDef dnd_data_defs[] = }, { - GIMP_TARGET_TOOL_INFO, + GIMP_TARGET_TOOL_ITEM, - "gimp-dnd-get-tool-info-func", - "gimp-dnd-get-tool-info-data", + "gimp-dnd-get-tool-item-func", + "gimp-dnd-get-tool-item-data", - "gimp-dnd-set-tool-info-func", - "gimp-dnd-set-tool-info-data", + "gimp-dnd-set-tool-item-func", + "gimp-dnd-set-tool-item-data", gimp_dnd_get_viewable_icon, gimp_dnd_get_object_data, - gimp_dnd_set_tool_info_data + gimp_dnd_set_tool_item_data }, { @@ -1923,9 +1923,9 @@ gimp_dnd_data_type_get_by_g_type (GType type) { dnd_type = GIMP_DND_TYPE_TEMPLATE; } - else if (g_type_is_a (type, GIMP_TYPE_TOOL_INFO)) + else if (g_type_is_a (type, GIMP_TYPE_TOOL_ITEM)) { - dnd_type = GIMP_DND_TYPE_TOOL_INFO; + dnd_type = GIMP_DND_TYPE_TOOL_ITEM; } return dnd_type; @@ -2437,29 +2437,29 @@ gimp_dnd_set_template_data (GtkWidget *widget, } -/********************************/ -/* GimpToolInfo dnd functions */ -/********************************/ +/*********************************/ +/* GimpToolEntry dnd functions */ +/*********************************/ static gboolean -gimp_dnd_set_tool_info_data (GtkWidget *widget, +gimp_dnd_set_tool_item_data (GtkWidget *widget, gint x, gint y, - GCallback set_tool_info_func, - gpointer set_tool_info_data, + GCallback set_tool_item_func, + gpointer set_tool_item_data, GtkSelectionData *selection) { - GimpToolInfo *tool_info = gimp_selection_data_get_tool_info (selection, + GimpToolItem *tool_item = gimp_selection_data_get_tool_item (selection, the_dnd_gimp); - GIMP_LOG (DND, "tool_info %p", tool_info); + GIMP_LOG (DND, "tool_item %p", tool_item); - if (! tool_info) + if (! tool_item) return FALSE; - (* (GimpDndDropViewableFunc) set_tool_info_func) (widget, x, y, - GIMP_VIEWABLE (tool_info), - set_tool_info_data); + (* (GimpDndDropViewableFunc) set_tool_item_func) (widget, x, y, + GIMP_VIEWABLE (tool_item), + set_tool_item_data); return TRUE; } diff --git a/app/widgets/gimpdnd.h b/app/widgets/gimpdnd.h index 409a0ad0a4..dde5ebfb47 100644 --- a/app/widgets/gimpdnd.h +++ b/app/widgets/gimpdnd.h @@ -88,8 +88,8 @@ #define GIMP_TARGET_TEMPLATE \ { "application/x-gimp-template-name", GTK_TARGET_SAME_APP, GIMP_DND_TYPE_TEMPLATE } -#define GIMP_TARGET_TOOL_INFO \ - { "application/x-gimp-tool-info-name", GTK_TARGET_SAME_APP, GIMP_DND_TYPE_TOOL_INFO } +#define GIMP_TARGET_TOOL_ITEM \ + { "application/x-gimp-tool-item-name", GTK_TARGET_SAME_APP, GIMP_DND_TYPE_TOOL_ITEM } #define GIMP_TARGET_DIALOG \ { "application/x-gimp-dialog", GTK_TARGET_SAME_APP, GIMP_DND_TYPE_DIALOG } diff --git a/app/widgets/gimpselectiondata.c b/app/widgets/gimpselectiondata.c index 16e2e4af3d..b441cc523d 100644 --- a/app/widgets/gimpselectiondata.c +++ b/app/widgets/gimpselectiondata.c @@ -753,17 +753,29 @@ gimp_selection_data_get_template (GtkSelectionData *selection, NULL); } -GimpToolInfo * -gimp_selection_data_get_tool_info (GtkSelectionData *selection, +GimpToolItem * +gimp_selection_data_get_tool_item (GtkSelectionData *selection, Gimp *gimp) { + GimpToolItem *tool_item; + g_return_val_if_fail (GIMP_IS_GIMP (gimp), NULL); g_return_val_if_fail (selection != NULL, NULL); - return (GimpToolInfo *) + tool_item = (GimpToolItem *) gimp_selection_data_get_object (selection, gimp->tool_info_list, GIMP_OBJECT (gimp_tool_info_get_standard (gimp))); + + if (! tool_item) + { + tool_item = (GimpToolItem *) + gimp_selection_data_get_object (selection, + gimp->tool_item_list, + NULL); + } + + return tool_item; } diff --git a/app/widgets/gimpselectiondata.h b/app/widgets/gimpselectiondata.h index 25b87cb6c3..c2e9865982 100644 --- a/app/widgets/gimpselectiondata.h +++ b/app/widgets/gimpselectiondata.h @@ -105,7 +105,7 @@ GimpImagefile * gimp_selection_data_get_imagefile (GtkSelectionData *selection, Gimp *gimp); GimpTemplate * gimp_selection_data_get_template (GtkSelectionData *selection, Gimp *gimp); -GimpToolInfo * gimp_selection_data_get_tool_info (GtkSelectionData *selection, +GimpToolItem * gimp_selection_data_get_tool_item (GtkSelectionData *selection, Gimp *gimp); diff --git a/app/widgets/gimptooleditor.c b/app/widgets/gimptooleditor.c index 68ead5e716..1045599b6c 100644 --- a/app/widgets/gimptooleditor.c +++ b/app/widgets/gimptooleditor.c @@ -24,6 +24,7 @@ #include #include +#include "libgimpconfig/gimpconfig.h" #include "libgimpwidgets/gimpwidgets.h" #include "widgets-types.h" @@ -31,10 +32,14 @@ #include "core/gimp.h" #include "core/gimpcontainer.h" #include "core/gimpcontext.h" -#include "core/gimptoolinfo.h" +#include "core/gimptoolgroup.h" +#include "core/gimptreehandler.h" + +#include "tools/gimp-tools.h" #include "gimpcontainertreestore.h" #include "gimpcontainerview.h" +#include "gimpdnd.h" #include "gimpviewrenderer.h" #include "gimptooleditor.h" #include "gimphelp-ids.h" @@ -43,222 +48,169 @@ #include "gimp-intl.h" -typedef struct _GimpToolEditorPrivate GimpToolEditorPrivate; - struct _GimpToolEditorPrivate { - GtkTreeModel *model; - GimpContext *context; - GimpContainer *container; - GtkWidget *scrolled; + GimpContainer *container; + GimpContext *context; - GtkWidget *raise_button; - GtkWidget *lower_button; - GtkWidget *reset_button; + GtkWidget *scrolled; + + GtkWidget *new_group_button; + GtkWidget *raise_button; + GtkWidget *lower_button; + GtkWidget *delete_button; + GtkWidget *reset_button; + + GimpTreeHandler *visible_changed_handler; /* State of tools at creation of the editor, stored to support * reverting changes */ - gchar **initial_tool_order; - gboolean *initial_tool_visibility; - gint n_tools; - - GQuark visible_handler_id; - GList *default_tool_order; + gchar *initial_tool_state; }; -static void gimp_tool_editor_dispose (GObject *object); -static void gimp_tool_editor_finalize (GObject *object); +/* local function prototypes */ -static void gimp_tool_editor_visible_notify - (GimpToolInfo *tool_info, - GParamSpec *pspec, - GimpToolEditor *tool_editor); -static void gimp_tool_editor_eye_data_func - (GtkTreeViewColumn *tree_column, - GtkCellRenderer *cell, - GtkTreeModel *tree_model, - GtkTreeIter *iter, - gpointer data); -static void gimp_tool_editor_eye_clicked (GtkCellRendererToggle *toggle, - gchar *path_str, - GdkModifierType state, - GimpToolEditor *tool_editor); +static void gimp_tool_editor_view_iface_init (GimpContainerViewInterface *iface); -static void gimp_tool_editor_raise_clicked - (GtkButton *button, - GimpToolEditor *tool_editor); -static void gimp_tool_editor_raise_extend_clicked - (GtkButton *button, - GdkModifierType mask, - GimpToolEditor *tool_editor); -static void gimp_tool_editor_lower_clicked - (GtkButton *button, - GimpToolEditor *tool_editor); -static void gimp_tool_editor_lower_extend_clicked - (GtkButton *button, - GdkModifierType mask, - GimpToolEditor *tool_editor); -static void gimp_tool_editor_reset_clicked - (GtkButton *button, - GimpToolEditor *tool_editor); +static void gimp_tool_editor_constructed (GObject *object); + +static gboolean gimp_tool_editor_select_item (GimpContainerView *view, + GimpViewable *viewable, + gpointer insert_data); +static void gimp_tool_editor_set_container (GimpContainerView *container_view, + GimpContainer *container); +static void gimp_tool_editor_set_context (GimpContainerView *container_view, + GimpContext *context); + +static gboolean gimp_tool_editor_drop_possible (GimpContainerTreeView *tree_view, + GimpDndType src_type, + GimpViewable *src_viewable, + GimpViewable *dest_viewable, + GtkTreePath *drop_path, + GtkTreeViewDropPosition drop_pos, + GtkTreeViewDropPosition *return_drop_pos, + GdkDragAction *return_drag_action); +static void gimp_tool_editor_drop_viewable (GimpContainerTreeView *tree_view, + GimpViewable *src_viewable, + GimpViewable *dest_viewable, + GtkTreeViewDropPosition drop_pos); + +static void gimp_tool_editor_visible_changed (GimpToolItem *tool_item, + GimpToolEditor *tool_editor); + +static void gimp_tool_editor_eye_data_func (GtkTreeViewColumn *tree_column, + GtkCellRenderer *cell, + GtkTreeModel *tree_model, + GtkTreeIter *iter, + gpointer data); +static void gimp_tool_editor_eye_clicked (GtkCellRendererToggle *toggle, + gchar *path_str, + GdkModifierType state, + GimpToolEditor *tool_editor); + +static void gimp_tool_editor_new_group_clicked (GtkButton *button, + GimpToolEditor *tool_editor); +static void gimp_tool_editor_raise_clicked (GtkButton *button, + GimpToolEditor *tool_editor); +static void gimp_tool_editor_raise_extend_clicked (GtkButton *button, + GdkModifierType mask, + GimpToolEditor *tool_editor); +static void gimp_tool_editor_lower_clicked (GtkButton *button, + GimpToolEditor *tool_editor); +static void gimp_tool_editor_lower_extend_clicked (GtkButton *button, + GdkModifierType mask, + GimpToolEditor *tool_editor); +static void gimp_tool_editor_delete_clicked (GtkButton *button, + GimpToolEditor *tool_editor); +static void gimp_tool_editor_reset_clicked (GtkButton *button, + GimpToolEditor *tool_editor); + +static GimpToolItem * gimp_tool_editor_get_selected_tool_item (GimpToolEditor *tool_editor); +static GimpContainer * gimp_tool_editor_get_tool_item_container (GimpToolEditor *tool_editor, + GimpToolItem *tool_item); + +static void gimp_tool_editor_update_container (GimpToolEditor *tool_editor); +static void gimp_tool_editor_update_sensitivity (GimpToolEditor *tool_editor); -G_DEFINE_TYPE_WITH_PRIVATE (GimpToolEditor, gimp_tool_editor, - GIMP_TYPE_CONTAINER_TREE_VIEW) +G_DEFINE_TYPE_WITH_CODE (GimpToolEditor, gimp_tool_editor, + GIMP_TYPE_CONTAINER_TREE_VIEW, + G_ADD_PRIVATE (GimpToolEditor) + G_IMPLEMENT_INTERFACE (GIMP_TYPE_CONTAINER_VIEW, + gimp_tool_editor_view_iface_init)) #define parent_class gimp_tool_editor_parent_class -#define GIMP_TOOL_EDITOR_GET_PRIVATE(obj) ((GimpToolEditorPrivate *) gimp_tool_editor_get_instance_private ((GimpToolEditor *) (obj))) +static GimpContainerViewInterface *parent_view_iface = NULL; +/* private functions */ + static void gimp_tool_editor_class_init (GimpToolEditorClass *klass) { - GObjectClass *object_class = G_OBJECT_CLASS (klass); + GObjectClass *object_class = G_OBJECT_CLASS (klass); + GimpContainerTreeViewClass *tree_view_class = GIMP_CONTAINER_TREE_VIEW_CLASS (klass); - object_class->dispose = gimp_tool_editor_dispose; - object_class->finalize = gimp_tool_editor_finalize; + object_class->constructed = gimp_tool_editor_constructed; + + tree_view_class->drop_possible = gimp_tool_editor_drop_possible; + tree_view_class->drop_viewable = gimp_tool_editor_drop_viewable; +} + +static void +gimp_tool_editor_view_iface_init (GimpContainerViewInterface *iface) +{ + parent_view_iface = g_type_interface_peek_parent (iface); + + if (! parent_view_iface) + parent_view_iface = g_type_default_interface_peek (GIMP_TYPE_CONTAINER_VIEW); + + iface->select_item = gimp_tool_editor_select_item; + iface->set_container = gimp_tool_editor_set_container; + iface->set_context = gimp_tool_editor_set_context; } static void gimp_tool_editor_init (GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - - priv->model = NULL; - priv->context = NULL; - priv->container = NULL; - priv->scrolled = NULL; - - priv->visible_handler_id = 0; - priv->default_tool_order = NULL; - - priv->initial_tool_order = NULL; - priv->initial_tool_visibility = NULL; - priv->n_tools = 0; - - priv->raise_button = NULL; - priv->lower_button = NULL; - priv->reset_button = NULL; + tool_editor->priv = gimp_tool_editor_get_instance_private (tool_editor); } static void -gimp_tool_editor_dispose (GObject *object) +gimp_tool_editor_constructed (GObject *object) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (object); + GimpToolEditor *tool_editor = GIMP_TOOL_EDITOR (object); + GimpContainerTreeView *tree_view = GIMP_CONTAINER_TREE_VIEW (object); + GimpContainerView *container_view = GIMP_CONTAINER_VIEW (object); + gint view_size; + gint border_width; - if (priv->visible_handler_id) - { - gimp_container_remove_handler (priv->container, - priv->visible_handler_id); - priv->visible_handler_id = 0; - } + G_OBJECT_CLASS (parent_class)->constructed (object); - priv->context = NULL; - priv->container = NULL; + view_size = gimp_container_view_get_view_size (container_view, + &border_width); - priv->raise_button = NULL; - priv->lower_button = NULL; - priv->reset_button = NULL; + gimp_editor_set_show_name (GIMP_EDITOR (tool_editor), FALSE); - priv->scrolled = NULL; + gtk_tree_view_set_level_indentation (tree_view->view, + 0.8 * (view_size + 2 * border_width)); - G_OBJECT_CLASS (parent_class)->dispose (object); -} + gimp_dnd_viewable_dest_add (GTK_WIDGET (tree_view->view), + GIMP_TYPE_TOOL_ITEM, + NULL, NULL); -static void -gimp_tool_editor_finalize (GObject *object) -{ - GimpToolEditor *tool_editor; - GimpToolEditorPrivate *priv; - - tool_editor = GIMP_TOOL_EDITOR (object); - priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - - if (priv->initial_tool_order) - { - int i; - - for (i = 0; i < priv->n_tools; i++) - { - g_free (priv->initial_tool_order[i]); - } - - g_clear_pointer (&priv->initial_tool_order, g_free); - } - - if (priv->initial_tool_visibility) - { - g_slice_free1 (sizeof (gboolean) * priv->n_tools, - priv->initial_tool_visibility); - - priv->initial_tool_visibility = NULL; - } - - G_OBJECT_CLASS (parent_class)->finalize (object); -} - -GtkWidget * -gimp_tool_editor_new (GimpContainer *container, - GimpContext *context, - GList *default_tool_order, - gint view_size, - gint view_border_width) -{ - int i; - GimpToolEditor *tool_editor; - GimpContainerTreeView *tree_view; - GimpContainerView *container_view; - GObject *object; - GimpObject *gimp_object; - GimpToolEditorPrivate *priv; - - g_return_val_if_fail (GIMP_IS_CONTAINER (container), NULL); - g_return_val_if_fail (GIMP_IS_CONTEXT (context), NULL); - - object = g_object_new (GIMP_TYPE_TOOL_EDITOR, NULL); - tool_editor = GIMP_TOOL_EDITOR (object); - tree_view = GIMP_CONTAINER_TREE_VIEW (object); - container_view = GIMP_CONTAINER_VIEW (object); - priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - - priv->container = container; - priv->context = context; - priv->model = tree_view->model; - priv->default_tool_order = default_tool_order; - priv->initial_tool_order = gimp_container_get_name_array (container, - &priv->n_tools); - priv->initial_tool_visibility = g_slice_alloc (sizeof (gboolean) * - priv->n_tools); - for (i = 0; i < priv->n_tools; i++) - { - gimp_object = gimp_container_get_child_by_index (container, i); - - g_object_get (gimp_object, - "visible", &(priv->initial_tool_visibility[i]), NULL); - } - - gimp_container_view_set_view_size (container_view, - view_size, view_border_width); - gimp_container_view_set_container (container_view, priv->container); - gimp_container_view_set_context (container_view, context); - gimp_container_view_set_reorderable (container_view, TRUE); - gimp_editor_set_show_name (GIMP_EDITOR (tree_view), FALSE); - - /* Construct tree view */ + /* construct tree view */ { - GimpContainerTreeView *tree_view = GIMP_CONTAINER_TREE_VIEW (tool_editor); - GtkWidget *tree_widget = GTK_WIDGET (tree_view); - GtkStyle *tree_style = gtk_widget_get_style (tree_widget); - GtkTreeViewColumn *column; - GtkCellRenderer *eye_cell; - GtkIconSize icon_size; + GtkTreeViewColumn *column; + GtkCellRenderer *eye_cell; + GtkStyle *tree_style; + GtkIconSize icon_size; + + tree_style = gtk_widget_get_style (GTK_WIDGET (tool_editor)); - column = gtk_tree_view_column_new (); - gtk_tree_view_insert_column (tree_view->view, column, 0); - eye_cell = gimp_cell_renderer_toggle_new (GIMP_ICON_VISIBLE); icon_size = gimp_get_icon_size (GTK_WIDGET (tool_editor), GIMP_ICON_VISIBLE, GTK_ICON_SIZE_BUTTON, @@ -267,6 +219,10 @@ gimp_tool_editor_new (GimpContainer *container, view_size - 2 * tree_style->ythickness); + column = gtk_tree_view_column_new (); + gtk_tree_view_insert_column (tree_view->view, column, 0); + + eye_cell = gimp_cell_renderer_toggle_new (GIMP_ICON_VISIBLE); g_object_set (eye_cell, "stock-size", icon_size, NULL); gtk_tree_view_column_pack_start (column, eye_cell, FALSE); gtk_tree_view_column_set_cell_data_func (column, eye_cell, @@ -278,83 +234,195 @@ gimp_tool_editor_new (GimpContainer *container, g_signal_connect (eye_cell, "clicked", G_CALLBACK (gimp_tool_editor_eye_clicked), tool_editor); - - priv->visible_handler_id = - gimp_container_add_handler (container, "notify::visible", - G_CALLBACK (gimp_tool_editor_visible_notify), - tool_editor); } /* buttons */ - priv->raise_button = - gimp_editor_add_button (GIMP_EDITOR (tree_view), GIMP_ICON_GO_UP, + tool_editor->priv->new_group_button = + gimp_editor_add_button (GIMP_EDITOR (tool_editor), GIMP_ICON_FOLDER_NEW, + _("Create a new tool group"), NULL, + G_CALLBACK (gimp_tool_editor_new_group_clicked), + NULL, + tool_editor); + + tool_editor->priv->raise_button = + gimp_editor_add_button (GIMP_EDITOR (tool_editor), GIMP_ICON_GO_UP, _("Raise this tool"), _("Raise this tool to the top"), G_CALLBACK (gimp_tool_editor_raise_clicked), G_CALLBACK (gimp_tool_editor_raise_extend_clicked), tool_editor); - priv->lower_button = - gimp_editor_add_button (GIMP_EDITOR (tree_view), GIMP_ICON_GO_DOWN, + tool_editor->priv->lower_button = + gimp_editor_add_button (GIMP_EDITOR (tool_editor), GIMP_ICON_GO_DOWN, _("Lower this tool"), _("Lower this tool to the bottom"), G_CALLBACK (gimp_tool_editor_lower_clicked), G_CALLBACK (gimp_tool_editor_lower_extend_clicked), tool_editor); - priv->reset_button = - gimp_editor_add_button (GIMP_EDITOR (tree_view), GIMP_ICON_RESET, - _("Reset tool order and visibility"), NULL, - G_CALLBACK (gimp_tool_editor_reset_clicked), NULL, + tool_editor->priv->delete_button = + gimp_editor_add_button (GIMP_EDITOR (tool_editor), GIMP_ICON_EDIT_DELETE, + _("Delete this tool"), NULL, + G_CALLBACK (gimp_tool_editor_delete_clicked), + NULL, tool_editor); - return GTK_WIDGET (tool_editor); + tool_editor->priv->reset_button = + gimp_editor_add_button (GIMP_EDITOR (tool_editor), GIMP_ICON_RESET, + _("Reset tool order and visibility"), NULL, + G_CALLBACK (gimp_tool_editor_reset_clicked), + NULL, + tool_editor); + + gimp_tool_editor_update_sensitivity (tool_editor); } -/** - * gimp_tool_editor_revert_changes: - * @tool_editor: - * - * Reverts the tool order and visibility to the state at creation. - **/ -void -gimp_tool_editor_revert_changes (GimpToolEditor *tool_editor) +static gboolean +gimp_tool_editor_select_item (GimpContainerView *container_view, + GimpViewable *viewable, + gpointer insert_data) { - int i; - GimpToolEditorPrivate *priv; + GimpToolEditor *tool_editor = GIMP_TOOL_EDITOR (container_view); + gboolean result; - priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); + result = parent_view_iface->select_item (container_view, + viewable, insert_data); - for (i = 0; i < priv->n_tools; i++) + gimp_tool_editor_update_sensitivity (tool_editor); + + return result; +} + +static void +gimp_tool_editor_set_container (GimpContainerView *container_view, + GimpContainer *container) +{ + GimpToolEditor *tool_editor = GIMP_TOOL_EDITOR (container_view); + + parent_view_iface->set_container (container_view, container); + + gimp_tool_editor_update_container (tool_editor); +} + +static void +gimp_tool_editor_set_context (GimpContainerView *container_view, + GimpContext *context) +{ + GimpToolEditor *tool_editor = GIMP_TOOL_EDITOR (container_view); + + parent_view_iface->set_context (container_view, context); + + gimp_tool_editor_update_container (tool_editor); +} + +static gboolean +gimp_tool_editor_drop_possible (GimpContainerTreeView *tree_view, + GimpDndType src_type, + GimpViewable *src_viewable, + GimpViewable *dest_viewable, + GtkTreePath *drop_path, + GtkTreeViewDropPosition drop_pos, + GtkTreeViewDropPosition *return_drop_pos, + GdkDragAction *return_drag_action) +{ + if (GIMP_CONTAINER_TREE_VIEW_CLASS (parent_class)->drop_possible ( + tree_view, + src_type, src_viewable, dest_viewable, drop_path, drop_pos, + return_drop_pos, return_drag_action)) { - GimpObject *object; + if (gimp_viewable_get_parent (dest_viewable) || + (gimp_viewable_get_children (dest_viewable) && + (drop_pos == GTK_TREE_VIEW_DROP_INTO_OR_AFTER || + drop_pos == GTK_TREE_VIEW_DROP_INTO_OR_BEFORE))) + { + return ! gimp_viewable_get_children (src_viewable); + } - object = gimp_container_get_child_by_name (priv->container, - priv->initial_tool_order[i]); + return TRUE; + } - gimp_container_reorder (priv->container, object, i); - g_object_set (object, "visible", priv->initial_tool_visibility[i], NULL); + return FALSE; +} + +static void +gimp_tool_editor_drop_viewable (GimpContainerTreeView *tree_view, + GimpViewable *src_viewable, + GimpViewable *dest_viewable, + GtkTreeViewDropPosition drop_pos) +{ + GimpContainerView *container_view = GIMP_CONTAINER_VIEW (tree_view); + + GIMP_CONTAINER_TREE_VIEW_CLASS (parent_class)->drop_viewable (tree_view, + src_viewable, + dest_viewable, + drop_pos); + + gimp_container_view_select_item (container_view, src_viewable); +} + +static void +gimp_tool_editor_new_group_clicked (GtkButton *button, + GimpToolEditor *tool_editor) +{ + GimpContainerView *container_view = GIMP_CONTAINER_VIEW (tool_editor); + GimpContainer *container; + GimpToolItem *tool_item; + GimpToolGroup *group; + gint index = 0; + + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); + + if (tool_item) + { + if (gimp_viewable_get_parent (GIMP_VIEWABLE (tool_item)) != NULL) + return; + + container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + index = gimp_container_get_child_index (container, + GIMP_OBJECT (tool_item)); + } + else + { + container = tool_editor->priv->container; + } + + if (container) + { + group = gimp_tool_group_new (); + + gimp_container_insert (container, GIMP_OBJECT (group), index); + + g_object_unref (group); + + gimp_container_view_select_item (container_view, GIMP_VIEWABLE (group)); } } static void -gimp_tool_editor_raise_clicked (GtkButton *button, +gimp_tool_editor_raise_clicked (GtkButton *button, GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - GimpToolInfo *tool_info; + GimpToolItem *tool_item; - tool_info = gimp_context_get_tool (priv->context); + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); - if (tool_info) + if (tool_item) { - gint index = gimp_container_get_child_index (priv->container, - GIMP_OBJECT (tool_info)); + GimpContainer *container; + gint index; + + container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + index = gimp_container_get_child_index (container, + GIMP_OBJECT (tool_item)); if (index > 0) { - gimp_container_reorder (priv->container, - GIMP_OBJECT (tool_info), index - 1); + gimp_container_reorder (container, + GIMP_OBJECT (tool_item), index - 1); } } } @@ -362,44 +430,54 @@ gimp_tool_editor_raise_clicked (GtkButton *button, static void gimp_tool_editor_raise_extend_clicked (GtkButton *button, GdkModifierType mask, - GimpToolEditor *tool_editor) + GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - GimpToolInfo *tool_info; + GimpToolItem *tool_item; - tool_info = gimp_context_get_tool (priv->context); + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); - if (tool_info && (mask & GDK_SHIFT_MASK)) + if (tool_item && (mask & GDK_SHIFT_MASK)) { - gint index = gimp_container_get_child_index (priv->container, - GIMP_OBJECT (tool_info)); + GimpContainer *container; + gint index; + + container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + index = gimp_container_get_child_index (container, + GIMP_OBJECT (tool_item)); if (index > 0) { - gimp_container_reorder (priv->container, - GIMP_OBJECT (tool_info), 0); + gimp_container_reorder (container, + GIMP_OBJECT (tool_item), 0); } } } static void -gimp_tool_editor_lower_clicked (GtkButton *button, +gimp_tool_editor_lower_clicked (GtkButton *button, GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - GimpToolInfo *tool_info; + GimpToolItem *tool_item; - tool_info = gimp_context_get_tool (priv->context); + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); - if (tool_info) + if (tool_item) { - gint index = gimp_container_get_child_index (priv->container, - GIMP_OBJECT (tool_info)); + GimpContainer *container; + gint index; - if (index + 1 < gimp_container_get_n_children (priv->container)) + container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + index = gimp_container_get_child_index (container, + GIMP_OBJECT (tool_item)); + + if (index + 1 < gimp_container_get_n_children (container)) { - gimp_container_reorder (priv->container, - GIMP_OBJECT (tool_info), index + 1); + gimp_container_reorder (container, + GIMP_OBJECT (tool_item), index + 1); } } } @@ -407,74 +485,125 @@ gimp_tool_editor_lower_clicked (GtkButton *button, static void gimp_tool_editor_lower_extend_clicked (GtkButton *button, GdkModifierType mask, - GimpToolEditor *tool_editor) + GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - GimpToolInfo *tool_info; + GimpToolItem *tool_item; - tool_info = gimp_context_get_tool (priv->context); + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); - if (tool_info && (mask & GDK_SHIFT_MASK)) + if (tool_item && (mask & GDK_SHIFT_MASK)) { - gint index = gimp_container_get_n_children (priv->container) - 1; + GimpContainer *container; + gint index; + container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + index = gimp_container_get_n_children (container) - 1; index = MAX (index, 0); - gimp_container_reorder (priv->container, - GIMP_OBJECT (tool_info), index); + gimp_container_reorder (container, + GIMP_OBJECT (tool_item), index); } } static void -gimp_tool_editor_reset_clicked (GtkButton *button, +gimp_tool_editor_delete_clicked (GtkButton *button, + GimpToolEditor *tool_editor) +{ + GimpContainerView *container_view = GIMP_CONTAINER_VIEW (tool_editor); + GimpToolItem *tool_item; + + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); + + if (tool_item) + { + GimpContainer *src_container; + GimpContainer *dest_container; + gint index; + gint dest_index; + + src_container = gimp_viewable_get_children (GIMP_VIEWABLE (tool_item)); + dest_container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + if (! src_container) + return; + + index = gimp_container_get_child_index (dest_container, + GIMP_OBJECT (tool_item)); + dest_index = index; + + g_object_ref (tool_item); + + gimp_container_freeze (src_container); + gimp_container_freeze (dest_container); + + gimp_container_remove (dest_container, GIMP_OBJECT (tool_item)); + + while (! gimp_container_is_empty (src_container)) + { + GimpObject *object = gimp_container_get_first_child (src_container); + + g_object_ref (object); + + gimp_container_remove (src_container, object); + gimp_container_insert (dest_container, object, dest_index++); + + g_object_unref (object); + } + + gimp_container_thaw (dest_container); + gimp_container_thaw (src_container); + + gimp_container_view_select_item ( + container_view, + GIMP_VIEWABLE (gimp_container_get_child_by_index (dest_container, + index))); + + g_object_unref (tool_item); + } +} + +static void +gimp_tool_editor_reset_clicked (GtkButton *button, GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); - GList *list; - gint i; - - for (list = priv->default_tool_order, i = 0; - list; - list = g_list_next (list), i++) - { - GimpObject *object = - gimp_container_get_child_by_name (priv->container, list->data); - - if (object) - { - gboolean visible; - gpointer data; - - gimp_container_reorder (priv->container, object, i); - data = g_object_get_data (G_OBJECT (object), - "gimp-tool-default-visible"); - - visible = GPOINTER_TO_INT (data); - g_object_set (object, "visible", visible, NULL); - } - } + gimp_tools_reset (tool_editor->priv->context->gimp, + tool_editor->priv->container, + FALSE); } static void -gimp_tool_editor_visible_notify (GimpToolInfo *tool_info, - GParamSpec *pspec, - GimpToolEditor *tool_editor) +gimp_tool_editor_visible_changed (GimpToolItem *tool_item, + GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); + GimpContainerTreeView *tree_view = GIMP_CONTAINER_TREE_VIEW (tool_editor); + GimpContainerView *container_view = GIMP_CONTAINER_VIEW (tool_editor); GtkTreeIter *iter; - iter = gimp_container_view_lookup (GIMP_CONTAINER_VIEW (tool_editor), - GIMP_VIEWABLE (tool_info)); + iter = gimp_container_view_lookup (container_view, + GIMP_VIEWABLE (tool_item)); if (iter) { - GtkTreePath *path; + GtkTreePath *path; + GimpContainer *children; - path = gtk_tree_model_get_path (priv->model, iter); + path = gtk_tree_model_get_path (tree_view->model, iter); - gtk_tree_model_row_changed (priv->model, path, iter); + gtk_tree_model_row_changed (tree_view->model, path, iter); gtk_tree_path_free (path); + + children = gimp_viewable_get_children (GIMP_VIEWABLE (tool_item)); + + if (children) + { + gimp_container_foreach (children, + (GFunc) gimp_tool_editor_visible_changed, + tool_editor); + } } } @@ -486,17 +615,21 @@ gimp_tool_editor_eye_data_func (GtkTreeViewColumn *tree_column, gpointer data) { GimpViewRenderer *renderer; - gboolean visible; + GimpToolItem *tool_item; gtk_tree_model_get (tree_model, iter, GIMP_CONTAINER_TREE_STORE_COLUMN_RENDERER, &renderer, -1); - g_object_get (renderer->viewable, "visible", &visible, NULL); + tool_item = GIMP_TOOL_ITEM (renderer->viewable); + + g_object_set (cell, + "active", gimp_tool_item_get_visible (tool_item), + "inconsistent", gimp_tool_item_get_visible (tool_item) && + ! gimp_tool_item_is_visible (tool_item), + NULL); g_object_unref (renderer); - - g_object_set (cell, "active", visible, NULL); } static void @@ -505,28 +638,215 @@ gimp_tool_editor_eye_clicked (GtkCellRendererToggle *toggle, GdkModifierType state, GimpToolEditor *tool_editor) { - GimpToolEditorPrivate *priv = GIMP_TOOL_EDITOR_GET_PRIVATE (tool_editor); + GimpContainerTreeView *tree_view = GIMP_CONTAINER_TREE_VIEW (tool_editor); GtkTreePath *path; GtkTreeIter iter; path = gtk_tree_path_new_from_string (path_str); - if (gtk_tree_model_get_iter (priv->model, &iter, path)) + if (gtk_tree_model_get_iter (tree_view->model, &iter, path)) { GimpViewRenderer *renderer; + GimpToolItem *tool_item; gboolean active; + gtk_tree_model_get (tree_view->model, &iter, + GIMP_CONTAINER_TREE_STORE_COLUMN_RENDERER, &renderer, + -1); + + tool_item = GIMP_TOOL_ITEM (renderer->viewable); + g_object_get (toggle, "active", &active, NULL); - gtk_tree_model_get (priv->model, &iter, - GIMP_CONTAINER_TREE_STORE_COLUMN_RENDERER, &renderer, - -1); - g_object_set (renderer->viewable, "visible", ! active, NULL); + gimp_tool_item_set_visible (tool_item, ! active); g_object_unref (renderer); } gtk_tree_path_free (path); } + +static GimpToolItem * +gimp_tool_editor_get_selected_tool_item (GimpToolEditor *tool_editor) +{ + GimpContainerTreeView *tree_view = GIMP_CONTAINER_TREE_VIEW (tool_editor); + + if (tool_editor->priv->container) + { + GimpViewRenderer *renderer; + GimpToolItem *tool_item; + GtkTreeSelection *selection; + GtkTreeModel *model; + GtkTreeIter iter; + + selection = gtk_tree_view_get_selection (tree_view->view); + + if (! gtk_tree_selection_get_selected (selection, &model, &iter)) + return NULL; + + gtk_tree_model_get (model, &iter, + GIMP_CONTAINER_TREE_STORE_COLUMN_RENDERER, &renderer, + -1); + + tool_item = GIMP_TOOL_ITEM (renderer->viewable); + + g_object_unref (renderer); + + return tool_item; + } + + return NULL; +} + +static GimpContainer * +gimp_tool_editor_get_tool_item_container (GimpToolEditor *tool_editor, + GimpToolItem *tool_item) +{ + GimpViewable *parent; + + parent = gimp_viewable_get_parent (GIMP_VIEWABLE (tool_item)); + + if (parent) + { + return gimp_viewable_get_children (parent); + } + else + { + return tool_editor->priv->container; + } +} + +static void +gimp_tool_editor_update_container (GimpToolEditor *tool_editor) +{ + GimpContainerView *container_view = GIMP_CONTAINER_VIEW (tool_editor); + GimpContainer *container; + GimpContext *context; + + g_clear_pointer (&tool_editor->priv->visible_changed_handler, + gimp_tree_handler_disconnect); + + g_clear_pointer (&tool_editor->priv->initial_tool_state, g_free); + + container = gimp_container_view_get_container (container_view); + context = gimp_container_view_get_context (container_view); + + if (container && context) + { + GString *string; + GimpConfigWriter *writer; + + tool_editor->priv->container = container; + tool_editor->priv->context = context; + + tool_editor->priv->visible_changed_handler = gimp_tree_handler_connect ( + container, "visible-changed", + G_CALLBACK (gimp_tool_editor_visible_changed), + tool_editor); + + /* save initial tool order */ + string = g_string_new (NULL); + + writer = gimp_config_writer_new_string (string); + + gimp_tools_serialize (context->gimp, container, writer); + + gimp_config_writer_finish (writer, NULL, NULL); + + tool_editor->priv->initial_tool_state = g_string_free (string, FALSE); + } +} + +static void +gimp_tool_editor_update_sensitivity (GimpToolEditor *tool_editor) +{ + GimpToolItem *tool_item; + + tool_item = gimp_tool_editor_get_selected_tool_item (tool_editor); + + if (tool_item) + { + GimpContainer *container; + gint index; + + container = gimp_tool_editor_get_tool_item_container (tool_editor, + tool_item); + + index = gimp_container_get_child_index (container, + GIMP_OBJECT (tool_item)); + + gtk_widget_set_sensitive ( + tool_editor->priv->new_group_button, + gimp_viewable_get_parent (GIMP_VIEWABLE (tool_item)) == NULL); + + gtk_widget_set_sensitive ( + tool_editor->priv->raise_button, + index > 0); + + gtk_widget_set_sensitive ( + tool_editor->priv->lower_button, + index < gimp_container_get_n_children (container) - 1); + + gtk_widget_set_sensitive ( + tool_editor->priv->delete_button, + gimp_viewable_get_children (GIMP_VIEWABLE (tool_item)) != NULL); + } + else + { + gtk_widget_set_sensitive (tool_editor->priv->new_group_button, TRUE); + gtk_widget_set_sensitive (tool_editor->priv->raise_button, FALSE); + gtk_widget_set_sensitive (tool_editor->priv->lower_button, FALSE); + gtk_widget_set_sensitive (tool_editor->priv->delete_button, FALSE); + } +} + + +/* public functions */ + +GtkWidget * +gimp_tool_editor_new (GimpContainer *container, + GimpContext *context, + gint view_size, + gint view_border_width) +{ + GimpContainerView *container_view; + + g_return_val_if_fail (GIMP_IS_CONTAINER (container), NULL); + g_return_val_if_fail (GIMP_IS_CONTEXT (context), NULL); + + container_view = g_object_new (GIMP_TYPE_TOOL_EDITOR, + "view-size", view_size, + "view-border-width", view_border_width, + NULL); + + gimp_container_view_set_context (container_view, context); + gimp_container_view_set_container (container_view, container); + gimp_container_view_set_reorderable (container_view, TRUE); + + return GTK_WIDGET (container_view); +} + +/** + * gimp_tool_editor_revert_changes: + * @tool_editor: + * + * Reverts the tool order and visibility to the state at creation. + **/ +void +gimp_tool_editor_revert_changes (GimpToolEditor *tool_editor) +{ + GScanner *scanner; + + g_return_if_fail (GIMP_IS_TOOL_EDITOR (tool_editor)); + + scanner = gimp_scanner_new_string (tool_editor->priv->initial_tool_state, -1, + NULL); + + gimp_tools_deserialize (tool_editor->priv->context->gimp, + tool_editor->priv->container, + scanner); + + gimp_scanner_destroy (scanner); +} diff --git a/app/widgets/gimptooleditor.h b/app/widgets/gimptooleditor.h index 33e7f570fa..ac34b92c12 100644 --- a/app/widgets/gimptooleditor.h +++ b/app/widgets/gimptooleditor.h @@ -34,16 +34,19 @@ #define GIMP_TOOL_EDITOR_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GIMP_TYPE_TOOL_EDITOR, GimpToolEditorClass)) -typedef struct _GimpToolEditorClass GimpToolEditorClass; +typedef struct _GimpToolEditorPrivate GimpToolEditorPrivate; +typedef struct _GimpToolEditorClass GimpToolEditorClass; struct _GimpToolEditor { - GimpContainerTreeView parent_instance; + GimpContainerTreeView parent_instance; + + GimpToolEditorPrivate *priv; }; struct _GimpToolEditorClass { - GimpContainerTreeViewClass parent_class; + GimpContainerTreeViewClass parent_class; }; @@ -51,7 +54,6 @@ GType gimp_tool_editor_get_type (void) G_GNUC_CONST; GtkWidget * gimp_tool_editor_new (GimpContainer *container, GimpContext *context, - GList *default_tool_order, gint view_size, gint view_border_width); diff --git a/app/widgets/widgets-enums.h b/app/widgets/widgets-enums.h index 59b7ed4928..9a09222290 100644 --- a/app/widgets/widgets-enums.h +++ b/app/widgets/widgets-enums.h @@ -166,7 +166,7 @@ typedef enum /*< skip >*/ GIMP_DND_TYPE_BUFFER = 20, GIMP_DND_TYPE_IMAGEFILE = 21, GIMP_DND_TYPE_TEMPLATE = 22, - GIMP_DND_TYPE_TOOL_INFO = 23, + GIMP_DND_TYPE_TOOL_ITEM = 23, GIMP_DND_TYPE_DIALOG = 24, GIMP_DND_TYPE_LAST = GIMP_DND_TYPE_DIALOG