[gimp] app: add GimpToolGroup as a subclass of GimpToolItem
- From: Ell <ell src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gimp] app: add GimpToolGroup as a subclass of GimpToolItem
- Date: Thu, 30 Jan 2020 00:57:17 +0000 (UTC)
commit 49196140e2a9ec4fbde82c770cd2afd49b7973b4
Author: Ell <ell_se yahoo com>
Date: Wed Jan 29 19:55:49 2020 +0200
app: add GimpToolGroup as a subclass of GimpToolItem
Add GimpToolGroup as a new subclass of GimpToolItem, representing a
collection of tools. The end goal is to display tool groups using
a single button in the toolbox.
Tool groups are not recursive: they can only contain individual
tools, not other groups. Each group has a single "active tool",
normally the most-recently-used tool of the group, which is
activated when clicking on the tool's button.
app/core/Makefile.am | 2 +
app/core/core-types.h | 1 +
app/core/gimptoolgroup.c | 385 +++++++++++++++++++++++++++++++++++++++++++++++
app/core/gimptoolgroup.h | 68 +++++++++
app/core/meson.build | 1 +
po/POTFILES.in | 1 +
6 files changed, 458 insertions(+)
---
diff --git a/app/core/Makefile.am b/app/core/Makefile.am
index cc09265741..90188d7249 100644
--- a/app/core/Makefile.am
+++ b/app/core/Makefile.am
@@ -467,6 +467,8 @@ libappcore_a_sources = \
gimptemplate.h \
gimptilehandlerprojectable.c \
gimptilehandlerprojectable.h \
+ gimptoolgroup.c \
+ gimptoolgroup.h \
gimptoolinfo.c \
gimptoolinfo.h \
gimptoolitem.c \
diff --git a/app/core/core-types.h b/app/core/core-types.h
index 12bfd7361c..f99f1d1ecd 100644
--- a/app/core/core-types.h
+++ b/app/core/core-types.h
@@ -128,6 +128,7 @@ typedef struct _GimpToolOptions GimpToolOptions;
/* info objects */
typedef struct _GimpPaintInfo GimpPaintInfo;
+typedef struct _GimpToolGroup GimpToolGroup;
typedef struct _GimpToolInfo GimpToolInfo;
typedef struct _GimpToolItem GimpToolItem;
diff --git a/app/core/gimptoolgroup.c b/app/core/gimptoolgroup.c
new file mode 100644
index 0000000000..b9a412ee68
--- /dev/null
+++ b/app/core/gimptoolgroup.c
@@ -0,0 +1,385 @@
+/* GIMP - The GNU Image Manipulation Program
+ * Copyright (C) 1995 Spencer Kimball and Peter Mattis
+ *
+ * gimptoolgroup.c
+ * Copyright (C) 2020 Ell
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+#include "config.h"
+
+#include <string.h>
+
+#include <gdk-pixbuf/gdk-pixbuf.h>
+#include <gegl.h>
+
+#include "libgimpbase/gimpbase.h"
+#include "libgimpconfig/gimpconfig.h"
+
+#include "core-types.h"
+
+#include "gimplist.h"
+#include "gimpmarshal.h"
+#include "gimptoolgroup.h"
+#include "gimptoolinfo.h"
+
+#include "gimp-intl.h"
+
+
+enum
+{
+ ACTIVE_TOOL_CHANGED,
+ LAST_SIGNAL
+};
+
+enum
+{
+ PROP_0,
+ PROP_ACTIVE_TOOL,
+ PROP_CHILDREN
+};
+
+
+struct _GimpToolGroupPrivate
+{
+ gchar *active_tool;
+ GimpContainer *children;
+};
+
+
+/* local function prototypes */
+
+
+static void gimp_tool_group_finalize (GObject *object);
+static void gimp_tool_group_get_property (GObject *object,
+ guint property_id,
+ GValue *value,
+ GParamSpec *pspec);
+static void gimp_tool_group_set_property (GObject *object,
+ guint property_id,
+ const GValue *value,
+ GParamSpec *pspec);
+
+static gint64 gimp_tool_group_get_memsize (GimpObject *object,
+ gint64 *gui_size);
+
+static gchar * gimp_tool_group_get_description (GimpViewable *viewable,
+ gchar **tooltip);
+static GimpContainer * gimp_tool_group_get_children (GimpViewable *viewable);
+static void gimp_tool_group_set_expanded (GimpViewable *viewable,
+ gboolean expand);
+static gboolean gimp_tool_group_get_expanded (GimpViewable *viewable);
+
+static void gimp_tool_group_child_add (GimpContainer *container,
+ GimpToolInfo *tool_info,
+ GimpToolGroup *tool_group);
+static void gimp_tool_group_child_remove (GimpContainer *container,
+ GimpToolInfo *tool_info,
+ GimpToolGroup *tool_group);
+
+
+G_DEFINE_TYPE_WITH_PRIVATE (GimpToolGroup, gimp_tool_group, GIMP_TYPE_TOOL_ITEM)
+
+#define parent_class gimp_tool_group_parent_class
+
+static guint gimp_tool_group_signals[LAST_SIGNAL] = { 0 };
+
+
+/* private functions */
+
+static void
+gimp_tool_group_class_init (GimpToolGroupClass *klass)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (klass);
+ GimpObjectClass *gimp_object_class = GIMP_OBJECT_CLASS (klass);
+ GimpViewableClass *viewable_class = GIMP_VIEWABLE_CLASS (klass);
+
+ gimp_tool_group_signals[ACTIVE_TOOL_CHANGED] =
+ g_signal_new ("active-tool-changed",
+ G_TYPE_FROM_CLASS (klass),
+ G_SIGNAL_RUN_FIRST,
+ G_STRUCT_OFFSET (GimpToolGroupClass, active_tool_changed),
+ NULL, NULL,
+ gimp_marshal_VOID__VOID,
+ G_TYPE_NONE, 0);
+
+ object_class->finalize = gimp_tool_group_finalize;
+ object_class->get_property = gimp_tool_group_get_property;
+ object_class->set_property = gimp_tool_group_set_property;
+
+ gimp_object_class->get_memsize = gimp_tool_group_get_memsize;
+
+ viewable_class->default_icon_name = "folder";
+ viewable_class->get_description = gimp_tool_group_get_description;
+ viewable_class->get_children = gimp_tool_group_get_children;
+ viewable_class->get_expanded = gimp_tool_group_get_expanded;
+ viewable_class->set_expanded = gimp_tool_group_set_expanded;
+
+ GIMP_CONFIG_PROP_STRING (object_class, PROP_ACTIVE_TOOL,
+ "active-tool", NULL, NULL,
+ NULL,
+ GIMP_PARAM_STATIC_STRINGS);
+
+ GIMP_CONFIG_PROP_OBJECT (object_class, PROP_CHILDREN,
+ "children", NULL, NULL,
+ GIMP_TYPE_CONTAINER,
+ GIMP_PARAM_STATIC_STRINGS |
+ GIMP_CONFIG_PARAM_AGGREGATE);
+}
+
+static void
+gimp_tool_group_init (GimpToolGroup *tool_group)
+{
+ tool_group->priv = gimp_tool_group_get_instance_private (tool_group);
+
+ tool_group->priv->children = g_object_new (
+ GIMP_TYPE_LIST,
+ "children-type", GIMP_TYPE_TOOL_INFO,
+ "append", TRUE,
+ NULL);
+
+ g_signal_connect (tool_group->priv->children, "add",
+ G_CALLBACK (gimp_tool_group_child_add),
+ tool_group);
+ g_signal_connect (tool_group->priv->children, "remove",
+ G_CALLBACK (gimp_tool_group_child_remove),
+ tool_group);
+}
+
+static void
+gimp_tool_group_finalize (GObject *object)
+{
+ GimpToolGroup *tool_group = GIMP_TOOL_GROUP (object);
+
+ g_clear_pointer (&tool_group->priv->active_tool, g_free);
+
+ g_clear_object (&tool_group->priv->children);
+
+ G_OBJECT_CLASS (parent_class)->finalize (object);
+}
+
+static void
+gimp_tool_group_get_property (GObject *object,
+ guint property_id,
+ GValue *value,
+ GParamSpec *pspec)
+{
+ GimpToolGroup *tool_group = GIMP_TOOL_GROUP (object);
+
+ switch (property_id)
+ {
+ case PROP_ACTIVE_TOOL:
+ g_value_set_string (value, tool_group->priv->active_tool);
+ break;
+
+ case PROP_CHILDREN:
+ g_value_set_object (value, tool_group->priv->children);
+ break;
+
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
+ break;
+ }
+}
+
+static void
+gimp_tool_group_set_property_add_tool (GimpToolInfo *tool_info,
+ GimpToolGroup *tool_group)
+{
+ gimp_container_add (tool_group->priv->children, GIMP_OBJECT (tool_info));
+}
+
+static void
+gimp_tool_group_set_property (GObject *object,
+ guint property_id,
+ const GValue *value,
+ GParamSpec *pspec)
+{
+ GimpToolGroup *tool_group = GIMP_TOOL_GROUP (object);
+
+ switch (property_id)
+ {
+ case PROP_ACTIVE_TOOL:
+ g_free (tool_group->priv->active_tool);
+
+ tool_group->priv->active_tool = g_value_dup_string (value);
+ break;
+
+ case PROP_CHILDREN:
+ {
+ GimpContainer *container = g_value_get_object (value);
+
+ gimp_container_clear (tool_group->priv->children);
+
+ if (! container)
+ break;
+
+ gimp_container_foreach (container,
+ (GFunc) gimp_tool_group_set_property_add_tool,
+ tool_group);
+ }
+ break;
+
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
+ break;
+ }
+}
+
+static gint64
+gimp_tool_group_get_memsize (GimpObject *object,
+ gint64 *gui_size)
+{
+ GimpToolGroup *tool_group = GIMP_TOOL_GROUP (object);
+ gint64 memsize = 0;
+
+ memsize += gimp_object_get_memsize (GIMP_OBJECT (tool_group->priv->children),
+ gui_size);
+
+ return memsize + GIMP_OBJECT_CLASS (parent_class)->get_memsize (object,
+ gui_size);
+}
+
+static gchar *
+gimp_tool_group_get_description (GimpViewable *viewable,
+ gchar **tooltip)
+{
+ /* Translators: this is a noun */
+ return g_strdup (C_("tool-item", "Group"));
+}
+
+static GimpContainer *
+gimp_tool_group_get_children (GimpViewable *viewable)
+{
+ GimpToolGroup *tool_group = GIMP_TOOL_GROUP (viewable);
+
+ return tool_group->priv->children;
+}
+
+static void
+gimp_tool_group_set_expanded (GimpViewable *viewable,
+ gboolean expand)
+{
+ if (! expand)
+ gimp_viewable_expanded_changed (viewable);
+}
+
+static gboolean
+gimp_tool_group_get_expanded (GimpViewable *viewable)
+{
+ return TRUE;
+}
+
+static void
+gimp_tool_group_child_add (GimpContainer *container,
+ GimpToolInfo *tool_info,
+ GimpToolGroup *tool_group)
+{
+ gimp_viewable_set_parent (GIMP_VIEWABLE (tool_info),
+ GIMP_VIEWABLE (tool_group));
+
+ if (! tool_group->priv->active_tool)
+ gimp_tool_group_set_active_tool_info (tool_group, tool_info);
+}
+
+static void
+gimp_tool_group_child_remove (GimpContainer *container,
+ GimpToolInfo *tool_info,
+ GimpToolGroup *tool_group)
+{
+ gimp_viewable_set_parent (GIMP_VIEWABLE (tool_info), NULL);
+
+ if (! g_strcmp0 (tool_group->priv->active_tool,
+ gimp_object_get_name (GIMP_OBJECT (tool_info))))
+ {
+ GimpToolInfo *active_tool_info = NULL;
+
+ if (! gimp_container_is_empty (tool_group->priv->children))
+ {
+ active_tool_info = GIMP_TOOL_INFO (
+ gimp_container_get_first_child (tool_group->priv->children));
+ }
+
+ gimp_tool_group_set_active_tool_info (tool_group, active_tool_info);
+ }
+}
+
+
+/* public functions */
+
+GimpToolGroup *
+gimp_tool_group_new (void)
+{
+ GimpToolGroup *group;
+
+ group = g_object_new (GIMP_TYPE_TOOL_GROUP, NULL);
+
+ gimp_object_set_static_name (GIMP_OBJECT (group), "tool group");
+
+ return group;
+}
+
+void
+gimp_tool_group_set_active_tool (GimpToolGroup *tool_group,
+ const gchar *tool_name)
+{
+ g_return_if_fail (GIMP_IS_TOOL_GROUP (tool_group));
+
+ if (g_strcmp0 (tool_group->priv->active_tool, tool_name))
+ {
+ g_return_if_fail (tool_name == NULL ||
+ gimp_container_get_child_by_name (
+ tool_group->priv->children, tool_name) != NULL);
+
+ g_free (tool_group->priv->active_tool);
+
+ tool_group->priv->active_tool = g_strdup (tool_name);;
+
+ g_signal_emit (tool_group,
+ gimp_tool_group_signals[ACTIVE_TOOL_CHANGED], 0);
+
+ g_object_notify (G_OBJECT (tool_group), "active-tool");
+ }
+}
+
+const gchar *
+gimp_tool_group_get_active_tool (GimpToolGroup *tool_group)
+{
+ g_return_val_if_fail (GIMP_IS_TOOL_GROUP (tool_group), NULL);
+
+ return tool_group->priv->active_tool;
+}
+
+void
+gimp_tool_group_set_active_tool_info (GimpToolGroup *tool_group,
+ GimpToolInfo *tool_info)
+{
+ g_return_if_fail (GIMP_IS_TOOL_GROUP (tool_group));
+ g_return_if_fail (tool_info == NULL || GIMP_IS_TOOL_INFO (tool_info));
+
+ gimp_tool_group_set_active_tool (
+ tool_group,
+ tool_info ? gimp_object_get_name (GIMP_OBJECT (tool_info)) : NULL);
+}
+
+GimpToolInfo *
+gimp_tool_group_get_active_tool_info (GimpToolGroup *tool_group)
+{
+ g_return_val_if_fail (GIMP_IS_TOOL_GROUP (tool_group), NULL);
+
+ return GIMP_TOOL_INFO (
+ gimp_container_get_child_by_name (tool_group->priv->children,
+ tool_group->priv->active_tool));
+}
diff --git a/app/core/gimptoolgroup.h b/app/core/gimptoolgroup.h
new file mode 100644
index 0000000000..ef4d979b5e
--- /dev/null
+++ b/app/core/gimptoolgroup.h
@@ -0,0 +1,68 @@
+/* GIMP - The GNU Image Manipulation Program
+ * Copyright (C) 1995 Spencer Kimball and Peter Mattis
+ *
+ * gimptoolgroup.h
+ * Copyright (C) 2020 Ell
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+#ifndef __GIMP_TOOL_GROUP_H__
+#define __GIMP_TOOL_GROUP_H__
+
+
+#include "gimptoolitem.h"
+
+
+#define GIMP_TYPE_TOOL_GROUP (gimp_tool_group_get_type ())
+#define GIMP_TOOL_GROUP(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GIMP_TYPE_TOOL_GROUP,
GimpToolGroup))
+#define GIMP_TOOL_GROUP_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GIMP_TYPE_TOOL_GROUP,
GimpToolGroupClass))
+#define GIMP_IS_TOOL_GROUP(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GIMP_TYPE_TOOL_GROUP))
+#define GIMP_IS_TOOL_GROUP_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GIMP_TYPE_TOOL_GROUP))
+#define GIMP_TOOL_GROUP_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GIMP_TYPE_TOOL_GROUP,
GimpToolGroupClass))
+
+
+typedef struct _GimpToolGroupPrivate GimpToolGroupPrivate;
+typedef struct _GimpToolGroupClass GimpToolGroupClass;
+
+struct _GimpToolGroup
+{
+ GimpToolItem parent_instance;
+
+ GimpToolGroupPrivate *priv;
+};
+
+struct _GimpToolGroupClass
+{
+ GimpToolItemClass parent_class;
+
+ /* signals */
+ void (* active_tool_changed) (GimpToolGroup *tool_group);
+};
+
+
+GType gimp_tool_group_get_type (void) G_GNUC_CONST;
+
+GimpToolGroup * gimp_tool_group_new (void);
+
+void gimp_tool_group_set_active_tool (GimpToolGroup *tool_group,
+ const gchar *tool_name);
+const gchar * gimp_tool_group_get_active_tool (GimpToolGroup *tool_group);
+
+void gimp_tool_group_set_active_tool_info (GimpToolGroup *tool_group,
+ GimpToolInfo *tool_info);
+GimpToolInfo * gimp_tool_group_get_active_tool_info (GimpToolGroup *tool_group);
+
+
+#endif /* __GIMP_TOOL_GROUP_H__ */
diff --git a/app/core/meson.build b/app/core/meson.build
index 5d6a75d43e..1ee94b6926 100644
--- a/app/core/meson.build
+++ b/app/core/meson.build
@@ -233,6 +233,7 @@ libappcore_sources = [
'gimptempbuf.c',
'gimptemplate.c',
'gimptilehandlerprojectable.c',
+ 'gimptoolgroup.c',
'gimptoolinfo.c',
'gimptoolitem.c',
'gimptooloptions.c',
diff --git a/po/POTFILES.in b/po/POTFILES.in
index 18aeb7f458..ee3e0da3b8 100644
--- a/po/POTFILES.in
+++ b/po/POTFILES.in
@@ -197,6 +197,7 @@ app/core/gimpsymmetry-mirror.c
app/core/gimpsymmetry-tiling.c
app/core/gimptagcache.c
app/core/gimptemplate.c
+app/core/gimptoolgroup.c
app/core/gimptooloptions.c
app/core/gimptoolpreset.c
app/core/gimptoolpreset-load.c
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]