1 /*
2 * Photos - access, organize and share your photos on GNOME
3 * Copyright © 2015 – 2019 Red Hat, Inc.
4 *
5 * This program is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
17 */
18
19
20 #include "config.h"
21
22 #include <gio/gio.h>
23
24 #include "photos-edit-palette.h"
25 #include "photos-edit-palette-row.h"
26 #include "photos-tool.h"
27 #include "photos-utils.h"
28
29
30 struct _PhotosEditPalette
31 {
32 GtkListBox parent_instance;
33 GIOExtensionPoint *extension_point;
34 GList *tools;
35 };
36
37 enum
38 {
39 TOOL_CHANGED,
40 LAST_SIGNAL
41 };
42
43 static guint signals[LAST_SIGNAL] = { 0 };
44
45
46 G_DEFINE_TYPE (PhotosEditPalette, photos_edit_palette, GTK_TYPE_LIST_BOX);
47
48
49 static gint
photos_edit_palette_extensions_sort_func(gconstpointer a,gconstpointer b)50 photos_edit_palette_extensions_sort_func (gconstpointer a, gconstpointer b)
51 {
52 GIOExtension *extension_a = (GIOExtension *) a;
53 GIOExtension *extension_b = (GIOExtension *) b;
54 gint priority_a;
55 gint priority_b;
56
57 priority_a = g_io_extension_get_priority (extension_a);
58 priority_b = g_io_extension_get_priority (extension_b);
59 return priority_a - priority_b;
60 }
61
62
63 static void
photos_edit_palette_hide_requested(PhotosEditPalette * self)64 photos_edit_palette_hide_requested (PhotosEditPalette *self)
65 {
66 g_signal_emit (self, signals[TOOL_CHANGED], 0, NULL);
67 }
68
69
70 static void
photos_edit_palette_row_activated(GtkListBox * box,GtkListBoxRow * row)71 photos_edit_palette_row_activated (GtkListBox *box, GtkListBoxRow *row)
72 {
73 PhotosEditPalette *self = PHOTOS_EDIT_PALETTE (box);
74 GtkListBoxRow *other_row;
75 PhotosTool *tool;
76 gint i;
77
78 photos_edit_palette_row_show_details (PHOTOS_EDIT_PALETTE_ROW (row));
79
80 for (i = 0; (other_row = gtk_list_box_get_row_at_index (box, i)) != NULL; i++)
81 {
82 if (other_row == row)
83 continue;
84
85 photos_edit_palette_row_hide_details (PHOTOS_EDIT_PALETTE_ROW (other_row));
86 }
87
88 tool = photos_edit_palette_row_get_tool (PHOTOS_EDIT_PALETTE_ROW (row));
89 g_signal_emit (self, signals[TOOL_CHANGED], 0, tool);
90 }
91
92
93 static void
photos_edit_palette_dispose(GObject * object)94 photos_edit_palette_dispose (GObject *object)
95 {
96 PhotosEditPalette *self = PHOTOS_EDIT_PALETTE (object);
97
98 g_list_free_full (self->tools, g_object_unref);
99 self->tools = NULL;
100
101 G_OBJECT_CLASS (photos_edit_palette_parent_class)->dispose (object);
102 }
103
104
105 static void
photos_edit_palette_init(PhotosEditPalette * self)106 photos_edit_palette_init (PhotosEditPalette *self)
107 {
108 gtk_list_box_set_selection_mode (GTK_LIST_BOX (self), GTK_SELECTION_NONE);
109 gtk_list_box_set_header_func (GTK_LIST_BOX (self), photos_utils_list_box_header_func, NULL, NULL);
110
111 self->extension_point = g_io_extension_point_lookup (PHOTOS_TOOL_EXTENSION_POINT_NAME);
112
113 gtk_widget_show_all (GTK_WIDGET (self));
114 }
115
116
117 static void
photos_edit_palette_class_init(PhotosEditPaletteClass * class)118 photos_edit_palette_class_init (PhotosEditPaletteClass *class)
119 {
120 GObjectClass *object_class = G_OBJECT_CLASS (class);
121 GtkListBoxClass *list_box_class = GTK_LIST_BOX_CLASS (class);
122
123 object_class->dispose = photos_edit_palette_dispose;
124 list_box_class->row_activated = photos_edit_palette_row_activated;
125
126 signals[TOOL_CHANGED] = g_signal_new ("tool-changed",
127 G_TYPE_FROM_CLASS (class),
128 G_SIGNAL_RUN_LAST,
129 0,
130 NULL, /* accumulator */
131 NULL, /* accu_data */
132 g_cclosure_marshal_VOID__OBJECT,
133 G_TYPE_NONE,
134 1,
135 PHOTOS_TYPE_TOOL);
136 }
137
138
139 GtkWidget *
photos_edit_palette_new(void)140 photos_edit_palette_new (void)
141 {
142 return g_object_new (PHOTOS_TYPE_EDIT_PALETTE, NULL);
143 }
144
145
146 void
photos_edit_palette_hide_details(PhotosEditPalette * self)147 photos_edit_palette_hide_details (PhotosEditPalette *self)
148 {
149 GtkListBoxRow *row;
150 gint i;
151
152 for (i = 0; (row = gtk_list_box_get_row_at_index (GTK_LIST_BOX (self), i)) != NULL; i++)
153 photos_edit_palette_row_hide_details (PHOTOS_EDIT_PALETTE_ROW (row));
154
155 g_signal_emit (self, signals[TOOL_CHANGED], 0, NULL);
156 }
157
158
159 void
photos_edit_palette_show(PhotosEditPalette * self)160 photos_edit_palette_show (PhotosEditPalette *self)
161 {
162 g_autoptr (GList) extensions = NULL;
163 GList *l;
164 g_autoptr (GtkSizeGroup) size_group = NULL;
165
166 gtk_container_foreach (GTK_CONTAINER (self), (GtkCallback) gtk_widget_destroy, NULL);
167 g_list_free_full (self->tools, g_object_unref);
168 self->tools = NULL;
169
170 extensions = g_io_extension_point_get_extensions (self->extension_point);
171 extensions = g_list_copy (extensions);
172 extensions = g_list_sort (extensions, photos_edit_palette_extensions_sort_func);
173
174 size_group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
175
176 for (l = extensions; l != NULL; l = l->next)
177 {
178 GIOExtension *extension = (GIOExtension *) l->data;
179 GType type;
180 GtkWidget *row;
181 g_autoptr (PhotosTool) tool = NULL;
182
183 type = g_io_extension_get_type (extension);
184 tool = PHOTOS_TOOL (g_object_new (type, NULL));
185 self->tools = g_list_prepend (self->tools, g_object_ref (tool));
186
187 row = photos_edit_palette_row_new (tool, size_group);
188 gtk_container_add (GTK_CONTAINER (self), row);
189 photos_edit_palette_row_show (PHOTOS_EDIT_PALETTE_ROW (row));
190
191 g_signal_connect_swapped (tool, "hide-requested", G_CALLBACK (photos_edit_palette_hide_requested), self);
192 }
193
194 gtk_widget_show_all (GTK_WIDGET (self));
195 }
196