Bug Summary

File:libbaul-private/baul-icon-container.c
Warning:line 1517, column 9
Value stored to 'y' is never read

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-pc-linux-gnu -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name baul-icon-container.c -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -fhalf-no-semantic-interposition -mframe-pointer=all -fmath-errno -ffp-contract=on -fno-rounding-math -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fdebug-compilation-dir=/rootdir/libbaul-private -fcoverage-compilation-dir=/rootdir/libbaul-private -resource-dir /usr/lib/llvm-19/lib/clang/19 -D HAVE_CONFIG_H -I . -I .. -I .. -I .. -I /usr/include/glib-2.0 -I /usr/lib/x86_64-linux-gnu/glib-2.0/include -I /usr/include/sysprof-6 -I /usr/include/cafe-desktop-2.0 -I /usr/include/ctk-3.0 -I /usr/include/pango-1.0 -I /usr/include/harfbuzz -I /usr/include/freetype2 -I /usr/include/libpng16 -I /usr/include/libmount -I /usr/include/blkid -I /usr/include/fribidi -I /usr/include/cairo -I /usr/include/pixman-1 -I /usr/include/gdk-pixbuf-2.0 -I /usr/include/x86_64-linux-gnu -I /usr/include/webp -I /usr/include/gio-unix-2.0 -I /usr/include/atk-1.0 -I /usr/include/at-spi2-atk/2.0 -I /usr/include/at-spi-2.0 -I /usr/include/dbus-1.0 -I /usr/lib/x86_64-linux-gnu/dbus-1.0/include -I /usr/include/startup-notification-1.0 -I /usr/include/dconf -I /usr/include/cail-3.0 -I /usr/include/libxml2 -D G_DISABLE_DEPRECATED -D GDK_PIXBUF_DISABLE_DEPRECATED -D DATADIR="/usr/share" -D SYSCONFDIR="/usr/etc" -D BAUL_DATADIR="/usr/share/baul" -D BAUL_EXTENSIONDIR="/usr/lib/baul/extensions-2.0" -D PIC -internal-isystem /usr/lib/llvm-19/lib/clang/19/include -internal-isystem /usr/local/include -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/14/../../../../x86_64-linux-gnu/include -internal-externc-isystem /usr/include/x86_64-linux-gnu -internal-externc-isystem /include -internal-externc-isystem /usr/include -ferror-limit 19 -fgnuc-version=4.2.1 -fskip-odr-check-in-gmf -analyzer-checker deadcode.DeadStores -analyzer-checker alpha.deadcode.UnreachableCode -analyzer-checker alpha.core.CastSize -analyzer-checker alpha.core.CastToStruct -analyzer-checker alpha.core.IdenticalExpr -analyzer-checker alpha.security.ArrayBoundV2 -analyzer-checker alpha.security.MallocOverflow -analyzer-checker alpha.security.ReturnPtrRange -analyzer-checker alpha.unix.SimpleStream -analyzer-checker alpha.unix.cstring.BufferOverlap -analyzer-checker alpha.unix.cstring.NotNullTerminated -analyzer-checker alpha.unix.cstring.OutOfBounds -analyzer-checker alpha.core.FixedAddr -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /rootdir/html-report/2025-01-24-093644-27604-1 -x c baul-icon-container.c
1/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
2
3/* baul-icon-container.c - Icon container widget.
4
5 Copyright (C) 1999, 2000 Free Software Foundation
6 Copyright (C) 2000, 2001 Eazel, Inc.
7 Copyright (C) 2002, 2003 Red Hat, Inc.
8
9 The Cafe Library is free software; you can redistribute it and/or
10 modify it under the terms of the GNU Library General Public License as
11 published by the Free Software Foundation; either version 2 of the
12 License, or (at your option) any later version.
13
14 The Cafe Library is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 Library General Public License for more details.
18
19 You should have received a copy of the GNU Library General Public
20 License along with the Cafe Library; see the file COPYING.LIB. If not,
21 write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
22 Boston, MA 02110-1301, USA.
23
24 Authors: Ettore Perazzoli <ettore@gnu.org>,
25 Darin Adler <darin@bentspoon.com>
26*/
27
28#include <config.h>
29#include <math.h>
30#include <atk/atkaction.h>
31#include <cdk/cdkkeysyms.h>
32#include <ctk/ctk.h>
33#include <cdk/cdkx.h>
34#include <glib/gi18n.h>
35#include <stdio.h>
36#include <string.h>
37
38#include <eel/eel-accessibility.h>
39#include <eel/eel-background.h>
40#include <eel/eel-vfs-extensions.h>
41#include <eel/eel-gdk-pixbuf-extensions.h>
42#include <eel/eel-cafe-extensions.h>
43#include <eel/eel-ctk-extensions.h>
44#include <eel/eel-art-extensions.h>
45#include <eel/eel-editable-label.h>
46#include <eel/eel-string.h>
47#include <eel/eel-canvas.h>
48#include <eel/eel-canvas-rect-ellipse.h>
49
50#include "baul-icon-container.h"
51#include "baul-debug-log.h"
52#include "baul-global-preferences.h"
53#include "baul-icon-private.h"
54#include "baul-lib-self-check-functions.h"
55#include "baul-marshal.h"
56
57#define TAB_NAVIGATION_DISABLED
58
59/* Interval for updating the rubberband selection, in milliseconds. */
60#define RUBBERBAND_TIMEOUT_INTERVAL10 10
61
62/* Initial unpositioned icon value */
63#define ICON_UNPOSITIONED_VALUE-1 -1
64
65/* Timeout for making the icon currently selected for keyboard operation visible.
66 * If this is 0, you can get into trouble with extra scrolling after holding
67 * down the arrow key for awhile when there are many items.
68 */
69#define KEYBOARD_ICON_REVEAL_TIMEOUT10 10
70
71#define CONTEXT_MENU_TIMEOUT_INTERVAL500 500
72
73/* Maximum amount of milliseconds the mouse button is allowed to stay down
74 * and still be considered a click.
75 */
76#define MAX_CLICK_TIME1500 1500
77
78/* Button assignments. */
79#define DRAG_BUTTON1 1
80#define RUBBERBAND_BUTTON1 1
81#define MIDDLE_BUTTON2 2
82#define CONTEXTUAL_MENU_BUTTON3 3
83#define DRAG_MENU_BUTTON2 2
84
85/* Maximum size (pixels) allowed for icons at the standard zoom level. */
86#define MINIMUM_IMAGE_SIZE24 24
87#define MAXIMUM_IMAGE_SIZE96 96
88
89#define ICON_PAD_LEFT4 4
90#define ICON_PAD_RIGHT4 4
91#define ICON_BASE_WIDTH96 96
92
93#define ICON_PAD_TOP4 4
94#define ICON_PAD_BOTTOM4 4
95
96#define CONTAINER_PAD_LEFT4 4
97#define CONTAINER_PAD_RIGHT4 4
98#define CONTAINER_PAD_TOP4 4
99#define CONTAINER_PAD_BOTTOM4 4
100
101#define STANDARD_ICON_GRID_WIDTH155 155
102
103#define TEXT_BESIDE_ICON_GRID_WIDTH205 205
104
105/* Desktop layout mode defines */
106#define DESKTOP_PAD_HORIZONTAL10 10
107#define DESKTOP_PAD_VERTICAL10 10
108#define SNAP_SIZE_X78 78
109#define SNAP_SIZE_Y20 20
110
111#define DEFAULT_SELECTION_BOX_ALPHA0x40 0x40
112#define DEFAULT_HIGHLIGHT_ALPHA0xff 0xff
113#define DEFAULT_NORMAL_ALPHA0xff 0xff
114#define DEFAULT_PRELIGHT_ALPHA0xff 0xff
115#define DEFAULT_LIGHT_INFO_COLOR"#AAAAFD" "#AAAAFD"
116#define DEFAULT_DARK_INFO_COLOR"#33337F" "#33337F"
117
118#define MINIMUM_EMBEDDED_TEXT_RECT_WIDTH20 20
119#define MINIMUM_EMBEDDED_TEXT_RECT_HEIGHT20 20
120
121/* If icon size is bigger than this, request large embedded text.
122 * Its selected so that the non-large text should fit in "normal" icon sizes
123 */
124#define ICON_SIZE_FOR_LARGE_EMBEDDED_TEXT55 55
125
126/* From baul-icon-canvas-item.c */
127#define MAX_TEXT_WIDTH_BESIDE90 90
128
129#define SNAP_HORIZONTAL(func,x)((func ((double)((x) - 10) / 78) * 78) + 10) ((func ((double)((x) - DESKTOP_PAD_HORIZONTAL10) / SNAP_SIZE_X78) * SNAP_SIZE_X78) + DESKTOP_PAD_HORIZONTAL10)
130#define SNAP_VERTICAL(func, y)((func ((double)((y) - 10) / 20) * 20) + 10) ((func ((double)((y) - DESKTOP_PAD_VERTICAL10) / SNAP_SIZE_Y20) * SNAP_SIZE_Y20) + DESKTOP_PAD_VERTICAL10)
131
132#define SNAP_NEAREST_HORIZONTAL(x)((eel_round ((double)((x) - 10) / 78) * 78) + 10) SNAP_HORIZONTAL (eel_round, x)((eel_round ((double)((x) - 10) / 78) * 78) + 10)
133#define SNAP_NEAREST_VERTICAL(y)((eel_round ((double)((y) - 10) / 20) * 20) + 10) SNAP_VERTICAL (eel_round, y)((eel_round ((double)((y) - 10) / 20) * 20) + 10)
134
135#define SNAP_CEIL_HORIZONTAL(x)((ceil ((double)((x) - 10) / 78) * 78) + 10) SNAP_HORIZONTAL (ceil, x)((ceil ((double)((x) - 10) / 78) * 78) + 10)
136#define SNAP_CEIL_VERTICAL(y)((ceil ((double)((y) - 10) / 20) * 20) + 10) SNAP_VERTICAL (ceil, y)((ceil ((double)((y) - 10) / 20) * 20) + 10)
137
138/* Copied from BaulIconContainer */
139#define BAUL_ICON_CONTAINER_SEARCH_DIALOG_TIMEOUT5 5
140
141/* Copied from BaulFile */
142#define UNDEFINED_TIME((time_t) (-1)) ((time_t) (-1))
143
144enum
145{
146 ACTION_ACTIVATE,
147 ACTION_MENU,
148 LAST_ACTION
149};
150
151typedef struct
152{
153 GList *selection;
154 char *action_descriptions[LAST_ACTION];
155} BaulIconContainerAccessiblePrivate;
156
157static GType baul_icon_container_accessible_get_type (void);
158
159typedef struct _BaulIconContainerAccessible BaulIconContainerAccessible;
160typedef struct _BaulIconContainerAccessibleClass BaulIconContainerAccessibleClass;
161
162struct _BaulIconContainerAccessible
163{
164 EelCanvasAccessible parent;
165};
166
167struct _BaulIconContainerAccessibleClass
168{
169 EelCanvasAccessibleClass parent_class;
170};
171
172static void activate_selected_items (BaulIconContainer *container);
173static void activate_selected_items_alternate (BaulIconContainer *container,
174 BaulIcon *icon);
175static void compute_stretch (StretchState *start,
176 StretchState *current);
177static BaulIcon *get_first_selected_icon (BaulIconContainer *container);
178static BaulIcon *get_nth_selected_icon (BaulIconContainer *container,
179 int index);
180static gboolean has_multiple_selection (BaulIconContainer *container);
181static gboolean all_selected (BaulIconContainer *container);
182static gboolean has_selection (BaulIconContainer *container);
183static void icon_destroy (BaulIconContainer *container,
184 BaulIcon *icon);
185static void end_renaming_mode (BaulIconContainer *container,
186 gboolean commit);
187static BaulIcon *get_icon_being_renamed (BaulIconContainer *container);
188static void finish_adding_new_icons (BaulIconContainer *container);
189static inline void icon_get_bounding_box (BaulIcon *icon,
190 int *x1_return,
191 int *y1_return,
192 int *x2_return,
193 int *y2_return,
194 BaulIconCanvasItemBoundsUsage usage);
195static gboolean is_renaming (BaulIconContainer *container);
196static gboolean is_renaming_pending (BaulIconContainer *container);
197static void process_pending_icon_to_rename (BaulIconContainer *container);
198static void handle_hadjustment_changed (CtkAdjustment *adjustment,
199 BaulIconContainer *container);
200static void handle_vadjustment_changed (CtkAdjustment *adjustment,
201 BaulIconContainer *container);
202static GList * baul_icon_container_get_selected_icons (BaulIconContainer *container);
203static void baul_icon_container_update_visible_icons (BaulIconContainer *container);
204static void reveal_icon (BaulIconContainer *container,
205 BaulIcon *icon);
206
207static void baul_icon_container_set_rtl_positions (BaulIconContainer *container);
208static double get_mirror_x_position (BaulIconContainer *container,
209 BaulIcon *icon,
210 double x);
211static void text_ellipsis_limit_changed_container_callback (gpointer callback_data);
212
213static int compare_icons_horizontal (BaulIconContainer *container,
214 BaulIcon *icon_a,
215 BaulIcon *icon_b);
216
217static int compare_icons_vertical (BaulIconContainer *container,
218 BaulIcon *icon_a,
219 BaulIcon *icon_b);
220
221static void store_layout_timestamps_now (BaulIconContainer *container);
222
223static gpointer accessible_parent_class;
224
225static GQuark accessible_private_data_quark = 0;
226
227static const char *baul_icon_container_accessible_action_names[] =
228{
229 "activate",
230 "menu",
231 NULL((void*)0)
232};
233
234static const char *baul_icon_container_accessible_action_descriptions[] =
235{
236 "Activate selected items",
237 "Popup context menu",
238 NULL((void*)0)
239};
240
241G_DEFINE_TYPE (BaulIconContainer, baul_icon_container, EEL_TYPE_CANVAS)static void baul_icon_container_init (BaulIconContainer *self
); static void baul_icon_container_class_init (BaulIconContainerClass
*klass); static GType baul_icon_container_get_type_once (void
); static gpointer baul_icon_container_parent_class = ((void*
)0); static gint BaulIconContainer_private_offset; static void
baul_icon_container_class_intern_init (gpointer klass) { baul_icon_container_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainer_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainer_private_offset
); baul_icon_container_class_init ((BaulIconContainerClass*) klass
); } __attribute__ ((__unused__)) static inline gpointer baul_icon_container_get_instance_private
(BaulIconContainer *self) { return (((gpointer) ((guint8*) (
self) + (glong) (BaulIconContainer_private_offset)))); } GType
baul_icon_container_get_type (void) { static GType static_g_define_type_id
= 0; if ((__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); (void
) (0 ? (gpointer) * (&static_g_define_type_id) : ((void*)
0)); (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_get_type_once (); (__extension__ ({ _Static_assert
(sizeof *(&static_g_define_type_id) == sizeof (gpointer)
, "Expression evaluates to false"); 0 ? (void) (*(&static_g_define_type_id
) = (g_define_type_id)) : (void) 0; g_once_init_leave_pointer
((&static_g_define_type_id), (gpointer) (guintptr) (g_define_type_id
)); })) ; } return static_g_define_type_id; } __attribute__ (
(__noinline__)) static GType baul_icon_container_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
((eel_canvas_get_type ()), g_intern_static_string ("BaulIconContainer"
), sizeof (BaulIconContainerClass), (GClassInitFunc)(void (*)
(void)) baul_icon_container_class_intern_init, sizeof (BaulIconContainer
), (GInstanceInitFunc)(void (*)(void)) baul_icon_container_init
, (GTypeFlags) 0); { {{};} } return g_define_type_id; }
;
242
243/* The BaulIconContainer signals. */
244enum
245{
246 ACTIVATE,
247 ACTIVATE_ALTERNATE,
248 BAND_SELECT_STARTED,
249 BAND_SELECT_ENDED,
250 BUTTON_PRESS,
251 CAN_ACCEPT_ITEM,
252 CONTEXT_CLICK_BACKGROUND,
253 CONTEXT_CLICK_SELECTION,
254 MIDDLE_CLICK,
255 GET_CONTAINER_URI,
256 GET_ICON_URI,
257 GET_ICON_DROP_TARGET_URI,
258 GET_STORED_ICON_POSITION,
259 ICON_POSITION_CHANGED,
260 GET_STORED_LAYOUT_TIMESTAMP,
261 STORE_LAYOUT_TIMESTAMP,
262 ICON_TEXT_CHANGED,
263 ICON_STRETCH_STARTED,
264 ICON_STRETCH_ENDED,
265 RENAMING_ICON,
266 LAYOUT_CHANGED,
267 MOVE_COPY_ITEMS,
268 HANDLE_NETSCAPE_URL,
269 HANDLE_URI_LIST,
270 HANDLE_TEXT,
271 HANDLE_RAW,
272 PREVIEW,
273 SELECTION_CHANGED,
274 ICON_ADDED,
275 ICON_REMOVED,
276 CLEARED,
277 START_INTERACTIVE_SEARCH,
278 LAST_SIGNAL
279};
280
281typedef struct
282{
283 int **icon_grid;
284 int *grid_memory;
285 int num_rows;
286 int num_columns;
287 gboolean tight;
288} PlacementGrid;
289
290static guint signals[LAST_SIGNAL] = { 0 };
291
292/* Functions dealing with BaulIcons. */
293
294static void
295icon_free (BaulIcon *icon)
296{
297 /* Destroy this canvas item; the parent will unref it. */
298 eel_canvas_item_destroy (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
);
299 g_free (icon);
300}
301
302static gboolean
303icon_is_positioned (const BaulIcon *icon)
304{
305 return icon->x != ICON_UNPOSITIONED_VALUE-1 && icon->y != ICON_UNPOSITIONED_VALUE-1;
306}
307
308
309/* x, y are the top-left coordinates of the icon. */
310static void
311icon_set_position (BaulIcon *icon,
312 double x, double y)
313{
314 BaulIconContainer *container;
315 int x1, x2, y1, y2;
316 EelDRect icon_bounds;
317
318 if (icon->x == x && icon->y == y)
319 {
320 return;
321 }
322
323 container = BAUL_ICON_CONTAINER (EEL_CANVAS_ITEM (icon->item)->canvas)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((((((EelCanvasItem*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((icon->item)), ((eel_canvas_item_get_type
()))))))->canvas)), (baul_icon_container_get_type())))))
;
324
325 if (icon == get_icon_being_renamed (container))
326 {
327 end_renaming_mode (container, TRUE(!(0)));
328 }
329
330 if (baul_icon_container_get_is_fixed_size (container))
331 {
332 double pixels_per_unit;
333 int container_left, container_top, container_right, container_bottom;
334 int container_x, container_y, container_width, container_height;
335 int item_width, item_height;
336 int height_above, width_left;
337 int min_x, max_x, min_y, max_y;
338 int scale;
339
340 /* FIXME: This should be:
341
342 container_x = CTK_WIDGET (container)->allocation.x;
343 container_y = CTK_WIDGET (container)->allocation.y;
344 container_width = CTK_WIDGET (container)->allocation.width;
345 container_height = CTK_WIDGET (container)->allocation.height;
346
347 But for some reason the widget allocation is sometimes not done
348 at startup, and the allocation is then only 45x60. which is
349 really bad.
350
351 For now, we have a cheesy workaround:
352 */
353 scale = ctk_widget_get_scale_factor (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
354 container_x = 0;
355 container_y = 0;
356 container_width = WidthOfScreen (cdk_x11_screen_get_xscreen (cdk_screen_get_default ()))((cdk_x11_screen_get_xscreen (cdk_screen_get_default ()))->
width)
/ scale - container_x
357 - container->details->left_margin
358 - container->details->right_margin;
359 container_height = HeightOfScreen (cdk_x11_screen_get_xscreen (cdk_screen_get_default ()))((cdk_x11_screen_get_xscreen (cdk_screen_get_default ()))->
height)
/ scale - container_y
360 - container->details->top_margin
361 - container->details->bottom_margin;
362 pixels_per_unit = EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
->pixels_per_unit;
363 /* Clip the position of the icon within our desktop bounds */
364 container_left = container_x / pixels_per_unit;
365 container_top = container_y / pixels_per_unit;
366 container_right = container_left + container_width / pixels_per_unit;
367 container_bottom = container_top + container_height / pixels_per_unit;
368
369 icon_get_bounding_box (icon, &x1, &y1, &x2, &y2,
370 BOUNDS_USAGE_FOR_ENTIRE_ITEM);
371 item_width = x2 - x1;
372 item_height = y2 - y1;
373
374 icon_bounds = baul_icon_canvas_item_get_icon_rectangle (icon->item);
375
376 /* determine icon rectangle relative to item rectangle */
377 height_above = icon_bounds.y0 - y1;
378 width_left = icon_bounds.x0 - x1;
379
380 min_x = container_left + DESKTOP_PAD_HORIZONTAL10 + width_left;
381 max_x = container_right - DESKTOP_PAD_HORIZONTAL10 - item_width + width_left;
382 x = CLAMP (x, min_x, max_x)(((x) > (max_x)) ? (max_x) : (((x) < (min_x)) ? (min_x)
: (x)))
;
383
384 min_y = container_top + height_above + DESKTOP_PAD_VERTICAL10;
385 max_y = container_bottom - DESKTOP_PAD_VERTICAL10 - item_height + height_above;
386 y = CLAMP (y, min_y, max_y)(((y) > (max_y)) ? (max_y) : (((y) < (min_y)) ? (min_y)
: (y)))
;
387 }
388
389 if (icon->x == ICON_UNPOSITIONED_VALUE-1)
390 {
391 icon->x = 0;
392 }
393 if (icon->y == ICON_UNPOSITIONED_VALUE-1)
394 {
395 icon->y = 0;
396 }
397
398 eel_canvas_item_move (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
399 x - icon->x,
400 y - icon->y);
401
402 icon->x = x;
403 icon->y = y;
404}
405
406static void
407icon_get_size (BaulIconContainer *container,
408 BaulIcon *icon,
409 guint *size)
410{
411 if (size != NULL((void*)0))
412 {
413 *size = MAX (baul_get_icon_size_for_zoom_level (container->details->zoom_level)(((baul_get_icon_size_for_zoom_level (container->details->
zoom_level) * icon->scale) > (16)) ? (baul_get_icon_size_for_zoom_level
(container->details->zoom_level) * icon->scale) : (
16))
414 * icon->scale, BAUL_ICON_SIZE_SMALLEST)(((baul_get_icon_size_for_zoom_level (container->details->
zoom_level) * icon->scale) > (16)) ? (baul_get_icon_size_for_zoom_level
(container->details->zoom_level) * icon->scale) : (
16))
;
415 }
416}
417
418/* The icon_set_size function is used by the stretching user
419 * interface, which currently stretches in a way that keeps the aspect
420 * ratio. Later we might have a stretching interface that stretches Y
421 * separate from X and we will change this around.
422 */
423static void
424icon_set_size (BaulIconContainer *container,
425 BaulIcon *icon,
426 guint icon_size,
427 gboolean snap,
428 gboolean update_position)
429{
430 guint old_size;
431 double scale;
432
433 icon_get_size (container, icon, &old_size);
434 if (icon_size == old_size)
435 {
436 return;
437 }
438
439 scale = (double) icon_size /
440 baul_get_icon_size_for_zoom_level
441 (container->details->zoom_level);
442 baul_icon_container_move_icon (container, icon,
443 icon->x, icon->y,
444 scale, FALSE(0),
445 snap, update_position);
446}
447
448static void
449icon_raise (BaulIcon *icon)
450{
451 EelCanvasItem *item, *band;
452
453 item = EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
;
454 band = BAUL_ICON_CONTAINER (item->canvas)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((item->canvas)), (baul_icon_container_get_type
())))))
->details->rubberband_info.selection_rectangle;
455
456 eel_canvas_item_send_behind (item, band);
457}
458
459static void
460emit_stretch_started (BaulIconContainer *container, BaulIcon *icon)
461{
462 g_signal_emit (container,
463 signals[ICON_STRETCH_STARTED], 0,
464 icon->data);
465}
466
467static void
468emit_stretch_ended (BaulIconContainer *container, BaulIcon *icon)
469{
470 g_signal_emit (container,
471 signals[ICON_STRETCH_ENDED], 0,
472 icon->data);
473}
474
475static void
476icon_toggle_selected (BaulIconContainer *container,
477 BaulIcon *icon)
478{
479 end_renaming_mode (container, TRUE(!(0)));
480
481 icon->is_selected = !icon->is_selected;
482 eel_canvas_item_set (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
483 "highlighted_for_selection", (gboolean) icon->is_selected,
484 NULL((void*)0));
485
486 /* If the icon is deselected, then get rid of the stretch handles.
487 * No harm in doing the same if the item is newly selected.
488 */
489 if (icon == container->details->stretch_icon)
490 {
491 container->details->stretch_icon = NULL((void*)0);
492 baul_icon_canvas_item_set_show_stretch_handles (icon->item, FALSE(0));
493 /* snap the icon if necessary */
494 if (container->details->keep_aligned)
495 {
496 baul_icon_container_move_icon (container,
497 icon,
498 icon->x, icon->y,
499 icon->scale,
500 FALSE(0), TRUE(!(0)), TRUE(!(0)));
501 }
502
503 emit_stretch_ended (container, icon);
504 }
505
506 /* Raise each newly-selected icon to the front as it is selected. */
507 if (icon->is_selected)
508 {
509 icon_raise (icon);
510 }
511}
512
513/* Select an icon. Return TRUE if selection has changed. */
514static gboolean
515icon_set_selected (BaulIconContainer *container,
516 BaulIcon *icon,
517 gboolean select)
518{
519 g_assert (select == FALSE || select == TRUE)do { if (select == (0) || select == (!(0))) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 519, ((const char*) (
__func__)), "select == FALSE || select == TRUE"); } while (0)
;
520 g_assert (icon->is_selected == FALSE || icon->is_selected == TRUE)do { if (icon->is_selected == (0) || icon->is_selected ==
(!(0))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 520, ((const char*) (__func__)), "icon->is_selected == FALSE || icon->is_selected == TRUE"
); } while (0)
;
521
522 if (select == icon->is_selected)
523 {
524 return FALSE(0);
525 }
526
527 icon_toggle_selected (container, icon);
528 g_assert (select == icon->is_selected)do { if (select == icon->is_selected) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 528, ((const char*) (
__func__)), "select == icon->is_selected"); } while (0)
;
529 return TRUE(!(0));
530}
531
532static inline void
533icon_get_bounding_box (BaulIcon *icon,
534 int *x1_return, int *y1_return,
535 int *x2_return, int *y2_return,
536 BaulIconCanvasItemBoundsUsage usage)
537{
538 double x1, y1, x2, y2;
539
540 if (usage == BOUNDS_USAGE_FOR_DISPLAY)
541 {
542 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
543 &x1, &y1, &x2, &y2);
544 }
545 else if (usage == BOUNDS_USAGE_FOR_LAYOUT)
546 {
547 baul_icon_canvas_item_get_bounds_for_layout (icon->item,
548 &x1, &y1, &x2, &y2);
549 }
550 else if (usage == BOUNDS_USAGE_FOR_ENTIRE_ITEM)
551 {
552 baul_icon_canvas_item_get_bounds_for_entire_item (icon->item,
553 &x1, &y1, &x2, &y2);
554 }
555 else
556 {
557 g_assert_not_reached ()do { g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 557, ((const char*) (__func__)), ((void*)0)); } while (0)
;
558 }
559
560 if (x1_return != NULL((void*)0))
561 {
562 *x1_return = x1;
563 }
564
565 if (y1_return != NULL((void*)0))
566 {
567 *y1_return = y1;
568 }
569
570 if (x2_return != NULL((void*)0))
571 {
572 *x2_return = x2;
573 }
574
575 if (y2_return != NULL((void*)0))
576 {
577 *y2_return = y2;
578 }
579}
580
581/* Utility functions for BaulIconContainer. */
582
583gboolean
584baul_icon_container_scroll (BaulIconContainer *container,
585 int delta_x, int delta_y)
586{
587 CtkAdjustment *hadj, *vadj;
588 int old_h_value, old_v_value;
589
590 hadj = ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
591 vadj = ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
592
593 /* Store the old ajustment values so we can tell if we
594 * ended up actually scrolling. We may not have in a case
595 * where the resulting value got pinned to the adjustment
596 * min or max.
597 */
598 old_h_value = ctk_adjustment_get_value (hadj);
599 old_v_value = ctk_adjustment_get_value (vadj);
600
601 ctk_adjustment_set_value (hadj, ctk_adjustment_get_value (hadj) + delta_x);
602 ctk_adjustment_set_value (vadj, ctk_adjustment_get_value (vadj) + delta_y);
603
604 /* return TRUE if we did scroll */
605 return ctk_adjustment_get_value (hadj) != old_h_value || ctk_adjustment_get_value (vadj) != old_v_value;
606}
607
608static void
609pending_icon_to_reveal_destroy_callback (BaulIconCanvasItem *item,
610 BaulIconContainer *container)
611{
612 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 612, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
613 g_assert (container->details->pending_icon_to_reveal != NULL)do { if (container->details->pending_icon_to_reveal != (
(void*)0)) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 613, ((const char*) (__func__)), "container->details->pending_icon_to_reveal != NULL"
); } while (0)
;
614 g_assert (container->details->pending_icon_to_reveal->item == item)do { if (container->details->pending_icon_to_reveal->
item == item) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 614, ((const char*) (__func__)), "container->details->pending_icon_to_reveal->item == item"
); } while (0)
;
615
616 container->details->pending_icon_to_reveal = NULL((void*)0);
617}
618
619static BaulIcon*
620get_pending_icon_to_reveal (BaulIconContainer *container)
621{
622 return container->details->pending_icon_to_reveal;
623}
624
625static void
626set_pending_icon_to_reveal (BaulIconContainer *container, BaulIcon *icon)
627{
628 BaulIcon *old_icon;
629
630 old_icon = container->details->pending_icon_to_reveal;
631
632 if (icon == old_icon)
633 {
634 return;
635 }
636
637 if (old_icon != NULL((void*)0))
638 {
639 g_signal_handlers_disconnect_by_funcg_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_reveal_destroy_callback)))
, (container))
640 (old_icon->item,g_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_reveal_destroy_callback)))
, (container))
641 G_CALLBACK (pending_icon_to_reveal_destroy_callback),g_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_reveal_destroy_callback)))
, (container))
642 container)g_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_reveal_destroy_callback)))
, (container))
;
643 }
644
645 if (icon != NULL((void*)0))
646 {
647 g_signal_connect (icon->item, "destroy",g_signal_connect_data ((icon->item), ("destroy"), (((GCallback
) (pending_icon_to_reveal_destroy_callback))), (container), (
(void*)0), (GConnectFlags) 0)
648 G_CALLBACK (pending_icon_to_reveal_destroy_callback),g_signal_connect_data ((icon->item), ("destroy"), (((GCallback
) (pending_icon_to_reveal_destroy_callback))), (container), (
(void*)0), (GConnectFlags) 0)
649 container)g_signal_connect_data ((icon->item), ("destroy"), (((GCallback
) (pending_icon_to_reveal_destroy_callback))), (container), (
(void*)0), (GConnectFlags) 0)
;
650 }
651
652 container->details->pending_icon_to_reveal = icon;
653}
654
655static void
656item_get_canvas_bounds (EelCanvasItem *item,
657 EelIRect *bounds,
658 gboolean safety_pad)
659{
660 EelDRect world_rect;
661
662 eel_canvas_item_get_bounds (item,
663 &world_rect.x0,
664 &world_rect.y0,
665 &world_rect.x1,
666 &world_rect.y1);
667 eel_canvas_item_i2w (item->parent,
668 &world_rect.x0,
669 &world_rect.y0);
670 eel_canvas_item_i2w (item->parent,
671 &world_rect.x1,
672 &world_rect.y1);
673 if (safety_pad)
674 {
675 world_rect.x0 -= ICON_PAD_LEFT4 + ICON_PAD_RIGHT4;
676 world_rect.x1 += ICON_PAD_LEFT4 + ICON_PAD_RIGHT4;
677
678 world_rect.y0 -= ICON_PAD_TOP4 + ICON_PAD_BOTTOM4;
679 world_rect.y1 += ICON_PAD_TOP4 + ICON_PAD_BOTTOM4;
680 }
681
682 eel_canvas_w2c (item->canvas,
683 world_rect.x0,
684 world_rect.y0,
685 &bounds->x0,
686 &bounds->y0);
687 eel_canvas_w2c (item->canvas,
688 world_rect.x1,
689 world_rect.y1,
690 &bounds->x1,
691 &bounds->y1);
692}
693
694static void
695icon_get_row_and_column_bounds (BaulIconContainer *container,
696 BaulIcon *icon,
697 EelIRect *bounds,
698 gboolean safety_pad)
699{
700 GList *p;
701 EelIRect one_bounds;
702 BaulIcon *one_icon = NULL((void*)0);
703
704 item_get_canvas_bounds (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
, bounds, safety_pad);
705
706 for (p = container->details->icons; p != NULL((void*)0); p = p->next) {
707 one_icon = p->data;
708
709 if (icon == one_icon) {
710 continue;
711 }
712
713 if (compare_icons_horizontal (container, icon, one_icon) == 0) {
714 item_get_canvas_bounds (EEL_CANVAS_ITEM (one_icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((one_icon->item)), ((eel_canvas_item_get_type ()))))))
, &one_bounds, safety_pad);
715 bounds->x0 = MIN (bounds->x0, one_bounds.x0)(((bounds->x0) < (one_bounds.x0)) ? (bounds->x0) : (
one_bounds.x0))
;
716 bounds->x1 = MAX (bounds->x1, one_bounds.x1)(((bounds->x1) > (one_bounds.x1)) ? (bounds->x1) : (
one_bounds.x1))
;
717 }
718
719 if (compare_icons_vertical (container, icon, one_icon) == 0) {
720 item_get_canvas_bounds (EEL_CANVAS_ITEM (one_icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((one_icon->item)), ((eel_canvas_item_get_type ()))))))
, &one_bounds, safety_pad);
721 bounds->y0 = MIN (bounds->y0, one_bounds.y0)(((bounds->y0) < (one_bounds.y0)) ? (bounds->y0) : (
one_bounds.y0))
;
722 bounds->y1 = MAX (bounds->y1, one_bounds.y1)(((bounds->y1) > (one_bounds.y1)) ? (bounds->y1) : (
one_bounds.y1))
;
723 }
724 }
725
726
727}
728
729static void
730reveal_icon (BaulIconContainer *container,
731 BaulIcon *icon)
732{
733 CtkAllocation allocation;
734 CtkAdjustment *hadj, *vadj;
735 EelIRect bounds;
736
737 if (!icon_is_positioned (icon)) {
738 set_pending_icon_to_reveal (container, icon);
739 return;
740 }
741
742 set_pending_icon_to_reveal (container, NULL((void*)0));
743
744 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
745
746 hadj = ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
747 vadj = ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
748
749 if (baul_icon_container_is_auto_layout (container)) {
750 /* ensure that we reveal the entire row/column */
751 icon_get_row_and_column_bounds (container, icon, &bounds, TRUE(!(0)));
752 } else {
753 item_get_canvas_bounds (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
, &bounds, TRUE(!(0)));
754 }
755 if (bounds.y0 < ctk_adjustment_get_value (vadj)) {
756 ctk_adjustment_set_value (vadj, bounds.y0);
757 } else if (bounds.y1 > ctk_adjustment_get_value (vadj) + allocation.height) {
758 ctk_adjustment_set_value (vadj, bounds.y1 - allocation.height);
759 }
760
761 if (bounds.x0 < ctk_adjustment_get_value (hadj)) {
762 ctk_adjustment_set_value (hadj, bounds.x0);
763 } else if (bounds.x1 > ctk_adjustment_get_value (hadj) + allocation.width) {
764 if (bounds.x1 - allocation.width > bounds.x0) {
765 ctk_adjustment_set_value (hadj, bounds.x0);
766 } else {
767 ctk_adjustment_set_value (hadj, bounds.x1 - allocation.width);
768 }
769 }
770}
771
772static void
773process_pending_icon_to_reveal (BaulIconContainer *container)
774{
775 BaulIcon *pending_icon_to_reveal;
776
777 pending_icon_to_reveal = get_pending_icon_to_reveal (container);
778
779 if (pending_icon_to_reveal != NULL((void*)0)) {
780 reveal_icon (container, pending_icon_to_reveal);
781 }
782}
783
784static gboolean
785keyboard_icon_reveal_timeout_callback (gpointer data)
786{
787 BaulIconContainer *container;
788 BaulIcon *icon;
789
790 container = BAUL_ICON_CONTAINER (data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((data)), (baul_icon_container_get_type())))
))
;
791 icon = container->details->keyboard_icon_to_reveal;
792
793 g_assert (icon != NULL)do { if (icon != ((void*)0)) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 793, ((const char*) (__func__
)), "icon != NULL"); } while (0)
;
794
795 /* Only reveal the icon if it's still the keyboard focus or if
796 * it's still selected. Someone originally thought we should
797 * cancel this reveal if the user manages to sneak a direct
798 * scroll in before the timeout fires, but we later realized
799 * this wouldn't actually be an improvement
800 * (see bugzilla.gnome.org 40612).
801 */
802 if (icon == container->details->keyboard_focus
803 || icon->is_selected) {
804 reveal_icon (container, icon);
805 }
806 container->details->keyboard_icon_reveal_timer_id = 0;
807
808 return FALSE(0);
809}
810
811static void
812unschedule_keyboard_icon_reveal (BaulIconContainer *container)
813{
814 BaulIconContainerDetails *details;
815
816 details = container->details;
817
818 if (details->keyboard_icon_reveal_timer_id != 0) {
819 g_source_remove (details->keyboard_icon_reveal_timer_id);
820 }
821}
822
823static void
824schedule_keyboard_icon_reveal (BaulIconContainer *container,
825 BaulIcon *icon)
826{
827 BaulIconContainerDetails *details;
828
829 details = container->details;
830
831 unschedule_keyboard_icon_reveal (container);
832
833 details->keyboard_icon_to_reveal = icon;
834 details->keyboard_icon_reveal_timer_id
835 = g_timeout_add (KEYBOARD_ICON_REVEAL_TIMEOUT10,
836 keyboard_icon_reveal_timeout_callback,
837 container);
838}
839
840static void
841clear_keyboard_focus (BaulIconContainer *container)
842{
843 if (container->details->keyboard_focus != NULL((void*)0))
844 {
845 eel_canvas_item_set (EEL_CANVAS_ITEM (container->details->keyboard_focus->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->keyboard_focus->item)), ((eel_canvas_item_get_type
()))))))
,
846 "highlighted_as_keyboard_focus", 0,
847 NULL((void*)0));
848 }
849
850 container->details->keyboard_focus = NULL((void*)0);
851}
852
853static void inline
854emit_atk_focus_state_change (BaulIcon *icon, gboolean focused)
855{
856 AtkObject *atk_object = atk_gobject_accessible_for_object (G_OBJECT (icon->item)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), (((GType) ((20) << (2))))))))
);
857 atk_object_notify_state_change (atk_object, ATK_STATE_FOCUSED, focused);
858}
859
860/* Set @icon as the icon currently selected for keyboard operations. */
861static void
862set_keyboard_focus (BaulIconContainer *container,
863 BaulIcon *icon)
864{
865 g_assert (icon != NULL)do { if (icon != ((void*)0)) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 865, ((const char*) (__func__
)), "icon != NULL"); } while (0)
;
866
867 if (icon == container->details->keyboard_focus)
868 {
869 return;
870 }
871
872 clear_keyboard_focus (container);
873
874 container->details->keyboard_focus = icon;
875
876 eel_canvas_item_set (EEL_CANVAS_ITEM (container->details->keyboard_focus->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->keyboard_focus->item)), ((eel_canvas_item_get_type
()))))))
,
877 "highlighted_as_keyboard_focus", 1,
878 NULL((void*)0));
879
880 emit_atk_focus_state_change (icon, TRUE(!(0)));
881}
882
883static void
884set_keyboard_rubberband_start (BaulIconContainer *container,
885 BaulIcon *icon)
886{
887 container->details->keyboard_rubberband_start = icon;
888}
889
890static void
891clear_keyboard_rubberband_start (BaulIconContainer *container)
892{
893 container->details->keyboard_rubberband_start = NULL((void*)0);
894}
895
896/* carbon-copy of eel_canvas_group_bounds(), but
897 * for BaulIconContainerItems it returns the
898 * bounds for the “entire item”.
899 */
900static void
901get_icon_bounds_for_canvas_bounds (EelCanvasGroup *group,
902 double *x1, double *y1,
903 double *x2, double *y2,
904 BaulIconCanvasItemBoundsUsage usage)
905{
906 EelCanvasItem *child;
907 GList *list;
908 double tx1, ty1, tx2, ty2;
909 double minx, miny, maxx, maxy;
910 int set;
911
912 /* Get the bounds of the first visible item */
913
914 child = NULL((void*)0); /* Unnecessary but eliminates a warning. */
915
916 set = FALSE(0);
917
918 for (list = group->item_list; list; list = list->next)
919 {
920 child = list->data;
921
922 if (child->flags & EEL_CANVAS_ITEM_VISIBLE)
923 {
924 set = TRUE(!(0));
925 if (!BAUL_IS_ICON_CANVAS_ITEM (child)(((__extension__ ({ GTypeInstance *__inst = (GTypeInstance*) (
(child)); GType __t = (baul_icon_canvas_item_get_type()); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))
||
926 usage == BOUNDS_USAGE_FOR_DISPLAY)
927 {
928 eel_canvas_item_get_bounds (child, &minx, &miny, &maxx, &maxy);
929 }
930 else if (usage == BOUNDS_USAGE_FOR_LAYOUT)
931 {
932 baul_icon_canvas_item_get_bounds_for_layout (BAUL_ICON_CANVAS_ITEM (child)((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((child)), (baul_icon_canvas_item_get_type()
)))))
,
933 &minx, &miny, &maxx, &maxy);
934 }
935 else if (usage == BOUNDS_USAGE_FOR_ENTIRE_ITEM)
936 {
937 baul_icon_canvas_item_get_bounds_for_entire_item (BAUL_ICON_CANVAS_ITEM (child)((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((child)), (baul_icon_canvas_item_get_type()
)))))
,
938 &minx, &miny, &maxx, &maxy);
939 }
940 else
941 {
942 g_assert_not_reached ()do { g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 942, ((const char*) (__func__)), ((void*)0)); } while (0)
;
943 }
944 break;
945 }
946 }
947
948 /* If there were no visible items, return an empty bounding box */
949
950 if (!set)
951 {
952 *x1 = *y1 = *x2 = *y2 = 0.0;
953 return;
954 }
955
956 /* Now we can grow the bounds using the rest of the items */
957
958 list = list->next;
959
960 for (; list; list = list->next)
961 {
962 child = list->data;
963
964 if (!(child->flags & EEL_CANVAS_ITEM_VISIBLE))
965 continue;
966
967 if (!BAUL_IS_ICON_CANVAS_ITEM (child)(((__extension__ ({ GTypeInstance *__inst = (GTypeInstance*) (
(child)); GType __t = (baul_icon_canvas_item_get_type()); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))
||
968 usage == BOUNDS_USAGE_FOR_DISPLAY)
969 {
970 eel_canvas_item_get_bounds (child, &tx1, &ty1, &tx2, &ty2);
971 }
972 else if (usage == BOUNDS_USAGE_FOR_LAYOUT)
973 {
974 baul_icon_canvas_item_get_bounds_for_layout (BAUL_ICON_CANVAS_ITEM (child)((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((child)), (baul_icon_canvas_item_get_type()
)))))
,
975 &tx1, &ty1, &tx2, &ty2);
976 }
977 else if (usage == BOUNDS_USAGE_FOR_ENTIRE_ITEM)
978 {
979 baul_icon_canvas_item_get_bounds_for_entire_item (BAUL_ICON_CANVAS_ITEM (child)((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((child)), (baul_icon_canvas_item_get_type()
)))))
,
980 &tx1, &ty1, &tx2, &ty2);
981 }
982 else
983 {
984 g_assert_not_reached ()do { g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 984, ((const char*) (__func__)), ((void*)0)); } while (0)
;
985 }
986
987 if (tx1 < minx)
988 minx = tx1;
989
990 if (ty1 < miny)
991 miny = ty1;
992
993 if (tx2 > maxx)
994 maxx = tx2;
995
996 if (ty2 > maxy)
997 maxy = ty2;
998 }
999
1000 /* Make the bounds be relative to our parent's coordinate system */
1001
1002 if (EEL_CANVAS_ITEM (group)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((group)), ((eel_canvas_item_get_type ()))))))
->parent)
1003 {
1004 minx += group->xpos;
1005 miny += group->ypos;
1006 maxx += group->xpos;
1007 maxy += group->ypos;
1008 }
1009
1010 if (x1 != NULL((void*)0))
1011 {
1012 *x1 = minx;
1013 }
1014
1015 if (y1 != NULL((void*)0))
1016 {
1017 *y1 = miny;
1018 }
1019
1020 if (x2 != NULL((void*)0))
1021 {
1022 *x2 = maxx;
1023 }
1024
1025 if (y2 != NULL((void*)0))
1026 {
1027 *y2 = maxy;
1028 }
1029}
1030
1031static void
1032get_all_icon_bounds (BaulIconContainer *container,
1033 double *x1, double *y1,
1034 double *x2, double *y2,
1035 BaulIconCanvasItemBoundsUsage usage)
1036{
1037 /* FIXME bugzilla.gnome.org 42477: Do we have to do something about the rubberband
1038 * here? Any other non-icon items?
1039 */
1040 get_icon_bounds_for_canvas_bounds (EEL_CANVAS_GROUP (EEL_CANVAS (container)->root)((((EelCanvasGroup*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))->root)), (
(eel_canvas_group_get_type ()))))))
,
1041 x1, y1, x2, y2, usage);
1042}
1043
1044/* Don't preserve visible white space the next time the scroll region
1045 * is recomputed when the container is not empty. */
1046void
1047baul_icon_container_reset_scroll_region (BaulIconContainer *container)
1048{
1049 container->details->reset_scroll_region_trigger = TRUE(!(0));
1050}
1051
1052/* Set a new scroll region without eliminating any of the currently-visible area. */
1053static void
1054canvas_set_scroll_region_include_visible_area (EelCanvas *canvas,
1055 double x1, double y1,
1056 double x2, double y2)
1057{
1058 double old_x1, old_y1, old_x2, old_y2;
1059 double old_scroll_x, old_scroll_y;
1060 double height, width;
1061 CtkAllocation allocation;
1062
1063 eel_canvas_get_scroll_region (canvas, &old_x1, &old_y1, &old_x2, &old_y2);
1064 ctk_widget_get_allocation (CTK_WIDGET (canvas)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((canvas)), ((ctk_widget_get_type ()))))))
, &allocation);
1065
1066 width = (allocation.width) / canvas->pixels_per_unit;
1067 height = (allocation.height) / canvas->pixels_per_unit;
1068
1069 old_scroll_x = ctk_adjustment_get_value (ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (canvas)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((canvas)), ((ctk_scrollable_get_type ()))))))
));
1070 old_scroll_y = ctk_adjustment_get_value (ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (canvas)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((canvas)), ((ctk_scrollable_get_type ()))))))
));
1071
1072 x1 = MIN (x1, old_x1 + old_scroll_x)(((x1) < (old_x1 + old_scroll_x)) ? (x1) : (old_x1 + old_scroll_x
))
;
1073 y1 = MIN (y1, old_y1 + old_scroll_y)(((y1) < (old_y1 + old_scroll_y)) ? (y1) : (old_y1 + old_scroll_y
))
;
1074 x2 = MAX (x2, old_x1 + old_scroll_x + width)(((x2) > (old_x1 + old_scroll_x + width)) ? (x2) : (old_x1
+ old_scroll_x + width))
;
1075 y2 = MAX (y2, old_y1 + old_scroll_y + height)(((y2) > (old_y1 + old_scroll_y + height)) ? (y2) : (old_y1
+ old_scroll_y + height))
;
1076
1077 eel_canvas_set_scroll_region
1078 (canvas, x1, y1, x2, y2);
1079}
1080
1081void
1082baul_icon_container_update_scroll_region (BaulIconContainer *container)
1083{
1084 double x1, y1, x2, y2;
1085 double pixels_per_unit;
1086 CtkAdjustment *hadj, *vadj;
1087 float step_increment;
1088 gboolean reset_scroll_region;
1089 CtkAllocation allocation;
1090
1091 pixels_per_unit = EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
->pixels_per_unit;
1092
1093 if (baul_icon_container_get_is_fixed_size (container))
1094 {
1095 /* Set the scroll region to the size of the container allocation */
1096 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1097 eel_canvas_set_scroll_region
1098 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
1099 (double) - container->details->left_margin / pixels_per_unit,
1100 (double) - container->details->top_margin / pixels_per_unit,
1101 ((double) (allocation.width - 1)
1102 - container->details->left_margin
1103 - container->details->right_margin)
1104 / pixels_per_unit,
1105 ((double) (allocation.height - 1)
1106 - container->details->top_margin
1107 - container->details->bottom_margin)
1108 / pixels_per_unit);
1109 return;
1110 }
1111
1112 reset_scroll_region = container->details->reset_scroll_region_trigger
1113 || baul_icon_container_is_empty (container)
1114 || baul_icon_container_is_auto_layout (container);
1115
1116 /* The trigger is only cleared when container is non-empty, so
1117 * callers can reliably reset the scroll region when an item
1118 * is added even if extraneous relayouts are called when the
1119 * window is still empty.
1120 */
1121 if (!baul_icon_container_is_empty (container))
1122 {
1123 container->details->reset_scroll_region_trigger = FALSE(0);
1124 }
1125
1126 get_all_icon_bounds (container, &x1, &y1, &x2, &y2, BOUNDS_USAGE_FOR_ENTIRE_ITEM);
1127
1128 /* Add border at the "end"of the layout (i.e. after the icons), to
1129 * ensure we get some space when scrolled to the end.
1130 * For horizontal layouts, we add a bottom border.
1131 * Vertical layout is used by the compact view so the end
1132 * depends on the RTL setting.
1133 */
1134 if (baul_icon_container_is_layout_vertical (container))
1135 {
1136 if (baul_icon_container_is_layout_rtl (container))
1137 {
1138 x1 -= ICON_PAD_LEFT4 + CONTAINER_PAD_LEFT4;
1139 }
1140 else
1141 {
1142 x2 += ICON_PAD_RIGHT4 + CONTAINER_PAD_RIGHT4;
1143 }
1144 }
1145 else
1146 {
1147 y2 += ICON_PAD_BOTTOM4 + CONTAINER_PAD_BOTTOM4;
1148 }
1149
1150 /* Auto-layout assumes a 0, 0 scroll origin and at least allocation->width.
1151 * Then we lay out to the right or to the left, so
1152 * x can be < 0 and > allocation */
1153 if (baul_icon_container_is_auto_layout (container))
1154 {
1155 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1156 x1 = MIN (x1, 0)(((x1) < (0)) ? (x1) : (0));
1157 x2 = MAX (x2, allocation.width / pixels_per_unit)(((x2) > (allocation.width / pixels_per_unit)) ? (x2) : (allocation
.width / pixels_per_unit))
;
1158 y1 = 0;
1159 }
1160 else
1161 {
1162 /* Otherwise we add the padding that is at the start of the
1163 layout */
1164 if (baul_icon_container_is_layout_rtl (container))
1165 {
1166 x2 += ICON_PAD_RIGHT4 + CONTAINER_PAD_RIGHT4;
1167 }
1168 else
1169 {
1170 x1 -= ICON_PAD_LEFT4 + CONTAINER_PAD_LEFT4;
1171 }
1172 y1 -= ICON_PAD_TOP4 + CONTAINER_PAD_TOP4;
1173 }
1174
1175 x2 -= 1;
1176 x2 = MAX(x1, x2)(((x1) > (x2)) ? (x1) : (x2));
1177
1178 y2 -= 1;
1179 y2 = MAX(y1, y2)(((y1) > (y2)) ? (y1) : (y2));
1180
1181 if (reset_scroll_region)
1182 {
1183 eel_canvas_set_scroll_region
1184 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
1185 x1, y1, x2, y2);
1186 }
1187 else
1188 {
1189 canvas_set_scroll_region_include_visible_area
1190 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
1191 x1, y1, x2, y2);
1192 }
1193
1194 hadj = ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
1195 vadj = ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
1196
1197 /* Scroll by 1/4 icon each time you click. */
1198 step_increment = baul_get_icon_size_for_zoom_level
1199 (container->details->zoom_level) / 4;
1200 if (ctk_adjustment_get_step_increment (hadj) != step_increment)
1201 {
1202 ctk_adjustment_set_step_increment (hadj, step_increment);
1203 }
1204 if (ctk_adjustment_get_step_increment (vadj) != step_increment)
1205 {
1206 ctk_adjustment_set_step_increment (vadj, step_increment);
1207 }
1208}
1209
1210static int
1211compare_icons (gconstpointer a, gconstpointer b, gpointer icon_container)
1212{
1213 BaulIconContainerClass *klass;
1214 const BaulIcon *icon_a, *icon_b;
1215
1216 icon_a = a;
1217 icon_b = b;
1218 klass = BAUL_ICON_CONTAINER_GET_CLASS (icon_container)((((BaulIconContainerClass*) (((GTypeInstance*) ((icon_container
)))->g_class))))
;
1219
1220 return klass->compare_icons (icon_container, icon_a->data, icon_b->data);
1221}
1222
1223static void
1224sort_icons (BaulIconContainer *container,
1225 GList **icons)
1226{
1227 BaulIconContainerClass *klass;
1228
1229 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
1230 g_assert (klass->compare_icons != NULL)do { if (klass->compare_icons != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 1230, ((const char*)
(__func__)), "klass->compare_icons != NULL"); } while (0)
;
1231
1232 *icons = g_list_sort_with_data (*icons, compare_icons, container);
1233}
1234
1235static void
1236resort (BaulIconContainer *container)
1237{
1238 sort_icons (container, &container->details->icons);
1239}
1240
1241typedef struct
1242{
1243 double width;
1244 double height;
1245 double x_offset;
1246 double y_offset;
1247} IconPositions;
1248
1249static void
1250lay_down_one_line (BaulIconContainer *container,
1251 GList *line_start,
1252 GList *line_end,
1253 double y,
1254 double max_height,
1255 GArray *positions,
1256 gboolean whole_text)
1257{
1258 GList *p;
1259 double x, y_offset;
1260 IconPositions *position;
1261 int i;
1262 gboolean is_rtl;
1263 BaulIcon *icon = NULL((void*)0);
1264
1265 is_rtl = baul_icon_container_is_layout_rtl (container);
1266
1267 /* Lay out the icons along the baseline. */
1268 x = ICON_PAD_LEFT4;
1269 i = 0;
1270 for (p = line_start; p != line_end; p = p->next)
1271 {
1272 icon = p->data;
1273
1274 position = &g_array_index (positions, IconPositions, i++)(((IconPositions*) (void *) (positions)->data) [(i++)]);
1275
1276 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
1277 {
1278 y_offset = (max_height - position->height) / 2;
1279 }
1280 else
1281 {
1282 y_offset = position->y_offset;
1283 }
1284
1285 icon_set_position
1286 (icon,
1287 is_rtl ? get_mirror_x_position (container, icon, x + position->x_offset) : x + position->x_offset,
1288 y + y_offset);
1289 baul_icon_canvas_item_set_entire_text (icon->item, whole_text);
1290
1291 icon->saved_ltr_x = is_rtl ? get_mirror_x_position (container, icon, icon->x) : icon->x;
1292
1293 x += position->width;
1294 }
1295}
1296
1297static void
1298lay_down_one_column (BaulIconContainer *container,
1299 GList *line_start,
1300 GList *line_end,
1301 double x,
1302 double y_start,
1303 double y_iter,
1304 GArray *positions)
1305{
1306 GList *p;
1307 double y;
1308 int i;
1309 gboolean is_rtl;
1310 IconPositions *position = NULL((void*)0);
1311 BaulIcon *icon = NULL((void*)0);
1312
1313 is_rtl = baul_icon_container_is_layout_rtl (container);
1314
1315 /* Lay out the icons along the baseline. */
1316 y = y_start;
1317 i = 0;
1318 for (p = line_start; p != line_end; p = p->next)
1319 {
1320 icon = p->data;
1321
1322 position = &g_array_index (positions, IconPositions, i++)(((IconPositions*) (void *) (positions)->data) [(i++)]);
1323
1324 icon_set_position
1325 (icon,
1326 is_rtl ? get_mirror_x_position (container, icon, x + position->x_offset) : x + position->x_offset,
1327 y + position->y_offset);
1328
1329 icon->saved_ltr_x = is_rtl ? get_mirror_x_position (container, icon, icon->x) : icon->x;
1330
1331 y += y_iter;
1332 }
1333}
1334
1335static void
1336lay_down_icons_horizontal (BaulIconContainer *container,
1337 GList *icons,
1338 double start_y)
1339{
1340 GList *p, *line_start;
1341 BaulIcon *icon;
1342 double canvas_width, y;
1343 EelDRect bounds;
1344 EelDRect icon_bounds;
1345 EelDRect text_bounds;
1346 double max_height_above, max_height_below;
1347 double line_width;
1348 gboolean gridded_layout;
1349 double grid_width;
1350 double max_text_width, max_icon_width;
1351 int icon_width;
1352 int i;
1353 CtkAllocation allocation;
1354 GArray *positions;
1355 IconPositions *position = NULL((void*)0);
1356
1357 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1357, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
1358
1359 if (icons == NULL((void*)0))
1360 {
1361 return;
1362 }
1363
1364 positions = g_array_new (FALSE(0), FALSE(0), sizeof (IconPositions));
1365 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1366
1367 /* Lay out icons a line at a time. */
1368 canvas_width = CANVAS_WIDTH(container, allocation)((allocation.width - container->details->left_margin - container
->details->right_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1369 max_icon_width = max_text_width = 0.0;
1370
1371 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
1372 {
1373 /* Would it be worth caching these bounds for the next loop? */
1374 for (p = icons; p != NULL((void*)0); p = p->next)
1375 {
1376 icon = p->data;
1377
1378 icon_bounds = baul_icon_canvas_item_get_icon_rectangle (icon->item);
1379 max_icon_width = MAX (max_icon_width, ceil (icon_bounds.x1 - icon_bounds.x0))(((max_icon_width) > (ceil (icon_bounds.x1 - icon_bounds.x0
))) ? (max_icon_width) : (ceil (icon_bounds.x1 - icon_bounds.
x0)))
;
1380
1381 text_bounds = baul_icon_canvas_item_get_text_rectangle (icon->item, TRUE(!(0)));
1382 max_text_width = MAX (max_text_width, ceil (text_bounds.x1 - text_bounds.x0))(((max_text_width) > (ceil (text_bounds.x1 - text_bounds.x0
))) ? (max_text_width) : (ceil (text_bounds.x1 - text_bounds.
x0)))
;
1383 }
1384
1385 grid_width = max_icon_width + max_text_width + ICON_PAD_LEFT4 + ICON_PAD_RIGHT4;
1386 }
1387 else
1388 {
1389 grid_width = STANDARD_ICON_GRID_WIDTH155;
1390 }
1391
1392 gridded_layout = !baul_icon_container_is_tighter_layout (container);
1393
1394 line_width = container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE ? ICON_PAD_LEFT4 : 0;
1395 line_start = icons;
1396 y = start_y + CONTAINER_PAD_TOP4;
1397 i = 0;
1398
1399 max_height_above = 0;
1400 max_height_below = 0;
1401 for (p = icons; p != NULL((void*)0); p = p->next)
1402 {
1403 double height_above, height_below;
1404
1405 icon = p->data;
1406
1407 /* Assume it's only one level hierarchy to avoid costly affine calculations */
1408 baul_icon_canvas_item_get_bounds_for_layout (icon->item,
1409 &bounds.x0, &bounds.y0,
1410 &bounds.x1, &bounds.y1);
1411
1412 icon_bounds = baul_icon_canvas_item_get_icon_rectangle (icon->item);
1413 text_bounds = baul_icon_canvas_item_get_text_rectangle (icon->item, TRUE(!(0)));
1414
1415 if (gridded_layout)
1416 {
1417 icon_width = ceil ((bounds.x1 - bounds.x0)/grid_width) * grid_width;
1418
1419
1420 }
1421 else
1422 {
1423 icon_width = (bounds.x1 - bounds.x0) + ICON_PAD_RIGHT4 + 8; /* 8 pixels extra for fancy selection box */
1424 }
1425
1426 /* Calculate size above/below baseline */
1427 height_above = icon_bounds.y1 - bounds.y0;
1428 height_below = bounds.y1 - icon_bounds.y1;
1429
1430 /* If this icon doesn't fit, it's time to lay out the line that's queued up. */
1431 if (line_start != p && line_width + icon_width >= canvas_width )
1432 {
1433 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
1434 {
1435 y += ICON_PAD_TOP4;
1436 }
1437 else
1438 {
1439 /* Advance to the baseline. */
1440 y += ICON_PAD_TOP4 + max_height_above;
1441 }
1442
1443 lay_down_one_line (container, line_start, p, y, max_height_above, positions, FALSE(0));
1444
1445 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
1446 {
1447 y += max_height_above + max_height_below + ICON_PAD_BOTTOM4;
1448 }
1449 else
1450 {
1451 /* Advance to next line. */
1452 y += max_height_below + ICON_PAD_BOTTOM4;
1453 }
1454
1455 line_width = container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE ? ICON_PAD_LEFT4 : 0;
1456 line_start = p;
1457 i = 0;
1458
1459 max_height_above = height_above;
1460 max_height_below = height_below;
1461 }
1462 else
1463 {
1464 if (height_above > max_height_above)
1465 {
1466 max_height_above = height_above;
1467 }
1468 if (height_below > max_height_below)
1469 {
1470 max_height_below = height_below;
1471 }
1472 }
1473
1474 g_array_set_size (positions, i + 1);
1475 position = &g_array_index (positions, IconPositions, i++)(((IconPositions*) (void *) (positions)->data) [(i++)]);
1476 position->width = icon_width;
1477 position->height = icon_bounds.y1 - icon_bounds.y0;
1478
1479 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
1480 {
1481 if (gridded_layout)
1482 {
1483 position->x_offset = max_icon_width + ICON_PAD_LEFT4 + ICON_PAD_RIGHT4 - (icon_bounds.x1 - icon_bounds.x0);
1484 }
1485 else
1486 {
1487 position->x_offset = icon_width - ((icon_bounds.x1 - icon_bounds.x0) + (text_bounds.x1 - text_bounds.x0));
1488 }
1489 position->y_offset = 0;
1490 }
1491 else
1492 {
1493 position->x_offset = (icon_width - (icon_bounds.x1 - icon_bounds.x0)) / 2;
1494 position->y_offset = icon_bounds.y0 - icon_bounds.y1;
1495 }
1496
1497 /* Add this icon. */
1498 line_width += icon_width;
1499 }
1500
1501 /* Lay down that last line of icons. */
1502 if (line_start != NULL((void*)0))
1503 {
1504 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
1505 {
1506 y += ICON_PAD_TOP4;
1507 }
1508 else
1509 {
1510 /* Advance to the baseline. */
1511 y += ICON_PAD_TOP4 + max_height_above;
1512 }
1513
1514 lay_down_one_line (container, line_start, NULL((void*)0), y, max_height_above, positions, TRUE(!(0)));
1515
1516 /* Advance to next line. */
1517 y += max_height_below + ICON_PAD_BOTTOM4;
Value stored to 'y' is never read
1518 }
1519
1520 g_array_free (positions, TRUE(!(0)));
1521}
1522
1523static void
1524get_max_icon_dimensions (GList *icon_start,
1525 GList *icon_end,
1526 double *max_icon_width,
1527 double *max_icon_height,
1528 double *max_text_width,
1529 double *max_text_height,
1530 double *max_bounds_height)
1531{
1532 EelDRect icon_bounds;
1533 EelDRect text_bounds;
1534 GList *p;
1535 double y1, y2;
1536 BaulIcon *icon = NULL((void*)0);
1537
1538 *max_icon_width = *max_text_width = 0.0;
1539 *max_icon_height = *max_text_height = 0.0;
1540 *max_bounds_height = 0.0;
1541
1542 /* Would it be worth caching these bounds for the next loop? */
1543 for (p = icon_start; p != icon_end; p = p->next)
1544 {
1545 icon = p->data;
1546
1547 icon_bounds = baul_icon_canvas_item_get_icon_rectangle (icon->item);
1548 *max_icon_width = MAX (*max_icon_width, ceil (icon_bounds.x1 - icon_bounds.x0))(((*max_icon_width) > (ceil (icon_bounds.x1 - icon_bounds.
x0))) ? (*max_icon_width) : (ceil (icon_bounds.x1 - icon_bounds
.x0)))
;
1549 *max_icon_height = MAX (*max_icon_height, ceil (icon_bounds.y1 - icon_bounds.y0))(((*max_icon_height) > (ceil (icon_bounds.y1 - icon_bounds
.y0))) ? (*max_icon_height) : (ceil (icon_bounds.y1 - icon_bounds
.y0)))
;
1550
1551 text_bounds = baul_icon_canvas_item_get_text_rectangle (icon->item, TRUE(!(0)));
1552 *max_text_width = MAX (*max_text_width, ceil (text_bounds.x1 - text_bounds.x0))(((*max_text_width) > (ceil (text_bounds.x1 - text_bounds.
x0))) ? (*max_text_width) : (ceil (text_bounds.x1 - text_bounds
.x0)))
;
1553 *max_text_height = MAX (*max_text_height, ceil (text_bounds.y1 - text_bounds.y0))(((*max_text_height) > (ceil (text_bounds.y1 - text_bounds
.y0))) ? (*max_text_height) : (ceil (text_bounds.y1 - text_bounds
.y0)))
;
1554
1555 baul_icon_canvas_item_get_bounds_for_layout (icon->item,
1556 NULL((void*)0), &y1,
1557 NULL((void*)0), &y2);
1558 *max_bounds_height = MAX (*max_bounds_height, y2 - y1)(((*max_bounds_height) > (y2 - y1)) ? (*max_bounds_height)
: (y2 - y1))
;
1559 }
1560}
1561
1562/* column-wise layout. At the moment, this only works with label-beside-icon (used by "Compact View"). */
1563static void
1564lay_down_icons_vertical (BaulIconContainer *container,
1565 GList *icons,
1566 double start_y G_GNUC_UNUSED__attribute__ ((__unused__)))
1567{
1568 GList *p, *line_start;
1569 double x, canvas_height;
1570 GArray *positions;
1571 IconPositions *position;
1572 EelDRect icon_bounds;
1573 EelDRect text_bounds;
1574 CtkAllocation allocation;
1575
1576 double line_height;
1577
1578 double max_height;
1579 double max_height_with_borders;
1580 double max_width;
1581 double max_width_in_column;
1582
1583 double max_bounds_height;
1584 double max_bounds_height_with_borders;
1585
1586 double max_text_width, max_icon_width;
1587 double max_text_height, max_icon_height;
1588 int i;
1589
1590 BaulIcon *icon = NULL((void*)0);
1591
1592 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1592, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
1593 g_assert (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)do { if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1593, ((const char*) (__func__)), "container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE"
); } while (0)
;
1594
1595 if (icons == NULL((void*)0))
1596 {
1597 return;
1598 }
1599
1600 positions = g_array_new (FALSE(0), FALSE(0), sizeof (IconPositions));
1601 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1602
1603 /* Lay out icons a column at a time. */
1604 canvas_height = CANVAS_HEIGHT(container, allocation)((allocation.height - container->details->top_margin - container
->details->bottom_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1605
1606 max_icon_width = max_text_width = 0.0;
1607 max_icon_height = max_text_height = 0.0;
1608 max_bounds_height = 0.0;
1609
1610 get_max_icon_dimensions (icons, NULL((void*)0),
1611 &max_icon_width, &max_icon_height,
1612 &max_text_width, &max_text_height,
1613 &max_bounds_height);
1614
1615 max_width = max_icon_width + max_text_width;
1616 max_height = MAX (max_icon_height, max_text_height)(((max_icon_height) > (max_text_height)) ? (max_icon_height
) : (max_text_height))
;
1617 max_height_with_borders = ICON_PAD_TOP4 + max_height;
1618
1619 max_bounds_height_with_borders = ICON_PAD_TOP4 + max_bounds_height;
1620
1621 line_height = ICON_PAD_TOP4;
1622 line_start = icons;
1623 x = 0;
1624 i = 0;
1625
1626 max_width_in_column = 0.0;
1627
1628 for (p = icons; p != NULL((void*)0); p = p->next)
1629 {
1630 int height;
1631
1632 icon = p->data;
1633
1634 /* If this icon doesn't fit, it's time to lay out the column that's queued up. */
1635
1636 /* We use the bounds height here, since for wrapping we also want to consider
1637 * overlapping emblems at the bottom. We may wrap a little bit too early since
1638 * the icon with the max. bounds height may actually not be in the last row, but
1639 * it is better than visual glitches
1640 */
1641 if (line_start != p && line_height + (max_bounds_height_with_borders-1) >= canvas_height )
1642 {
1643 x += ICON_PAD_LEFT4;
1644
1645 /* correctly set (per-column) width */
1646 if (!container->details->all_columns_same_width)
1647 {
1648 for (i = 0; i < (int) positions->len; i++)
1649 {
1650 position = &g_array_index (positions, IconPositions, i)(((IconPositions*) (void *) (positions)->data) [(i)]);
1651 position->width = max_width_in_column;
1652 }
1653 }
1654
1655 lay_down_one_column (container, line_start, p, x, CONTAINER_PAD_TOP4, max_height_with_borders, positions);
1656
1657 /* Advance to next column. */
1658 if (container->details->all_columns_same_width)
1659 {
1660 x += max_width + ICON_PAD_RIGHT4;
1661 }
1662 else
1663 {
1664 x += max_width_in_column + ICON_PAD_RIGHT4;
1665 }
1666
1667 line_height = ICON_PAD_TOP4;
1668 line_start = p;
1669 i = 0;
1670
1671 max_width_in_column = 0;
1672 }
1673
1674 icon_bounds = baul_icon_canvas_item_get_icon_rectangle (icon->item);
1675 text_bounds = baul_icon_canvas_item_get_text_rectangle (icon->item, TRUE(!(0)));
1676
1677 max_width_in_column = MAX (max_width_in_column,(((max_width_in_column) > (ceil (icon_bounds.x1 - icon_bounds
.x0) + ceil (text_bounds.x1 - text_bounds.x0))) ? (max_width_in_column
) : (ceil (icon_bounds.x1 - icon_bounds.x0) + ceil (text_bounds
.x1 - text_bounds.x0)))
1678 ceil (icon_bounds.x1 - icon_bounds.x0) +(((max_width_in_column) > (ceil (icon_bounds.x1 - icon_bounds
.x0) + ceil (text_bounds.x1 - text_bounds.x0))) ? (max_width_in_column
) : (ceil (icon_bounds.x1 - icon_bounds.x0) + ceil (text_bounds
.x1 - text_bounds.x0)))
1679 ceil (text_bounds.x1 - text_bounds.x0))(((max_width_in_column) > (ceil (icon_bounds.x1 - icon_bounds
.x0) + ceil (text_bounds.x1 - text_bounds.x0))) ? (max_width_in_column
) : (ceil (icon_bounds.x1 - icon_bounds.x0) + ceil (text_bounds
.x1 - text_bounds.x0)))
;
1680
1681 g_array_set_size (positions, i + 1);
1682 position = &g_array_index (positions, IconPositions, i++)(((IconPositions*) (void *) (positions)->data) [(i++)]);
1683 if (container->details->all_columns_same_width)
1684 {
1685 position->width = max_width;
1686 }
1687 position->height = max_height;
1688 position->y_offset = ICON_PAD_TOP4;
1689 position->x_offset = ICON_PAD_LEFT4;
1690
1691 position->x_offset += max_icon_width - ceil (icon_bounds.x1 - icon_bounds.x0);
1692
1693 height = MAX (ceil (icon_bounds.y1 - icon_bounds.y0), ceil(text_bounds.y1 - text_bounds.y0))(((ceil (icon_bounds.y1 - icon_bounds.y0)) > (ceil(text_bounds
.y1 - text_bounds.y0))) ? (ceil (icon_bounds.y1 - icon_bounds
.y0)) : (ceil(text_bounds.y1 - text_bounds.y0)))
;
1694 position->y_offset += (max_height - height) / 2;
1695
1696 /* Add this icon. */
1697 line_height += max_height_with_borders;
1698 }
1699
1700 /* Lay down that last column of icons. */
1701 if (line_start != NULL((void*)0))
1702 {
1703 x += ICON_PAD_LEFT4;
1704 lay_down_one_column (container, line_start, NULL((void*)0), x, CONTAINER_PAD_TOP4, max_height_with_borders, positions);
1705 }
1706
1707 g_array_free (positions, TRUE(!(0)));
1708}
1709
1710static void
1711snap_position (BaulIconContainer *container,
1712 BaulIcon *icon,
1713 int *x, int *y)
1714{
1715 int center_x;
1716 int baseline_y;
1717 int icon_width;
1718 int icon_height;
1719 int total_width;
1720 int total_height;
1721 EelDRect icon_position;
1722 CtkAllocation allocation;
1723
1724 icon_position = baul_icon_canvas_item_get_icon_rectangle (icon->item);
1725 icon_width = icon_position.x1 - icon_position.x0;
1726 icon_height = icon_position.y1 - icon_position.y0;
1727
1728 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1729 total_width = CANVAS_WIDTH (container, allocation)((allocation.width - container->details->left_margin - container
->details->right_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1730 total_height = CANVAS_HEIGHT (container, allocation)((allocation.height - container->details->top_margin - container
->details->bottom_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1731
1732 if (baul_icon_container_is_layout_rtl (container))
1733 *x = get_mirror_x_position (container, icon, *x);
1734
1735 if (*x + icon_width / 2 < DESKTOP_PAD_HORIZONTAL10 + SNAP_SIZE_X78)
1736 {
1737 *x = DESKTOP_PAD_HORIZONTAL10 + SNAP_SIZE_X78 - icon_width / 2;
1738 }
1739
1740 if (*x + icon_width / 2 > total_width - (DESKTOP_PAD_HORIZONTAL10 + SNAP_SIZE_X78))
1741 {
1742 *x = total_width - (DESKTOP_PAD_HORIZONTAL10 + SNAP_SIZE_X78 + (icon_width / 2));
1743 }
1744
1745 if (*y + icon_height < DESKTOP_PAD_VERTICAL10 + SNAP_SIZE_Y20)
1746 {
1747 *y = DESKTOP_PAD_VERTICAL10 + SNAP_SIZE_Y20 - icon_height;
1748 }
1749
1750 if (*y + icon_height > total_height - (DESKTOP_PAD_VERTICAL10 + SNAP_SIZE_Y20))
1751 {
1752 *y = total_height - (DESKTOP_PAD_VERTICAL10 + SNAP_SIZE_Y20 + (icon_height / 2));
1753 }
1754
1755 center_x = *x + icon_width / 2;
1756 *x = SNAP_NEAREST_HORIZONTAL (center_x)((eel_round ((double)((center_x) - 10) / 78) * 78) + 10) - (icon_width / 2);
1757 if (baul_icon_container_is_layout_rtl (container))
1758 {
1759 *x = get_mirror_x_position (container, icon, *x);
1760 }
1761
1762
1763 /* Find the grid position vertically and place on the proper baseline */
1764 baseline_y = *y + icon_height;
1765 baseline_y = SNAP_NEAREST_VERTICAL (baseline_y)((eel_round ((double)((baseline_y) - 10) / 20) * 20) + 10);
1766 *y = baseline_y - icon_height;
1767}
1768
1769static int
1770compare_icons_by_position (gconstpointer a, gconstpointer b)
1771{
1772 BaulIcon *icon_a, *icon_b;
1773 int x1, y1, x2, y2;
1774 int center_a;
1775 int center_b;
1776
1777 icon_a = (BaulIcon*)a;
1778 icon_b = (BaulIcon*)b;
1779
1780 icon_get_bounding_box (icon_a, &x1, &y1, &x2, &y2,
1781 BOUNDS_USAGE_FOR_DISPLAY);
1782 center_a = x1 + (x2 - x1) / 2;
1783 icon_get_bounding_box (icon_b, &x1, &y1, &x2, &y2,
1784 BOUNDS_USAGE_FOR_DISPLAY);
1785 center_b = x1 + (x2 - x1) / 2;
1786
1787 return center_a == center_b ?
1788 icon_a->y - icon_b->y :
1789 center_a - center_b;
1790}
1791
1792static PlacementGrid *
1793placement_grid_new (BaulIconContainer *container, gboolean tight)
1794{
1795 PlacementGrid *grid;
1796 int width, height;
1797 int num_columns;
1798 int num_rows;
1799 int i;
1800 CtkAllocation allocation;
1801
1802 /* Get container dimensions */
1803 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1804 width = CANVAS_WIDTH(container, allocation)((allocation.width - container->details->left_margin - container
->details->right_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1805 height = CANVAS_HEIGHT(container, allocation)((allocation.height - container->details->top_margin - container
->details->bottom_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1806
1807 num_columns = width / SNAP_SIZE_X78;
1808 num_rows = height / SNAP_SIZE_Y20;
1809
1810 if (num_columns == 0 || num_rows == 0)
1811 {
1812 return NULL((void*)0);
1813 }
1814
1815 grid = g_new0 (PlacementGrid, 1)((PlacementGrid *) g_malloc0_n ((1), sizeof (PlacementGrid)));
1816 grid->tight = tight;
1817 grid->num_columns = num_columns;
1818 grid->num_rows = num_rows;
1819
1820 grid->grid_memory = g_new0 (int, (num_rows * num_columns))((int *) g_malloc0_n (((num_rows * num_columns)), sizeof (int
)))
;
1821 grid->icon_grid = g_new0 (int *, num_columns)((int * *) g_malloc0_n ((num_columns), sizeof (int *)));
1822
1823 for (i = 0; i < num_columns; i++)
1824 {
1825 grid->icon_grid[i] = grid->grid_memory + (i * num_rows);
1826 }
1827
1828 return grid;
1829}
1830
1831static void
1832placement_grid_free (PlacementGrid *grid)
1833{
1834 g_free (grid->icon_grid);
1835 g_free (grid->grid_memory);
1836 g_free (grid);
1837}
1838
1839static gboolean
1840placement_grid_position_is_free (PlacementGrid *grid, EelIRect pos)
1841{
1842 int x, y;
1843
1844 g_assert (pos.x0 >= 0 && pos.x0 < grid->num_columns)do { if (pos.x0 >= 0 && pos.x0 < grid->num_columns
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1844, ((const char*) (__func__)), "pos.x0 >= 0 && pos.x0 < grid->num_columns"
); } while (0)
;
1845 g_assert (pos.y0 >= 0 && pos.y0 < grid->num_rows)do { if (pos.y0 >= 0 && pos.y0 < grid->num_rows
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1845, ((const char*) (__func__)), "pos.y0 >= 0 && pos.y0 < grid->num_rows"
); } while (0)
;
1846 g_assert (pos.x1 >= 0 && pos.x1 < grid->num_columns)do { if (pos.x1 >= 0 && pos.x1 < grid->num_columns
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1846, ((const char*) (__func__)), "pos.x1 >= 0 && pos.x1 < grid->num_columns"
); } while (0)
;
1847 g_assert (pos.y1 >= 0 && pos.y1 < grid->num_rows)do { if (pos.y1 >= 0 && pos.y1 < grid->num_rows
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1847, ((const char*) (__func__)), "pos.y1 >= 0 && pos.y1 < grid->num_rows"
); } while (0)
;
1848
1849 for (x = pos.x0; x <= pos.x1; x++)
1850 {
1851 for (y = pos.y0; y <= pos.y1; y++)
1852 {
1853 if (grid->icon_grid[x][y] != 0)
1854 {
1855 return FALSE(0);
1856 }
1857 }
1858 }
1859
1860 return TRUE(!(0));
1861}
1862
1863static void
1864placement_grid_mark (PlacementGrid *grid, EelIRect pos)
1865{
1866 int x, y;
1867
1868 g_assert (pos.x0 >= 0 && pos.x0 < grid->num_columns)do { if (pos.x0 >= 0 && pos.x0 < grid->num_columns
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1868, ((const char*) (__func__)), "pos.x0 >= 0 && pos.x0 < grid->num_columns"
); } while (0)
;
1869 g_assert (pos.y0 >= 0 && pos.y0 < grid->num_rows)do { if (pos.y0 >= 0 && pos.y0 < grid->num_rows
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1869, ((const char*) (__func__)), "pos.y0 >= 0 && pos.y0 < grid->num_rows"
); } while (0)
;
1870 g_assert (pos.x1 >= 0 && pos.x1 < grid->num_columns)do { if (pos.x1 >= 0 && pos.x1 < grid->num_columns
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1870, ((const char*) (__func__)), "pos.x1 >= 0 && pos.x1 < grid->num_columns"
); } while (0)
;
1871 g_assert (pos.y1 >= 0 && pos.y1 < grid->num_rows)do { if (pos.y1 >= 0 && pos.y1 < grid->num_rows
) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 1871, ((const char*) (__func__)), "pos.y1 >= 0 && pos.y1 < grid->num_rows"
); } while (0)
;
1872
1873 for (x = pos.x0; x <= pos.x1; x++)
1874 {
1875 for (y = pos.y0; y <= pos.y1; y++)
1876 {
1877 grid->icon_grid[x][y] = 1;
1878 }
1879 }
1880}
1881
1882static void
1883canvas_position_to_grid_position (PlacementGrid *grid,
1884 EelIRect canvas_position,
1885 EelIRect *grid_position)
1886{
1887 /* The first causes minimal moving around during a snap, but
1888 * can end up with partially overlapping icons. The second one won't
1889 * allow any overlapping, but can cause more movement to happen
1890 * during a snap. */
1891 if (grid->tight)
1892 {
1893 grid_position->x0 = ceil ((double)(canvas_position.x0 - DESKTOP_PAD_HORIZONTAL10) / SNAP_SIZE_X78);
1894 grid_position->y0 = ceil ((double)(canvas_position.y0 - DESKTOP_PAD_VERTICAL10) / SNAP_SIZE_Y20);
1895 grid_position->x1 = floor ((double)(canvas_position.x1 - DESKTOP_PAD_HORIZONTAL10) / SNAP_SIZE_X78);
1896 grid_position->y1 = floor ((double)(canvas_position.y1 - DESKTOP_PAD_VERTICAL10) / SNAP_SIZE_Y20);
1897 }
1898 else
1899 {
1900 grid_position->x0 = floor ((double)(canvas_position.x0 - DESKTOP_PAD_HORIZONTAL10) / SNAP_SIZE_X78);
1901 grid_position->y0 = floor ((double)(canvas_position.y0 - DESKTOP_PAD_VERTICAL10) / SNAP_SIZE_Y20);
1902 grid_position->x1 = floor ((double)(canvas_position.x1 - DESKTOP_PAD_HORIZONTAL10) / SNAP_SIZE_X78);
1903 grid_position->y1 = floor ((double)(canvas_position.y1 - DESKTOP_PAD_VERTICAL10) / SNAP_SIZE_Y20);
1904 }
1905
1906 grid_position->x0 = CLAMP (grid_position->x0, 0, grid->num_columns - 1)(((grid_position->x0) > (grid->num_columns - 1)) ? (
grid->num_columns - 1) : (((grid_position->x0) < (0)
) ? (0) : (grid_position->x0)))
;
1907 grid_position->y0 = CLAMP (grid_position->y0, 0, grid->num_rows - 1)(((grid_position->y0) > (grid->num_rows - 1)) ? (grid
->num_rows - 1) : (((grid_position->y0) < (0)) ? (0)
: (grid_position->y0)))
;
1908 grid_position->x1 = CLAMP (grid_position->x1, grid_position->x0, grid->num_columns - 1)(((grid_position->x1) > (grid->num_columns - 1)) ? (
grid->num_columns - 1) : (((grid_position->x1) < (grid_position
->x0)) ? (grid_position->x0) : (grid_position->x1)))
;
1909 grid_position->y1 = CLAMP (grid_position->y1, grid_position->y0, grid->num_rows - 1)(((grid_position->y1) > (grid->num_rows - 1)) ? (grid
->num_rows - 1) : (((grid_position->y1) < (grid_position
->y0)) ? (grid_position->y0) : (grid_position->y1)))
;
1910}
1911
1912static void
1913placement_grid_mark_icon (PlacementGrid *grid, BaulIcon *icon)
1914{
1915 EelIRect icon_pos;
1916 EelIRect grid_pos;
1917
1918 icon_get_bounding_box (icon,
1919 &icon_pos.x0, &icon_pos.y0,
1920 &icon_pos.x1, &icon_pos.y1,
1921 BOUNDS_USAGE_FOR_LAYOUT);
1922 canvas_position_to_grid_position (grid,
1923 icon_pos,
1924 &grid_pos);
1925 placement_grid_mark (grid, grid_pos);
1926}
1927
1928static void
1929find_empty_location (BaulIconContainer *container,
1930 PlacementGrid *grid,
1931 BaulIcon *icon,
1932 int start_x,
1933 int start_y,
1934 int *x,
1935 int *y)
1936{
1937 double icon_width, icon_height;
1938 int canvas_width;
1939 int canvas_height;
1940 int height_for_bound_check;
1941 EelIRect icon_position;
1942 EelDRect pixbuf_rect;
1943 gboolean collision;
1944 CtkAllocation allocation;
1945
1946 /* Get container dimensions */
1947 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
1948 canvas_width = CANVAS_WIDTH(container, allocation)((allocation.width - container->details->left_margin - container
->details->right_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1949 canvas_height = CANVAS_HEIGHT(container, allocation)((allocation.height - container->details->top_margin - container
->details->bottom_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
1950
1951 icon_get_bounding_box (icon,
1952 &icon_position.x0, &icon_position.y0,
1953 &icon_position.x1, &icon_position.y1,
1954 BOUNDS_USAGE_FOR_LAYOUT);
1955 icon_width = icon_position.x1 - icon_position.x0;
1956 icon_height = icon_position.y1 - icon_position.y0;
1957
1958 icon_get_bounding_box (icon,
1959 NULL((void*)0), &icon_position.y0,
1960 NULL((void*)0), &icon_position.y1,
1961 BOUNDS_USAGE_FOR_ENTIRE_ITEM);
1962 height_for_bound_check = icon_position.y1 - icon_position.y0;
1963
1964 pixbuf_rect = baul_icon_canvas_item_get_icon_rectangle (icon->item);
1965
1966 /* Start the icon on a grid location */
1967 snap_position (container, icon, &start_x, &start_y);
1968
1969 icon_position.x0 = start_x;
1970 icon_position.y0 = start_y;
1971 icon_position.x1 = icon_position.x0 + icon_width;
1972 icon_position.y1 = icon_position.y0 + icon_height;
1973
1974 do
1975 {
1976 EelIRect grid_position;
1977 gboolean need_new_column;
1978
1979 collision = FALSE(0);
1980
1981 canvas_position_to_grid_position (grid,
1982 icon_position,
1983 &grid_position);
1984
1985 need_new_column = icon_position.y0 + height_for_bound_check + DESKTOP_PAD_VERTICAL10 > canvas_height;
1986
1987 if (need_new_column ||
1988 !placement_grid_position_is_free (grid, grid_position))
1989 {
1990 icon_position.y0 += SNAP_SIZE_Y20;
1991 icon_position.y1 = icon_position.y0 + icon_height;
1992
1993 if (need_new_column)
1994 {
1995 /* Move to the next column */
1996 icon_position.y0 = DESKTOP_PAD_VERTICAL10 + SNAP_SIZE_Y20 - (pixbuf_rect.y1 - pixbuf_rect.y0);
1997 while (icon_position.y0 < DESKTOP_PAD_VERTICAL10)
1998 {
1999 icon_position.y0 += SNAP_SIZE_Y20;
2000 }
2001 icon_position.y1 = icon_position.y0 + icon_height;
2002
2003 icon_position.x0 += SNAP_SIZE_X78;
2004 icon_position.x1 = icon_position.x0 + icon_width;
2005 }
2006
2007 collision = TRUE(!(0));
2008 }
2009 }
2010 while (collision && (icon_position.x1 < canvas_width));
2011
2012 *x = icon_position.x0;
2013 *y = icon_position.y0;
2014}
2015
2016static void
2017align_icons (BaulIconContainer *container)
2018{
2019 GList *unplaced_icons;
2020 GList *l;
2021 PlacementGrid *grid;
2022
2023 unplaced_icons = g_list_copy (container->details->icons);
2024
2025 unplaced_icons = g_list_sort (unplaced_icons,
2026 compare_icons_by_position);
2027
2028 if (baul_icon_container_is_layout_rtl (container))
2029 {
2030 unplaced_icons = g_list_reverse (unplaced_icons);
2031 }
2032
2033 grid = placement_grid_new (container, TRUE(!(0)));
2034
2035 if (!grid)
2036 {
2037 g_list_free (unplaced_icons);
2038 return;
2039 }
2040
2041 for (l = unplaced_icons; l != NULL((void*)0); l = l->next)
2042 {
2043 BaulIcon *icon;
2044 int x, y;
2045
2046 icon = l->data;
2047 x = icon->saved_ltr_x;
2048 y = icon->y;
2049 find_empty_location (container, grid,
2050 icon, x, y, &x, &y);
2051
2052 icon_set_position (icon, x, y);
2053 icon->saved_ltr_x = icon->x;
2054 placement_grid_mark_icon (grid, icon);
2055 }
2056
2057 g_list_free (unplaced_icons);
2058
2059 placement_grid_free (grid);
2060
2061 if (baul_icon_container_is_layout_rtl (container))
2062 {
2063 baul_icon_container_set_rtl_positions (container);
2064 }
2065}
2066
2067static double
2068get_mirror_x_position (BaulIconContainer *container, BaulIcon *icon, double x)
2069{
2070 EelDRect icon_bounds;
2071 CtkAllocation allocation;
2072
2073 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
2074 icon_bounds = baul_icon_canvas_item_get_icon_rectangle (icon->item);
2075
2076 return CANVAS_WIDTH(container, allocation)((allocation.width - container->details->left_margin - container
->details->right_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
- x - (icon_bounds.x1 - icon_bounds.x0);
2077}
2078
2079static void
2080baul_icon_container_set_rtl_positions (BaulIconContainer *container)
2081{
2082 GList *l;
2083 BaulIcon *icon = NULL((void*)0);
2084
2085 if (!container->details->icons)
2086 {
2087 return;
2088 }
2089
2090 for (l = container->details->icons; l != NULL((void*)0); l = l->next)
2091 {
2092 double x;
2093
2094 icon = l->data;
2095 x = get_mirror_x_position (container, icon, icon->saved_ltr_x);
2096 icon_set_position (icon, x, icon->y);
2097 }
2098}
2099
2100static void
2101lay_down_icons_vertical_desktop (BaulIconContainer *container, GList *icons)
2102{
2103 GList *p, *placed_icons, *unplaced_icons;
2104 int total, new_length, placed;
2105 BaulIcon *icon;
2106 int height;
2107 int x, y, x1, x2, y1, y2;
2108 EelDRect icon_rect;
2109 CtkAllocation allocation;
2110
2111 /* Get container dimensions */
2112 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
2113 height = CANVAS_HEIGHT(container, allocation)((allocation.height - container->details->top_margin - container
->details->bottom_margin) / ((((EelCanvas*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((eel_canvas_get_type ())))
)))->pixels_per_unit)
;
2114
2115 /* Determine which icons have and have not been placed */
2116 placed_icons = NULL((void*)0);
2117 unplaced_icons = NULL((void*)0);
2118
2119 total = g_list_length (container->details->icons);
2120 new_length = g_list_length (icons);
2121 placed = total - new_length;
2122 if (placed > 0)
2123 {
2124 PlacementGrid *grid;
2125 /* Add only placed icons in list */
2126 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2127 {
2128 icon = p->data;
2129 if (icon_is_positioned (icon))
2130 {
2131 icon_set_position(icon, icon->saved_ltr_x, icon->y);
2132 placed_icons = g_list_prepend (placed_icons, icon);
2133 }
2134 else
2135 {
2136 icon->x = 0;
2137 icon->y = 0;
2138 unplaced_icons = g_list_prepend (unplaced_icons, icon);
2139 }
2140 }
2141 placed_icons = g_list_reverse (placed_icons);
2142 unplaced_icons = g_list_reverse (unplaced_icons);
2143
2144 grid = placement_grid_new (container, FALSE(0));
2145
2146 if (grid)
2147 {
2148 for (p = placed_icons; p != NULL((void*)0); p = p->next)
2149 {
2150 placement_grid_mark_icon
2151 (grid, (BaulIcon*)p->data);
2152 }
2153
2154 /* Place unplaced icons in the best locations */
2155 for (p = unplaced_icons; p != NULL((void*)0); p = p->next)
2156 {
2157 icon = p->data;
2158
2159 icon_rect = baul_icon_canvas_item_get_icon_rectangle (icon->item);
2160
2161 /* Start the icon in the first column */
2162 x = DESKTOP_PAD_HORIZONTAL10 + (SNAP_SIZE_X78 / 2) - ((icon_rect.x1 - icon_rect.x0) / 2);
2163 y = DESKTOP_PAD_VERTICAL10 + SNAP_SIZE_Y20 - (icon_rect.y1 - icon_rect.y0);
2164
2165 find_empty_location (container,
2166 grid,
2167 icon,
2168 x, y,
2169 &x, &y);
2170
2171 icon_set_position (icon, x, y);
2172 icon->saved_ltr_x = x;
2173 placement_grid_mark_icon (grid, icon);
2174 }
2175
2176 placement_grid_free (grid);
2177 }
2178
2179 g_list_free (placed_icons);
2180 g_list_free (unplaced_icons);
2181 }
2182 else
2183 {
2184 /* There are no placed icons. Just lay them down using our rules */
2185 x = DESKTOP_PAD_HORIZONTAL10;
2186
2187 while (icons != NULL((void*)0))
2188 {
2189 int max_width, column_width, icon_height;
2190 int center_x;
2191 int baseline;
2192 int icon_height_for_bound_check;
2193 gboolean should_snap;
2194
2195 should_snap = !(container->details->tighter_layout && !container->details->keep_aligned);
2196
2197 y = DESKTOP_PAD_VERTICAL10;
2198
2199 max_width = 0;
2200
2201 /* Calculate max width for column */
2202 for (p = icons; p != NULL((void*)0); p = p->next)
2203 {
2204 int icon_width;
2205
2206 icon = p->data;
2207
2208 icon_get_bounding_box (icon, &x1, &y1, &x2, &y2,
2209 BOUNDS_USAGE_FOR_LAYOUT);
2210 icon_width = x2 - x1;
2211 icon_height = y2 - y1;
2212
2213 icon_get_bounding_box (icon, NULL((void*)0), &y1, NULL((void*)0), &y2,
2214 BOUNDS_USAGE_FOR_ENTIRE_ITEM);
2215 icon_height_for_bound_check = y2 - y1;
2216
2217 if (should_snap)
2218 {
2219 /* Snap the baseline to a grid position */
2220 icon_rect = baul_icon_canvas_item_get_icon_rectangle (icon->item);
2221 baseline = y + (icon_rect.y1 - icon_rect.y0);
2222 baseline = SNAP_CEIL_VERTICAL (baseline)((ceil ((double)((baseline) - 10) / 20) * 20) + 10);
2223 y = baseline - (icon_rect.y1 - icon_rect.y0);
2224 }
2225
2226 /* Check and see if we need to move to a new column */
2227 if (y != DESKTOP_PAD_VERTICAL10 && y + icon_height_for_bound_check > height)
2228 {
2229 break;
2230 }
2231
2232 if (max_width < icon_width)
2233 {
2234 max_width = icon_width;
2235 }
2236
2237 y += icon_height + DESKTOP_PAD_VERTICAL10;
2238 }
2239
2240 y = DESKTOP_PAD_VERTICAL10;
2241
2242 center_x = x + max_width / 2;
2243 column_width = max_width;
2244 if (should_snap)
2245 {
2246 /* Find the grid column to center on */
2247 center_x = SNAP_CEIL_HORIZONTAL (center_x)((ceil ((double)((center_x) - 10) / 78) * 78) + 10);
2248 column_width = (center_x - x) + (max_width / 2);
2249 }
2250
2251 /* Lay out column */
2252 for (p = icons; p != NULL((void*)0); p = p->next)
2253 {
2254 icon = p->data;
2255 icon_get_bounding_box (icon, &x1, &y1, &x2, &y2,
2256 BOUNDS_USAGE_FOR_LAYOUT);
2257 icon_height = y2 - y1;
2258
2259 icon_get_bounding_box (icon, NULL((void*)0), &y1, NULL((void*)0), &y2,
2260 BOUNDS_USAGE_FOR_ENTIRE_ITEM);
2261 icon_height_for_bound_check = y2 - y1;
2262
2263 icon_rect = baul_icon_canvas_item_get_icon_rectangle (icon->item);
2264
2265 if (should_snap)
2266 {
2267 baseline = y + (icon_rect.y1 - icon_rect.y0);
2268 baseline = SNAP_CEIL_VERTICAL (baseline)((ceil ((double)((baseline) - 10) / 20) * 20) + 10);
2269 y = baseline - (icon_rect.y1 - icon_rect.y0);
2270 }
2271
2272 /* Check and see if we need to move to a new column */
2273 if (y != DESKTOP_PAD_VERTICAL10 && y > height - icon_height_for_bound_check &&
2274 /* Make sure we lay out at least one icon per column, to make progress */
2275 p != icons)
2276 {
2277 x += column_width + DESKTOP_PAD_HORIZONTAL10;
2278 break;
2279 }
2280
2281 icon_set_position (icon,
2282 center_x - (icon_rect.x1 - icon_rect.x0) / 2,
2283 y);
2284
2285 icon->saved_ltr_x = icon->x;
2286 y += icon_height + DESKTOP_PAD_VERTICAL10;
2287 }
2288 icons = p;
2289 }
2290 }
2291
2292 /* These modes are special. We freeze all of our positions
2293 * after we do the layout.
2294 */
2295 /* FIXME bugzilla.gnome.org 42478:
2296 * This should not be tied to the direction of layout.
2297 * It should be a separate switch.
2298 */
2299 baul_icon_container_freeze_icon_positions (container);
2300}
2301
2302
2303static void
2304lay_down_icons (BaulIconContainer *container, GList *icons, double start_y)
2305{
2306 switch (container->details->layout_mode)
2307 {
2308 case BAUL_ICON_LAYOUT_L_R_T_B:
2309 case BAUL_ICON_LAYOUT_R_L_T_B:
2310 lay_down_icons_horizontal (container, icons, start_y);
2311 break;
2312
2313 case BAUL_ICON_LAYOUT_T_B_L_R:
2314 case BAUL_ICON_LAYOUT_T_B_R_L:
2315 if (baul_icon_container_get_is_desktop (container))
2316 {
2317 lay_down_icons_vertical_desktop (container, icons);
2318 }
2319 else
2320 {
2321 lay_down_icons_vertical (container, icons, start_y);
2322 }
2323 break;
2324
2325 default:
2326 g_assert_not_reached ()do { g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 2326, ((const char*) (__func__)), ((void*)0)); } while (0)
;
2327 }
2328}
2329
2330static void
2331redo_layout_internal (BaulIconContainer *container)
2332{
2333 finish_adding_new_icons (container);
2334
2335 /* Don't do any re-laying-out during stretching. Later we
2336 * might add smart logic that does this and leaves room for
2337 * the stretched icon, but if we do it we want it to be fast
2338 * and only re-lay-out when it's really needed.
2339 */
2340 if (container->details->auto_layout
2341 && container->details->drag_state != DRAG_STATE_STRETCH)
2342 {
2343 resort (container);
2344 lay_down_icons (container, container->details->icons, 0);
2345 }
2346
2347 if (baul_icon_container_is_layout_rtl (container))
2348 {
2349 baul_icon_container_set_rtl_positions (container);
2350 }
2351
2352 baul_icon_container_update_scroll_region (container);
2353
2354 process_pending_icon_to_reveal (container);
2355 process_pending_icon_to_rename (container);
2356 baul_icon_container_update_visible_icons (container);
2357}
2358
2359static gboolean
2360redo_layout_callback (gpointer callback_data)
2361{
2362 BaulIconContainer *container;
2363
2364 container = BAUL_ICON_CONTAINER (callback_data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((callback_data)), (baul_icon_container_get_type
())))))
;
2365 redo_layout_internal (container);
2366 container->details->idle_id = 0;
2367
2368 return FALSE(0);
2369}
2370
2371static void
2372unschedule_redo_layout (BaulIconContainer *container)
2373{
2374 if (container->details->idle_id != 0)
2375 {
2376 g_source_remove (container->details->idle_id);
2377 container->details->idle_id = 0;
2378 }
2379}
2380
2381static void
2382schedule_redo_layout (BaulIconContainer *container)
2383{
2384 if (container->details->idle_id == 0
2385 && container->details->has_been_allocated)
2386 {
2387 container->details->idle_id = g_idle_add
2388 (redo_layout_callback, container);
2389 }
2390}
2391
2392static void
2393redo_layout (BaulIconContainer *container)
2394{
2395 unschedule_redo_layout (container);
2396 redo_layout_internal (container);
2397}
2398
2399static void
2400reload_icon_positions (BaulIconContainer *container)
2401{
2402 GList *p, *no_position_icons;
2403 gboolean have_stored_position;
2404 BaulIconPosition position;
2405 EelDRect bounds;
2406 double bottom;
2407 EelCanvasItem *item;
2408 BaulIcon *icon = NULL((void*)0);
2409
2410 g_assert (!container->details->auto_layout)do { if (!container->details->auto_layout) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 2410, ((const char*)
(__func__)), "!container->details->auto_layout"); } while
(0)
;
2411
2412 resort (container);
2413
2414 no_position_icons = NULL((void*)0);
2415
2416 /* Place all the icons with positions. */
2417 bottom = 0;
2418 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2419 {
2420 icon = p->data;
2421
2422 have_stored_position = FALSE(0);
2423 g_signal_emit (container,
2424 signals[GET_STORED_ICON_POSITION], 0,
2425 icon->data,
2426 &position,
2427 &have_stored_position);
2428 if (have_stored_position)
2429 {
2430 icon_set_position (icon, position.x, position.y);
2431 item = EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
;
2432 baul_icon_canvas_item_get_bounds_for_layout (icon->item,
2433 &bounds.x0,
2434 &bounds.y0,
2435 &bounds.x1,
2436 &bounds.y1);
2437 eel_canvas_item_i2w (item->parent,
2438 &bounds.x0,
2439 &bounds.y0);
2440 eel_canvas_item_i2w (item->parent,
2441 &bounds.x1,
2442 &bounds.y1);
2443 if (bounds.y1 > bottom)
2444 {
2445 bottom = bounds.y1;
2446 }
2447 }
2448 else
2449 {
2450 no_position_icons = g_list_prepend (no_position_icons, icon);
2451 }
2452 }
2453 no_position_icons = g_list_reverse (no_position_icons);
2454
2455 /* Place all the other icons. */
2456 lay_down_icons (container, no_position_icons, bottom + ICON_PAD_BOTTOM4);
2457 g_list_free (no_position_icons);
2458}
2459
2460/* Container-level icon handling functions. */
2461
2462static gboolean
2463button_event_modifies_selection (CdkEventButton *event)
2464{
2465 return (event->state & (CDK_CONTROL_MASK | CDK_SHIFT_MASK)) != 0;
2466}
2467
2468/* invalidate the cached label sizes for all the icons */
2469static void
2470invalidate_label_sizes (BaulIconContainer *container)
2471{
2472 GList *p;
2473 BaulIcon *icon = NULL((void*)0);
2474
2475 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2476 {
2477 icon = p->data;
2478
2479 baul_icon_canvas_item_invalidate_label_size (icon->item);
2480 }
2481}
2482
2483/* invalidate the entire labels (i.e. their attributes) for all the icons */
2484static void
2485invalidate_labels (BaulIconContainer *container)
2486{
2487 GList *p;
2488 BaulIcon *icon = NULL((void*)0);
2489
2490 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2491 {
2492 icon = p->data;
2493
2494 baul_icon_canvas_item_invalidate_label (icon->item);
2495 }
2496}
2497
2498static gboolean
2499select_range (BaulIconContainer *container,
2500 BaulIcon *icon1,
2501 BaulIcon *icon2,
2502 gboolean unselect_outside_range)
2503{
2504 gboolean selection_changed;
2505 GList *p;
2506 BaulIcon *icon = NULL((void*)0);
2507 BaulIcon *unmatched_icon;
2508 gboolean select;
2509
2510 selection_changed = FALSE(0);
2511
2512 unmatched_icon = NULL((void*)0);
2513 select = FALSE(0);
2514 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2515 {
2516 icon = p->data;
2517
2518 if (unmatched_icon == NULL((void*)0))
2519 {
2520 if (icon == icon1)
2521 {
2522 unmatched_icon = icon2;
2523 select = TRUE(!(0));
2524 }
2525 else if (icon == icon2)
2526 {
2527 unmatched_icon = icon1;
2528 select = TRUE(!(0));
2529 }
2530 }
2531
2532 if (select || unselect_outside_range)
2533 {
2534 selection_changed |= icon_set_selected
2535 (container, icon, select);
2536 }
2537
2538 if (unmatched_icon != NULL((void*)0) && icon == unmatched_icon)
2539 {
2540 select = FALSE(0);
2541 }
2542
2543 }
2544
2545 if (selection_changed && icon2 != NULL((void*)0))
2546 {
2547 emit_atk_focus_state_change (icon2, TRUE(!(0)));
2548 }
2549 return selection_changed;
2550}
2551
2552
2553static gboolean
2554select_one_unselect_others (BaulIconContainer *container,
2555 BaulIcon *icon_to_select)
2556{
2557 gboolean selection_changed;
2558 GList *p;
2559 BaulIcon *icon = NULL((void*)0);
2560
2561 selection_changed = FALSE(0);
2562
2563 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2564 {
2565 icon = p->data;
2566
2567 selection_changed |= icon_set_selected
2568 (container, icon, icon == icon_to_select);
2569 }
2570
2571 if (selection_changed && icon_to_select != NULL((void*)0))
2572 {
2573 emit_atk_focus_state_change (icon_to_select, TRUE(!(0)));
2574 reveal_icon (container, icon_to_select);
2575 }
2576 return selection_changed;
2577}
2578
2579static gboolean
2580unselect_all (BaulIconContainer *container)
2581{
2582 return select_one_unselect_others (container, NULL((void*)0));
2583}
2584
2585void
2586baul_icon_container_move_icon (BaulIconContainer *container,
2587 BaulIcon *icon,
2588 int x, int y,
2589 double scale,
2590 gboolean raise,
2591 gboolean snap,
2592 gboolean update_position)
2593{
2594 BaulIconContainerDetails *details;
2595 gboolean emit_signal;
2596 BaulIconPosition position;
2597
2598 details = container->details;
2599
2600 emit_signal = FALSE(0);
2601
2602 if (icon == get_icon_being_renamed (container))
2603 {
2604 end_renaming_mode (container, TRUE(!(0)));
2605 }
2606
2607 if (scale != icon->scale)
2608 {
2609 icon->scale = scale;
2610 baul_icon_container_update_icon (container, icon);
2611 if (update_position)
2612 {
2613 redo_layout (container);
2614 emit_signal = TRUE(!(0));
2615 }
2616 }
2617
2618 if (!details->auto_layout)
2619 {
2620 if (details->keep_aligned && snap)
2621 {
2622 snap_position (container, icon, &x, &y);
2623 }
2624
2625 if (x != icon->x || y != icon->y)
2626 {
2627 icon_set_position (icon, x, y);
2628 emit_signal = update_position;
2629 }
2630
2631 icon->saved_ltr_x = baul_icon_container_is_layout_rtl (container) ? get_mirror_x_position (container, icon, icon->x) : icon->x;
2632 }
2633
2634 if (emit_signal)
2635 {
2636 position.x = icon->saved_ltr_x;
2637 position.y = icon->y;
2638 position.scale = scale;
2639 g_signal_emit (container,
2640 signals[ICON_POSITION_CHANGED], 0,
2641 icon->data, &position);
2642 }
2643
2644 if (raise)
2645 {
2646 icon_raise (icon);
2647 }
2648
2649 /* FIXME bugzilla.gnome.org 42474:
2650 * Handling of the scroll region is inconsistent here. In
2651 * the scale-changing case, redo_layout is called, which updates the
2652 * scroll region appropriately. In other cases, it's up to the
2653 * caller to make sure the scroll region is updated. This could
2654 * lead to hard-to-track-down bugs.
2655 */
2656}
2657
2658/* Implementation of rubberband selection. */
2659static void
2660rubberband_select (BaulIconContainer *container,
2661 const EelDRect *previous_rect G_GNUC_UNUSED__attribute__ ((__unused__)),
2662 const EelDRect *current_rect)
2663{
2664 GList *p;
2665 gboolean selection_changed, is_in, canvas_rect_calculated;
2666 EelIRect canvas_rect;
2667 EelCanvas *canvas;
2668 BaulIcon *icon = NULL((void*)0);
2669
2670 selection_changed = FALSE(0);
2671 canvas_rect_calculated = FALSE(0);
2672
2673 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2674 {
2675 icon = p->data;
2676
2677 if (!canvas_rect_calculated)
2678 {
2679 /* Only do this calculation once, since all the canvas items
2680 * we are interating are in the same coordinate space
2681 */
2682 canvas = EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
->canvas;
2683 eel_canvas_w2c (canvas,
2684 current_rect->x0,
2685 current_rect->y0,
2686 &canvas_rect.x0,
2687 &canvas_rect.y0);
2688 eel_canvas_w2c (canvas,
2689 current_rect->x1,
2690 current_rect->y1,
2691 &canvas_rect.x1,
2692 &canvas_rect.y1);
2693 canvas_rect_calculated = TRUE(!(0));
2694 }
2695
2696 is_in = baul_icon_canvas_item_hit_test_rectangle (icon->item, canvas_rect);
2697
2698 selection_changed |= icon_set_selected
2699 (container, icon,
2700 is_in ^ icon->was_selected_before_rubberband);
2701 }
2702
2703 if (selection_changed)
2704 {
2705 g_signal_emit (container,
2706 signals[SELECTION_CHANGED], 0);
2707 }
2708}
2709
2710static int
2711rubberband_timeout_callback (gpointer data)
2712{
2713 BaulIconContainer *container;
2714 CtkWidget *widget;
2715 BaulIconRubberbandInfo *band_info;
2716 int x, y;
2717 double x1, y1, x2, y2;
2718 double world_x, world_y;
2719 int x_scroll, y_scroll;
2720 int adj_x, adj_y;
2721 CdkDisplay *display;
2722 CdkSeat *seat;
2723 gboolean adj_changed;
2724 CtkAllocation allocation;
2725
2726 EelDRect selection_rect;
2727
2728 widget = CTK_WIDGET (data)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((data)), ((ctk_widget_get_type ()))))))
;
2729 container = BAUL_ICON_CONTAINER (data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((data)), (baul_icon_container_get_type())))
))
;
2730 band_info = &container->details->rubberband_info;
2731
2732 g_assert (band_info->timer_id != 0)do { if (band_info->timer_id != 0) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 2732, ((const char*)
(__func__)), "band_info->timer_id != 0"); } while (0)
;
2733 g_assert (EEL_IS_CANVAS_RECT (band_info->selection_rectangle) ||do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((band_info->selection_rectangle)); GType __t = ((eel_canvas_rect_get_type
())); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))) || (((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((band_info->selection_rectangle)); GType __t = ((eel_canvas_rect_get_type
())); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 2734, ((const char*) (__func__)), "EEL_IS_CANVAS_RECT (band_info->selection_rectangle) || EEL_IS_CANVAS_RECT (band_info->selection_rectangle)"
); } while (0)
2734 EEL_IS_CANVAS_RECT (band_info->selection_rectangle))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((band_info->selection_rectangle)); GType __t = ((eel_canvas_rect_get_type
())); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))) || (((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((band_info->selection_rectangle)); GType __t = ((eel_canvas_rect_get_type
())); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 2734, ((const char*) (__func__)), "EEL_IS_CANVAS_RECT (band_info->selection_rectangle) || EEL_IS_CANVAS_RECT (band_info->selection_rectangle)"
); } while (0)
;
2735
2736 adj_changed = FALSE(0);
2737 ctk_widget_get_allocation (widget, &allocation);
2738
2739 adj_x = ctk_adjustment_get_value (ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
2740 if (adj_x != band_info->last_adj_x)
2741 {
2742 band_info->last_adj_x = adj_x;
2743 adj_changed = TRUE(!(0));
2744 }
2745
2746 adj_y = ctk_adjustment_get_value (ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
2747 if (adj_y != band_info->last_adj_y)
2748 {
2749 band_info->last_adj_y = adj_y;
2750 adj_changed = TRUE(!(0));
2751 }
2752 display = ctk_widget_get_display (widget);
2753 seat = cdk_display_get_default_seat (display);
2754
2755 cdk_window_get_device_position (ctk_widget_get_window (widget),
2756 cdk_seat_get_pointer (seat),
2757 &x, &y, NULL((void*)0));
2758
2759 if (x < 0)
2760 {
2761 x_scroll = x;
2762 x = 0;
2763 }
2764 else if (x >= allocation.width)
2765 {
2766 x_scroll = x - allocation.width + 1;
2767 x = allocation.width - 1;
2768 }
2769 else
2770 {
2771 x_scroll = 0;
2772 }
2773
2774 if (y < 0)
2775 {
2776 y_scroll = y;
2777 y = 0;
2778 }
2779 else if (y >= allocation.height)
2780 {
2781 y_scroll = y - allocation.height + 1;
2782 y = allocation.height - 1;
2783 }
2784 else
2785 {
2786 y_scroll = 0;
2787 }
2788
2789 if (y_scroll == 0 && x_scroll == 0
2790 && (int) band_info->prev_x == x && (int) band_info->prev_y == y && !adj_changed)
2791 {
2792 return TRUE(!(0));
2793 }
2794
2795 baul_icon_container_scroll (container, x_scroll, y_scroll);
2796
2797 /* Remember to convert from widget to scrolled window coords */
2798 eel_canvas_window_to_world (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
2799 x + ctk_adjustment_get_value (ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
)),
2800 y + ctk_adjustment_get_value (ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
)),
2801 &world_x, &world_y);
2802
2803 if (world_x < band_info->start_x)
2804 {
2805 x1 = world_x;
2806 x2 = band_info->start_x;
2807 }
2808 else
2809 {
2810 x1 = band_info->start_x;
2811 x2 = world_x;
2812 }
2813
2814 if (world_y < band_info->start_y)
2815 {
2816 y1 = world_y;
2817 y2 = band_info->start_y;
2818 }
2819 else
2820 {
2821 y1 = band_info->start_y;
2822 y2 = world_y;
2823 }
2824
2825 /* Don't let the area of the selection rectangle be empty.
2826 * Aside from the fact that it would be funny when the rectangle disappears,
2827 * this also works around a crash in libart that happens sometimes when a
2828 * zero height rectangle is passed.
2829 */
2830 x2 = MAX (x1 + 1, x2)(((x1 + 1) > (x2)) ? (x1 + 1) : (x2));
2831 y2 = MAX (y1 + 1, y2)(((y1 + 1) > (y2)) ? (y1 + 1) : (y2));
2832
2833 eel_canvas_item_set
2834 (band_info->selection_rectangle,
2835 "x1", x1, "y1", y1,
2836 "x2", x2, "y2", y2,
2837 NULL((void*)0));
2838
2839 selection_rect.x0 = x1;
2840 selection_rect.y0 = y1;
2841 selection_rect.x1 = x2;
2842 selection_rect.y1 = y2;
2843
2844 rubberband_select (container,
2845 &band_info->prev_rect,
2846 &selection_rect);
2847
2848 band_info->prev_x = x;
2849 band_info->prev_y = y;
2850
2851 band_info->prev_rect = selection_rect;
2852
2853 return TRUE(!(0));
2854}
2855
2856/*borrowed from Nemo, makes Baul rubberbanding follow same selectors as Nemo and presumably Nautilus */
2857static void
2858start_rubberbanding (BaulIconContainer *container,
2859 CdkEventButton *event)
2860{
2861 AtkObject *accessible;
2862 BaulIconContainerDetails *details;
2863 BaulIconRubberbandInfo *band_info;
2864 CdkRGBA bg_color, border_color;
2865 CdkRGBA *c;
2866 GList *p;
2867 BaulIcon *icon;
2868 CtkStyleContext *context;
2869
2870 details = container->details;
2871 band_info = &details->rubberband_info;
2872
2873 g_signal_emit (container,
2874 signals[BAND_SELECT_STARTED], 0);
2875
2876 for (p = details->icons; p != NULL((void*)0); p = p->next) {
2877 icon = p->data;
2878 icon->was_selected_before_rubberband = icon->is_selected;
2879 }
2880
2881 eel_canvas_window_to_world
2882 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
, event->x, event->y,
2883 &band_info->start_x, &band_info->start_y);
2884
2885 context = ctk_widget_get_style_context (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
2886 ctk_style_context_save (context);
2887 ctk_style_context_add_class (context, CTK_STYLE_CLASS_RUBBERBAND"rubberband");
2888
2889 ctk_style_context_get (context, CTK_STATE_FLAG_NORMAL,
2890 CTK_STYLE_PROPERTY_BACKGROUND_COLOR"background-color",
2891 &c, NULL((void*)0));
2892
2893 bg_color = *c;
2894
2895 ctk_style_context_get (context, CTK_STATE_FLAG_NORMAL,
2896 CTK_STYLE_PROPERTY_BORDER_COLOR"border-color",
2897 &c, NULL((void*)0));
2898
2899 border_color = *c;
2900 cdk_rgba_free (c);
2901
2902 ctk_style_context_restore (context);
2903
2904 band_info->selection_rectangle = eel_canvas_item_new
2905 (eel_canvas_root
2906 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
),
2907 EEL_TYPE_CANVAS_RECT(eel_canvas_rect_get_type ()),
2908 "x1", band_info->start_x,
2909 "y1", band_info->start_y,
2910 "x2", band_info->start_x,
2911 "y2", band_info->start_y,
2912 "fill_color_rgba", &bg_color,
2913 "outline_color_rgba", &border_color,
2914 "width_pixels", 1,
2915 NULL((void*)0));
2916
2917 accessible = atk_gobject_accessible_for_object
2918 (G_OBJECT (band_info->selection_rectangle)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((band_info->selection_rectangle)), (((GType) ((20) <<
(2))))))))
);
2919 atk_object_set_name (accessible, "selection");
2920 atk_object_set_description (accessible, _("The selection rectangle")gettext ("The selection rectangle"));
2921
2922 band_info->prev_x = event->x - ctk_adjustment_get_value (ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
2923 band_info->prev_y = event->y - ctk_adjustment_get_value (ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
2924
2925 band_info->active = TRUE(!(0));
2926
2927 if (band_info->timer_id == 0) {
2928 band_info->timer_id = g_timeout_add
2929 (RUBBERBAND_TIMEOUT_INTERVAL10,
2930 rubberband_timeout_callback,
2931 container);
2932 }
2933
2934 eel_canvas_item_grab (band_info->selection_rectangle,
2935 (CDK_POINTER_MOTION_MASK
2936 | CDK_BUTTON_RELEASE_MASK
2937 | CDK_SCROLL_MASK),
2938 NULL((void*)0),
2939 (CdkEvent *)event);
2940}
2941
2942static void
2943stop_rubberbanding (BaulIconContainer *container)
2944{
2945 BaulIconRubberbandInfo *band_info;
2946 GList *icons;
2947
2948 band_info = &container->details->rubberband_info;
2949
2950 g_assert (band_info->timer_id != 0)do { if (band_info->timer_id != 0) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 2950, ((const char*)
(__func__)), "band_info->timer_id != 0"); } while (0)
;
2951 g_source_remove (band_info->timer_id);
2952 band_info->timer_id = 0;
2953
2954 band_info->active = FALSE(0);
2955
2956 /* Destroy this canvas item; the parent will unref it. */
2957 eel_canvas_item_ungrab (band_info->selection_rectangle);
2958 eel_canvas_item_destroy (band_info->selection_rectangle);
2959 band_info->selection_rectangle = NULL((void*)0);
2960
2961 /* if only one item has been selected, use it as range
2962 * selection base (cf. handle_icon_button_press) */
2963 icons = baul_icon_container_get_selected_icons (container);
2964 if (g_list_length (icons) == 1)
2965 {
2966 container->details->range_selection_base_icon = icons->data;
2967 }
2968 g_list_free (icons);
2969
2970 g_signal_emit (container,
2971 signals[BAND_SELECT_ENDED], 0);
2972}
2973
2974/* Keyboard navigation. */
2975
2976typedef gboolean (* IsBetterIconFunction) (BaulIconContainer *container,
2977 BaulIcon *start_icon,
2978 BaulIcon *best_so_far,
2979 BaulIcon *candidate,
2980 void *data);
2981
2982static BaulIcon *
2983find_best_icon (BaulIconContainer *container,
2984 BaulIcon *start_icon,
2985 IsBetterIconFunction function,
2986 void *data)
2987{
2988 GList *p;
2989 BaulIcon *best, *candidate;
2990
2991 best = NULL((void*)0);
2992 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
2993 {
2994 candidate = p->data;
2995
2996 if (candidate != start_icon)
2997 {
2998 if ((* function) (container, start_icon, best, candidate, data))
2999 {
3000 best = candidate;
3001 }
3002 }
3003 }
3004 return best;
3005}
3006
3007static BaulIcon *
3008find_best_selected_icon (BaulIconContainer *container,
3009 BaulIcon *start_icon,
3010 IsBetterIconFunction function,
3011 void *data)
3012{
3013 GList *p;
3014 BaulIcon *best, *candidate;
3015
3016 best = NULL((void*)0);
3017 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
3018 {
3019 candidate = p->data;
3020
3021 if (candidate != start_icon && candidate->is_selected)
3022 {
3023 if ((* function) (container, start_icon, best, candidate, data))
3024 {
3025 best = candidate;
3026 }
3027 }
3028 }
3029 return best;
3030}
3031
3032static int
3033compare_icons_by_uri (BaulIconContainer *container,
3034 BaulIcon *icon_a,
3035 BaulIcon *icon_b)
3036{
3037 char *uri_a, *uri_b;
3038 int result;
3039
3040 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 3040, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
3041 g_assert (icon_a != NULL)do { if (icon_a != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 3041, ((const char*)
(__func__)), "icon_a != NULL"); } while (0)
;
3042 g_assert (icon_b != NULL)do { if (icon_b != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 3042, ((const char*)
(__func__)), "icon_b != NULL"); } while (0)
;
3043 g_assert (icon_a != icon_b)do { if (icon_a != icon_b) ; else g_assertion_message_expr ((
(gchar*) 0), "baul-icon-container.c", 3043, ((const char*) (__func__
)), "icon_a != icon_b"); } while (0)
;
3044
3045 uri_a = baul_icon_container_get_icon_uri (container, icon_a);
3046 uri_b = baul_icon_container_get_icon_uri (container, icon_b);
3047 result = strcmp (uri_a, uri_b);
3048 g_assert (result != 0)do { if (result != 0) ; else g_assertion_message_expr (((gchar
*) 0), "baul-icon-container.c", 3048, ((const char*) (__func__
)), "result != 0"); } while (0)
;
3049 g_free (uri_a);
3050 g_free (uri_b);
3051
3052 return result;
3053}
3054
3055static int
3056get_cmp_point_x (BaulIconContainer *container,
3057 EelDRect icon_rect)
3058{
3059 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
3060 {
3061 if (ctk_widget_get_direction (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
) == CTK_TEXT_DIR_RTL)
3062 {
3063 return icon_rect.x0;
3064 }
3065 else
3066 {
3067 return icon_rect.x1;
3068 }
3069 }
3070 else
3071 {
3072 return (icon_rect.x0 + icon_rect.x1) / 2;
3073 }
3074}
3075
3076static int
3077get_cmp_point_y (BaulIconContainer *container,
3078 EelDRect icon_rect)
3079{
3080 if (container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
3081 {
3082 return (icon_rect.y0 + icon_rect.y1)/2;
3083 }
3084 else
3085 {
3086 return icon_rect.y1;
3087 }
3088}
3089
3090
3091static int
3092compare_icons_horizontal (BaulIconContainer *container,
3093 BaulIcon *icon_a,
3094 BaulIcon *icon_b)
3095{
3096 EelDRect world_rect;
3097 int ax, bx;
3098
3099 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_a->item);
3100 eel_canvas_w2c
3101 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3102 get_cmp_point_x (container, world_rect),
3103 get_cmp_point_y (container, world_rect),
3104 &ax,
3105 NULL((void*)0));
3106 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_b->item);
3107 eel_canvas_w2c
3108 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3109 get_cmp_point_x (container, world_rect),
3110 get_cmp_point_y (container, world_rect),
3111 &bx,
3112 NULL((void*)0));
3113
3114 if (ax < bx)
3115 {
3116 return -1;
3117 }
3118 if (ax > bx)
3119 {
3120 return +1;
3121 }
3122 return 0;
3123}
3124
3125static int
3126compare_icons_vertical (BaulIconContainer *container,
3127 BaulIcon *icon_a,
3128 BaulIcon *icon_b)
3129{
3130 EelDRect world_rect;
3131 int ay, by;
3132
3133 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_a->item);
3134 eel_canvas_w2c
3135 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3136 get_cmp_point_x (container, world_rect),
3137 get_cmp_point_y (container, world_rect),
3138 NULL((void*)0),
3139 &ay);
3140 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_b->item);
3141 eel_canvas_w2c
3142 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3143 get_cmp_point_x (container, world_rect),
3144 get_cmp_point_y (container, world_rect),
3145 NULL((void*)0),
3146 &by);
3147
3148 if (ay < by)
3149 {
3150 return -1;
3151 }
3152 if (ay > by)
3153 {
3154 return +1;
3155 }
3156 return 0;
3157}
3158
3159static int
3160compare_icons_horizontal_first (BaulIconContainer *container,
3161 BaulIcon *icon_a,
3162 BaulIcon *icon_b)
3163{
3164 EelDRect world_rect;
3165 int ax, ay, bx, by;
3166
3167 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_a->item);
3168 eel_canvas_w2c
3169 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3170 get_cmp_point_x (container, world_rect),
3171 get_cmp_point_y (container, world_rect),
3172 &ax,
3173 &ay);
3174 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_b->item);
3175 eel_canvas_w2c
3176 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3177 get_cmp_point_x (container, world_rect),
3178 get_cmp_point_y (container, world_rect),
3179 &bx,
3180 &by);
3181
3182 if (ax < bx)
3183 {
3184 return -1;
3185 }
3186 if (ax > bx)
3187 {
3188 return +1;
3189 }
3190 if (ay < by)
3191 {
3192 return -1;
3193 }
3194 if (ay > by)
3195 {
3196 return +1;
3197 }
3198 return compare_icons_by_uri (container, icon_a, icon_b);
3199}
3200
3201static int
3202compare_icons_vertical_first (BaulIconContainer *container,
3203 BaulIcon *icon_a,
3204 BaulIcon *icon_b)
3205{
3206 EelDRect world_rect;
3207 int ax, ay, bx, by;
3208
3209 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_a->item);
3210 eel_canvas_w2c
3211 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3212 get_cmp_point_x (container, world_rect),
3213 get_cmp_point_y (container, world_rect),
3214 &ax,
3215 &ay);
3216 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon_b->item);
3217 eel_canvas_w2c
3218 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3219 get_cmp_point_x (container, world_rect),
3220 get_cmp_point_y (container, world_rect),
3221 &bx,
3222 &by);
3223
3224 if (ay < by)
3225 {
3226 return -1;
3227 }
3228 if (ay > by)
3229 {
3230 return +1;
3231 }
3232 if (ax < bx)
3233 {
3234 return -1;
3235 }
3236 if (ax > bx)
3237 {
3238 return +1;
3239 }
3240 return compare_icons_by_uri (container, icon_a, icon_b);
3241}
3242
3243static gboolean
3244leftmost_in_top_row (BaulIconContainer *container,
3245 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3246 BaulIcon *best_so_far,
3247 BaulIcon *candidate,
3248 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3249{
3250 if (best_so_far == NULL((void*)0))
3251 {
3252 return TRUE(!(0));
3253 }
3254 return compare_icons_vertical_first (container, best_so_far, candidate) > 0;
3255}
3256
3257static gboolean
3258rightmost_in_top_row (BaulIconContainer *container,
3259 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3260 BaulIcon *best_so_far,
3261 BaulIcon *candidate,
3262 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3263{
3264 if (best_so_far == NULL((void*)0))
3265 {
3266 return TRUE(!(0));
3267 }
3268 return compare_icons_vertical (container, best_so_far, candidate) > 0;
3269 return compare_icons_horizontal (container, best_so_far, candidate) < 0;
3270}
3271
3272static gboolean
3273rightmost_in_bottom_row (BaulIconContainer *container,
3274 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3275 BaulIcon *best_so_far,
3276 BaulIcon *candidate,
3277 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3278{
3279 if (best_so_far == NULL((void*)0))
3280 {
3281 return TRUE(!(0));
3282 }
3283 return compare_icons_vertical_first (container, best_so_far, candidate) < 0;
3284}
3285
3286static int
3287compare_with_start_row (BaulIconContainer *container,
3288 BaulIcon *icon)
3289{
3290 EelCanvasItem *item;
3291
3292 item = EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
;
3293
3294 if (container->details->arrow_key_start_y < item->y1)
3295 {
3296 return -1;
3297 }
3298 if (container->details->arrow_key_start_y > item->y2)
3299 {
3300 return +1;
3301 }
3302 return 0;
3303}
3304
3305static int
3306compare_with_start_column (BaulIconContainer *container,
3307 BaulIcon *icon)
3308{
3309 EelCanvasItem *item;
3310
3311 item = EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
;
3312
3313 if (container->details->arrow_key_start_x < item->x1)
3314 {
3315 return -1;
3316 }
3317 if (container->details->arrow_key_start_x > item->x2)
3318 {
3319 return +1;
3320 }
3321 return 0;
3322}
3323
3324static gboolean
3325same_row_right_side_leftmost (BaulIconContainer *container,
3326 BaulIcon *start_icon,
3327 BaulIcon *best_so_far,
3328 BaulIcon *candidate,
3329 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3330{
3331 /* Candidates not on the start row do not qualify. */
3332 if (compare_with_start_row (container, candidate) != 0)
3333 {
3334 return FALSE(0);
3335 }
3336
3337 /* Candidates that are farther right lose out. */
3338 if (best_so_far != NULL((void*)0))
3339 {
3340 if (compare_icons_horizontal_first (container,
3341 best_so_far,
3342 candidate) < 0)
3343 {
3344 return FALSE(0);
3345 }
3346 }
3347
3348 /* Candidate to the left of the start do not qualify. */
3349 if (compare_icons_horizontal_first (container,
3350 candidate,
3351 start_icon) <= 0)
3352 {
3353 return FALSE(0);
3354 }
3355
3356 return TRUE(!(0));
3357}
3358
3359static gboolean
3360same_row_left_side_rightmost (BaulIconContainer *container,
3361 BaulIcon *start_icon,
3362 BaulIcon *best_so_far,
3363 BaulIcon *candidate,
3364 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3365{
3366 /* Candidates not on the start row do not qualify. */
3367 if (compare_with_start_row (container, candidate) != 0)
3368 {
3369 return FALSE(0);
3370 }
3371
3372 /* Candidates that are farther left lose out. */
3373 if (best_so_far != NULL((void*)0))
3374 {
3375 if (compare_icons_horizontal_first (container,
3376 best_so_far,
3377 candidate) > 0)
3378 {
3379 return FALSE(0);
3380 }
3381 }
3382
3383 /* Candidate to the right of the start do not qualify. */
3384 if (compare_icons_horizontal_first (container,
3385 candidate,
3386 start_icon) >= 0)
3387 {
3388 return FALSE(0);
3389 }
3390
3391 return TRUE(!(0));
3392}
3393
3394static gboolean
3395next_row_leftmost (BaulIconContainer *container,
3396 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3397 BaulIcon *best_so_far,
3398 BaulIcon *candidate,
3399 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3400{
3401 /* sort out icons that are not below the current row */
3402 if (compare_with_start_row (container, candidate) >= 0)
3403 {
3404 return FALSE(0);
3405 }
3406
3407 if (best_so_far != NULL((void*)0))
3408 {
3409 if (compare_icons_vertical_first (container,
3410 best_so_far,
3411 candidate) > 0)
3412 {
3413 /* candidate is above best choice, but below the current row */
3414 return TRUE(!(0));
3415 }
3416
3417 if (compare_icons_horizontal_first (container,
3418 best_so_far,
3419 candidate) > 0)
3420 {
3421 return TRUE(!(0));
3422 }
3423 }
3424
3425 return best_so_far == NULL((void*)0);
3426}
3427
3428static gboolean
3429next_row_rightmost (BaulIconContainer *container,
3430 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3431 BaulIcon *best_so_far,
3432 BaulIcon *candidate,
3433 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3434{
3435 /* sort out icons that are not below the current row */
3436 if (compare_with_start_row (container, candidate) >= 0)
3437 {
3438 return FALSE(0);
3439 }
3440
3441 if (best_so_far != NULL((void*)0))
3442 {
3443 if (compare_icons_vertical_first (container,
3444 best_so_far,
3445 candidate) > 0)
3446 {
3447 /* candidate is above best choice, but below the current row */
3448 return TRUE(!(0));
3449 }
3450
3451 if (compare_icons_horizontal_first (container,
3452 best_so_far,
3453 candidate) < 0)
3454 {
3455 return TRUE(!(0));
3456 }
3457 }
3458
3459 return best_so_far == NULL((void*)0);
3460}
3461
3462static gboolean
3463next_column_bottommost (BaulIconContainer *container,
3464 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3465 BaulIcon *best_so_far,
3466 BaulIcon *candidate,
3467 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3468{
3469 /* sort out icons that are not on the right of the current column */
3470 if (compare_with_start_column (container, candidate) >= 0)
3471 {
3472 return FALSE(0);
3473 }
3474
3475 if (best_so_far != NULL((void*)0))
3476 {
3477 if (compare_icons_horizontal_first (container,
3478 best_so_far,
3479 candidate) > 0)
3480 {
3481 /* candidate is above best choice, but below the current row */
3482 return TRUE(!(0));
3483 }
3484
3485 if (compare_icons_vertical_first (container,
3486 best_so_far,
3487 candidate) < 0)
3488 {
3489 return TRUE(!(0));
3490 }
3491 }
3492
3493 return best_so_far == NULL((void*)0);
3494}
3495
3496static gboolean
3497previous_row_rightmost (BaulIconContainer *container,
3498 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3499 BaulIcon *best_so_far,
3500 BaulIcon *candidate,
3501 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3502{
3503 /* sort out icons that are not above the current row */
3504 if (compare_with_start_row (container, candidate) <= 0)
3505 {
3506 return FALSE(0);
3507 }
3508
3509 if (best_so_far != NULL((void*)0))
3510 {
3511 if (compare_icons_vertical_first (container,
3512 best_so_far,
3513 candidate) < 0)
3514 {
3515 /* candidate is below the best choice, but above the current row */
3516 return TRUE(!(0));
3517 }
3518
3519 if (compare_icons_horizontal_first (container,
3520 best_so_far,
3521 candidate) < 0)
3522 {
3523 return TRUE(!(0));
3524 }
3525 }
3526
3527 return best_so_far == NULL((void*)0);
3528}
3529
3530static gboolean
3531same_column_above_lowest (BaulIconContainer *container,
3532 BaulIcon *start_icon,
3533 BaulIcon *best_so_far,
3534 BaulIcon *candidate,
3535 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3536{
3537 /* Candidates not on the start column do not qualify. */
3538 if (compare_with_start_column (container, candidate) != 0)
3539 {
3540 return FALSE(0);
3541 }
3542
3543 /* Candidates that are higher lose out. */
3544 if (best_so_far != NULL((void*)0))
3545 {
3546 if (compare_icons_vertical_first (container,
3547 best_so_far,
3548 candidate) > 0)
3549 {
3550 return FALSE(0);
3551 }
3552 }
3553
3554 /* Candidates below the start do not qualify. */
3555 if (compare_icons_vertical_first (container,
3556 candidate,
3557 start_icon) >= 0)
3558 {
3559 return FALSE(0);
3560 }
3561
3562 return TRUE(!(0));
3563}
3564
3565static gboolean
3566same_column_below_highest (BaulIconContainer *container,
3567 BaulIcon *start_icon,
3568 BaulIcon *best_so_far,
3569 BaulIcon *candidate,
3570 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3571{
3572 /* Candidates not on the start column do not qualify. */
3573 if (compare_with_start_column (container, candidate) != 0)
3574 {
3575 return FALSE(0);
3576 }
3577
3578 /* Candidates that are lower lose out. */
3579 if (best_so_far != NULL((void*)0))
3580 {
3581 if (compare_icons_vertical_first (container,
3582 best_so_far,
3583 candidate) < 0)
3584 {
3585 return FALSE(0);
3586 }
3587 }
3588
3589 /* Candidates above the start do not qualify. */
3590 if (compare_icons_vertical_first (container,
3591 candidate,
3592 start_icon) <= 0)
3593 {
3594 return FALSE(0);
3595 }
3596
3597 return TRUE(!(0));
3598}
3599
3600static gboolean
3601previous_column_highest (BaulIconContainer *container,
3602 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3603 BaulIcon *best_so_far,
3604 BaulIcon *candidate,
3605 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3606{
3607 /* sort out icons that are not before the current column */
3608 if (compare_with_start_column (container, candidate) <= 0)
3609 {
3610 return FALSE(0);
3611 }
3612
3613 if (best_so_far != NULL((void*)0))
3614 {
3615 if (compare_icons_horizontal (container,
3616 best_so_far,
3617 candidate) < 0)
3618 {
3619 /* candidate is right of the best choice, but left of the current column */
3620 return TRUE(!(0));
3621 }
3622
3623 if (compare_icons_vertical (container,
3624 best_so_far,
3625 candidate) > 0)
3626 {
3627 return TRUE(!(0));
3628 }
3629 }
3630
3631 return best_so_far == NULL((void*)0);
3632}
3633
3634
3635static gboolean
3636next_column_highest (BaulIconContainer *container,
3637 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3638 BaulIcon *best_so_far,
3639 BaulIcon *candidate,
3640 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3641{
3642 /* sort out icons that are not after the current column */
3643 if (compare_with_start_column (container, candidate) >= 0)
3644 {
3645 return FALSE(0);
3646 }
3647
3648 if (best_so_far != NULL((void*)0))
3649 {
3650 if (compare_icons_horizontal_first (container,
3651 best_so_far,
3652 candidate) > 0)
3653 {
3654 /* candidate is left of the best choice, but right of the current column */
3655 return TRUE(!(0));
3656 }
3657
3658 if (compare_icons_vertical_first (container,
3659 best_so_far,
3660 candidate) > 0)
3661 {
3662 return TRUE(!(0));
3663 }
3664 }
3665
3666 return best_so_far == NULL((void*)0);
3667}
3668
3669static gboolean
3670previous_column_lowest (BaulIconContainer *container,
3671 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3672 BaulIcon *best_so_far,
3673 BaulIcon *candidate,
3674 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3675{
3676 /* sort out icons that are not before the current column */
3677 if (compare_with_start_column (container, candidate) <= 0)
3678 {
3679 return FALSE(0);
3680 }
3681
3682 if (best_so_far != NULL((void*)0))
3683 {
3684 if (compare_icons_horizontal_first (container,
3685 best_so_far,
3686 candidate) < 0)
3687 {
3688 /* candidate is right of the best choice, but left of the current column */
3689 return TRUE(!(0));
3690 }
3691
3692 if (compare_icons_vertical_first (container,
3693 best_so_far,
3694 candidate) < 0)
3695 {
3696 return TRUE(!(0));
3697 }
3698 }
3699
3700 return best_so_far == NULL((void*)0);
3701}
3702
3703static gboolean
3704last_column_lowest (BaulIconContainer *container,
3705 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3706 BaulIcon *best_so_far,
3707 BaulIcon *candidate,
3708 void *data G_GNUC_UNUSED__attribute__ ((__unused__)))
3709{
3710 if (best_so_far == NULL((void*)0))
3711 {
3712 return TRUE(!(0));
3713 }
3714 return compare_icons_horizontal_first (container, best_so_far, candidate) < 0;
3715}
3716
3717static gboolean
3718closest_in_90_degrees (BaulIconContainer *container,
3719 BaulIcon *start_icon G_GNUC_UNUSED__attribute__ ((__unused__)),
3720 BaulIcon *best_so_far,
3721 BaulIcon *candidate,
3722 void *data)
3723{
3724 EelDRect world_rect;
3725 int x, y;
3726 int dx, dy;
3727 int dist;
3728 int *best_dist;
3729
3730
3731 world_rect = baul_icon_canvas_item_get_icon_rectangle (candidate->item);
3732 eel_canvas_w2c
3733 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3734 get_cmp_point_x (container, world_rect),
3735 get_cmp_point_y (container, world_rect),
3736 &x,
3737 &y);
3738
3739 dx = x - container->details->arrow_key_start_x;
3740 dy = y - container->details->arrow_key_start_y;
3741
3742 switch (container->details->arrow_key_direction)
3743 {
3744 case CTK_DIR_UP:
3745 if (dy > 0 ||
3746 ABS(dx)(((dx) < 0) ? -(dx) : (dx)) > ABS(dy)(((dy) < 0) ? -(dy) : (dy)))
3747 {
3748 return FALSE(0);
3749 }
3750 break;
3751 case CTK_DIR_DOWN:
3752 if (dy < 0 ||
3753 ABS(dx)(((dx) < 0) ? -(dx) : (dx)) > ABS(dy)(((dy) < 0) ? -(dy) : (dy)))
3754 {
3755 return FALSE(0);
3756 }
3757 break;
3758 case CTK_DIR_LEFT:
3759 if (dx > 0 ||
3760 ABS(dy)(((dy) < 0) ? -(dy) : (dy)) > ABS(dx)(((dx) < 0) ? -(dx) : (dx)))
3761 {
3762 return FALSE(0);
3763 }
3764 break;
3765 case CTK_DIR_RIGHT:
3766 if (dx < 0 ||
3767 ABS(dy)(((dy) < 0) ? -(dy) : (dy)) > ABS(dx)(((dx) < 0) ? -(dx) : (dx)))
3768 {
3769 return FALSE(0);
3770 }
3771 break;
3772 default:
3773 g_assert_not_reached()do { g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 3773, ((const char*) (__func__)), ((void*)0)); } while (0)
;
3774 }
3775
3776 dist = dx*dx + dy*dy;
3777 best_dist = data;
3778
3779 if (best_so_far == NULL((void*)0))
3780 {
3781 *best_dist = dist;
3782 return TRUE(!(0));
3783 }
3784
3785 if (dist < *best_dist)
3786 {
3787 *best_dist = dist;
3788 return TRUE(!(0));
3789 }
3790
3791 return FALSE(0);
3792}
3793
3794static EelDRect
3795get_rubberband (BaulIcon *icon1,
3796 BaulIcon *icon2)
3797{
3798 EelDRect rect1;
3799 EelDRect rect2;
3800 EelDRect ret;
3801
3802 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (icon1->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon1->item)), ((eel_canvas_item_get_type ()))))))
,
3803 &rect1.x0, &rect1.y0,
3804 &rect1.x1, &rect1.y1);
3805 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (icon2->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon2->item)), ((eel_canvas_item_get_type ()))))))
,
3806 &rect2.x0, &rect2.y0,
3807 &rect2.x1, &rect2.y1);
3808
3809 eel_drect_union (&ret, &rect1, &rect2);
3810
3811 return ret;
3812}
3813
3814static void
3815keyboard_move_to (BaulIconContainer *container,
3816 BaulIcon *icon,
3817 BaulIcon *from,
3818 CdkEventKey *event)
3819{
3820 if (icon == NULL((void*)0))
3821 {
3822 return;
3823 }
3824
3825 if (event != NULL((void*)0) &&
3826 (event->state & CDK_CONTROL_MASK) != 0 &&
3827 (event->state & CDK_SHIFT_MASK) == 0)
3828 {
3829 /* Move the keyboard focus. Use Control modifier
3830 * rather than Alt to avoid Sawfish conflict.
3831 */
3832 set_keyboard_focus (container, icon);
3833 container->details->keyboard_rubberband_start = NULL((void*)0);
3834 }
3835 else if (event != NULL((void*)0) &&
3836 ((event->state & CDK_CONTROL_MASK) != 0 ||
3837 !container->details->auto_layout) &&
3838 (event->state & CDK_SHIFT_MASK) != 0)
3839 {
3840 /* Do rubberband selection */
3841 EelDRect rect;
3842
3843 if (from && !container->details->keyboard_rubberband_start)
3844 {
3845 set_keyboard_rubberband_start (container, from);
3846 }
3847
3848 set_keyboard_focus (container, icon);
3849
3850 if (icon && container->details->keyboard_rubberband_start)
3851 {
3852 rect = get_rubberband (container->details->keyboard_rubberband_start,
3853 icon);
3854 rubberband_select (container, NULL((void*)0), &rect);
3855 }
3856 }
3857 else if (event != NULL((void*)0) &&
3858 (event->state & CDK_CONTROL_MASK) == 0 &&
3859 (event->state & CDK_SHIFT_MASK) != 0)
3860 {
3861 /* Select range */
3862 BaulIcon *start_icon;
3863
3864 start_icon = container->details->range_selection_base_icon;
3865 if (start_icon == NULL((void*)0) || !start_icon->is_selected)
3866 {
3867 start_icon = icon;
3868 container->details->range_selection_base_icon = icon;
3869 }
3870
3871 set_keyboard_focus (container, icon);
3872
3873 if (select_range (container, start_icon, icon, TRUE(!(0))))
3874 {
3875 g_signal_emit (container,
3876 signals[SELECTION_CHANGED], 0);
3877 }
3878 }
3879 else
3880 {
3881 /* Select icons and get rid of the special keyboard focus. */
3882 clear_keyboard_focus (container);
3883 clear_keyboard_rubberband_start (container);
3884
3885 container->details->range_selection_base_icon = icon;
3886 if (select_one_unselect_others (container, icon))
3887 {
3888 g_signal_emit (container,
3889 signals[SELECTION_CHANGED], 0);
3890 }
3891 }
3892 schedule_keyboard_icon_reveal (container, icon);
3893}
3894
3895static void
3896keyboard_home (BaulIconContainer *container,
3897 CdkEventKey *event)
3898{
3899 BaulIcon *from;
3900 BaulIcon *to;
3901
3902 /* Home selects the first icon.
3903 * Control-Home sets the keyboard focus to the first icon.
3904 */
3905
3906 from = find_best_selected_icon (container, NULL((void*)0),
3907 rightmost_in_bottom_row,
3908 NULL((void*)0));
3909 to = find_best_icon (container, NULL((void*)0), leftmost_in_top_row, NULL((void*)0));
3910
3911 keyboard_move_to (container, to, from, event);
3912}
3913
3914static void
3915keyboard_end (BaulIconContainer *container,
3916 CdkEventKey *event)
3917{
3918 BaulIcon *to;
3919 BaulIcon *from;
3920
3921 /* End selects the last icon.
3922 * Control-End sets the keyboard focus to the last icon.
3923 */
3924 from = find_best_selected_icon (container, NULL((void*)0),
3925 leftmost_in_top_row,
3926 NULL((void*)0));
3927 to = find_best_icon (container, NULL((void*)0),
3928 baul_icon_container_is_layout_vertical (container) ?
3929 last_column_lowest :
3930 rightmost_in_bottom_row,
3931 NULL((void*)0));
3932
3933 keyboard_move_to (container, to, from, event);
3934}
3935
3936static void
3937record_arrow_key_start (BaulIconContainer *container,
3938 BaulIcon *icon,
3939 CtkDirectionType direction)
3940{
3941 EelDRect world_rect;
3942
3943 world_rect = baul_icon_canvas_item_get_icon_rectangle (icon->item);
3944 eel_canvas_w2c
3945 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
3946 get_cmp_point_x (container, world_rect),
3947 get_cmp_point_y (container, world_rect),
3948 &container->details->arrow_key_start_x,
3949 &container->details->arrow_key_start_y);
3950 container->details->arrow_key_direction = direction;
3951}
3952
3953static void
3954keyboard_arrow_key (BaulIconContainer *container,
3955 CdkEventKey *event,
3956 CtkDirectionType direction,
3957 IsBetterIconFunction better_start,
3958 IsBetterIconFunction empty_start,
3959 IsBetterIconFunction better_destination,
3960 IsBetterIconFunction better_destination_fallback,
3961 IsBetterIconFunction better_destination_fallback_fallback,
3962 IsBetterIconFunction better_destination_manual)
3963{
3964 BaulIcon *from;
3965 BaulIcon *to;
3966 int data;
3967
3968 /* Chose the icon to start with.
3969 * If we have a keyboard focus, start with it.
3970 * Otherwise, use the single selected icon.
3971 * If there's multiple selection, use the icon farthest toward the end.
3972 */
3973
3974 from = container->details->keyboard_focus;
3975
3976 if (from == NULL((void*)0))
3977 {
3978 if (has_multiple_selection (container))
3979 {
3980 if (all_selected (container))
3981 {
3982 from = find_best_selected_icon
3983 (container, NULL((void*)0),
3984 empty_start, NULL((void*)0));
3985 }
3986 else
3987 {
3988 from = find_best_selected_icon
3989 (container, NULL((void*)0),
3990 better_start, NULL((void*)0));
3991 }
3992 }
3993 else
3994 {
3995 from = get_first_selected_icon (container);
3996 }
3997 }
3998
3999 /* If there's no icon, select the icon farthest toward the end.
4000 * If there is an icon, select the next icon based on the arrow direction.
4001 */
4002 if (from == NULL((void*)0))
4003 {
4004 to = from = find_best_icon
4005 (container, NULL((void*)0),
4006 empty_start, NULL((void*)0));
4007 }
4008 else
4009 {
4010 record_arrow_key_start (container, from, direction);
4011
4012 to = find_best_icon
4013 (container, from,
4014 container->details->auto_layout ? better_destination : better_destination_manual,
4015 &data);
4016
4017 /* Wrap around to next/previous row/column */
4018 if (to == NULL((void*)0) &&
4019 better_destination_fallback != NULL((void*)0)) {
4020 to = find_best_icon
4021 (container, from,
4022 better_destination_fallback,
4023 &data);
4024 }
4025
4026 /* With a layout like
4027 * 1 2 3
4028 * 4
4029 * (horizontal layout)
4030 *
4031 * or
4032 *
4033 * 1 4
4034 * 2
4035 * 3
4036 * (vertical layout)
4037 *
4038 * * pressing down for any of 1,2,3 (horizontal layout)
4039 * * pressing right for any of 1,2,3 (vertical layout)
4040 *
4041 * Should select 4.
4042 */
4043 if (to == NULL((void*)0) &&
4044 container->details->auto_layout &&
4045 better_destination_fallback_fallback != NULL((void*)0))
4046 {
4047 to = find_best_icon
4048 (container, from,
4049 better_destination_fallback_fallback,
4050 &data);
4051 }
4052
4053 if (to == NULL((void*)0))
4054 {
4055 to = from;
4056 }
4057
4058 }
4059
4060 keyboard_move_to (container, to, from, event);
4061}
4062
4063static gboolean
4064is_rectangle_selection_event (CdkEventKey *event)
4065{
4066 return (event->state & CDK_CONTROL_MASK) != 0 &&
4067 (event->state & CDK_SHIFT_MASK) != 0;
4068}
4069
4070static void
4071keyboard_right (BaulIconContainer *container,
4072 CdkEventKey *event)
4073{
4074 IsBetterIconFunction fallback;
4075 IsBetterIconFunction next_column_fallback;
4076
4077 fallback = NULL((void*)0);
4078 if (container->details->auto_layout &&
4079 !baul_icon_container_is_layout_vertical (container) &&
4080 !is_rectangle_selection_event (event))
4081 {
4082 fallback = next_row_leftmost;
4083 }
4084
4085 next_column_fallback = NULL((void*)0);
4086 if (baul_icon_container_is_layout_vertical (container) &&
4087 ctk_widget_get_direction (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
) != CTK_TEXT_DIR_RTL)
4088 {
4089 next_column_fallback = next_column_bottommost;
4090 }
4091
4092 /* Right selects the next icon in the same row.
4093 * Control-Right sets the keyboard focus to the next icon in the same row.
4094 */
4095 keyboard_arrow_key (container,
4096 event,
4097 CTK_DIR_RIGHT,
4098 rightmost_in_bottom_row,
4099 baul_icon_container_is_layout_rtl (container) ?
4100 rightmost_in_top_row : leftmost_in_top_row,
4101 same_row_right_side_leftmost,
4102 fallback,
4103 next_column_fallback,
4104 closest_in_90_degrees);
4105}
4106
4107static void
4108keyboard_left (BaulIconContainer *container,
4109 CdkEventKey *event)
4110{
4111 IsBetterIconFunction fallback;
4112 IsBetterIconFunction previous_column_fallback;
4113
4114 fallback = NULL((void*)0);
4115 if (container->details->auto_layout &&
4116 !baul_icon_container_is_layout_vertical (container) &&
4117 !is_rectangle_selection_event (event))
4118 {
4119 fallback = previous_row_rightmost;
4120 }
4121
4122 previous_column_fallback = NULL((void*)0);
4123 if (baul_icon_container_is_layout_vertical (container) &&
4124 ctk_widget_get_direction (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
) == CTK_TEXT_DIR_RTL)
4125 {
4126 previous_column_fallback = previous_column_lowest;
4127 }
4128
4129 /* Left selects the next icon in the same row.
4130 * Control-Left sets the keyboard focus to the next icon in the same row.
4131 */
4132 keyboard_arrow_key (container,
4133 event,
4134 CTK_DIR_LEFT,
4135 rightmost_in_bottom_row,
4136 baul_icon_container_is_layout_rtl (container) ?
4137 rightmost_in_top_row : leftmost_in_top_row,
4138 same_row_left_side_rightmost,
4139 fallback,
4140 previous_column_fallback,
4141 closest_in_90_degrees);
4142}
4143
4144static void
4145keyboard_down (BaulIconContainer *container,
4146 CdkEventKey *event)
4147{
4148 IsBetterIconFunction fallback;
4149 IsBetterIconFunction next_row_fallback;
4150
4151 fallback = NULL((void*)0);
4152 if (container->details->auto_layout &&
4153 baul_icon_container_is_layout_vertical (container) &&
4154 !is_rectangle_selection_event (event))
4155 {
4156 if (ctk_widget_get_direction (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
) == CTK_TEXT_DIR_RTL)
4157 {
4158 fallback = previous_column_highest;
4159 }
4160 else
4161 {
4162 fallback = next_column_highest;
4163 }
4164 }
4165
4166 next_row_fallback = NULL((void*)0);
4167 if (!baul_icon_container_is_layout_vertical (container))
4168 {
4169 if (ctk_widget_get_direction (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
) == CTK_TEXT_DIR_RTL)
4170 {
4171 next_row_fallback = next_row_leftmost;
4172 }
4173 else
4174 {
4175 next_row_fallback = next_row_rightmost;
4176 }
4177 }
4178
4179 /* Down selects the next icon in the same column.
4180 * Control-Down sets the keyboard focus to the next icon in the same column.
4181 */
4182 keyboard_arrow_key (container,
4183 event,
4184 CTK_DIR_DOWN,
4185 rightmost_in_bottom_row,
4186 baul_icon_container_is_layout_rtl (container) ?
4187 rightmost_in_top_row : leftmost_in_top_row,
4188 same_column_below_highest,
4189 fallback,
4190 next_row_fallback,
4191 closest_in_90_degrees);
4192}
4193
4194static void
4195keyboard_up (BaulIconContainer *container,
4196 CdkEventKey *event)
4197{
4198 IsBetterIconFunction fallback;
4199
4200 fallback = NULL((void*)0);
4201 if (container->details->auto_layout &&
4202 baul_icon_container_is_layout_vertical (container) &&
4203 !is_rectangle_selection_event (event))
4204 {
4205 if (ctk_widget_get_direction (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
) == CTK_TEXT_DIR_RTL)
4206 {
4207 fallback = next_column_bottommost;
4208 }
4209 else
4210 {
4211 fallback = previous_column_lowest;
4212 }
4213 }
4214
4215 /* Up selects the next icon in the same column.
4216 * Control-Up sets the keyboard focus to the next icon in the same column.
4217 */
4218 keyboard_arrow_key (container,
4219 event,
4220 CTK_DIR_UP,
4221 rightmost_in_bottom_row,
4222 baul_icon_container_is_layout_rtl (container) ?
4223 rightmost_in_top_row : leftmost_in_top_row,
4224 same_column_above_lowest,
4225 fallback,
4226 NULL((void*)0),
4227 closest_in_90_degrees);
4228}
4229
4230static void
4231keyboard_space (BaulIconContainer *container,
4232 CdkEventKey *event)
4233{
4234 BaulIcon *icon;
4235
4236 if (!has_selection (container) &&
4237 container->details->keyboard_focus != NULL((void*)0))
4238 {
4239 keyboard_move_to (container,
4240 container->details->keyboard_focus,
4241 NULL((void*)0), NULL((void*)0));
4242 }
4243 else if ((event->state & CDK_CONTROL_MASK) != 0 &&
4244 (event->state & CDK_SHIFT_MASK) == 0)
4245 {
4246 /* Control-space toggles the selection state of the current icon. */
4247 if (container->details->keyboard_focus != NULL((void*)0))
4248 {
4249 icon_toggle_selected (container, container->details->keyboard_focus);
4250 g_signal_emit (container, signals[SELECTION_CHANGED], 0);
4251 if (container->details->keyboard_focus->is_selected)
4252 {
4253 container->details->range_selection_base_icon = container->details->keyboard_focus;
4254 }
4255 }
4256 else
4257 {
4258 icon = find_best_selected_icon (container,
4259 NULL((void*)0),
4260 leftmost_in_top_row,
4261 NULL((void*)0));
4262 if (icon == NULL((void*)0))
4263 {
4264 icon = find_best_icon (container,
4265 NULL((void*)0),
4266 leftmost_in_top_row,
4267 NULL((void*)0));
4268 }
4269 if (icon != NULL((void*)0))
4270 {
4271 set_keyboard_focus (container, icon);
4272 }
4273 }
4274 }
4275 else if ((event->state & CDK_SHIFT_MASK) != 0)
4276 {
4277 activate_selected_items_alternate (container, NULL((void*)0));
4278 }
4279 else
4280 {
4281 activate_selected_items (container);
4282 }
4283}
4284
4285/* look for the first icon that matches the longest part of a given
4286 * search pattern
4287 */
4288typedef struct
4289{
4290 gunichar *name;
4291 int last_match_length;
4292} BestNameMatch;
4293
4294#ifndef TAB_NAVIGATION_DISABLED
4295static void
4296select_previous_or_next_icon (BaulIconContainer *container,
4297 gboolean next,
4298 CdkEventKey *event)
4299{
4300 BaulIcon *icon;
4301 const GList *item;
4302
4303 item = NULL((void*)0);
4304 /* Chose the icon to start with.
4305 * If we have a keyboard focus, start with it.
4306 * Otherwise, use the single selected icon.
4307 */
4308 icon = container->details->keyboard_focus;
4309 if (icon == NULL((void*)0))
4310 {
4311 icon = get_first_selected_icon (container);
4312 }
4313
4314 if (icon != NULL((void*)0))
4315 {
4316 /* must have at least @icon in the list */
4317 g_assert (container->details->icons != NULL)do { if (container->details->icons != ((void*)0)) ; else
g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 4317, ((const char*) (__func__)), "container->details->icons != NULL"
); } while (0)
;
4318 item = g_list_find (container->details->icons, icon);
4319 g_assert (item != NULL)do { if (item != ((void*)0)) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 4319, ((const char*) (
__func__)), "item != NULL"); } while (0)
;
4320
4321 item = next ? item->next : item->prev;
4322 if (item == NULL((void*)0))
4323 {
4324 item = next ? g_list_first (container->details->icons) : g_list_last (container->details->icons);
4325 }
4326
4327 }
4328 else if (container->details->icons != NULL((void*)0))
4329 {
4330 /* no selection yet, pick the first or last item to select */
4331 item = next ? g_list_first (container->details->icons) : g_list_last (container->details->icons);
4332 }
4333
4334 icon = (item != NULL((void*)0)) ? item->data : NULL((void*)0);
4335
4336 if (icon != NULL((void*)0))
4337 {
4338 keyboard_move_to (container, icon, NULL((void*)0), event);
4339 }
4340}
4341#endif
4342
4343static void
4344destroy (CtkWidget *object)
4345{
4346 BaulIconContainer *container;
4347
4348 container = BAUL_ICON_CONTAINER (object)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((object)), (baul_icon_container_get_type())
))))
;
4349
4350 baul_icon_container_clear (container);
4351
4352 if (container->details->rubberband_info.timer_id != 0)
4353 {
4354 g_source_remove (container->details->rubberband_info.timer_id);
4355 container->details->rubberband_info.timer_id = 0;
4356 }
4357
4358 if (container->details->idle_id != 0)
4359 {
4360 g_source_remove (container->details->idle_id);
4361 container->details->idle_id = 0;
4362 }
4363
4364 if (container->details->stretch_idle_id != 0)
4365 {
4366 g_source_remove (container->details->stretch_idle_id);
4367 container->details->stretch_idle_id = 0;
4368 }
4369
4370 if (container->details->align_idle_id != 0)
4371 {
4372 g_source_remove (container->details->align_idle_id);
4373 container->details->align_idle_id = 0;
4374 }
4375
4376 if (container->details->selection_changed_id != 0)
4377 {
4378 g_source_remove (container->details->selection_changed_id);
4379 container->details->selection_changed_id = 0;
4380 }
4381
4382 if (container->details->size_allocation_count_id != 0)
4383 {
4384 g_source_remove (container->details->size_allocation_count_id);
4385 container->details->size_allocation_count_id = 0;
4386 }
4387
4388 /* destroy interactive search dialog */
4389 if (container->details->search_window)
4390 {
4391 ctk_widget_destroy (container->details->search_window);
4392 container->details->search_window = NULL((void*)0);
4393 container->details->search_entry = NULL((void*)0);
4394 if (container->details->typeselect_flush_timeout)
4395 {
4396 g_source_remove (container->details->typeselect_flush_timeout);
4397 container->details->typeselect_flush_timeout = 0;
4398 }
4399 }
4400
4401 CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->destroy (object);
4402}
4403
4404static void
4405finalize (GObject *object)
4406{
4407 BaulIconContainerDetails *details;
4408
4409 details = BAUL_ICON_CONTAINER (object)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((object)), (baul_icon_container_get_type())
))))
->details;
4410
4411 g_signal_handlers_disconnect_by_func (baul_icon_view_preferences,g_signal_handlers_disconnect_matched ((baul_icon_view_preferences
), (GSignalMatchType) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA
), 0, 0, ((void*)0), (text_ellipsis_limit_changed_container_callback
), (object))
4412 text_ellipsis_limit_changed_container_callback,g_signal_handlers_disconnect_matched ((baul_icon_view_preferences
), (GSignalMatchType) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA
), 0, 0, ((void*)0), (text_ellipsis_limit_changed_container_callback
), (object))
4413 object)g_signal_handlers_disconnect_matched ((baul_icon_view_preferences
), (GSignalMatchType) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA
), 0, 0, ((void*)0), (text_ellipsis_limit_changed_container_callback
), (object))
;
4414 g_signal_handlers_disconnect_by_func (baul_desktop_preferences,g_signal_handlers_disconnect_matched ((baul_desktop_preferences
), (GSignalMatchType) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA
), 0, 0, ((void*)0), (text_ellipsis_limit_changed_container_callback
), (object))
4415 text_ellipsis_limit_changed_container_callback,g_signal_handlers_disconnect_matched ((baul_desktop_preferences
), (GSignalMatchType) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA
), 0, 0, ((void*)0), (text_ellipsis_limit_changed_container_callback
), (object))
4416 object)g_signal_handlers_disconnect_matched ((baul_desktop_preferences
), (GSignalMatchType) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA
), 0, 0, ((void*)0), (text_ellipsis_limit_changed_container_callback
), (object))
;
4417
4418 g_hash_table_destroy (details->icon_set);
4419 details->icon_set = NULL((void*)0);
4420
4421 g_free (details->font);
4422
4423 if (details->a11y_item_action_queue != NULL((void*)0))
4424 {
4425 while (!g_queue_is_empty (details->a11y_item_action_queue))
4426 {
4427 g_free (g_queue_pop_head (details->a11y_item_action_queue));
4428 }
4429 g_queue_free (details->a11y_item_action_queue);
4430 }
4431 if (details->a11y_item_action_idle_handler != 0)
4432 {
4433 g_source_remove (details->a11y_item_action_idle_handler);
4434 }
4435
4436 g_free (details);
4437
4438 G_OBJECT_CLASS (baul_icon_container_parent_class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), (((GType) ((20) <<
(2))))))))
->finalize (object);
4439}
4440
4441/* CtkWidget methods. */
4442
4443static gboolean
4444clear_size_allocation_count (gpointer data)
4445{
4446 BaulIconContainer *container;
4447
4448 container = BAUL_ICON_CONTAINER (data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((data)), (baul_icon_container_get_type())))
))
;
4449
4450 container->details->size_allocation_count_id = 0;
4451 container->details->size_allocation_count = 0;
4452
4453 return FALSE(0);
4454}
4455
4456static void
4457size_allocate (CtkWidget *widget,
4458 CtkAllocation *allocation)
4459{
4460 BaulIconContainer *container;
4461 gboolean need_layout_redone;
4462 CtkAllocation wid_allocation;
4463
4464 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
4465
4466 need_layout_redone = !container->details->has_been_allocated;
4467 ctk_widget_get_allocation (widget, &wid_allocation);
4468
4469 if (allocation->width != wid_allocation.width)
4470 {
4471 need_layout_redone = TRUE(!(0));
4472 }
4473
4474 if (allocation->height != wid_allocation.height)
4475 {
4476 need_layout_redone = TRUE(!(0));
4477 }
4478
4479 /* Under some conditions we can end up in a loop when size allocating.
4480 * This happens when the icons don't fit without a scrollbar, but fits
4481 * when a scrollbar is added (bug #129963 for details).
4482 * We keep track of this looping by increasing a counter in size_allocate
4483 * and clearing it in a high-prio idle (the only way to detect the loop is
4484 * done).
4485 * When we've done at more than two iterations (with/without scrollbar)
4486 * we terminate this looping by not redoing the layout when the width
4487 * is wider than the current one (i.e when removing the scrollbar).
4488 */
4489 if (container->details->size_allocation_count_id == 0)
4490 {
4491 container->details->size_allocation_count_id =
4492 g_idle_add_full (G_PRIORITY_HIGH-100,
4493 clear_size_allocation_count,
4494 container, NULL((void*)0));
4495 }
4496 container->details->size_allocation_count++;
4497 if (container->details->size_allocation_count > 2 &&
4498 allocation->width >= wid_allocation.width)
4499 {
4500 need_layout_redone = FALSE(0);
4501 }
4502
4503 CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->size_allocate (widget, allocation);
4504
4505 container->details->has_been_allocated = TRUE(!(0));
4506
4507 if (need_layout_redone)
4508 {
4509 redo_layout (container);
4510 }
4511}
4512
4513static CtkSizeRequestMode
4514get_request_mode (CtkWidget *widget G_GNUC_UNUSED__attribute__ ((__unused__)))
4515{
4516 /* Don't trade size at all, since we get whatever we get anyway. */
4517 return CTK_SIZE_REQUEST_CONSTANT_SIZE;
4518}
4519
4520 /* We need to implement these since the CtkScrolledWindow uses them
4521 to guess whether to show scrollbars or not, and if we don't report
4522 anything it'll tend to get it wrong causing double calls
4523 to size_allocate (at different sizes) during its size allocation. */
4524static void
4525get_prefered_width (CtkWidget *widget,
4526 gint *minimum_size,
4527 gint *natural_size)
4528{
4529 EelCanvasGroup *root;
4530 double x1, x2;
4531 int cx1, cx2;
4532 int width;
4533
4534 root = eel_canvas_root (EEL_CANVAS (widget)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((eel_canvas_get_type ()))))))
);
4535 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (root)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((root)), ((eel_canvas_item_get_type ()))))))
,
4536 &x1, NULL((void*)0), &x2, NULL((void*)0));
4537 eel_canvas_w2c (EEL_CANVAS (widget)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((eel_canvas_get_type ()))))))
, x1, 0, &cx1, NULL((void*)0));
4538 eel_canvas_w2c (EEL_CANVAS (widget)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((eel_canvas_get_type ()))))))
, x2, 0, &cx2, NULL((void*)0));
4539
4540 width = cx2 - cx1;
4541 if (natural_size) {
4542 *natural_size = width;
4543 }
4544 if (minimum_size) {
4545 *minimum_size = width;
4546 }
4547}
4548
4549static void
4550get_prefered_height (CtkWidget *widget,
4551 gint *minimum_size,
4552 gint *natural_size)
4553{
4554 EelCanvasGroup *root;
4555 double y1, y2;
4556 int cy1, cy2;
4557 int height;
4558
4559 root = eel_canvas_root (EEL_CANVAS (widget)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((eel_canvas_get_type ()))))))
);
4560 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (root)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((root)), ((eel_canvas_item_get_type ()))))))
,
4561 NULL((void*)0), &y1, NULL((void*)0), &y2);
4562 eel_canvas_w2c (EEL_CANVAS (widget)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((eel_canvas_get_type ()))))))
, 0, y1, NULL((void*)0), &cy1);
4563 eel_canvas_w2c (EEL_CANVAS (widget)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((eel_canvas_get_type ()))))))
, 0, y2, NULL((void*)0), &cy2);
4564
4565 height = cy2 - cy1;
4566 if (natural_size) {
4567 *natural_size = height;
4568 }
4569 if (minimum_size) {
4570 *minimum_size = height;
4571 }
4572}
4573
4574static gboolean
4575draw (CtkWidget *widget, cairo_t *cr)
4576{
4577 if (!BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
->details->is_desktop)
4578 {
4579 eel_background_draw (widget, cr);
4580 }
4581
4582 return CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->draw (widget,
4583 cr);
4584}
4585
4586static void
4587realize (CtkWidget *widget)
4588{
4589 CtkAdjustment *vadj, *hadj;
4590 BaulIconContainer *container;
4591
4592 CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->realize (widget);
4593
4594 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
4595
4596 /* Set up DnD. */
4597 baul_icon_dnd_init (container);
4598
4599 hadj = ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (widget)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((ctk_scrollable_get_type ()))))))
);
4600 g_signal_connect (hadj, "value_changed",g_signal_connect_data ((hadj), ("value_changed"), (((GCallback
) (handle_hadjustment_changed))), (widget), ((void*)0), (GConnectFlags
) 0)
4601 G_CALLBACK (handle_hadjustment_changed), widget)g_signal_connect_data ((hadj), ("value_changed"), (((GCallback
) (handle_hadjustment_changed))), (widget), ((void*)0), (GConnectFlags
) 0)
;
4602
4603 vadj = ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (widget)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), ((ctk_scrollable_get_type ()))))))
);
4604 g_signal_connect (vadj, "value_changed",g_signal_connect_data ((vadj), ("value_changed"), (((GCallback
) (handle_vadjustment_changed))), (widget), ((void*)0), (GConnectFlags
) 0)
4605 G_CALLBACK (handle_vadjustment_changed), widget)g_signal_connect_data ((vadj), ("value_changed"), (((GCallback
) (handle_vadjustment_changed))), (widget), ((void*)0), (GConnectFlags
) 0)
;
4606
4607}
4608
4609static void
4610unrealize (CtkWidget *widget)
4611{
4612 BaulIconContainer *container;
4613
4614 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
4615
4616 baul_icon_dnd_fini (container);
4617
4618 if (container->details->typeselect_flush_timeout)
4619 {
4620 g_source_remove (container->details->typeselect_flush_timeout);
4621 container->details->typeselect_flush_timeout = 0;
4622 }
4623
4624 CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->unrealize (widget);
4625}
4626
4627static void
4628style_updated (CtkWidget *widget)
4629{
4630 BaulIconContainer *container;
4631
4632 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
4633 container->details->use_drop_shadows = container->details->drop_shadows_requested;
4634
4635 /* Don't chain up to parent, if this is a desktop container,
4636 * because that resets the background of the window.
4637 */
4638 if (!baul_icon_container_get_is_desktop (container)) {
4639 CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->style_updated (widget);
4640 }
4641
4642 if (ctk_widget_get_realized (widget))
4643 {
4644 invalidate_labels (container);
4645 baul_icon_container_request_update_all (container);
4646 }
4647}
4648
4649static gboolean
4650button_press_event (CtkWidget *widget,
4651 CdkEventButton *event)
4652{
4653 BaulIconContainer *container;
4654 gboolean selection_changed;
4655 gboolean return_value;
4656 gboolean clicked_on_icon;
4657
4658 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
4659 container->details->button_down_time = event->time;
4660
4661 /* Forget about the old keyboard selection now that we've started mousing. */
4662 clear_keyboard_focus (container);
4663 clear_keyboard_rubberband_start (container);
4664
4665 if (event->type == CDK_2BUTTON_PRESS || event->type == CDK_3BUTTON_PRESS)
4666 {
4667 /* We use our own double-click detection. */
4668 return TRUE(!(0));
4669 }
4670
4671 /* Invoke the canvas event handler and see if an item picks up the event. */
4672 clicked_on_icon = CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->button_press_event (widget, event);
4673
4674 /* Move focus to icon container, unless we're still renaming (to avoid exiting
4675 * renaming mode)
4676 */
4677 if (!ctk_widget_has_focus (widget) && !(is_renaming (container) || is_renaming_pending (container)))
4678 {
4679 ctk_widget_grab_focus (widget);
4680 }
4681
4682 if (clicked_on_icon)
4683 {
4684 return TRUE(!(0));
4685 }
4686
4687 if (event->button == DRAG_BUTTON1 &&
4688 event->type == CDK_BUTTON_PRESS)
4689 {
4690 /* Clear the last click icon for double click */
4691 container->details->double_click_icon[1] = container->details->double_click_icon[0];
4692 container->details->double_click_icon[0] = NULL((void*)0);
4693 }
4694
4695 /* Button 1 does rubber banding. */
4696 if (event->button == RUBBERBAND_BUTTON1)
4697 {
4698 if (! button_event_modifies_selection (event))
4699 {
4700 selection_changed = unselect_all (container);
4701 if (selection_changed)
4702 {
4703 g_signal_emit (container,
4704 signals[SELECTION_CHANGED], 0);
4705 }
4706 }
4707
4708 start_rubberbanding (container, event);
4709 return TRUE(!(0));
4710 }
4711
4712 /* Prevent multi-button weirdness such as bug 6181 */
4713 if (container->details->rubberband_info.active)
4714 {
4715 return TRUE(!(0));
4716 }
4717
4718 /* Button 2 may be passed to the window manager. */
4719 if (event->button == MIDDLE_BUTTON2)
4720 {
4721 selection_changed = unselect_all (container);
4722 if (selection_changed)
4723 {
4724 g_signal_emit (container, signals[SELECTION_CHANGED], 0);
4725 }
4726 g_signal_emit (widget, signals[MIDDLE_CLICK], 0, event);
4727 return TRUE(!(0));
4728 }
4729
4730 /* Button 3 does a contextual menu. */
4731 if (event->button == CONTEXTUAL_MENU_BUTTON3)
4732 {
4733 end_renaming_mode (container, TRUE(!(0)));
4734 selection_changed = unselect_all (container);
4735 if (selection_changed)
4736 {
4737 g_signal_emit (container, signals[SELECTION_CHANGED], 0);
4738 }
4739 g_signal_emit (widget, signals[CONTEXT_CLICK_BACKGROUND], 0, event);
4740 return TRUE(!(0));
4741 }
4742
4743 /* Otherwise, we emit a button_press message. */
4744 g_signal_emit (widget,
4745 signals[BUTTON_PRESS], 0, event,
4746 &return_value);
4747 return return_value;
4748}
4749
4750static void
4751baul_icon_container_did_not_drag (BaulIconContainer *container,
4752 CdkEventButton *event)
4753{
4754 BaulIconContainerDetails *details;
4755 gboolean selection_changed;
4756 static gint64 last_click_time = 0;
4757 static gint click_count = 0;
4758 gint double_click_time;
4759 gint64 current_time;
4760
4761 details = container->details;
4762
4763 if (details->icon_selected_on_button_down &&
4764 ((event->state & CDK_CONTROL_MASK) != 0 ||
4765 (event->state & CDK_SHIFT_MASK) == 0))
4766 {
4767 if (button_event_modifies_selection (event))
4768 {
4769 details->range_selection_base_icon = NULL((void*)0);
4770 icon_toggle_selected (container, details->drag_icon);
4771 g_signal_emit (container,
4772 signals[SELECTION_CHANGED], 0);
4773 }
4774 else
4775 {
4776 details->range_selection_base_icon = details->drag_icon;
4777 selection_changed = select_one_unselect_others
4778 (container, details->drag_icon);
4779
4780 if (selection_changed)
4781 {
4782 g_signal_emit (container,
4783 signals[SELECTION_CHANGED], 0);
4784 }
4785 }
4786 }
4787
4788 if (details->drag_icon != NULL((void*)0) &&
4789 (details->single_click_mode ||
4790 event->button == MIDDLE_BUTTON2))
4791 {
4792 /* Determine click count */
4793 g_object_get (G_OBJECT (ctk_widget_get_settings (CTK_WIDGET (container)))((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((ctk_widget_get_settings (((((CtkWidget*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((ctk_widget_get_type ())))
)))))), (((GType) ((20) << (2))))))))
,
4794 "ctk-double-click-time", &double_click_time,
4795 NULL((void*)0));
4796 current_time = g_get_monotonic_time ();
4797 if (current_time - last_click_time < double_click_time * 1000)
4798 {
4799 click_count++;
4800 }
4801 else
4802 {
4803 click_count = 0;
4804 }
4805
4806 /* Stash time for next compare */
4807 last_click_time = current_time;
4808
4809 /* If single-click mode, activate the selected icons, unless modifying
4810 * the selection or pressing for a very long time, or double clicking.
4811 */
4812
4813
4814 if (click_count == 0 &&
4815 event->time - details->button_down_time < MAX_CLICK_TIME1500 &&
4816 ! button_event_modifies_selection (event))
4817 {
4818
4819 /* It's a tricky UI issue whether this should activate
4820 * just the clicked item (as if it were a link), or all
4821 * the selected items (as if you were issuing an "activate
4822 * selection" command). For now, we're trying the activate
4823 * entire selection version to see how it feels. Note that
4824 * BaulList goes the other way because its "links" seem
4825 * much more link-like.
4826 */
4827 if (event->button == MIDDLE_BUTTON2)
4828 {
4829 activate_selected_items_alternate (container, NULL((void*)0));
4830 }
4831 else
4832 {
4833 activate_selected_items (container);
4834 }
4835 }
4836 }
4837}
4838
4839static gboolean
4840clicked_within_double_click_interval (BaulIconContainer *container)
4841{
4842 static gint64 last_click_time = 0;
4843 static gint click_count = 0;
4844 gint double_click_time;
4845 gint64 current_time;
4846
4847 /* Determine click count */
4848 g_object_get (G_OBJECT (ctk_widget_get_settings (CTK_WIDGET (container)))((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((ctk_widget_get_settings (((((CtkWidget*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((ctk_widget_get_type ())))
)))))), (((GType) ((20) << (2))))))))
,
4849 "ctk-double-click-time", &double_click_time,
4850 NULL((void*)0));
4851 current_time = g_get_monotonic_time ();
4852 if (current_time - last_click_time < double_click_time * 1000)
4853 {
4854 click_count++;
4855 }
4856 else
4857 {
4858 click_count = 0;
4859 }
4860
4861 /* Stash time for next compare */
4862 last_click_time = current_time;
4863
4864 /* Only allow double click */
4865 if (click_count == 1) {
4866 click_count = 0;
4867 return TRUE(!(0));
4868 } else {
4869 return FALSE(0);
4870 }
4871}
4872
4873static void
4874clear_drag_state (BaulIconContainer *container)
4875{
4876 container->details->drag_icon = NULL((void*)0);
4877 container->details->drag_state = DRAG_STATE_INITIAL;
4878}
4879
4880static gboolean
4881start_stretching (BaulIconContainer *container,
4882 CdkEvent *event)
4883{
4884 BaulIconContainerDetails *details;
4885 BaulIcon *icon;
4886 EelDPoint world_point;
4887 CtkWidget *toplevel;
4888 CdkDisplay *display;
4889 CtkCornerType corner;
4890 CdkCursor *cursor;
4891
4892 details = container->details;
4893 icon = details->stretch_icon;
4894 display = ctk_widget_get_display (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
4895
4896 /* Check if we hit the stretch handles. */
4897 world_point.x = details->drag_x;
4898 world_point.y = details->drag_y;
4899 if (!baul_icon_canvas_item_hit_test_stretch_handles (icon->item, world_point, &corner))
4900 {
4901 return FALSE(0);
4902 }
4903
4904 switch (corner)
4905 {
4906 case CTK_CORNER_TOP_LEFT:
4907 cursor = cdk_cursor_new_for_display (display, CDK_TOP_LEFT_CORNER);
4908 break;
4909 case CTK_CORNER_BOTTOM_LEFT:
4910 cursor = cdk_cursor_new_for_display (display, CDK_BOTTOM_LEFT_CORNER);
4911 break;
4912 case CTK_CORNER_TOP_RIGHT:
4913 cursor = cdk_cursor_new_for_display (display, CDK_TOP_RIGHT_CORNER);
4914 break;
4915 case CTK_CORNER_BOTTOM_RIGHT:
4916 cursor = cdk_cursor_new_for_display (display, CDK_BOTTOM_RIGHT_CORNER);
4917 break;
4918 default:
4919 cursor = NULL((void*)0);
4920 break;
4921 }
4922 /* Set up the dragging. */
4923 details->drag_state = DRAG_STATE_STRETCH;
4924 eel_canvas_w2c (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
4925 details->drag_x,
4926 details->drag_y,
4927 &details->stretch_start.pointer_x,
4928 &details->stretch_start.pointer_y);
4929 eel_canvas_w2c (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
4930 icon->x, icon->y,
4931 &details->stretch_start.icon_x,
4932 &details->stretch_start.icon_y);
4933 icon_get_size (container, icon,
4934 &details->stretch_start.icon_size);
4935
4936 eel_canvas_item_grab (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
4937 (CDK_POINTER_MOTION_MASK
4938 | CDK_BUTTON_RELEASE_MASK),
4939 cursor,
4940 event);
4941
4942 if (cursor)
4943 g_object_unref (cursor);
4944
4945 /* Ensure the window itself is focused.. */
4946 toplevel = ctk_widget_get_toplevel (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
4947 if (toplevel != NULL((void*)0) && ctk_widget_get_realized (toplevel))
4948 {
4949 cdk_window_focus (ctk_widget_get_window (toplevel), CDK_CURRENT_TIME0L);
4950 }
4951
4952 return TRUE(!(0));
4953}
4954
4955static gboolean
4956update_stretch_at_idle (BaulIconContainer *container)
4957{
4958 BaulIconContainerDetails *details;
4959 BaulIcon *icon;
4960 double world_x, world_y;
4961 StretchState stretch_state;
4962
4963 details = container->details;
4964 icon = details->stretch_icon;
4965
4966 if (icon == NULL((void*)0))
4967 {
4968 container->details->stretch_idle_id = 0;
4969 return FALSE(0);
4970 }
4971
4972 eel_canvas_w2c (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
4973 details->world_x, details->world_y,
4974 &stretch_state.pointer_x, &stretch_state.pointer_y);
4975
4976 compute_stretch (&details->stretch_start,
4977 &stretch_state);
4978
4979 eel_canvas_c2w (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
4980 stretch_state.icon_x, stretch_state.icon_y,
4981 &world_x, &world_y);
4982
4983 icon_set_position (icon, world_x, world_y);
4984 icon_set_size (container, icon, stretch_state.icon_size, FALSE(0), FALSE(0));
4985
4986 container->details->stretch_idle_id = 0;
4987
4988 return FALSE(0);
4989}
4990
4991static void
4992continue_stretching (BaulIconContainer *container,
4993 double world_x, double world_y)
4994{
4995
4996 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
4997
4998 container->details->world_x = world_x;
4999 container->details->world_y = world_y;
5000
5001 if (container->details->stretch_idle_id == 0)
5002 {
5003 container->details->stretch_idle_id = g_idle_add ((GSourceFunc) update_stretch_at_idle, container);
5004 }
5005}
5006
5007static gboolean
5008keyboard_stretching (BaulIconContainer *container,
5009 CdkEventKey *event)
5010{
5011 BaulIcon *icon;
5012 guint size;
5013
5014 icon = container->details->stretch_icon;
5015
5016 if (icon == NULL((void*)0) || !icon->is_selected)
5017 {
5018 return FALSE(0);
5019 }
5020
5021 icon_get_size (container, icon, &size);
5022
5023 switch (event->keyval)
5024 {
5025 case CDK_KEY_equal0x03d:
5026 case CDK_KEY_plus0x02b:
5027 case CDK_KEY_KP_Add0xffab:
5028 icon_set_size (container, icon, size + 5, FALSE(0), FALSE(0));
5029 break;
5030 case CDK_KEY_minus0x02d:
5031 case CDK_KEY_KP_Subtract0xffad:
5032 icon_set_size (container, icon, size - 5, FALSE(0), FALSE(0));
5033 break;
5034 case CDK_KEY_00x030:
5035 case CDK_KEY_KP_00xffb0:
5036 baul_icon_container_move_icon (container, icon,
5037 icon->x, icon->y,
5038 1.0,
5039 FALSE(0), TRUE(!(0)), TRUE(!(0)));
5040 break;
5041 }
5042
5043 return TRUE(!(0));
5044}
5045
5046static void
5047ungrab_stretch_icon (BaulIconContainer *container)
5048{
5049 eel_canvas_item_ungrab (EEL_CANVAS_ITEM (container->details->stretch_icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->stretch_icon->item)), ((eel_canvas_item_get_type
()))))))
);
5050}
5051
5052static void
5053end_stretching (BaulIconContainer *container,
5054 double world_x, double world_y)
5055{
5056 BaulIconPosition position;
5057 BaulIcon *icon;
5058
5059 continue_stretching (container, world_x, world_y);
5060 ungrab_stretch_icon (container);
5061
5062 /* now that we're done stretching, update the icon's position */
5063
5064 icon = container->details->drag_icon;
5065 if (baul_icon_container_is_layout_rtl (container))
5066 {
5067 position.x = icon->saved_ltr_x = get_mirror_x_position (container, icon, icon->x);
5068 }
5069 else
5070 {
5071 position.x = icon->x;
5072 }
5073 position.y = icon->y;
5074 position.scale = icon->scale;
5075 g_signal_emit (container,
5076 signals[ICON_POSITION_CHANGED], 0,
5077 icon->data, &position);
5078
5079 clear_drag_state (container);
5080 redo_layout (container);
5081}
5082
5083static gboolean
5084undo_stretching (BaulIconContainer *container)
5085{
5086 BaulIcon *stretched_icon;
5087
5088 stretched_icon = container->details->stretch_icon;
5089
5090 if (stretched_icon == NULL((void*)0))
5091 {
5092 return FALSE(0);
5093 }
5094
5095 if (container->details->drag_state == DRAG_STATE_STRETCH)
5096 {
5097 ungrab_stretch_icon (container);
5098 clear_drag_state (container);
5099 }
5100 baul_icon_canvas_item_set_show_stretch_handles
5101 (stretched_icon->item, FALSE(0));
5102
5103 icon_set_position (stretched_icon,
5104 container->details->stretch_initial_x,
5105 container->details->stretch_initial_y);
5106 icon_set_size (container,
5107 stretched_icon,
5108 container->details->stretch_initial_size,
5109 TRUE(!(0)),
5110 TRUE(!(0)));
5111
5112 container->details->stretch_icon = NULL((void*)0);
5113 emit_stretch_ended (container, stretched_icon);
5114 redo_layout (container);
5115
5116 return TRUE(!(0));
5117}
5118
5119static gboolean
5120button_release_event (CtkWidget *widget,
5121 CdkEventButton *event)
5122{
5123 BaulIconContainer *container;
5124 BaulIconContainerDetails *details;
5125 double world_x, world_y;
5126
5127 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
5128 details = container->details;
5129
5130 if (event->button == RUBBERBAND_BUTTON1 && details->rubberband_info.active)
5131 {
5132 stop_rubberbanding (container);
5133 return TRUE(!(0));
5134 }
5135
5136 if (event->button == details->drag_button)
5137 {
5138 details->drag_button = 0;
5139
5140 switch (details->drag_state)
5141 {
5142 case DRAG_STATE_MOVE_OR_COPY:
5143 if (!details->drag_started)
5144 {
5145 baul_icon_container_did_not_drag (container, event);
5146 }
5147 else
5148 {
5149 baul_icon_dnd_end_drag (container);
5150 baul_debug_log (FALSE(0), BAUL_DEBUG_LOG_DOMAIN_USER"USER",
5151 "end drag from icon container");
5152 }
5153 break;
5154 case DRAG_STATE_STRETCH:
5155 eel_canvas_window_to_world
5156 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
, event->x, event->y, &world_x, &world_y);
5157 end_stretching (container, world_x, world_y);
5158 break;
5159 default:
5160 break;
5161 }
5162
5163 clear_drag_state (container);
5164 return TRUE(!(0));
5165 }
5166
5167 return CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->button_release_event (widget, event);
5168}
5169
5170static int
5171motion_notify_event (CtkWidget *widget,
5172 CdkEventMotion *event)
5173{
5174 BaulIconContainer *container;
5175 BaulIconContainerDetails *details;
5176 double world_x, world_y;
5177 int canvas_x, canvas_y;
5178 CdkDragAction actions;
5179
5180 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
5181 details = container->details;
5182
5183 if (details->drag_button != 0)
5184 {
5185 switch (details->drag_state)
5186 {
5187 case DRAG_STATE_MOVE_OR_COPY:
5188 if (details->drag_started)
5189 {
5190 break;
5191 }
5192
5193 eel_canvas_window_to_world
5194 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
, event->x, event->y, &world_x, &world_y);
5195
5196 if (ctk_drag_check_threshold (widget,
5197 details->drag_x,
5198 details->drag_y,
5199 world_x,
5200 world_y))
5201 {
5202 details->drag_started = TRUE(!(0));
5203 details->drag_state = DRAG_STATE_MOVE_OR_COPY;
5204
5205 end_renaming_mode (container, TRUE(!(0)));
5206
5207 eel_canvas_w2c (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
5208 details->drag_x,
5209 details->drag_y,
5210 &canvas_x,
5211 &canvas_y);
5212
5213 actions = CDK_ACTION_COPY
5214 | CDK_ACTION_LINK
5215 | CDK_ACTION_ASK;
5216
5217 if (container->details->drag_allow_moves)
5218 {
5219 actions |= CDK_ACTION_MOVE;
5220 }
5221
5222 baul_icon_dnd_begin_drag (container,
5223 actions,
5224 details->drag_button,
5225 event,
5226 canvas_x,
5227 canvas_y);
5228 baul_debug_log (FALSE(0), BAUL_DEBUG_LOG_DOMAIN_USER"USER",
5229 "begin drag from icon container");
5230 }
5231 break;
5232 case DRAG_STATE_STRETCH:
5233 eel_canvas_window_to_world
5234 (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
, event->x, event->y, &world_x, &world_y);
5235 continue_stretching (container, world_x, world_y);
5236 break;
5237 default:
5238 break;
5239 }
5240 }
5241
5242 return CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->motion_notify_event (widget, event);
5243}
5244
5245static void
5246baul_icon_container_search_position_func (BaulIconContainer *container,
5247 CtkWidget *search_dialog)
5248{
5249 gint x, y;
5250 gint cont_x, cont_y;
5251 gint cont_width, cont_height;
5252 gint scale;
5253 CdkWindow *cont_window;
5254 CdkScreen *screen;
5255 CtkRequisition requisition;
5256 CdkMonitor *monitor_num;
5257 CdkRectangle monitor;
5258
5259
5260 cont_window = ctk_widget_get_window (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
5261 scale = ctk_widget_get_scale_factor (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
5262 screen = cdk_window_get_screen (cont_window);
5263
5264 monitor_num = cdk_display_get_monitor_at_window (cdk_screen_get_display (screen),
5265 cont_window);
5266 cdk_monitor_get_geometry (monitor_num, &monitor);
5267
5268 ctk_widget_realize (search_dialog);
5269
5270 cdk_window_get_origin (cont_window, &cont_x, &cont_y);
5271
5272 cont_width = cdk_window_get_width (cont_window);
5273 cont_height = cdk_window_get_height (cont_window);
5274
5275 ctk_widget_get_preferred_size (search_dialog, &requisition, NULL((void*)0));
5276
5277 if (cont_x + cont_width - requisition.width > WidthOfScreen (cdk_x11_screen_get_xscreen (screen))((cdk_x11_screen_get_xscreen (screen))->width) / scale)
5278 {
5279 x = WidthOfScreen (cdk_x11_screen_get_xscreen (screen))((cdk_x11_screen_get_xscreen (screen))->width) / scale - requisition.width;
5280 }
5281 else if (cont_x + cont_width - requisition.width < 0)
5282 {
5283 x = 0;
5284 }
5285 else
5286 {
5287 x = cont_x + cont_width - requisition.width;
5288 }
5289
5290 if (cont_y + cont_height > HeightOfScreen (cdk_x11_screen_get_xscreen (screen))((cdk_x11_screen_get_xscreen (screen))->height))
5291 {
5292 y = HeightOfScreen (cdk_x11_screen_get_xscreen (screen))((cdk_x11_screen_get_xscreen (screen))->height) - requisition.height;
5293 }
5294 else if (cont_y + cont_height < 0) /* isn't really possible ... */
5295 {
5296 y = 0;
5297 }
5298 else
5299 {
5300 y = cont_y + cont_height;
5301 }
5302
5303 ctk_window_move (CTK_WINDOW (search_dialog)((((CtkWindow*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((search_dialog)), ((ctk_window_get_type ()))))))
, x, y);
5304}
5305
5306static gboolean
5307baul_icon_container_real_search_enable_popdown (gpointer data)
5308{
5309 BaulIconContainer *container = (BaulIconContainer *)data;
5310
5311 container->details->disable_popdown = FALSE(0);
5312
5313 g_object_unref (container);
5314
5315 return FALSE(0);
5316}
5317
5318static void
5319baul_icon_container_search_enable_popdown (CtkWidget *widget G_GNUC_UNUSED__attribute__ ((__unused__)),
5320 gpointer data)
5321{
5322 BaulIconContainer *container = (BaulIconContainer *) data;
5323
5324 g_object_ref (container)((__typeof__ (container)) (g_object_ref) (container));
5325 g_timeout_add (200, baul_icon_container_real_search_enable_popdown, data);
5326}
5327
5328static void
5329baul_icon_container_search_disable_popdown (CtkEntry *entry G_GNUC_UNUSED__attribute__ ((__unused__)),
5330 CtkMenu *menu,
5331 gpointer data)
5332{
5333 BaulIconContainer *container = (BaulIconContainer *) data;
5334
5335 container->details->disable_popdown = TRUE(!(0));
5336 g_signal_connect (menu, "hide",g_signal_connect_data ((menu), ("hide"), (((GCallback) (baul_icon_container_search_enable_popdown
))), (data), ((void*)0), (GConnectFlags) 0)
5337 G_CALLBACK (baul_icon_container_search_enable_popdown),g_signal_connect_data ((menu), ("hide"), (((GCallback) (baul_icon_container_search_enable_popdown
))), (data), ((void*)0), (GConnectFlags) 0)
5338 data)g_signal_connect_data ((menu), ("hide"), (((GCallback) (baul_icon_container_search_enable_popdown
))), (data), ((void*)0), (GConnectFlags) 0)
;
5339}
5340
5341/* Cut and paste from ctkwindow.c */
5342static void
5343send_focus_change (CtkWidget *widget, gboolean in)
5344{
5345 CdkEvent *fevent;
5346
5347 fevent = cdk_event_new (CDK_FOCUS_CHANGE);
5348
5349 g_object_ref (widget)((__typeof__ (widget)) (g_object_ref) (widget));
5350 ((CdkEventFocus *) fevent)->in = in;
5351
5352 ctk_widget_send_focus_change (widget, fevent);
5353
5354 fevent->focus_change.type = CDK_FOCUS_CHANGE;
5355 fevent->focus_change.window = g_object_ref (ctk_widget_get_window (widget))((__typeof__ (ctk_widget_get_window (widget))) (g_object_ref)
(ctk_widget_get_window (widget)))
;
5356 fevent->focus_change.in = in;
5357
5358 ctk_widget_event (widget, fevent);
5359
5360 g_object_notify (G_OBJECT (widget)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((widget)), (((GType) ((20) << (2))))))))
, "has-focus");
5361
5362 g_object_unref (widget);
5363 cdk_event_free (fevent);
5364}
5365
5366static void
5367baul_icon_container_search_dialog_hide (CtkWidget *search_dialog,
5368 BaulIconContainer *container)
5369{
5370 if (container->details->disable_popdown)
5371 {
5372 return;
5373 }
5374
5375 if (container->details->search_entry_changed_id)
5376 {
5377 g_signal_handler_disconnect (container->details->search_entry,
5378 container->details->search_entry_changed_id);
5379 container->details->search_entry_changed_id = 0;
5380 }
5381 if (container->details->typeselect_flush_timeout)
5382 {
5383 g_source_remove (container->details->typeselect_flush_timeout);
5384 container->details->typeselect_flush_timeout = 0;
5385 }
5386
5387 /* send focus-in event */
5388 send_focus_change (CTK_WIDGET (container->details->search_entry)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_entry)), ((ctk_widget_get_type
()))))))
, FALSE(0));
5389 ctk_widget_hide (search_dialog);
5390 ctk_entry_set_text (CTK_ENTRY (container->details->search_entry)((((CtkEntry*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_entry)), ((ctk_entry_get_type
()))))))
, "");
5391}
5392
5393static gboolean
5394baul_icon_container_search_entry_flush_timeout (BaulIconContainer *container)
5395{
5396 baul_icon_container_search_dialog_hide (container->details->search_window, container);
5397
5398 return TRUE(!(0));
5399}
5400
5401/* Because we're visible but offscreen, we just set a flag in the preedit
5402 * callback.
5403 */
5404static void
5405baul_icon_container_search_preedit_changed (CtkEntry *entry G_GNUC_UNUSED__attribute__ ((__unused__)),
5406 gchar *preedit G_GNUC_UNUSED__attribute__ ((__unused__)),
5407 BaulIconContainer *container)
5408{
5409 container->details->imcontext_changed = 1;
5410 if (container->details->typeselect_flush_timeout)
5411 {
5412 g_source_remove (container->details->typeselect_flush_timeout);
5413 container->details->typeselect_flush_timeout =
5414 g_timeout_add_seconds (BAUL_ICON_CONTAINER_SEARCH_DIALOG_TIMEOUT5,
5415 (GSourceFunc) baul_icon_container_search_entry_flush_timeout,
5416 container);
5417 }
5418}
5419
5420static void
5421baul_icon_container_search_activate (CtkEntry *entry G_GNUC_UNUSED__attribute__ ((__unused__)),
5422 BaulIconContainer *container)
5423{
5424 baul_icon_container_search_dialog_hide (container->details->search_window,
5425 container);
5426
5427 activate_selected_items (container);
5428}
5429
5430static gboolean
5431baul_icon_container_search_delete_event (CtkWidget *widget,
5432 CdkEventAny *event G_GNUC_UNUSED__attribute__ ((__unused__)),
5433 BaulIconContainer *container)
5434{
5435 g_assert (CTK_IS_WIDGET (widget))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((widget)); GType __t = ((ctk_widget_get_type ())); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))) ; else
g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 5435, ((const char*) (__func__)), "CTK_IS_WIDGET (widget)")
; } while (0)
;
5436
5437 baul_icon_container_search_dialog_hide (widget, container);
5438
5439 return TRUE(!(0));
5440}
5441
5442static gboolean
5443baul_icon_container_search_button_press_event (CtkWidget *widget,
5444 CdkEventButton *event,
5445 BaulIconContainer *container)
5446{
5447 g_assert (CTK_IS_WIDGET (widget))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((widget)); GType __t = ((ctk_widget_get_type ())); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))) ; else
g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 5447, ((const char*) (__func__)), "CTK_IS_WIDGET (widget)")
; } while (0)
;
5448
5449 baul_icon_container_search_dialog_hide (widget, container);
5450
5451 if (event->window == ctk_layout_get_bin_window (CTK_LAYOUT (container)((((CtkLayout*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_layout_get_type ()))))))
))
5452 {
5453 button_press_event (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, event);
5454 }
5455
5456 return TRUE(!(0));
5457}
5458
5459static void
5460baul_icon_container_get_icon_text (BaulIconContainer *container,
5461 BaulIconData *data,
5462 char **editable_text,
5463 char **additional_text,
5464 gboolean include_invisible)
5465{
5466 BaulIconContainerClass *klass;
5467
5468 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
5469 g_assert (klass->get_icon_text != NULL)do { if (klass->get_icon_text != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 5469, ((const char*)
(__func__)), "klass->get_icon_text != NULL"); } while (0)
;
5470
5471 klass->get_icon_text (container, data, editable_text, additional_text, include_invisible);
5472}
5473
5474static gboolean
5475baul_icon_container_search_iter (BaulIconContainer *container,
5476 const char *key, gint n)
5477{
5478 GList *p;
5479 BaulIcon *icon;
5480 char *name;
5481 int count;
5482 char *normalized_key, *case_normalized_key;
5483 char *normalized_name, *case_normalized_name;
5484
5485 g_assert (key != NULL)do { if (key != ((void*)0)) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 5485, ((const char*) (
__func__)), "key != NULL"); } while (0)
;
5486 g_assert (n >= 1)do { if (n >= 1) ; else g_assertion_message_expr (((gchar*
) 0), "baul-icon-container.c", 5486, ((const char*) (__func__
)), "n >= 1"); } while (0)
;
5487
5488 normalized_key = g_utf8_normalize (key, -1, G_NORMALIZE_ALL);
5489 if (!normalized_key)
5490 {
5491 return FALSE(0);
5492 }
5493 case_normalized_key = g_utf8_casefold (normalized_key, -1);
5494 g_free (normalized_key);
5495 if (!case_normalized_key)
5496 {
5497 return FALSE(0);
5498 }
5499
5500 icon = NULL((void*)0);
5501 name = NULL((void*)0);
5502 count = 0;
5503 for (p = container->details->icons; p != NULL((void*)0) && count != n; p = p->next)
5504 {
5505 icon = p->data;
5506 baul_icon_container_get_icon_text (container, icon->data, &name,
5507 NULL((void*)0), TRUE(!(0)));
5508
5509 /* This can happen if a key event is handled really early while
5510 * loading the icon container, before the items have all been
5511 * updated once.
5512 */
5513 if (!name)
5514 {
5515 continue;
5516 }
5517
5518 normalized_name = g_utf8_normalize (name, -1, G_NORMALIZE_ALL);
5519 if (!normalized_name)
5520 {
5521 continue;
5522 }
5523 case_normalized_name = g_utf8_casefold (normalized_name, -1);
5524 g_free (normalized_name);
5525 if (!case_normalized_name)
5526 {
5527 continue;
5528 }
5529
5530 if (strncmp (case_normalized_key, case_normalized_name,
5531 strlen (case_normalized_key)) == 0)
5532 {
5533 count++;
5534 }
5535
5536 g_free (case_normalized_name);
5537 g_free (name);
5538 name = NULL((void*)0);
5539 }
5540
5541 g_free (case_normalized_key);
5542
5543 if (count == n)
5544 {
5545 if (select_one_unselect_others (container, icon))
5546 {
5547 g_signal_emit (container, signals[SELECTION_CHANGED], 0);
5548 }
5549 schedule_keyboard_icon_reveal (container, icon);
5550
5551 return TRUE(!(0));
5552 }
5553
5554 return FALSE(0);
5555}
5556
5557static void
5558baul_icon_container_search_move (CtkWidget *window G_GNUC_UNUSED__attribute__ ((__unused__)),
5559 BaulIconContainer *container,
5560 gboolean up)
5561{
5562 gboolean ret;
5563 gint len;
5564 const gchar *text;
5565
5566 text = ctk_entry_get_text (CTK_ENTRY (container->details->search_entry)((((CtkEntry*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_entry)), ((ctk_entry_get_type
()))))))
);
5567
5568 g_assert (text != NULL)do { if (text != ((void*)0)) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 5568, ((const char*) (
__func__)), "text != NULL"); } while (0)
;
5569
5570 if (container->details->selected_iter == 0)
5571 {
5572 return;
5573 }
5574
5575 if (up && container->details->selected_iter == 1)
5576 {
5577 return;
5578 }
5579
5580 len = strlen (text);
5581
5582 if (len < 1)
5583 {
5584 return;
5585 }
5586
5587 /* search */
5588 unselect_all (container);
5589
5590 ret = baul_icon_container_search_iter (container, text,
5591 up?((container->details->selected_iter) - 1):((container->details->selected_iter + 1)));
5592
5593 if (ret)
5594 {
5595 /* found */
5596 container->details->selected_iter += up?(-1):(1);
5597 }
5598 else
5599 {
5600 /* return to old iter */
5601 baul_icon_container_search_iter (container, text,
5602 container->details->selected_iter);
5603 }
5604}
5605
5606static gboolean
5607baul_icon_container_search_scroll_event (CtkWidget *widget,
5608 CdkEventScroll *event,
5609 BaulIconContainer *container)
5610{
5611 gboolean retval = FALSE(0);
5612
5613 if (event->direction == CDK_SCROLL_UP)
5614 {
5615 baul_icon_container_search_move (widget, container, TRUE(!(0)));
5616 retval = TRUE(!(0));
5617 }
5618 else if (event->direction == CDK_SCROLL_DOWN)
5619 {
5620 baul_icon_container_search_move (widget, container, FALSE(0));
5621 retval = TRUE(!(0));
5622 }
5623
5624 /* renew the flush timeout */
5625 if (retval && container->details->typeselect_flush_timeout)
5626 {
5627 g_source_remove (container->details->typeselect_flush_timeout);
5628 container->details->typeselect_flush_timeout =
5629 g_timeout_add_seconds (BAUL_ICON_CONTAINER_SEARCH_DIALOG_TIMEOUT5,
5630 (GSourceFunc) baul_icon_container_search_entry_flush_timeout,
5631 container);
5632 }
5633
5634 return retval;
5635}
5636
5637static gboolean
5638baul_icon_container_search_key_press_event (CtkWidget *widget,
5639 CdkEventKey *event,
5640 BaulIconContainer *container)
5641{
5642 gboolean retval = FALSE(0);
5643
5644 g_assert (CTK_IS_WIDGET (widget))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((widget)); GType __t = ((ctk_widget_get_type ())); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))) ; else
g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 5644, ((const char*) (__func__)), "CTK_IS_WIDGET (widget)")
; } while (0)
;
5645 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 5645, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
5646
5647 /* close window and cancel the search */
5648 if (event->keyval == CDK_KEY_Escape0xff1b || event->keyval == CDK_KEY_Tab0xff09)
5649 {
5650 baul_icon_container_search_dialog_hide (widget, container);
5651 return TRUE(!(0));
5652 }
5653
5654 /* close window and activate alternate */
5655 if (event->keyval == CDK_KEY_Return0xff0d && event->state & CDK_SHIFT_MASK)
5656 {
5657 baul_icon_container_search_dialog_hide (widget,
5658 container);
5659
5660 activate_selected_items_alternate (container, NULL((void*)0));
5661 return TRUE(!(0));
5662 }
5663
5664 /* select previous matching iter */
5665 if (event->keyval == CDK_KEY_Up0xff52 || event->keyval == CDK_KEY_KP_Up0xff97)
5666 {
5667 baul_icon_container_search_move (widget, container, TRUE(!(0)));
5668 retval = TRUE(!(0));
5669 }
5670
5671 if (((event->state & (CDK_CONTROL_MASK | CDK_SHIFT_MASK)) == (CDK_CONTROL_MASK | CDK_SHIFT_MASK))
5672 && (event->keyval == CDK_KEY_g0x067 || event->keyval == CDK_KEY_G0x047))
5673 {
5674 baul_icon_container_search_move (widget, container, TRUE(!(0)));
5675 retval = TRUE(!(0));
5676 }
5677
5678 /* select next matching iter */
5679 if (event->keyval == CDK_KEY_Down0xff54 || event->keyval == CDK_KEY_KP_Down0xff99)
5680 {
5681 baul_icon_container_search_move (widget, container, FALSE(0));
5682 retval = TRUE(!(0));
5683 }
5684
5685 if (((event->state & (CDK_CONTROL_MASK | CDK_SHIFT_MASK)) == CDK_CONTROL_MASK)
5686 && (event->keyval == CDK_KEY_g0x067 || event->keyval == CDK_KEY_G0x047))
5687 {
5688 baul_icon_container_search_move (widget, container, FALSE(0));
5689 retval = TRUE(!(0));
5690 }
5691
5692 /* renew the flush timeout */
5693 if (retval && container->details->typeselect_flush_timeout)
5694 {
5695 g_source_remove (container->details->typeselect_flush_timeout);
5696 container->details->typeselect_flush_timeout =
5697 g_timeout_add_seconds (BAUL_ICON_CONTAINER_SEARCH_DIALOG_TIMEOUT5,
5698 (GSourceFunc) baul_icon_container_search_entry_flush_timeout,
5699 container);
5700 }
5701
5702 return retval;
5703}
5704
5705static void
5706baul_icon_container_search_init (CtkWidget *entry,
5707 BaulIconContainer *container)
5708{
5709 gint ret;
5710 gint len;
5711 const gchar *text;
5712
5713 g_assert (CTK_IS_ENTRY (entry))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((entry)); GType __t = ((ctk_entry_get_type ())); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))) ; else
g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 5713, ((const char*) (__func__)), "CTK_IS_ENTRY (entry)"); }
while (0)
;
5714 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 5714, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
5715
5716 text = ctk_entry_get_text (CTK_ENTRY (entry)((((CtkEntry*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((entry)), ((ctk_entry_get_type ()))))))
);
5717 len = strlen (text);
5718
5719 /* search */
5720 unselect_all (container);
5721 if (container->details->typeselect_flush_timeout)
5722 {
5723 g_source_remove (container->details->typeselect_flush_timeout);
5724 container->details->typeselect_flush_timeout =
5725 g_timeout_add_seconds (BAUL_ICON_CONTAINER_SEARCH_DIALOG_TIMEOUT5,
5726 (GSourceFunc) baul_icon_container_search_entry_flush_timeout,
5727 container);
5728 }
5729
5730 if (len < 1)
5731 {
5732 return;
5733 }
5734
5735 ret = baul_icon_container_search_iter (container, text, 1);
5736
5737 if (ret)
5738 {
5739 container->details->selected_iter = 1;
5740 }
5741}
5742
5743static void
5744baul_icon_container_ensure_interactive_directory (BaulIconContainer *container)
5745{
5746 CtkWidget *frame, *vbox;
5747
5748 if (container->details->search_window != NULL((void*)0))
5749 {
5750 return;
5751 }
5752
5753 container->details->search_window = ctk_window_new (CTK_WINDOW_POPUP);
5754
5755 ctk_window_set_modal (CTK_WINDOW (container->details->search_window)((((CtkWindow*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_window)), ((ctk_window_get_type
()))))))
, TRUE(!(0)));
5756 ctk_window_set_type_hint (CTK_WINDOW (container->details->search_window)((((CtkWindow*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_window)), ((ctk_window_get_type
()))))))
,
5757 CDK_WINDOW_TYPE_HINT_COMBO);
5758
5759 g_signal_connect (container->details->search_window, "delete_event",g_signal_connect_data ((container->details->search_window
), ("delete_event"), (((GCallback) (baul_icon_container_search_delete_event
))), (container), ((void*)0), (GConnectFlags) 0)
5760 G_CALLBACK (baul_icon_container_search_delete_event),g_signal_connect_data ((container->details->search_window
), ("delete_event"), (((GCallback) (baul_icon_container_search_delete_event
))), (container), ((void*)0), (GConnectFlags) 0)
5761 container)g_signal_connect_data ((container->details->search_window
), ("delete_event"), (((GCallback) (baul_icon_container_search_delete_event
))), (container), ((void*)0), (GConnectFlags) 0)
;
5762 g_signal_connect (container->details->search_window, "key_press_event",g_signal_connect_data ((container->details->search_window
), ("key_press_event"), (((GCallback) (baul_icon_container_search_key_press_event
))), (container), ((void*)0), (GConnectFlags) 0)
5763 G_CALLBACK (baul_icon_container_search_key_press_event),g_signal_connect_data ((container->details->search_window
), ("key_press_event"), (((GCallback) (baul_icon_container_search_key_press_event
))), (container), ((void*)0), (GConnectFlags) 0)
5764 container)g_signal_connect_data ((container->details->search_window
), ("key_press_event"), (((GCallback) (baul_icon_container_search_key_press_event
))), (container), ((void*)0), (GConnectFlags) 0)
;
5765 g_signal_connect (container->details->search_window, "button_press_event",g_signal_connect_data ((container->details->search_window
), ("button_press_event"), (((GCallback) (baul_icon_container_search_button_press_event
))), (container), ((void*)0), (GConnectFlags) 0)
5766 G_CALLBACK (baul_icon_container_search_button_press_event),g_signal_connect_data ((container->details->search_window
), ("button_press_event"), (((GCallback) (baul_icon_container_search_button_press_event
))), (container), ((void*)0), (GConnectFlags) 0)
5767 container)g_signal_connect_data ((container->details->search_window
), ("button_press_event"), (((GCallback) (baul_icon_container_search_button_press_event
))), (container), ((void*)0), (GConnectFlags) 0)
;
5768 g_signal_connect (container->details->search_window, "scroll_event",g_signal_connect_data ((container->details->search_window
), ("scroll_event"), (((GCallback) (baul_icon_container_search_scroll_event
))), (container), ((void*)0), (GConnectFlags) 0)
5769 G_CALLBACK (baul_icon_container_search_scroll_event),g_signal_connect_data ((container->details->search_window
), ("scroll_event"), (((GCallback) (baul_icon_container_search_scroll_event
))), (container), ((void*)0), (GConnectFlags) 0)
5770 container)g_signal_connect_data ((container->details->search_window
), ("scroll_event"), (((GCallback) (baul_icon_container_search_scroll_event
))), (container), ((void*)0), (GConnectFlags) 0)
;
5771
5772 frame = ctk_frame_new (NULL((void*)0));
5773 ctk_frame_set_shadow_type (CTK_FRAME (frame)((((CtkFrame*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((frame)), ((ctk_frame_get_type ()))))))
, CTK_SHADOW_ETCHED_IN);
5774 ctk_widget_show (frame);
5775 ctk_container_add (CTK_CONTAINER (container->details->search_window)((((CtkContainer*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_window)), ((ctk_container_get_type
()))))))
, frame);
5776
5777 vbox = ctk_box_new (CTK_ORIENTATION_VERTICAL, 0);
5778 ctk_widget_show (vbox);
5779 ctk_container_add (CTK_CONTAINER (frame)((((CtkContainer*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((frame)), ((ctk_container_get_type ()))))))
, vbox);
5780 ctk_container_set_border_width (CTK_CONTAINER (vbox)((((CtkContainer*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((vbox)), ((ctk_container_get_type ()))))))
, 3);
5781
5782 /* add entry */
5783 container->details->search_entry = ctk_entry_new ();
5784 ctk_widget_show (container->details->search_entry);
5785 g_signal_connect (container->details->search_entry, "populate_popup",g_signal_connect_data ((container->details->search_entry
), ("populate_popup"), (((GCallback) (baul_icon_container_search_disable_popdown
))), (container), ((void*)0), (GConnectFlags) 0)
5786 G_CALLBACK (baul_icon_container_search_disable_popdown),g_signal_connect_data ((container->details->search_entry
), ("populate_popup"), (((GCallback) (baul_icon_container_search_disable_popdown
))), (container), ((void*)0), (GConnectFlags) 0)
5787 container)g_signal_connect_data ((container->details->search_entry
), ("populate_popup"), (((GCallback) (baul_icon_container_search_disable_popdown
))), (container), ((void*)0), (GConnectFlags) 0)
;
5788 g_signal_connect (container->details->search_entry, "activate",g_signal_connect_data ((container->details->search_entry
), ("activate"), (((GCallback) (baul_icon_container_search_activate
))), (container), ((void*)0), (GConnectFlags) 0)
5789 G_CALLBACK (baul_icon_container_search_activate),g_signal_connect_data ((container->details->search_entry
), ("activate"), (((GCallback) (baul_icon_container_search_activate
))), (container), ((void*)0), (GConnectFlags) 0)
5790 container)g_signal_connect_data ((container->details->search_entry
), ("activate"), (((GCallback) (baul_icon_container_search_activate
))), (container), ((void*)0), (GConnectFlags) 0)
;
5791 g_signal_connect (container->details->search_entry,g_signal_connect_data ((container->details->search_entry
), ("preedit-changed"), (((GCallback) (baul_icon_container_search_preedit_changed
))), (container), ((void*)0), (GConnectFlags) 0)
5792 "preedit-changed",g_signal_connect_data ((container->details->search_entry
), ("preedit-changed"), (((GCallback) (baul_icon_container_search_preedit_changed
))), (container), ((void*)0), (GConnectFlags) 0)
5793 G_CALLBACK (baul_icon_container_search_preedit_changed),g_signal_connect_data ((container->details->search_entry
), ("preedit-changed"), (((GCallback) (baul_icon_container_search_preedit_changed
))), (container), ((void*)0), (GConnectFlags) 0)
5794 container)g_signal_connect_data ((container->details->search_entry
), ("preedit-changed"), (((GCallback) (baul_icon_container_search_preedit_changed
))), (container), ((void*)0), (GConnectFlags) 0)
;
5795 ctk_container_add (CTK_CONTAINER (vbox)((((CtkContainer*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((vbox)), ((ctk_container_get_type ()))))))
, container->details->search_entry);
5796
5797 ctk_widget_realize (container->details->search_entry);
5798}
5799
5800/* Pops up the interactive search entry. If keybinding is TRUE then the user
5801 * started this by typing the start_interactive_search keybinding. Otherwise, it came from
5802 */
5803static gboolean
5804baul_icon_container_real_start_interactive_search (BaulIconContainer *container,
5805 gboolean keybinding)
5806{
5807 /* We only start interactive search if we have focus. If one of our
5808 * children have focus, we don't want to start the search.
5809 */
5810 CtkWidgetClass *entry_parent_class;
5811
5812 if (container->details->search_window != NULL((void*)0) &&
5813 ctk_widget_get_visible (container->details->search_window))
5814 {
5815 return TRUE(!(0));
5816 }
5817
5818 if (!ctk_widget_has_focus (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
))
5819 {
5820 return FALSE(0);
5821 }
5822
5823 baul_icon_container_ensure_interactive_directory (container);
5824
5825 if (keybinding)
5826 {
5827 ctk_entry_set_text (CTK_ENTRY (container->details->search_entry)((((CtkEntry*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_entry)), ((ctk_entry_get_type
()))))))
, "");
5828 }
5829
5830 /* done, show it */
5831 baul_icon_container_search_position_func (container, container->details->search_window);
5832 ctk_widget_show (container->details->search_window);
5833 if (container->details->search_entry_changed_id == 0)
5834 {
5835 container->details->search_entry_changed_id =
5836 g_signal_connect (container->details->search_entry, "changed",g_signal_connect_data ((container->details->search_entry
), ("changed"), (((GCallback) (baul_icon_container_search_init
))), (container), ((void*)0), (GConnectFlags) 0)
5837 G_CALLBACK (baul_icon_container_search_init),g_signal_connect_data ((container->details->search_entry
), ("changed"), (((GCallback) (baul_icon_container_search_init
))), (container), ((void*)0), (GConnectFlags) 0)
5838 container)g_signal_connect_data ((container->details->search_entry
), ("changed"), (((GCallback) (baul_icon_container_search_init
))), (container), ((void*)0), (GConnectFlags) 0)
;
5839 }
5840
5841 container->details->typeselect_flush_timeout =
5842 g_timeout_add_seconds (BAUL_ICON_CONTAINER_SEARCH_DIALOG_TIMEOUT5,
5843 (GSourceFunc) baul_icon_container_search_entry_flush_timeout,
5844 container);
5845
5846 /* Grab focus will select all the text. We don't want that to happen, so we
5847 * call the parent instance and bypass the selection change. This is probably
5848 * really non-kosher. */
5849 entry_parent_class = g_type_class_peek_parent (CTK_ENTRY_GET_CLASS (container->details->search_entry)((((CtkEntryClass*) (((GTypeInstance*) ((container->details
->search_entry)))->g_class))))
);
5850 (entry_parent_class->grab_focus) (container->details->search_entry);
5851
5852 /* send focus-in event */
5853 send_focus_change (container->details->search_entry, TRUE(!(0)));
5854
5855 /* search first matching iter */
5856 baul_icon_container_search_init (container->details->search_entry, container);
5857
5858 return TRUE(!(0));
5859}
5860
5861static gboolean
5862baul_icon_container_start_interactive_search (BaulIconContainer *container)
5863{
5864 return baul_icon_container_real_start_interactive_search (container, TRUE(!(0)));
5865}
5866
5867static gboolean
5868handle_popups (BaulIconContainer *container,
5869 CdkEventKey *event G_GNUC_UNUSED__attribute__ ((__unused__)),
5870 const char *signal)
5871{
5872 CdkEventButton button_event = { 0 };
5873
5874 g_signal_emit_by_name (container, signal, &button_event);
5875
5876 return TRUE(!(0));
5877}
5878
5879static int
5880key_press_event (CtkWidget *widget,
5881 CdkEventKey *event)
5882{
5883 BaulIconContainer *container;
5884 gboolean handled;
5885
5886 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
5887 handled = FALSE(0);
5888
5889 if (is_renaming (container) || is_renaming_pending (container))
5890 {
5891 switch (event->keyval)
5892 {
5893 case CDK_KEY_Return0xff0d:
5894 case CDK_KEY_KP_Enter0xff8d:
5895 end_renaming_mode (container, TRUE(!(0)));
5896 handled = TRUE(!(0));
5897 break;
5898 case CDK_KEY_Escape0xff1b:
5899 end_renaming_mode (container, FALSE(0));
5900 handled = TRUE(!(0));
5901 break;
5902 default:
5903 break;
5904 }
5905 }
5906 else
5907 {
5908 switch (event->keyval)
5909 {
5910 case CDK_KEY_Home0xff50:
5911 case CDK_KEY_KP_Home0xff95:
5912 keyboard_home (container, event);
5913 handled = TRUE(!(0));
5914 break;
5915 case CDK_KEY_End0xff57:
5916 case CDK_KEY_KP_End0xff9c:
5917 keyboard_end (container, event);
5918 handled = TRUE(!(0));
5919 break;
5920 case CDK_KEY_Left0xff51:
5921 case CDK_KEY_KP_Left0xff96:
5922 /* Don't eat Alt-Left, as that is used for history browsing */
5923 if ((event->state & CDK_MOD1_MASK) == 0)
5924 {
5925 keyboard_left (container, event);
5926 handled = TRUE(!(0));
5927 }
5928 break;
5929 case CDK_KEY_Up0xff52:
5930 case CDK_KEY_KP_Up0xff97:
5931 /* Don't eat Alt-Up, as that is used for alt-shift-Up */
5932 if ((event->state & CDK_MOD1_MASK) == 0)
5933 {
5934 keyboard_up (container, event);
5935 handled = TRUE(!(0));
5936 }
5937 break;
5938 case CDK_KEY_Right0xff53:
5939 case CDK_KEY_KP_Right0xff98:
5940 /* Don't eat Alt-Right, as that is used for history browsing */
5941 if ((event->state & CDK_MOD1_MASK) == 0)
5942 {
5943 keyboard_right (container, event);
5944 handled = TRUE(!(0));
5945 }
5946 break;
5947 case CDK_KEY_Down0xff54:
5948 case CDK_KEY_KP_Down0xff99:
5949 /* Don't eat Alt-Down, as that is used for Open */
5950 if ((event->state & CDK_MOD1_MASK) == 0)
5951 {
5952 keyboard_down (container, event);
5953 handled = TRUE(!(0));
5954 }
5955 break;
5956 case CDK_KEY_space0x020:
5957 keyboard_space (container, event);
5958 handled = TRUE(!(0));
5959 break;
5960#ifndef TAB_NAVIGATION_DISABLED
5961 case CDK_KEY_Tab0xff09:
5962 case CDK_KEY_ISO_Left_Tab0xfe20:
5963 select_previous_or_next_icon (container,
5964 (event->state & CDK_SHIFT_MASK) == 0, event);
5965 handled = TRUE(!(0));
5966 break;
5967#endif
5968 case CDK_KEY_Return0xff0d:
5969 case CDK_KEY_KP_Enter0xff8d:
5970 if ((event->state & CDK_SHIFT_MASK) != 0)
5971 {
5972 activate_selected_items_alternate (container, NULL((void*)0));
5973 }
5974 else
5975 {
5976 activate_selected_items (container);
5977 }
5978
5979 handled = TRUE(!(0));
5980 break;
5981 case CDK_KEY_Escape0xff1b:
5982 handled = undo_stretching (container);
5983 break;
5984 case CDK_KEY_plus0x02b:
5985 case CDK_KEY_minus0x02d:
5986 case CDK_KEY_equal0x03d:
5987 case CDK_KEY_KP_Add0xffab:
5988 case CDK_KEY_KP_Subtract0xffad:
5989 case CDK_KEY_00x030:
5990 case CDK_KEY_KP_00xffb0:
5991 if (event->state & CDK_CONTROL_MASK)
5992 {
5993 handled = keyboard_stretching (container, event);
5994 }
5995 break;
5996 case CDK_KEY_F100xffc7:
5997 /* handle Ctrl+F10 because we want to display the
5998 * background popup even if something is selected.
5999 * The other cases are handled by popup_menu().
6000 */
6001 if (event->state & CDK_CONTROL_MASK)
6002 {
6003 handled = handle_popups (container, event,
6004 "context_click_background");
6005 }
6006 break;
6007 case CDK_KEY_v0x076:
6008 /* Eat Control + v to not enable type ahead */
6009 if ((event->state & CDK_CONTROL_MASK) != 0)
6010 {
6011 handled = TRUE(!(0));
6012 }
6013 break;
6014 default:
6015 break;
6016 }
6017 }
6018
6019 if (!handled)
6020 {
6021 handled = CTK_WIDGET_CLASS (baul_icon_container_parent_class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), ((ctk_widget_get_type
()))))))
->key_press_event (widget, event);
6022 }
6023
6024 /* We pass the event to the search_entry. If its text changes, then we
6025 * start the typeahead find capabilities.
6026 * Copied from BaulIconContainer */
6027 if (!handled &&
6028 event->keyval != CDK_KEY_slash0x02f /* don't steal slash key event, used for "go to" */ &&
6029 event->keyval != CDK_KEY_BackSpace0xff08 &&
6030 event->keyval != CDK_KEY_Delete0xffff)
6031 {
6032 CdkEvent *new_event;
6033 CdkWindow *window;
6034 char *old_text;
6035 const char *new_text;
6036 gboolean retval;
6037 CdkScreen *screen;
6038 gboolean text_modified;
6039 gulong popup_menu_id;
6040 gint scale;
6041
6042 baul_icon_container_ensure_interactive_directory (container);
6043
6044 /* Make a copy of the current text */
6045 old_text = g_strdup (ctk_entry_get_text (CTK_ENTRY (container->details->search_entry)))g_strdup_inline (ctk_entry_get_text (((((CtkEntry*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container->details->search_entry))
, ((ctk_entry_get_type ()))))))))
;
6046 new_event = cdk_event_copy ((CdkEvent *) event);
6047 window = ((CdkEventKey *) new_event)->window;
6048 ((CdkEventKey *) new_event)->window = ctk_widget_get_window (container->details->search_entry);
6049 ctk_widget_realize (container->details->search_window);
6050
6051 popup_menu_id = g_signal_connect (container->details->search_entry,g_signal_connect_data ((container->details->search_entry
), ("popup_menu"), (((GCallback) (ctk_true))), (((void*)0)), (
(void*)0), (GConnectFlags) 0)
6052 "popup_menu", G_CALLBACK (ctk_true), NULL)g_signal_connect_data ((container->details->search_entry
), ("popup_menu"), (((GCallback) (ctk_true))), (((void*)0)), (
(void*)0), (GConnectFlags) 0)
;
6053
6054 /* Move the entry off screen */
6055 screen = ctk_widget_get_screen (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
6056 scale = ctk_widget_get_scale_factor (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
6057 ctk_window_move (CTK_WINDOW (container->details->search_window)((((CtkWindow*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_window)), ((ctk_window_get_type
()))))))
,
6058 WidthOfScreen (cdk_x11_screen_get_xscreen (screen))((cdk_x11_screen_get_xscreen (screen))->width) / scale + 1,
6059 HeightOfScreen (cdk_x11_screen_get_xscreen (screen))((cdk_x11_screen_get_xscreen (screen))->height) / scale + 1);
6060 ctk_widget_show (container->details->search_window);
6061
6062 /* Send the event to the window. If the preedit_changed signal is emitted
6063 * during this event, we will set priv->imcontext_changed */
6064 container->details->imcontext_changed = FALSE(0);
6065 retval = ctk_widget_event (container->details->search_entry, new_event);
6066 ctk_widget_hide (container->details->search_window);
6067
6068 g_signal_handler_disconnect (container->details->search_entry,
6069 popup_menu_id);
6070
6071 /* We check to make sure that the entry tried to handle the text, and that
6072 * the text has changed. */
6073 new_text = ctk_entry_get_text (CTK_ENTRY (container->details->search_entry)((((CtkEntry*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_entry)), ((ctk_entry_get_type
()))))))
);
6074 text_modified = strcmp (old_text, new_text) != 0;
6075 g_free (old_text);
6076 if (container->details->imcontext_changed || /* we're in a preedit */
6077 (retval && text_modified)) /* ...or the text was modified */
6078 {
6079 if (baul_icon_container_real_start_interactive_search (container, FALSE(0)))
6080 {
6081 ctk_widget_grab_focus (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
6082 return TRUE(!(0));
6083 }
6084 else
6085 {
6086 ctk_entry_set_text (CTK_ENTRY (container->details->search_entry)((((CtkEntry*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container->details->search_entry)), ((ctk_entry_get_type
()))))))
, "");
6087 return FALSE(0);
6088 }
6089 }
6090
6091 ((CdkEventKey *) new_event)->window = window;
6092 cdk_event_free (new_event);
6093 }
6094
6095 return handled;
6096}
6097
6098static gboolean
6099popup_menu (CtkWidget *widget)
6100{
6101 BaulIconContainer *container;
6102
6103 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
6104
6105 if (has_selection (container))
6106 {
6107 handle_popups (container, NULL((void*)0),
6108 "context_click_selection");
6109 }
6110 else
6111 {
6112 handle_popups (container, NULL((void*)0),
6113 "context_click_background");
6114 }
6115
6116 return TRUE(!(0));
6117}
6118
6119static void
6120draw_canvas_background (EelCanvas *canvas G_GNUC_UNUSED__attribute__ ((__unused__)),
6121 cairo_t *cr G_GNUC_UNUSED__attribute__ ((__unused__)))
6122{
6123 /* Don't chain up to the parent to avoid clearing and redrawing */
6124}
6125
6126static void
6127grab_notify_cb (CtkWidget *widget,
6128 gboolean was_grabbed)
6129{
6130 BaulIconContainer *container;
6131
6132 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
6133
6134 if (container->details->rubberband_info.active &&
6135 !was_grabbed)
6136 {
6137 /* we got a (un)grab-notify during rubberband.
6138 * This happens when a new modal dialog shows
6139 * up (e.g. authentication or an error). Stop
6140 * the rubberbanding so that we can handle the
6141 * dialog. */
6142 stop_rubberbanding (container);
6143 }
6144}
6145
6146static void
6147text_ellipsis_limit_changed_container_callback (gpointer callback_data)
6148{
6149 BaulIconContainer *container;
6150
6151 container = BAUL_ICON_CONTAINER (callback_data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((callback_data)), (baul_icon_container_get_type
())))))
;
6152 invalidate_label_sizes (container);
6153 schedule_redo_layout (container);
6154}
6155
6156static GObject*
6157baul_icon_container_constructor (GType type,
6158 guint n_construct_params,
6159 GObjectConstructParam *construct_params)
6160{
6161 BaulIconContainer *container;
6162 GObject *object;
6163
6164 object = G_OBJECT_CLASS (baul_icon_container_parent_class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((baul_icon_container_parent_class)), (((GType) ((20) <<
(2))))))))
->constructor
6165 (type,
6166 n_construct_params,
6167 construct_params);
6168
6169 container = BAUL_ICON_CONTAINER (object)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((object)), (baul_icon_container_get_type())
))))
;
6170 if (baul_icon_container_get_is_desktop (container))
6171 {
6172 g_signal_connect_swapped (baul_desktop_preferences,g_signal_connect_data ((baul_desktop_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
6173 "changed::" BAUL_PREFERENCES_DESKTOP_TEXT_ELLIPSIS_LIMIT,g_signal_connect_data ((baul_desktop_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
6174 G_CALLBACK (text_ellipsis_limit_changed_container_callback),g_signal_connect_data ((baul_desktop_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
6175 container)g_signal_connect_data ((baul_desktop_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
;
6176 }
6177 else
6178 {
6179 g_signal_connect_swapped (baul_icon_view_preferences,g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
6180 "changed::" BAUL_PREFERENCES_ICON_VIEW_TEXT_ELLIPSIS_LIMIT,g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
6181 G_CALLBACK (text_ellipsis_limit_changed_container_callback),g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
6182 container)g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_container_callback
))), (container), ((void*)0), G_CONNECT_SWAPPED)
;
6183 }
6184
6185 return object;
6186}
6187
6188/* Initialization. */
6189
6190static void
6191baul_icon_container_class_init (BaulIconContainerClass *class)
6192{
6193 CtkWidgetClass *widget_class;
6194 EelCanvasClass *canvas_class;
6195 CtkBindingSet *binding_set;
6196
6197 G_OBJECT_CLASS (class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((class)), (((GType) ((20) << (2))))))))
->constructor = baul_icon_container_constructor;
6198 G_OBJECT_CLASS (class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((class)), (((GType) ((20) << (2))))))))
->finalize = finalize;
6199
6200 CTK_WIDGET_CLASS (class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((class)), ((ctk_widget_get_type ()))))))
->destroy = destroy;
6201
6202 /* Signals. */
6203
6204 signals[SELECTION_CHANGED]
6205 = g_signal_new ("selection_changed",
6206 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6207 G_SIGNAL_RUN_LAST,
6208 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, selection_changed
))
6209 selection_changed)((glong) __builtin_offsetof(BaulIconContainerClass, selection_changed
))
,
6210 NULL((void*)0), NULL((void*)0),
6211 g_cclosure_marshal_VOID__VOID,
6212 G_TYPE_NONE((GType) ((1) << (2))), 0);
6213 signals[BUTTON_PRESS]
6214 = g_signal_new ("button_press",
6215 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6216 G_SIGNAL_RUN_LAST,
6217 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, button_press
))
6218 button_press)((glong) __builtin_offsetof(BaulIconContainerClass, button_press
))
,
6219 NULL((void*)0), NULL((void*)0),
6220 baul_marshal_BOOLEAN__POINTER,
6221 G_TYPE_BOOLEAN((GType) ((5) << (2))), 1,
6222 CDK_TYPE_EVENT(cdk_event_get_type ()));
6223 signals[ACTIVATE]
6224 = g_signal_new ("activate",
6225 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6226 G_SIGNAL_RUN_LAST,
6227 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, activate)
)
6228 activate)((glong) __builtin_offsetof(BaulIconContainerClass, activate)
)
,
6229 NULL((void*)0), NULL((void*)0),
6230 g_cclosure_marshal_VOID__POINTER,
6231 G_TYPE_NONE((GType) ((1) << (2))), 1,
6232 G_TYPE_POINTER((GType) ((17) << (2))));
6233 signals[ACTIVATE_ALTERNATE]
6234 = g_signal_new ("activate_alternate",
6235 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6236 G_SIGNAL_RUN_LAST,
6237 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, activate_alternate
))
6238 activate_alternate)((glong) __builtin_offsetof(BaulIconContainerClass, activate_alternate
))
,
6239 NULL((void*)0), NULL((void*)0),
6240 g_cclosure_marshal_VOID__POINTER,
6241 G_TYPE_NONE((GType) ((1) << (2))), 1,
6242 G_TYPE_POINTER((GType) ((17) << (2))));
6243 signals[CONTEXT_CLICK_SELECTION]
6244 = g_signal_new ("context_click_selection",
6245 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6246 G_SIGNAL_RUN_LAST,
6247 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, context_click_selection
))
6248 context_click_selection)((glong) __builtin_offsetof(BaulIconContainerClass, context_click_selection
))
,
6249 NULL((void*)0), NULL((void*)0),
6250 g_cclosure_marshal_VOID__POINTER,
6251 G_TYPE_NONE((GType) ((1) << (2))), 1,
6252 G_TYPE_POINTER((GType) ((17) << (2))));
6253 signals[CONTEXT_CLICK_BACKGROUND]
6254 = g_signal_new ("context_click_background",
6255 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6256 G_SIGNAL_RUN_LAST,
6257 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, context_click_background
))
6258 context_click_background)((glong) __builtin_offsetof(BaulIconContainerClass, context_click_background
))
,
6259 NULL((void*)0), NULL((void*)0),
6260 g_cclosure_marshal_VOID__POINTER,
6261 G_TYPE_NONE((GType) ((1) << (2))), 1,
6262 G_TYPE_POINTER((GType) ((17) << (2))));
6263 signals[MIDDLE_CLICK]
6264 = g_signal_new ("middle_click",
6265 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6266 G_SIGNAL_RUN_LAST,
6267 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, middle_click
))
6268 middle_click)((glong) __builtin_offsetof(BaulIconContainerClass, middle_click
))
,
6269 NULL((void*)0), NULL((void*)0),
6270 g_cclosure_marshal_VOID__POINTER,
6271 G_TYPE_NONE((GType) ((1) << (2))), 1,
6272 G_TYPE_POINTER((GType) ((17) << (2))));
6273 signals[ICON_POSITION_CHANGED]
6274 = g_signal_new ("icon_position_changed",
6275 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6276 G_SIGNAL_RUN_LAST,
6277 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, icon_position_changed
))
6278 icon_position_changed)((glong) __builtin_offsetof(BaulIconContainerClass, icon_position_changed
))
,
6279 NULL((void*)0), NULL((void*)0),
6280 baul_marshal_VOID__POINTER_POINTER,
6281 G_TYPE_NONE((GType) ((1) << (2))), 2,
6282 G_TYPE_POINTER((GType) ((17) << (2))),
6283 G_TYPE_POINTER((GType) ((17) << (2))));
6284 signals[ICON_TEXT_CHANGED]
6285 = g_signal_new ("icon_text_changed",
6286 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6287 G_SIGNAL_RUN_LAST,
6288 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, icon_text_changed
))
6289 icon_text_changed)((glong) __builtin_offsetof(BaulIconContainerClass, icon_text_changed
))
,
6290 NULL((void*)0), NULL((void*)0),
6291 baul_marshal_VOID__POINTER_STRING,
6292 G_TYPE_NONE((GType) ((1) << (2))), 2,
6293 G_TYPE_POINTER((GType) ((17) << (2))),
6294 G_TYPE_STRING((GType) ((16) << (2))));
6295 signals[ICON_STRETCH_STARTED]
6296 = g_signal_new ("icon_stretch_started",
6297 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6298 G_SIGNAL_RUN_LAST,
6299 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, icon_stretch_started
))
6300 icon_stretch_started)((glong) __builtin_offsetof(BaulIconContainerClass, icon_stretch_started
))
,
6301 NULL((void*)0), NULL((void*)0),
6302 g_cclosure_marshal_VOID__POINTER,
6303 G_TYPE_NONE((GType) ((1) << (2))), 1,
6304 G_TYPE_POINTER((GType) ((17) << (2))));
6305 signals[ICON_STRETCH_ENDED]
6306 = g_signal_new ("icon_stretch_ended",
6307 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6308 G_SIGNAL_RUN_LAST,
6309 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, icon_stretch_ended
))
6310 icon_stretch_ended)((glong) __builtin_offsetof(BaulIconContainerClass, icon_stretch_ended
))
,
6311 NULL((void*)0), NULL((void*)0),
6312 g_cclosure_marshal_VOID__POINTER,
6313 G_TYPE_NONE((GType) ((1) << (2))), 1,
6314 G_TYPE_POINTER((GType) ((17) << (2))));
6315 signals[RENAMING_ICON]
6316 = g_signal_new ("renaming_icon",
6317 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6318 G_SIGNAL_RUN_LAST,
6319 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, renaming_icon
))
6320 renaming_icon)((glong) __builtin_offsetof(BaulIconContainerClass, renaming_icon
))
,
6321 NULL((void*)0), NULL((void*)0),
6322 g_cclosure_marshal_VOID__POINTER,
6323 G_TYPE_NONE((GType) ((1) << (2))), 1,
6324 G_TYPE_POINTER((GType) ((17) << (2))));
6325 signals[GET_ICON_URI]
6326 = g_signal_new ("get_icon_uri",
6327 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6328 G_SIGNAL_RUN_LAST,
6329 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, get_icon_uri
))
6330 get_icon_uri)((glong) __builtin_offsetof(BaulIconContainerClass, get_icon_uri
))
,
6331 NULL((void*)0), NULL((void*)0),
6332 baul_marshal_STRING__POINTER,
6333 G_TYPE_STRING((GType) ((16) << (2))), 1,
6334 G_TYPE_POINTER((GType) ((17) << (2))));
6335 signals[GET_ICON_DROP_TARGET_URI]
6336 = g_signal_new ("get_icon_drop_target_uri",
6337 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6338 G_SIGNAL_RUN_LAST,
6339 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, get_icon_drop_target_uri
))
6340 get_icon_drop_target_uri)((glong) __builtin_offsetof(BaulIconContainerClass, get_icon_drop_target_uri
))
,
6341 NULL((void*)0), NULL((void*)0),
6342 baul_marshal_STRING__POINTER,
6343 G_TYPE_STRING((GType) ((16) << (2))), 1,
6344 G_TYPE_POINTER((GType) ((17) << (2))));
6345 signals[MOVE_COPY_ITEMS]
6346 = g_signal_new ("move_copy_items",
6347 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6348 G_SIGNAL_RUN_LAST,
6349 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, move_copy_items
))
6350 move_copy_items)((glong) __builtin_offsetof(BaulIconContainerClass, move_copy_items
))
,
6351 NULL((void*)0), NULL((void*)0),
6352 baul_marshal_VOID__POINTER_POINTER_POINTER_ENUM_INT_INT,
6353 G_TYPE_NONE((GType) ((1) << (2))), 6,
6354 G_TYPE_POINTER((GType) ((17) << (2))),
6355 G_TYPE_POINTER((GType) ((17) << (2))),
6356 G_TYPE_POINTER((GType) ((17) << (2))),
6357 CDK_TYPE_DRAG_ACTION(cdk_drag_action_get_type ()),
6358 G_TYPE_INT((GType) ((6) << (2))),
6359 G_TYPE_INT((GType) ((6) << (2))));
6360 signals[HANDLE_NETSCAPE_URL]
6361 = g_signal_new ("handle_netscape_url",
6362 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6363 G_SIGNAL_RUN_LAST,
6364 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, handle_netscape_url
))
6365 handle_netscape_url)((glong) __builtin_offsetof(BaulIconContainerClass, handle_netscape_url
))
,
6366 NULL((void*)0), NULL((void*)0),
6367 baul_marshal_VOID__STRING_STRING_ENUM_INT_INT,
6368 G_TYPE_NONE((GType) ((1) << (2))), 5,
6369 G_TYPE_STRING((GType) ((16) << (2))),
6370 G_TYPE_STRING((GType) ((16) << (2))),
6371 CDK_TYPE_DRAG_ACTION(cdk_drag_action_get_type ()),
6372 G_TYPE_INT((GType) ((6) << (2))),
6373 G_TYPE_INT((GType) ((6) << (2))));
6374 signals[HANDLE_URI_LIST]
6375 = g_signal_new ("handle_uri_list",
6376 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6377 G_SIGNAL_RUN_LAST,
6378 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, handle_uri_list
))
6379 handle_uri_list)((glong) __builtin_offsetof(BaulIconContainerClass, handle_uri_list
))
,
6380 NULL((void*)0), NULL((void*)0),
6381 baul_marshal_VOID__STRING_STRING_ENUM_INT_INT,
6382 G_TYPE_NONE((GType) ((1) << (2))), 5,
6383 G_TYPE_STRING((GType) ((16) << (2))),
6384 G_TYPE_STRING((GType) ((16) << (2))),
6385 CDK_TYPE_DRAG_ACTION(cdk_drag_action_get_type ()),
6386 G_TYPE_INT((GType) ((6) << (2))),
6387 G_TYPE_INT((GType) ((6) << (2))));
6388 signals[HANDLE_TEXT]
6389 = g_signal_new ("handle_text",
6390 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6391 G_SIGNAL_RUN_LAST,
6392 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, handle_text
))
6393 handle_text)((glong) __builtin_offsetof(BaulIconContainerClass, handle_text
))
,
6394 NULL((void*)0), NULL((void*)0),
6395 baul_marshal_VOID__STRING_STRING_ENUM_INT_INT,
6396 G_TYPE_NONE((GType) ((1) << (2))), 5,
6397 G_TYPE_STRING((GType) ((16) << (2))),
6398 G_TYPE_STRING((GType) ((16) << (2))),
6399 CDK_TYPE_DRAG_ACTION(cdk_drag_action_get_type ()),
6400 G_TYPE_INT((GType) ((6) << (2))),
6401 G_TYPE_INT((GType) ((6) << (2))));
6402 signals[HANDLE_RAW]
6403 = g_signal_new ("handle_raw",
6404 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6405 G_SIGNAL_RUN_LAST,
6406 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, handle_raw
))
6407 handle_raw)((glong) __builtin_offsetof(BaulIconContainerClass, handle_raw
))
,
6408 NULL((void*)0), NULL((void*)0),
6409 baul_marshal_VOID__POINTER_INT_STRING_STRING_ENUM_INT_INT,
6410 G_TYPE_NONE((GType) ((1) << (2))), 7,
6411 G_TYPE_POINTER((GType) ((17) << (2))),
6412 G_TYPE_INT((GType) ((6) << (2))),
6413 G_TYPE_STRING((GType) ((16) << (2))),
6414 G_TYPE_STRING((GType) ((16) << (2))),
6415 CDK_TYPE_DRAG_ACTION(cdk_drag_action_get_type ()),
6416 G_TYPE_INT((GType) ((6) << (2))),
6417 G_TYPE_INT((GType) ((6) << (2))));
6418 signals[GET_CONTAINER_URI]
6419 = g_signal_new ("get_container_uri",
6420 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6421 G_SIGNAL_RUN_LAST,
6422 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, get_container_uri
))
6423 get_container_uri)((glong) __builtin_offsetof(BaulIconContainerClass, get_container_uri
))
,
6424 NULL((void*)0), NULL((void*)0),
6425 baul_marshal_STRING__VOID,
6426 G_TYPE_STRING((GType) ((16) << (2))), 0);
6427 signals[CAN_ACCEPT_ITEM]
6428 = g_signal_new ("can_accept_item",
6429 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6430 G_SIGNAL_RUN_LAST,
6431 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, can_accept_item
))
6432 can_accept_item)((glong) __builtin_offsetof(BaulIconContainerClass, can_accept_item
))
,
6433 NULL((void*)0), NULL((void*)0),
6434 baul_marshal_INT__POINTER_STRING,
6435 G_TYPE_INT((GType) ((6) << (2))), 2,
6436 G_TYPE_POINTER((GType) ((17) << (2))),
6437 G_TYPE_STRING((GType) ((16) << (2))));
6438 signals[GET_STORED_ICON_POSITION]
6439 = g_signal_new ("get_stored_icon_position",
6440 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6441 G_SIGNAL_RUN_LAST,
6442 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, get_stored_icon_position
))
6443 get_stored_icon_position)((glong) __builtin_offsetof(BaulIconContainerClass, get_stored_icon_position
))
,
6444 NULL((void*)0), NULL((void*)0),
6445 baul_marshal_BOOLEAN__POINTER_POINTER,
6446 G_TYPE_BOOLEAN((GType) ((5) << (2))), 2,
6447 G_TYPE_POINTER((GType) ((17) << (2))),
6448 G_TYPE_POINTER((GType) ((17) << (2))));
6449 signals[GET_STORED_LAYOUT_TIMESTAMP]
6450 = g_signal_new ("get_stored_layout_timestamp",
6451 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6452 G_SIGNAL_RUN_LAST,
6453 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, get_stored_layout_timestamp
))
6454 get_stored_layout_timestamp)((glong) __builtin_offsetof(BaulIconContainerClass, get_stored_layout_timestamp
))
,
6455 NULL((void*)0), NULL((void*)0),
6456 baul_marshal_BOOLEAN__POINTER_POINTER,
6457 G_TYPE_BOOLEAN((GType) ((5) << (2))), 2,
6458 G_TYPE_POINTER((GType) ((17) << (2))),
6459 G_TYPE_POINTER((GType) ((17) << (2))));
6460 signals[STORE_LAYOUT_TIMESTAMP]
6461 = g_signal_new ("store_layout_timestamp",
6462 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6463 G_SIGNAL_RUN_LAST,
6464 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, store_layout_timestamp
))
6465 store_layout_timestamp)((glong) __builtin_offsetof(BaulIconContainerClass, store_layout_timestamp
))
,
6466 NULL((void*)0), NULL((void*)0),
6467 baul_marshal_BOOLEAN__POINTER_POINTER,
6468 G_TYPE_BOOLEAN((GType) ((5) << (2))), 2,
6469 G_TYPE_POINTER((GType) ((17) << (2))),
6470 G_TYPE_POINTER((GType) ((17) << (2))));
6471 signals[LAYOUT_CHANGED]
6472 = g_signal_new ("layout_changed",
6473 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6474 G_SIGNAL_RUN_LAST,
6475 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, layout_changed
))
6476 layout_changed)((glong) __builtin_offsetof(BaulIconContainerClass, layout_changed
))
,
6477 NULL((void*)0), NULL((void*)0),
6478 g_cclosure_marshal_VOID__VOID,
6479 G_TYPE_NONE((GType) ((1) << (2))), 0);
6480 signals[PREVIEW]
6481 = g_signal_new ("preview",
6482 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6483 G_SIGNAL_RUN_LAST,
6484 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, preview))
6485 preview)((glong) __builtin_offsetof(BaulIconContainerClass, preview)),
6486 NULL((void*)0), NULL((void*)0),
6487 baul_marshal_INT__POINTER_BOOLEAN,
6488 G_TYPE_INT((GType) ((6) << (2))), 2,
6489 G_TYPE_POINTER((GType) ((17) << (2))),
6490 G_TYPE_BOOLEAN((GType) ((5) << (2))));
6491 signals[BAND_SELECT_STARTED]
6492 = g_signal_new ("band_select_started",
6493 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6494 G_SIGNAL_RUN_LAST,
6495 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, band_select_started
))
6496 band_select_started)((glong) __builtin_offsetof(BaulIconContainerClass, band_select_started
))
,
6497 NULL((void*)0), NULL((void*)0),
6498 g_cclosure_marshal_VOID__VOID,
6499 G_TYPE_NONE((GType) ((1) << (2))), 0);
6500 signals[BAND_SELECT_ENDED]
6501 = g_signal_new ("band_select_ended",
6502 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6503 G_SIGNAL_RUN_LAST,
6504 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, band_select_ended
))
6505 band_select_ended)((glong) __builtin_offsetof(BaulIconContainerClass, band_select_ended
))
,
6506 NULL((void*)0), NULL((void*)0),
6507 g_cclosure_marshal_VOID__VOID,
6508 G_TYPE_NONE((GType) ((1) << (2))), 0);
6509 signals[ICON_ADDED]
6510 = g_signal_new ("icon_added",
6511 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6512 G_SIGNAL_RUN_LAST,
6513 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, icon_added
))
6514 icon_added)((glong) __builtin_offsetof(BaulIconContainerClass, icon_added
))
,
6515 NULL((void*)0), NULL((void*)0),
6516 g_cclosure_marshal_VOID__POINTER,
6517 G_TYPE_NONE((GType) ((1) << (2))), 1, G_TYPE_POINTER((GType) ((17) << (2))));
6518 signals[ICON_REMOVED]
6519 = g_signal_new ("icon_removed",
6520 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6521 G_SIGNAL_RUN_LAST,
6522 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, icon_removed
))
6523 icon_removed)((glong) __builtin_offsetof(BaulIconContainerClass, icon_removed
))
,
6524 NULL((void*)0), NULL((void*)0),
6525 g_cclosure_marshal_VOID__POINTER,
6526 G_TYPE_NONE((GType) ((1) << (2))), 1, G_TYPE_POINTER((GType) ((17) << (2))));
6527
6528 signals[CLEARED]
6529 = g_signal_new ("cleared",
6530 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6531 G_SIGNAL_RUN_LAST,
6532 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, cleared))
6533 cleared)((glong) __builtin_offsetof(BaulIconContainerClass, cleared)),
6534 NULL((void*)0), NULL((void*)0),
6535 g_cclosure_marshal_VOID__VOID,
6536 G_TYPE_NONE((GType) ((1) << (2))), 0);
6537
6538 signals[START_INTERACTIVE_SEARCH]
6539 = g_signal_new ("start_interactive_search",
6540 G_TYPE_FROM_CLASS (class)(((GTypeClass*) (class))->g_type),
6541 G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
6542 G_STRUCT_OFFSET (BaulIconContainerClass,((glong) __builtin_offsetof(BaulIconContainerClass, start_interactive_search
))
6543 start_interactive_search)((glong) __builtin_offsetof(BaulIconContainerClass, start_interactive_search
))
,
6544 NULL((void*)0), NULL((void*)0),
6545 baul_marshal_BOOLEAN__VOID,
6546 G_TYPE_BOOLEAN((GType) ((5) << (2))), 0);
6547
6548 /* CtkWidget class. */
6549
6550 widget_class = CTK_WIDGET_CLASS (class)((((CtkWidgetClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((class)), ((ctk_widget_get_type ()))))))
;
6551 widget_class->size_allocate = size_allocate;
6552 widget_class->get_request_mode = get_request_mode;
6553 widget_class->get_preferred_width = get_prefered_width;
6554 widget_class->get_preferred_height = get_prefered_height;
6555 widget_class->draw = draw;
6556 widget_class->realize = realize;
6557 widget_class->unrealize = unrealize;
6558 widget_class->button_press_event = button_press_event;
6559 widget_class->button_release_event = button_release_event;
6560 widget_class->motion_notify_event = motion_notify_event;
6561 widget_class->key_press_event = key_press_event;
6562 widget_class->popup_menu = popup_menu;
6563 widget_class->style_updated = style_updated;
6564 widget_class->grab_notify = grab_notify_cb;
6565
6566 ctk_widget_class_set_accessible_type (widget_class, baul_icon_container_accessible_get_type ());
6567
6568 canvas_class = EEL_CANVAS_CLASS (class)((((EelCanvasClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((class)), ((eel_canvas_get_type ()))))))
;
6569 canvas_class->draw_background = draw_canvas_background;
6570 class->start_interactive_search = baul_icon_container_start_interactive_search;
6571
6572 ctk_widget_class_install_style_property (widget_class,
6573 g_param_spec_boxed ("selection_box_rgba",
6574 "Selection Box RGBA",
6575 "Color of the selection box",
6576 CDK_TYPE_RGBA(cdk_rgba_get_type ()),
6577 G_PARAM_READABLE));
6578 ctk_widget_class_install_style_property (widget_class,
6579 g_param_spec_boxed ("light_info_rgba",
6580 "Light Info RGBA",
6581 "Color used for information text against a dark background",
6582 CDK_TYPE_RGBA(cdk_rgba_get_type ()),
6583 G_PARAM_READABLE));
6584 ctk_widget_class_install_style_property (widget_class,
6585 g_param_spec_boxed ("dark_info_rgba",
6586 "Dark Info RGBA",
6587 "Color used for information text against a light background",
6588 CDK_TYPE_RGBA(cdk_rgba_get_type ()),
6589 G_PARAM_READABLE));
6590 ctk_widget_class_install_style_property (widget_class,
6591 g_param_spec_boolean ("activate_prelight_icon_label",
6592 "Activate Prelight Icon Label",
6593 "Whether icon labels should make use of its prelight color in prelight state",
6594 FALSE(0),
6595 G_PARAM_READABLE));
6596
6597
6598 binding_set = ctk_binding_set_by_class (class);
6599
6600 ctk_binding_entry_add_signal (binding_set, CDK_KEY_f0x066, CDK_CONTROL_MASK, "start_interactive_search", 0);
6601 ctk_binding_entry_add_signal (binding_set, CDK_KEY_F0x046, CDK_CONTROL_MASK, "start_interactive_search", 0);
6602}
6603
6604static void
6605update_selected (BaulIconContainer *container)
6606{
6607 GList *node;
6608 BaulIcon *icon = NULL((void*)0);
6609
6610 for (node = container->details->icons; node != NULL((void*)0); node = node->next)
6611 {
6612 icon = node->data;
6613 if (icon->is_selected)
6614 {
6615 eel_canvas_item_request_update (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
);
6616 }
6617 }
6618}
6619
6620static gboolean
6621handle_focus_in_event (CtkWidget *widget,
6622 CdkEventFocus *event G_GNUC_UNUSED__attribute__ ((__unused__)),
6623 gpointer user_data G_GNUC_UNUSED__attribute__ ((__unused__)))
6624{
6625 update_selected (BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
);
6626
6627 return FALSE(0);
6628}
6629
6630static gboolean
6631handle_focus_out_event (CtkWidget *widget,
6632 CdkEventFocus *event G_GNUC_UNUSED__attribute__ ((__unused__)),
6633 gpointer user_data G_GNUC_UNUSED__attribute__ ((__unused__)))
6634{
6635 /* End renaming and commit change. */
6636 end_renaming_mode (BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
, TRUE(!(0)));
6637 update_selected (BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
);
6638
6639 return FALSE(0);
6640}
6641
6642static void
6643handle_scale_factor_changed (GObject *object,
6644 GParamSpec *pspec G_GNUC_UNUSED__attribute__ ((__unused__)),
6645 gpointer user_data G_GNUC_UNUSED__attribute__ ((__unused__)))
6646{
6647 invalidate_labels (BAUL_ICON_CONTAINER (object)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((object)), (baul_icon_container_get_type())
))))
);
6648 baul_icon_container_request_update_all (BAUL_ICON_CONTAINER (object)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((object)), (baul_icon_container_get_type())
))))
);
6649}
6650
6651
6652static int text_ellipsis_limits[BAUL_ZOOM_LEVEL_N_ENTRIES(BAUL_ZOOM_LEVEL_LARGEST + 1)];
6653static int desktop_text_ellipsis_limit;
6654
6655static gboolean
6656get_text_ellipsis_limit_for_zoom (char **strs,
6657 const char *zoom_level,
6658 int *limit)
6659{
6660 char *str;
6661 gboolean success;
6662
6663 success = FALSE(0);
6664
6665 /* default */
6666 *limit = 3;
6667
6668 if (zoom_level != NULL((void*)0))
6669 {
6670 str = g_strdup_printf ("%s:%%d", zoom_level);
6671 }
6672 else
6673 {
6674 str = g_strdup ("%d")g_strdup_inline ("%d");
6675 }
6676
6677 if (strs != NULL((void*)0))
6678 {
6679 char **p;
6680
6681 for (p = strs; *p != NULL((void*)0); p++)
6682 {
6683 if (sscanf (*p, str, limit))
6684 {
6685 success = TRUE(!(0));
6686 }
6687 }
6688 }
6689
6690 g_free (str);
6691
6692 return success;
6693}
6694
6695static const char * zoom_level_names[] = {
6696 "smallest",
6697 "smaller",
6698 "small",
6699 "standard",
6700 "large",
6701 "larger",
6702 "largest"
6703};
6704
6705static void
6706text_ellipsis_limit_changed_callback (gpointer callback_data G_GNUC_UNUSED__attribute__ ((__unused__)))
6707{
6708 char **pref;
6709 unsigned int i;
6710 int one_limit;
6711
6712 pref = g_settings_get_strv (baul_icon_view_preferences, BAUL_PREFERENCES_ICON_VIEW_TEXT_ELLIPSIS_LIMIT"text-ellipsis-limit");
6713
6714 /* set default */
6715 get_text_ellipsis_limit_for_zoom (pref, NULL((void*)0), &one_limit);
6716 for (i = 0; i < BAUL_ZOOM_LEVEL_N_ENTRIES(BAUL_ZOOM_LEVEL_LARGEST + 1); i++)
6717 {
6718 text_ellipsis_limits[i] = one_limit;
6719 }
6720
6721 /* override for each zoom level */
6722 for (i = 0; i < G_N_ELEMENTS(zoom_level_names)(sizeof (zoom_level_names) / sizeof ((zoom_level_names)[0])); i++) {
6723 if (get_text_ellipsis_limit_for_zoom (pref,
6724 zoom_level_names[i],
6725 &one_limit)) {
6726 text_ellipsis_limits[i] = one_limit;
6727 }
6728 }
6729
6730 g_strfreev (pref);
6731}
6732
6733static void
6734desktop_text_ellipsis_limit_changed_callback (gpointer callback_data G_GNUC_UNUSED__attribute__ ((__unused__)))
6735{
6736 int pref;
6737
6738 pref = g_settings_get_int (baul_desktop_preferences, BAUL_PREFERENCES_DESKTOP_TEXT_ELLIPSIS_LIMIT"text-ellipsis-limit");
6739 desktop_text_ellipsis_limit = pref;
6740}
6741
6742static void
6743baul_icon_container_init (BaulIconContainer *container)
6744{
6745 BaulIconContainerDetails *details;
6746 EelBackground *background;
6747 static gboolean setup_prefs = FALSE(0);
6748
6749 details = g_new0 (BaulIconContainerDetails, 1)((BaulIconContainerDetails *) g_malloc0_n ((1), sizeof (BaulIconContainerDetails
)))
;
6750
6751 details->icon_set = g_hash_table_new (g_direct_hash, g_direct_equal);
6752 details->layout_timestamp = UNDEFINED_TIME((time_t) (-1));
6753
6754 details->zoom_level = BAUL_ZOOM_LEVEL_STANDARD;
6755
6756 details->font_size_table[BAUL_ZOOM_LEVEL_SMALLEST] = -2 * PANGO_SCALE1024;
6757 details->font_size_table[BAUL_ZOOM_LEVEL_SMALLER] = -2 * PANGO_SCALE1024;
6758 details->font_size_table[BAUL_ZOOM_LEVEL_SMALL] = -0 * PANGO_SCALE1024;
6759 details->font_size_table[BAUL_ZOOM_LEVEL_STANDARD] = 0 * PANGO_SCALE1024;
6760 details->font_size_table[BAUL_ZOOM_LEVEL_LARGE] = 0 * PANGO_SCALE1024;
6761 details->font_size_table[BAUL_ZOOM_LEVEL_LARGER] = 0 * PANGO_SCALE1024;
6762 details->font_size_table[BAUL_ZOOM_LEVEL_LARGEST] = 0 * PANGO_SCALE1024;
6763
6764 container->details = details;
6765
6766 /* when the background changes, we must set up the label text color */
6767 background = eel_get_widget_background (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
6768
6769 g_signal_connect (container, "focus-in-event",g_signal_connect_data ((container), ("focus-in-event"), (((GCallback
) (handle_focus_in_event))), (((void*)0)), ((void*)0), (GConnectFlags
) 0)
6770 G_CALLBACK (handle_focus_in_event), NULL)g_signal_connect_data ((container), ("focus-in-event"), (((GCallback
) (handle_focus_in_event))), (((void*)0)), ((void*)0), (GConnectFlags
) 0)
;
6771 g_signal_connect (container, "focus-out-event",g_signal_connect_data ((container), ("focus-out-event"), (((GCallback
) (handle_focus_out_event))), (((void*)0)), ((void*)0), (GConnectFlags
) 0)
6772 G_CALLBACK (handle_focus_out_event), NULL)g_signal_connect_data ((container), ("focus-out-event"), (((GCallback
) (handle_focus_out_event))), (((void*)0)), ((void*)0), (GConnectFlags
) 0)
;
6773
6774 g_signal_connect (container, "notify::scale-factor",g_signal_connect_data ((container), ("notify::scale-factor"),
(((GCallback) (handle_scale_factor_changed))), (((void*)0)),
((void*)0), (GConnectFlags) 0)
6775 G_CALLBACK (handle_scale_factor_changed), NULL)g_signal_connect_data ((container), ("notify::scale-factor"),
(((GCallback) (handle_scale_factor_changed))), (((void*)0)),
((void*)0), (GConnectFlags) 0)
;
6776
6777 eel_background_set_use_base (background, TRUE(!(0)));
6778
6779 if (!setup_prefs)
6780 {
6781 g_signal_connect_swapped (baul_icon_view_preferences,g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
6782 "changed::" BAUL_PREFERENCES_ICON_VIEW_TEXT_ELLIPSIS_LIMIT,g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
6783 G_CALLBACK (text_ellipsis_limit_changed_callback),g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
6784 NULL)g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
;
6785 text_ellipsis_limit_changed_callback (NULL((void*)0));
6786
6787 g_signal_connect_swapped (baul_icon_view_preferences,g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (desktop_text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
6788 "changed::" BAUL_PREFERENCES_DESKTOP_TEXT_ELLIPSIS_LIMIT,g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (desktop_text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
6789 G_CALLBACK (desktop_text_ellipsis_limit_changed_callback),g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (desktop_text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
6790 NULL)g_signal_connect_data ((baul_icon_view_preferences), ("changed::"
"text-ellipsis-limit"), (((GCallback) (desktop_text_ellipsis_limit_changed_callback
))), (((void*)0)), ((void*)0), G_CONNECT_SWAPPED)
;
6791 desktop_text_ellipsis_limit_changed_callback (NULL((void*)0));
6792
6793 setup_prefs = TRUE(!(0));
6794 }
6795}
6796
6797typedef struct
6798{
6799 BaulIconContainer *container;
6800 CdkEventButton *event;
6801} ContextMenuParameters;
6802
6803static gboolean
6804handle_icon_double_click (BaulIconContainer *container,
6805 BaulIcon *icon,
6806 CdkEventButton *event)
6807{
6808 BaulIconContainerDetails *details;
6809
6810 if (event->button != DRAG_BUTTON1)
6811 {
6812 return FALSE(0);
6813 }
6814
6815 details = container->details;
6816
6817 if (!details->single_click_mode &&
6818 clicked_within_double_click_interval (container) &&
6819 details->double_click_icon[0] == details->double_click_icon[1] &&
6820 details->double_click_button[0] == details->double_click_button[1])
6821 {
6822 if (!button_event_modifies_selection (event))
6823 {
6824 activate_selected_items (container);
6825 return TRUE(!(0));
6826 }
6827 else if ((event->state & CDK_CONTROL_MASK) == 0 &&
6828 (event->state & CDK_SHIFT_MASK) != 0)
6829 {
6830 activate_selected_items_alternate (container, icon);
6831 return TRUE(!(0));
6832 }
6833 }
6834
6835 return FALSE(0);
6836}
6837
6838/* BaulIcon event handling. */
6839
6840/* Conceptually, pressing button 1 together with CTRL or SHIFT toggles
6841 * selection of a single icon without affecting the other icons;
6842 * without CTRL or SHIFT, it selects a single icon and un-selects all
6843 * the other icons. But in this latter case, the de-selection should
6844 * only happen when the button is released if the icon is already
6845 * selected, because the user might select multiple icons and drag all
6846 * of them by doing a simple click-drag.
6847*/
6848
6849static gboolean
6850handle_icon_button_press (BaulIconContainer *container,
6851 BaulIcon *icon,
6852 CdkEventButton *event)
6853{
6854 BaulIconContainerDetails *details;
6855
6856 details = container->details;
6857
6858 if (event->type == CDK_2BUTTON_PRESS || event->type == CDK_3BUTTON_PRESS)
6859 {
6860 return TRUE(!(0));
6861 }
6862
6863 if (event->button != DRAG_BUTTON1
6864 && event->button != CONTEXTUAL_MENU_BUTTON3
6865 && event->button != DRAG_MENU_BUTTON2)
6866 {
6867 return TRUE(!(0));
6868 }
6869
6870 if ((event->button == DRAG_BUTTON1) &&
6871 event->type == CDK_BUTTON_PRESS)
6872 {
6873 /* The next double click has to be on this icon */
6874 details->double_click_icon[1] = details->double_click_icon[0];
6875 details->double_click_icon[0] = icon;
6876
6877 details->double_click_button[1] = details->double_click_button[0];
6878 details->double_click_button[0] = event->button;
6879 }
6880
6881 if (handle_icon_double_click (container, icon, event))
6882 {
6883 /* Double clicking does not trigger a D&D action. */
6884 details->drag_button = 0;
6885 details->drag_icon = NULL((void*)0);
6886 return TRUE(!(0));
6887 }
6888
6889 if (event->button == DRAG_BUTTON1
6890 || event->button == DRAG_MENU_BUTTON2)
6891 {
6892 details->drag_button = event->button;
6893 details->drag_icon = icon;
6894 details->drag_x = event->x;
6895 details->drag_y = event->y;
6896 details->drag_state = DRAG_STATE_MOVE_OR_COPY;
6897 details->drag_started = FALSE(0);
6898
6899 /* Check to see if this is a click on the stretch handles.
6900 * If so, it won't modify the selection.
6901 */
6902 if (icon == container->details->stretch_icon)
6903 {
6904 if (start_stretching (container, (CdkEvent *)event))
6905 {
6906 return TRUE(!(0));
6907 }
6908 }
6909 }
6910
6911 /* Modify the selection as appropriate. Selection is modified
6912 * the same way for contextual menu as it would be without.
6913 */
6914 details->icon_selected_on_button_down = icon->is_selected;
6915
6916 if ((event->button == DRAG_BUTTON1 || event->button == MIDDLE_BUTTON2) &&
6917 (event->state & CDK_SHIFT_MASK) != 0)
6918 {
6919 BaulIcon *start_icon;
6920
6921 start_icon = details->range_selection_base_icon;
6922 if (start_icon == NULL((void*)0) || !start_icon->is_selected)
6923 {
6924 start_icon = icon;
6925 details->range_selection_base_icon = icon;
6926 }
6927 if (select_range (container, start_icon, icon,
6928 (event->state & CDK_CONTROL_MASK) == 0))
6929 {
6930 g_signal_emit (container,
6931 signals[SELECTION_CHANGED], 0);
6932 }
6933 }
6934 else if (!details->icon_selected_on_button_down)
6935 {
6936 details->range_selection_base_icon = icon;
6937 if (button_event_modifies_selection (event))
6938 {
6939 icon_toggle_selected (container, icon);
6940 g_signal_emit (container,
6941 signals[SELECTION_CHANGED], 0);
6942 }
6943 else
6944 {
6945 select_one_unselect_others (container, icon);
6946 g_signal_emit (container,
6947 signals[SELECTION_CHANGED], 0);
6948 }
6949 }
6950
6951 if (event->button == CONTEXTUAL_MENU_BUTTON3)
6952 {
6953 g_signal_emit (container,
6954 signals[CONTEXT_CLICK_SELECTION], 0,
6955 event);
6956 }
6957
6958
6959 return TRUE(!(0));
6960}
6961
6962static int
6963item_event_callback (EelCanvasItem *item,
6964 CdkEvent *event,
6965 gpointer data)
6966{
6967 BaulIconContainer *container;
6968 BaulIcon *icon;
6969
6970 container = BAUL_ICON_CONTAINER (data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((data)), (baul_icon_container_get_type())))
))
;
6971
6972 icon = BAUL_ICON_CANVAS_ITEM (item)((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((item)), (baul_icon_canvas_item_get_type())
))))
->user_data;
6973 g_assert (icon != NULL)do { if (icon != ((void*)0)) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 6973, ((const char*) (
__func__)), "icon != NULL"); } while (0)
;
6974
6975 switch (event->type)
6976 {
6977 case CDK_BUTTON_PRESS:
6978 if (handle_icon_button_press (container, icon, &event->button))
6979 {
6980 /* Stop the event from being passed along further. Returning
6981 * TRUE ain't enough.
6982 */
6983 return TRUE(!(0));
6984 }
6985 return FALSE(0);
6986 default:
6987 return FALSE(0);
6988 }
6989}
6990
6991CtkWidget *
6992baul_icon_container_new (void)
6993{
6994 return ctk_widget_new (BAUL_TYPE_ICON_CONTAINERbaul_icon_container_get_type(), NULL((void*)0));
6995}
6996
6997/* Clear all of the icons in the container. */
6998void
6999baul_icon_container_clear (BaulIconContainer *container)
7000{
7001 BaulIconContainerDetails *details;
7002 GList *p;
7003
7004 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
7005
7006 details = container->details;
7007 details->layout_timestamp = UNDEFINED_TIME((time_t) (-1));
7008 details->store_layout_timestamps_when_finishing_new_icons = FALSE(0);
7009
7010 if (details->icons == NULL((void*)0))
7011 {
7012 return;
7013 }
7014
7015 end_renaming_mode (container, TRUE(!(0)));
7016
7017 clear_keyboard_focus (container);
7018 clear_keyboard_rubberband_start (container);
7019 unschedule_keyboard_icon_reveal (container);
7020 set_pending_icon_to_reveal (container, NULL((void*)0));
7021 details->stretch_icon = NULL((void*)0);
7022 details->drop_target = NULL((void*)0);
7023
7024 for (p = details->icons; p != NULL((void*)0); p = p->next)
7025 {
7026 icon_free (p->data);
7027 }
7028 g_list_free (details->icons);
7029 details->icons = NULL((void*)0);
7030 g_list_free (details->new_icons);
7031 details->new_icons = NULL((void*)0);
7032
7033 g_hash_table_destroy (details->icon_set);
7034 details->icon_set = g_hash_table_new (g_direct_hash, g_direct_equal);
7035
7036 baul_icon_container_update_scroll_region (container);
7037}
7038
7039gboolean
7040baul_icon_container_is_empty (BaulIconContainer *container)
7041{
7042 return container->details->icons == NULL((void*)0);
7043}
7044
7045BaulIconData *
7046baul_icon_container_get_first_visible_icon (BaulIconContainer *container)
7047{
7048 GList *l;
7049 BaulIcon *icon, *best_icon;
7050 double x, y;
7051 double x1, y1, x2, y2;
7052 double *pos, best_pos;
7053 double hadj_v, vadj_v, h_page_size;
7054 gboolean better_icon;
7055 gboolean compare_lt;
7056
7057 hadj_v = ctk_adjustment_get_value (ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
7058 vadj_v = ctk_adjustment_get_value (ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
7059 h_page_size = ctk_adjustment_get_page_size (ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
));
7060
7061 if (baul_icon_container_is_layout_rtl (container))
7062 {
7063 x = hadj_v + h_page_size - ICON_PAD_LEFT4 - 1;
7064 y = vadj_v;
7065 }
7066 else
7067 {
7068 x = hadj_v;
7069 y = vadj_v;
7070 }
7071
7072 eel_canvas_c2w (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
7073 x, y,
7074 &x, &y);
7075
7076 l = container->details->icons;
7077 best_icon = NULL((void*)0);
7078 best_pos = 0;
7079 while (l != NULL((void*)0))
7080 {
7081 icon = l->data;
7082
7083 if (icon_is_positioned (icon))
7084 {
7085 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
7086 &x1, &y1, &x2, &y2);
7087
7088 compare_lt = FALSE(0);
7089 if (baul_icon_container_is_layout_vertical (container))
7090 {
7091 pos = &x1;
7092 if (baul_icon_container_is_layout_rtl (container))
7093 {
7094 compare_lt = TRUE(!(0));
7095 better_icon = x1 < x + ICON_PAD_LEFT4;
7096 }
7097 else
7098 {
7099 better_icon = x2 > x + ICON_PAD_LEFT4;
7100 }
7101 }
7102 else
7103 {
7104 pos = &y1;
7105 better_icon = y2 > y + ICON_PAD_TOP4;
7106 }
7107 if (better_icon)
7108 {
7109 if (best_icon == NULL((void*)0))
7110 {
7111 better_icon = TRUE(!(0));
7112 }
7113 else if (compare_lt)
7114 {
7115 better_icon = best_pos < *pos;
7116 }
7117 else
7118 {
7119 better_icon = best_pos > *pos;
7120 }
7121
7122 if (better_icon)
7123 {
7124 best_icon = icon;
7125 best_pos = *pos;
7126 }
7127 }
7128 }
7129
7130 l = l->next;
7131 }
7132
7133 return best_icon ? best_icon->data : NULL((void*)0);
7134}
7135
7136/* puts the icon at the top of the screen */
7137void
7138baul_icon_container_scroll_to_icon (BaulIconContainer *container,
7139 BaulIconData *data)
7140{
7141 GList *l;
7142 CtkAdjustment *hadj, *vadj;
7143 EelIRect bounds;
7144 CtkAllocation allocation;
7145 BaulIcon *icon = NULL((void*)0);
7146
7147 hadj = ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
7148 vadj = ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
7149 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
7150
7151 /* We need to force a relayout now if there are updates queued
7152 * since we need the final positions */
7153 baul_icon_container_layout_now (container);
7154
7155 l = container->details->icons;
7156 while (l != NULL((void*)0)) {
7157 icon = l->data;
7158
7159 if (icon->data == data &&
7160 icon_is_positioned (icon)) {
7161
7162 if (baul_icon_container_is_auto_layout (container)) {
7163 /* ensure that we reveal the entire row/column */
7164 icon_get_row_and_column_bounds (container, icon, &bounds, TRUE(!(0)));
7165 } else {
7166 item_get_canvas_bounds (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
, &bounds, TRUE(!(0)));
7167 }
7168
7169 if (baul_icon_container_is_layout_vertical (container)) {
7170 if (baul_icon_container_is_layout_rtl (container)) {
7171 ctk_adjustment_set_value (hadj, bounds.x1 - allocation.width);
7172 } else {
7173 ctk_adjustment_set_value (hadj, bounds.x0);
7174 }
7175 } else {
7176 ctk_adjustment_set_value (vadj, bounds.y0);
7177 }
7178 }
7179
7180 l = l->next;
7181 }
7182}
7183
7184/* Call a function for all the icons. */
7185typedef struct
7186{
7187 BaulIconCallback callback;
7188 gpointer callback_data;
7189} CallbackAndData;
7190
7191static void
7192call_icon_callback (gpointer data, gpointer callback_data)
7193{
7194 BaulIcon *icon;
7195 CallbackAndData *callback_and_data;
7196
7197 icon = data;
7198 callback_and_data = callback_data;
7199 (* callback_and_data->callback) (icon->data, callback_and_data->callback_data);
7200}
7201
7202void
7203baul_icon_container_for_each (BaulIconContainer *container,
7204 BaulIconCallback callback,
7205 gpointer callback_data)
7206{
7207 CallbackAndData callback_and_data;
7208
7209 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
7210
7211 callback_and_data.callback = callback;
7212 callback_and_data.callback_data = callback_data;
7213
7214 g_list_foreach (container->details->icons,
7215 call_icon_callback, &callback_and_data);
7216}
7217
7218static int
7219selection_changed_at_idle_callback (gpointer data)
7220{
7221 BaulIconContainer *container;
7222
7223 container = BAUL_ICON_CONTAINER (data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((data)), (baul_icon_container_get_type())))
))
;
7224
7225 g_signal_emit (container,
7226 signals[SELECTION_CHANGED], 0);
7227
7228 container->details->selection_changed_id = 0;
7229 return FALSE(0);
7230}
7231
7232/* utility routine to remove a single icon from the container */
7233
7234static void
7235icon_destroy (BaulIconContainer *container,
7236 BaulIcon *icon)
7237{
7238 BaulIconContainerDetails *details;
7239 gboolean was_selected;
7240 BaulIcon *icon_to_focus;
7241 GList *item;
7242
7243 details = container->details;
7244
7245 item = g_list_find (details->icons, icon);
7246 item = item->next ? item->next : item->prev;
7247 icon_to_focus = (item != NULL((void*)0)) ? item->data : NULL((void*)0);
7248
7249 details->icons = g_list_remove (details->icons, icon);
7250 details->new_icons = g_list_remove (details->new_icons, icon);
7251 g_hash_table_remove (details->icon_set, icon->data);
7252
7253 was_selected = icon->is_selected;
7254
7255 if (details->keyboard_focus == icon ||
7256 details->keyboard_focus == NULL((void*)0))
7257 {
7258 if (icon_to_focus != NULL((void*)0))
7259 {
7260 set_keyboard_focus (container, icon_to_focus);
7261 }
7262 else
7263 {
7264 clear_keyboard_focus (container);
7265 }
7266 }
7267
7268 if (details->keyboard_rubberband_start == icon)
7269 {
7270 clear_keyboard_rubberband_start (container);
7271 }
7272
7273 if (details->keyboard_icon_to_reveal == icon)
7274 {
7275 unschedule_keyboard_icon_reveal (container);
7276 }
7277 if (details->drag_icon == icon)
7278 {
7279 clear_drag_state (container);
7280 }
7281 if (details->drop_target == icon)
7282 {
7283 details->drop_target = NULL((void*)0);
7284 }
7285 if (details->range_selection_base_icon == icon)
7286 {
7287 details->range_selection_base_icon = NULL((void*)0);
7288 }
7289 if (details->pending_icon_to_reveal == icon)
7290 {
7291 set_pending_icon_to_reveal (container, NULL((void*)0));
7292 }
7293 if (details->stretch_icon == icon)
7294 {
7295 details->stretch_icon = NULL((void*)0);
7296 }
7297
7298 icon_free (icon);
7299
7300 if (was_selected)
7301 {
7302 /* Coalesce multiple removals causing multiple selection_changed events */
7303 details->selection_changed_id = g_idle_add (selection_changed_at_idle_callback, container);
7304 }
7305}
7306
7307/* activate any selected items in the container */
7308static void
7309activate_selected_items (BaulIconContainer *container)
7310{
7311 GList *selection;
7312
7313 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
7314
7315 selection = baul_icon_container_get_selection (container);
7316 if (selection != NULL((void*)0))
7317 {
7318 g_signal_emit (container,
7319 signals[ACTIVATE], 0,
7320 selection);
7321 }
7322 g_list_free (selection);
7323}
7324
7325static void
7326activate_selected_items_alternate (BaulIconContainer *container,
7327 BaulIcon *icon)
7328{
7329 GList *selection;
7330
7331 g_assert (BAUL_IS_ICON_CONTAINER (container))do { if ((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; }))))) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 7331, ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); } while (0)
;
7332
7333 if (icon != NULL((void*)0))
7334 {
7335 selection = g_list_prepend (NULL((void*)0), icon->data);
7336 }
7337 else
7338 {
7339 selection = baul_icon_container_get_selection (container);
7340 }
7341 if (selection != NULL((void*)0))
7342 {
7343 g_signal_emit (container,
7344 signals[ACTIVATE_ALTERNATE], 0,
7345 selection);
7346 }
7347 g_list_free (selection);
7348}
7349
7350static BaulIcon *
7351get_icon_being_renamed (BaulIconContainer *container)
7352{
7353 BaulIcon *rename_icon;
7354
7355 if (!is_renaming (container))
7356 {
7357 return NULL((void*)0);
7358 }
7359
7360 g_assert (!has_multiple_selection (container))do { if (!has_multiple_selection (container)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7360, ((const char*)
(__func__)), "!has_multiple_selection (container)"); } while
(0)
;
7361
7362 rename_icon = get_first_selected_icon (container);
7363 g_assert (rename_icon != NULL)do { if (rename_icon != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7363, ((const char*)
(__func__)), "rename_icon != NULL"); } while (0)
;
7364
7365 return rename_icon;
7366}
7367
7368static BaulIconInfo *
7369baul_icon_container_get_icon_images (BaulIconContainer *container,
7370 BaulIconData *data,
7371 int size,
7372 GList **emblem_pixbufs,
7373 char **embedded_text,
7374 gboolean for_drag_accept,
7375 gboolean need_large_embeddded_text,
7376 gboolean *embedded_text_needs_loading,
7377 gboolean *has_open_window)
7378{
7379 BaulIconContainerClass *klass;
7380
7381 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
7382 g_assert (klass->get_icon_images != NULL)do { if (klass->get_icon_images != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7382, ((const char*)
(__func__)), "klass->get_icon_images != NULL"); } while (
0)
;
7383
7384 return klass->get_icon_images (container, data, size, emblem_pixbufs, embedded_text, for_drag_accept, need_large_embeddded_text, embedded_text_needs_loading, has_open_window);
7385}
7386
7387static void
7388baul_icon_container_freeze_updates (BaulIconContainer *container)
7389{
7390 BaulIconContainerClass *klass;
7391
7392 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
7393 g_assert (klass->freeze_updates != NULL)do { if (klass->freeze_updates != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7393, ((const char*)
(__func__)), "klass->freeze_updates != NULL"); } while (0
)
;
7394
7395 klass->freeze_updates (container);
7396}
7397
7398static void
7399baul_icon_container_unfreeze_updates (BaulIconContainer *container)
7400{
7401 BaulIconContainerClass *klass;
7402
7403 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
7404 g_assert (klass->unfreeze_updates != NULL)do { if (klass->unfreeze_updates != ((void*)0)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7404, ((const char*)
(__func__)), "klass->unfreeze_updates != NULL"); } while (
0)
;
7405
7406 klass->unfreeze_updates (container);
7407}
7408
7409static void
7410baul_icon_container_prioritize_thumbnailing (BaulIconContainer *container,
7411 BaulIcon *icon)
7412{
7413 BaulIconContainerClass *klass;
7414
7415 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
7416 g_assert (klass->prioritize_thumbnailing != NULL)do { if (klass->prioritize_thumbnailing != ((void*)0)) ; else
g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 7416, ((const char*) (__func__)), "klass->prioritize_thumbnailing != NULL"
); } while (0)
;
7417
7418 klass->prioritize_thumbnailing (container, icon->data);
7419}
7420
7421static void
7422baul_icon_container_update_visible_icons (BaulIconContainer *container)
7423{
7424 CtkAdjustment *vadj, *hadj;
7425 double min_y, max_y;
7426 double min_x, max_x;
7427 double x0, y0, x1, y1;
7428 GList *node;
7429 gboolean visible;
7430 CtkAllocation allocation;
7431 BaulIcon *icon = NULL((void*)0);
7432
7433 hadj = ctk_scrollable_get_hadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
7434 vadj = ctk_scrollable_get_vadjustment (CTK_SCROLLABLE (container)((((CtkScrollable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_scrollable_get_type ()))))))
);
7435 ctk_widget_get_allocation (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
, &allocation);
7436
7437 min_x = ctk_adjustment_get_value (hadj);
7438 max_x = min_x + allocation.width;
7439
7440 min_y = ctk_adjustment_get_value (vadj);
7441 max_y = min_y + allocation.height;
7442
7443 eel_canvas_c2w (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
7444 min_x, min_y, &min_x, &min_y);
7445 eel_canvas_c2w (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
,
7446 max_x, max_y, &max_x, &max_y);
7447
7448 /* Do the iteration in reverse to get the render-order from top to
7449 * bottom for the prioritized thumbnails.
7450 */
7451 for (node = g_list_last (container->details->icons); node != NULL((void*)0); node = node->prev)
7452 {
7453 icon = node->data;
7454
7455 if (icon_is_positioned (icon))
7456 {
7457 eel_canvas_item_get_bounds (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
7458 &x0,
7459 &y0,
7460 &x1,
7461 &y1);
7462 eel_canvas_item_i2w (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
->parent,
7463 &x0,
7464 &y0);
7465 eel_canvas_item_i2w (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
->parent,
7466 &x1,
7467 &y1);
7468
7469 if (baul_icon_container_is_layout_vertical (container))
7470 {
7471 visible = x1 >= min_x && x0 <= max_x;
7472 }
7473 else
7474 {
7475 visible = y1 >= min_y && y0 <= max_y;
7476 }
7477
7478 if (visible)
7479 {
7480 baul_icon_canvas_item_set_is_visible (icon->item, TRUE(!(0)));
7481 baul_icon_container_prioritize_thumbnailing (container,
7482 icon);
7483 }
7484 else
7485 {
7486 baul_icon_canvas_item_set_is_visible (icon->item, FALSE(0));
7487 }
7488 }
7489 }
7490}
7491
7492static void
7493handle_vadjustment_changed (CtkAdjustment *adjustment G_GNUC_UNUSED__attribute__ ((__unused__)),
7494 BaulIconContainer *container)
7495{
7496 if (!baul_icon_container_is_layout_vertical (container))
7497 {
7498 baul_icon_container_update_visible_icons (container);
7499 }
7500}
7501
7502static void
7503handle_hadjustment_changed (CtkAdjustment *adjustment G_GNUC_UNUSED__attribute__ ((__unused__)),
7504 BaulIconContainer *container)
7505{
7506 if (baul_icon_container_is_layout_vertical (container))
7507 {
7508 baul_icon_container_update_visible_icons (container);
7509 }
7510}
7511
7512
7513void
7514baul_icon_container_update_icon (BaulIconContainer *container,
7515 BaulIcon *icon)
7516{
7517 BaulIconContainerDetails *details;
7518 guint icon_size;
7519 guint min_image_size, max_image_size;
7520 BaulIconInfo *icon_info;
7521 CdkPoint *attach_points;
7522 int n_attach_points;
7523 GdkPixbuf *pixbuf;
7524 GList *emblem_pixbufs;
7525 char *editable_text, *additional_text;
7526 char *embedded_text;
7527 CdkRectangle embedded_text_rect;
7528 gboolean large_embedded_text;
7529 gboolean embedded_text_needs_loading;
7530 gboolean has_open_window;
7531
7532 if (icon == NULL((void*)0))
7533 {
7534 return;
7535 }
7536
7537 details = container->details;
7538
7539 /* compute the maximum size based on the scale factor */
7540 min_image_size = MINIMUM_IMAGE_SIZE24 * EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
->pixels_per_unit;
7541 max_image_size = MAX (MAXIMUM_IMAGE_SIZE * EEL_CANVAS (container)->pixels_per_unit, BAUL_ICON_MAXIMUM_SIZE)(((96 * ((((EelCanvas*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((container)), ((eel_canvas_get_type ())))))
)->pixels_per_unit) > (320)) ? (96 * ((((EelCanvas*) (void
*) g_type_check_instance_cast ((GTypeInstance*) ((container)
), ((eel_canvas_get_type ()))))))->pixels_per_unit) : (320
))
;
7542
7543 /* Get the appropriate images for the file. */
7544 if (container->details->forced_icon_size > 0)
7545 {
7546 icon_size = container->details->forced_icon_size;
7547 }
7548 else
7549 {
7550 icon_get_size (container, icon, &icon_size);
7551 }
7552
7553
7554 icon_size = MAX (icon_size, min_image_size)(((icon_size) > (min_image_size)) ? (icon_size) : (min_image_size
))
;
7555 icon_size = MIN (icon_size, max_image_size)(((icon_size) < (max_image_size)) ? (icon_size) : (max_image_size
))
;
7556
7557 /* Get the icons. */
7558 emblem_pixbufs = NULL((void*)0);
7559 embedded_text = NULL((void*)0);
7560 large_embedded_text = icon_size > ICON_SIZE_FOR_LARGE_EMBEDDED_TEXT55;
7561 icon_info = baul_icon_container_get_icon_images (container, icon->data, icon_size,
7562 &emblem_pixbufs,
7563 &embedded_text,
7564 icon == details->drop_target,
7565 large_embedded_text, &embedded_text_needs_loading,
7566 &has_open_window);
7567
7568
7569 if (container->details->forced_icon_size > 0)
7570 pixbuf = baul_icon_info_get_pixbuf_at_size (icon_info, icon_size);
7571 else
7572 pixbuf = baul_icon_info_get_pixbuf (icon_info);
7573 baul_icon_info_get_attach_points (icon_info, &attach_points, &n_attach_points);
7574
7575 baul_icon_container_get_icon_text (container,
7576 icon->data,
7577 &editable_text,
7578 &additional_text,
7579 FALSE(0));
7580
7581 /* If name of icon being renamed was changed from elsewhere, end renaming mode.
7582 * Alternatively, we could replace the characters in the editable text widget
7583 * with the new name, but that could cause timing problems if the user just
7584 * happened to be typing at that moment.
7585 */
7586 if (icon == get_icon_being_renamed (container) &&
7587 g_strcmp0 (editable_text,
7588 baul_icon_canvas_item_get_editable_text (icon->item)) != 0)
7589 {
7590 end_renaming_mode (container, FALSE(0));
7591 }
7592
7593 eel_canvas_item_set (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
7594 "editable_text", editable_text,
7595 "additional_text", additional_text,
7596 "highlighted_for_drop", icon == details->drop_target,
7597 NULL((void*)0));
7598
7599 baul_icon_canvas_item_set_image (icon->item, pixbuf);
7600 baul_icon_canvas_item_set_attach_points (icon->item, attach_points, n_attach_points);
7601 baul_icon_canvas_item_set_emblems (icon->item, emblem_pixbufs);
7602 baul_icon_canvas_item_set_embedded_text_rect (icon->item, &embedded_text_rect);
7603 baul_icon_canvas_item_set_embedded_text (icon->item, embedded_text);
7604
7605 /* Let the pixbufs go. */
7606 g_object_unref (pixbuf);
7607 g_list_free_full (emblem_pixbufs, g_object_unref);
7608
7609 g_free (editable_text);
7610 g_free (additional_text);
7611
7612 g_object_unref (icon_info);
7613}
7614
7615static gboolean
7616assign_icon_position (BaulIconContainer *container,
7617 BaulIcon *icon)
7618{
7619 gboolean have_stored_position;
7620 BaulIconPosition position;
7621
7622 /* Get the stored position. */
7623 have_stored_position = FALSE(0);
7624 position.scale = 1.0;
7625 g_signal_emit (container,
7626 signals[GET_STORED_ICON_POSITION], 0,
7627 icon->data,
7628 &position,
7629 &have_stored_position);
7630 icon->scale = position.scale;
7631 if (!container->details->auto_layout)
7632 {
7633 if (have_stored_position)
7634 {
7635 icon_set_position (icon, position.x, position.y);
7636 icon->saved_ltr_x = icon->x;
7637 }
7638 else
7639 {
7640 return FALSE(0);
7641 }
7642 }
7643 return TRUE(!(0));
7644}
7645
7646static void
7647finish_adding_icon (BaulIconContainer *container,
7648 BaulIcon *icon)
7649{
7650 baul_icon_container_update_icon (container, icon);
7651 eel_canvas_item_show (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
);
7652
7653 g_signal_connect_object (icon->item, "event",
7654 G_CALLBACK (item_event_callback)((GCallback) (item_event_callback)), container, 0);
7655
7656 g_signal_emit (container, signals[ICON_ADDED], 0, icon->data);
7657}
7658
7659static void
7660finish_adding_new_icons (BaulIconContainer *container)
7661{
7662 GList *p, *new_icons, *no_position_icons, *semi_position_icons;
7663 BaulIcon *icon;
7664 double bottom;
7665
7666 new_icons = container->details->new_icons;
7667 container->details->new_icons = NULL((void*)0);
7668 container->details->is_populating_container =
7669 g_list_length(new_icons) == g_hash_table_size(container->details->icon_set);
7670
7671 /* Position most icons (not unpositioned manual-layout icons). */
7672 new_icons = g_list_reverse (new_icons);
7673 no_position_icons = semi_position_icons = NULL((void*)0);
7674 for (p = new_icons; p != NULL((void*)0); p = p->next)
7675 {
7676 icon = p->data;
7677 if (icon->has_lazy_position)
7678 {
7679 assign_icon_position (container, icon);
7680 semi_position_icons = g_list_prepend (semi_position_icons, icon);
7681 }
7682 else if (!assign_icon_position (container, icon))
7683 {
7684 no_position_icons = g_list_prepend (no_position_icons, icon);
7685 }
7686
7687 finish_adding_icon (container, icon);
7688 }
7689 g_list_free (new_icons);
7690
7691 if (semi_position_icons != NULL((void*)0))
7692 {
7693 PlacementGrid *grid;
7694 time_t now;
7695 gboolean dummy;
7696
7697 g_assert (!container->details->auto_layout)do { if (!container->details->auto_layout) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7697, ((const char*)
(__func__)), "!container->details->auto_layout"); } while
(0)
;
7698
7699 semi_position_icons = g_list_reverse (semi_position_icons);
7700
7701 /* This is currently only used on the desktop.
7702 * Thus, we pass FALSE for tight, like lay_down_icons_tblr */
7703 grid = placement_grid_new (container, FALSE(0));
7704
7705 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
7706 {
7707 icon = p->data;
7708
7709 if (icon_is_positioned (icon) && !icon->has_lazy_position)
7710 {
7711 placement_grid_mark_icon (grid, icon);
7712 }
7713 }
7714
7715 now = time (NULL((void*)0));
7716
7717 for (p = semi_position_icons; p != NULL((void*)0); p = p->next)
7718 {
7719 BaulIcon *icon;
7720 BaulIconPosition position;
7721 int x, y;
7722
7723 icon = p->data;
7724 x = icon->x;
7725 y = icon->y;
7726
7727 find_empty_location (container, grid,
7728 icon, x, y, &x, &y);
7729
7730 icon_set_position (icon, x, y);
7731
7732 position.x = icon->x;
7733 position.y = icon->y;
7734 position.scale = icon->scale;
7735 placement_grid_mark_icon (grid, icon);
7736 g_signal_emit (container, signals[ICON_POSITION_CHANGED], 0,
7737 icon->data, &position);
7738 g_signal_emit (container, signals[STORE_LAYOUT_TIMESTAMP], 0,
7739 icon->data, &now, &dummy);
7740
7741 /* ensure that next time we run this code, the formerly semi-positioned
7742 * icons are treated as being positioned. */
7743 icon->has_lazy_position = FALSE(0);
7744 }
7745
7746 placement_grid_free (grid);
7747
7748 g_list_free (semi_position_icons);
7749 }
7750
7751 /* Position the unpositioned manual layout icons. */
7752 if (no_position_icons != NULL((void*)0))
7753 {
7754 g_assert (!container->details->auto_layout)do { if (!container->details->auto_layout) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 7754, ((const char*)
(__func__)), "!container->details->auto_layout"); } while
(0)
;
7755
7756 sort_icons (container, &no_position_icons);
7757 if (baul_icon_container_get_is_desktop (container))
7758 {
7759 lay_down_icons (container, no_position_icons, CONTAINER_PAD_TOP4);
7760 }
7761 else
7762 {
7763 get_all_icon_bounds (container, NULL((void*)0), NULL((void*)0), NULL((void*)0), &bottom, BOUNDS_USAGE_FOR_LAYOUT);
7764 lay_down_icons (container, no_position_icons, bottom + ICON_PAD_BOTTOM4);
7765 }
7766 g_list_free (no_position_icons);
7767 }
7768
7769 if (container->details->store_layout_timestamps_when_finishing_new_icons)
7770 {
7771 store_layout_timestamps_now (container);
7772 container->details->store_layout_timestamps_when_finishing_new_icons = FALSE(0);
7773 }
7774}
7775
7776static gboolean
7777is_old_or_unknown_icon_data (BaulIconContainer *container,
7778 BaulIconData *data)
7779{
7780 time_t timestamp;
7781 gboolean success;
7782
7783 if (container->details->layout_timestamp == UNDEFINED_TIME((time_t) (-1)))
7784 {
7785 /* don't know */
7786 return FALSE(0);
7787 }
7788
7789 g_signal_emit (container,
7790 signals[GET_STORED_LAYOUT_TIMESTAMP], 0,
7791 data, &timestamp, &success);
7792 return (!success || timestamp < container->details->layout_timestamp);
7793}
7794
7795/**
7796 * baul_icon_container_add:
7797 * @container: A BaulIconContainer
7798 * @data: Icon data.
7799 *
7800 * Add icon to represent @data to container.
7801 * Returns FALSE if there was already such an icon.
7802 **/
7803gboolean
7804baul_icon_container_add (BaulIconContainer *container,
7805 BaulIconData *data)
7806{
7807 BaulIconContainerDetails *details;
7808 BaulIcon *icon;
7809 EelCanvasItem *band, *item;
7810
7811 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
7812 g_return_val_if_fail (data != NULL, FALSE)do { if ((data != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "data != NULL"); return
((0)); } } while (0)
;
7813
7814 details = container->details;
7815
7816 if (g_hash_table_lookup (details->icon_set, data) != NULL((void*)0))
7817 {
7818 return FALSE(0);
7819 }
7820
7821 /* Create the new icon, including the canvas item. */
7822 icon = g_new0 (BaulIcon, 1)((BaulIcon *) g_malloc0_n ((1), sizeof (BaulIcon)));
7823 icon->data = data;
7824 icon->x = ICON_UNPOSITIONED_VALUE-1;
7825 icon->y = ICON_UNPOSITIONED_VALUE-1;
7826
7827 /* Whether the saved icon position should only be used
7828 * if the previous icon position is free. If the position
7829 * is occupied, another position near the last one will
7830 */
7831 icon->has_lazy_position = is_old_or_unknown_icon_data (container, data);
7832 icon->scale = 1.0;
7833 icon->item = BAUL_ICON_CANVAS_ITEM((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((eel_canvas_item_new (((((EelCanvasGroup*) (
void *) g_type_check_instance_cast ((GTypeInstance*) ((((((EelCanvas
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((container
)), ((eel_canvas_get_type ()))))))->root)), ((eel_canvas_group_get_type
())))))), baul_icon_canvas_item_get_type (), "visible", (0),
((void*)0)))), (baul_icon_canvas_item_get_type())))))
7834 (eel_canvas_item_new (EEL_CANVAS_GROUP (EEL_CANVAS (container)->root),((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((eel_canvas_item_new (((((EelCanvasGroup*) (
void *) g_type_check_instance_cast ((GTypeInstance*) ((((((EelCanvas
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((container
)), ((eel_canvas_get_type ()))))))->root)), ((eel_canvas_group_get_type
())))))), baul_icon_canvas_item_get_type (), "visible", (0),
((void*)0)))), (baul_icon_canvas_item_get_type())))))
7835 baul_icon_canvas_item_get_type (),((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((eel_canvas_item_new (((((EelCanvasGroup*) (
void *) g_type_check_instance_cast ((GTypeInstance*) ((((((EelCanvas
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((container
)), ((eel_canvas_get_type ()))))))->root)), ((eel_canvas_group_get_type
())))))), baul_icon_canvas_item_get_type (), "visible", (0),
((void*)0)))), (baul_icon_canvas_item_get_type())))))
7836 "visible", FALSE,((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((eel_canvas_item_new (((((EelCanvasGroup*) (
void *) g_type_check_instance_cast ((GTypeInstance*) ((((((EelCanvas
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((container
)), ((eel_canvas_get_type ()))))))->root)), ((eel_canvas_group_get_type
())))))), baul_icon_canvas_item_get_type (), "visible", (0),
((void*)0)))), (baul_icon_canvas_item_get_type())))))
7837 NULL))((((BaulIconCanvasItem*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((eel_canvas_item_new (((((EelCanvasGroup*) (
void *) g_type_check_instance_cast ((GTypeInstance*) ((((((EelCanvas
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((container
)), ((eel_canvas_get_type ()))))))->root)), ((eel_canvas_group_get_type
())))))), baul_icon_canvas_item_get_type (), "visible", (0),
((void*)0)))), (baul_icon_canvas_item_get_type())))))
;
7838 icon->item->user_data = icon;
7839
7840 /* Make sure the icon is under the selection_rectangle */
7841 item = EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
;
7842 band = BAUL_ICON_CONTAINER (item->canvas)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((item->canvas)), (baul_icon_container_get_type
())))))
->details->rubberband_info.selection_rectangle;
7843 if (band)
7844 {
7845 eel_canvas_item_send_behind (item, band);
7846 }
7847
7848 /* Put it on both lists. */
7849 details->icons = g_list_prepend (details->icons, icon);
7850 details->new_icons = g_list_prepend (details->new_icons, icon);
7851
7852 g_hash_table_insert (details->icon_set, data, icon);
7853
7854 /* Run an idle function to add the icons. */
7855 schedule_redo_layout (container);
7856
7857 return TRUE(!(0));
7858}
7859
7860void
7861baul_icon_container_layout_now (BaulIconContainer *container)
7862{
7863 if (container->details->idle_id != 0)
7864 {
7865 unschedule_redo_layout (container);
7866 redo_layout_internal (container);
7867 }
7868
7869 /* Also need to make sure we're properly resized, for instance
7870 * newly added files may trigger a change in the size allocation and
7871 * thus toggle scrollbars on */
7872 ctk_container_check_resize (CTK_CONTAINER (ctk_widget_get_parent (CTK_WIDGET (container)))((((CtkContainer*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((ctk_widget_get_parent (((((CtkWidget*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), ((ctk_widget_get_type ())))
)))))), ((ctk_container_get_type ()))))))
);
7873}
7874
7875/**
7876 * baul_icon_container_remove:
7877 * @container: A BaulIconContainer.
7878 * @data: Icon data.
7879 *
7880 * Remove the icon with this data.
7881 **/
7882gboolean
7883baul_icon_container_remove (BaulIconContainer *container,
7884 BaulIconData *data)
7885{
7886 BaulIcon *icon;
7887
7888 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
7889 g_return_val_if_fail (data != NULL, FALSE)do { if ((data != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "data != NULL"); return
((0)); } } while (0)
;
7890
7891 end_renaming_mode (container, FALSE(0));
7892
7893 icon = g_hash_table_lookup (container->details->icon_set, data);
7894
7895 if (icon == NULL((void*)0))
7896 {
7897 return FALSE(0);
7898 }
7899
7900 g_signal_emit (container, signals[ICON_REMOVED], 0, icon);
7901
7902 icon_destroy (container, icon);
7903 schedule_redo_layout (container);
7904
7905 return TRUE(!(0));
7906}
7907
7908/**
7909 * baul_icon_container_request_update:
7910 * @container: A BaulIconContainer.
7911 * @data: Icon data.
7912 *
7913 * Update the icon with this data.
7914 **/
7915void
7916baul_icon_container_request_update (BaulIconContainer *container,
7917 BaulIconData *data)
7918{
7919 BaulIcon *icon;
7920
7921 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
7922 g_return_if_fail (data != NULL)do { if ((data != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "data != NULL"); return
; } } while (0)
;
7923
7924 icon = g_hash_table_lookup (container->details->icon_set, data);
7925
7926 if (icon != NULL((void*)0))
7927 {
7928 baul_icon_container_update_icon (container, icon);
7929 schedule_redo_layout (container);
7930 }
7931}
7932
7933/* zooming */
7934
7935BaulZoomLevel
7936baul_icon_container_get_zoom_level (BaulIconContainer *container)
7937{
7938 return container->details->zoom_level;
7939}
7940
7941void
7942baul_icon_container_set_zoom_level (BaulIconContainer *container, int new_level)
7943{
7944 BaulIconContainerDetails *details;
7945 int pinned_level;
7946 double pixels_per_unit;
7947
7948 details = container->details;
7949
7950 end_renaming_mode (container, TRUE(!(0)));
7951
7952 pinned_level = new_level;
7953 if (pinned_level < BAUL_ZOOM_LEVEL_SMALLEST)
7954 {
7955 pinned_level = BAUL_ZOOM_LEVEL_SMALLEST;
7956 }
7957 else if (pinned_level > BAUL_ZOOM_LEVEL_LARGEST)
7958 {
7959 pinned_level = BAUL_ZOOM_LEVEL_LARGEST;
7960 }
7961
7962 if (pinned_level == details->zoom_level)
7963 {
7964 return;
7965 }
7966
7967 details->zoom_level = pinned_level;
7968
7969 pixels_per_unit = (double) baul_get_icon_size_for_zoom_level (pinned_level)
7970 / BAUL_ICON_SIZE_STANDARD48;
7971 eel_canvas_set_pixels_per_unit (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
, pixels_per_unit);
7972
7973 invalidate_labels (container);
7974 baul_icon_container_request_update_all (container);
7975}
7976
7977/**
7978 * baul_icon_container_request_update_all:
7979 * For each icon, synchronizes the displayed information (image, text) with the
7980 * information from the model.
7981 *
7982 * @container: An icon container.
7983 **/
7984void
7985baul_icon_container_request_update_all (BaulIconContainer *container)
7986{
7987 GList *node;
7988 BaulIcon *icon = NULL((void*)0);
7989
7990 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
7991
7992 container->details->is_loading = TRUE(!(0));
7993 for (node = container->details->icons; node != NULL((void*)0); node = node->next)
7994 {
7995 icon = node->data;
7996 baul_icon_container_update_icon (container, icon);
7997 }
7998
7999 redo_layout (container);
8000 container->details->is_loading = FALSE(0);
8001}
8002
8003/**
8004 * baul_icon_container_reveal:
8005 * Change scroll position as necessary to reveal the specified item.
8006 */
8007void
8008baul_icon_container_reveal (BaulIconContainer *container, BaulIconData *data)
8009{
8010 BaulIcon *icon;
8011
8012 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8013 g_return_if_fail (data != NULL)do { if ((data != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "data != NULL"); return
; } } while (0)
;
8014
8015 icon = g_hash_table_lookup (container->details->icon_set, data);
8016
8017 if (icon != NULL((void*)0))
8018 {
8019 reveal_icon (container, icon);
8020 }
8021}
8022
8023/**
8024 * baul_icon_container_get_selection:
8025 * @container: An icon container.
8026 *
8027 * Get a list of the icons currently selected in @container.
8028 *
8029 * Return value: A GList of the programmer-specified data associated to each
8030 * selected icon, or NULL if no icon is selected. The caller is expected to
8031 * free the list when it is not needed anymore.
8032 **/
8033GList *
8034baul_icon_container_get_selection (BaulIconContainer *container)
8035{
8036 GList *list, *p;
8037
8038 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), NULL)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return (((void*)0)); } } while (0)
;
8039
8040 list = NULL((void*)0);
8041 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8042 {
8043 BaulIcon *icon;
8044
8045 icon = p->data;
8046 if (icon->is_selected)
8047 {
8048 list = g_list_prepend (list, icon->data);
8049 }
8050 }
8051
8052 return g_list_reverse (list);
8053}
8054
8055static GList *
8056baul_icon_container_get_selected_icons (BaulIconContainer *container)
8057{
8058 GList *list, *p;
8059
8060 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), NULL)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return (((void*)0)); } } while (0)
;
8061
8062 list = NULL((void*)0);
8063 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8064 {
8065 BaulIcon *icon;
8066
8067 icon = p->data;
8068 if (icon->is_selected)
8069 {
8070 list = g_list_prepend (list, icon);
8071 }
8072 }
8073
8074 return g_list_reverse (list);
8075}
8076
8077/**
8078 * baul_icon_container_invert_selection:
8079 * @container: An icon container.
8080 *
8081 * Inverts the selection in @container.
8082 *
8083 **/
8084void
8085baul_icon_container_invert_selection (BaulIconContainer *container)
8086{
8087 GList *p;
8088
8089 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8090
8091 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8092 {
8093 BaulIcon *icon;
8094
8095 icon = p->data;
8096 icon_toggle_selected (container, icon);
8097 }
8098
8099 g_signal_emit (container, signals[SELECTION_CHANGED], 0);
8100}
8101
8102
8103/* Returns an array of CdkPoints of locations of the icons. */
8104static GArray *
8105baul_icon_container_get_icon_locations (BaulIconContainer *container G_GNUC_UNUSED__attribute__ ((__unused__)),
8106 GList *icons)
8107{
8108 GArray *result;
8109 GList *node;
8110 int index;
8111
8112 result = g_array_new (FALSE(0), TRUE(!(0)), sizeof (CdkPoint));
8113 result = g_array_set_size (result, g_list_length (icons));
8114
8115 for (index = 0, node = icons; node != NULL((void*)0); index++, node = node->next)
8116 {
8117 g_array_index (result, CdkPoint, index)(((CdkPoint*) (void *) (result)->data) [(index)]).x =
8118 ((BaulIcon *)node->data)->x;
8119 g_array_index (result, CdkPoint, index)(((CdkPoint*) (void *) (result)->data) [(index)]).y =
8120 ((BaulIcon *)node->data)->y;
8121 }
8122
8123 return result;
8124}
8125
8126/**
8127 * baul_icon_container_get_selected_icon_locations:
8128 * @container: An icon container widget.
8129 *
8130 * Returns an array of CdkPoints of locations of the selected icons.
8131 **/
8132GArray *
8133baul_icon_container_get_selected_icon_locations (BaulIconContainer *container)
8134{
8135 GArray *result;
8136 GList *icons;
8137
8138 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), NULL)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return (((void*)0)); } } while (0)
;
8139
8140 icons = baul_icon_container_get_selected_icons (container);
8141 result = baul_icon_container_get_icon_locations (container, icons);
8142 g_list_free (icons);
8143
8144 return result;
8145}
8146
8147/**
8148 * baul_icon_container_select_all:
8149 * @container: An icon container widget.
8150 *
8151 * Select all the icons in @container at once.
8152 **/
8153void
8154baul_icon_container_select_all (BaulIconContainer *container)
8155{
8156 gboolean selection_changed;
8157 GList *p;
8158 BaulIcon *icon = NULL((void*)0);
8159
8160 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8161
8162 selection_changed = FALSE(0);
8163
8164 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8165 {
8166 icon = p->data;
8167
8168 selection_changed |= icon_set_selected (container, icon, TRUE(!(0)));
8169 }
8170
8171 if (selection_changed)
8172 {
8173 g_signal_emit (container,
8174 signals[SELECTION_CHANGED], 0);
8175 }
8176}
8177
8178/**
8179 * baul_icon_container_set_selection:
8180 * @container: An icon container widget.
8181 * @selection: A list of BaulIconData *.
8182 *
8183 * Set the selection to exactly the icons in @container which have
8184 * programmer data matching one of the items in @selection.
8185 **/
8186void
8187baul_icon_container_set_selection (BaulIconContainer *container,
8188 GList *selection)
8189{
8190 gboolean selection_changed;
8191 GHashTable *hash;
8192 GList *p;
8193 BaulIcon *icon = NULL((void*)0);
8194
8195 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8196
8197 selection_changed = FALSE(0);
8198
8199 hash = g_hash_table_new (NULL((void*)0), NULL((void*)0));
8200 for (p = selection; p != NULL((void*)0); p = p->next)
8201 {
8202 g_hash_table_insert (hash, p->data, p->data);
8203 }
8204 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8205 {
8206 icon = p->data;
8207
8208 selection_changed |= icon_set_selected
8209 (container, icon,
8210 g_hash_table_lookup (hash, icon->data) != NULL((void*)0));
8211 }
8212 g_hash_table_destroy (hash);
8213
8214 if (selection_changed)
8215 {
8216 g_signal_emit (container,
8217 signals[SELECTION_CHANGED], 0);
8218 }
8219}
8220
8221/**
8222 * baul_icon_container_select_list_unselect_others.
8223 * @container: An icon container widget.
8224 * @selection: A list of BaulIcon *.
8225 *
8226 * Set the selection to exactly the icons in @selection.
8227 **/
8228void
8229baul_icon_container_select_list_unselect_others (BaulIconContainer *container,
8230 GList *selection)
8231{
8232 gboolean selection_changed;
8233 GHashTable *hash;
8234 GList *p;
8235 BaulIcon *icon = NULL((void*)0);
8236
8237 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8238
8239 selection_changed = FALSE(0);
8240
8241 hash = g_hash_table_new (NULL((void*)0), NULL((void*)0));
8242 for (p = selection; p != NULL((void*)0); p = p->next)
8243 {
8244 g_hash_table_insert (hash, p->data, p->data);
8245 }
8246 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8247 {
8248 icon = p->data;
8249
8250 selection_changed |= icon_set_selected
8251 (container, icon,
8252 g_hash_table_lookup (hash, icon) != NULL((void*)0));
8253 }
8254 g_hash_table_destroy (hash);
8255
8256 if (selection_changed)
8257 {
8258 g_signal_emit (container,
8259 signals[SELECTION_CHANGED], 0);
8260 }
8261}
8262
8263/**
8264 * baul_icon_container_unselect_all:
8265 * @container: An icon container widget.
8266 *
8267 * Deselect all the icons in @container.
8268 **/
8269void
8270baul_icon_container_unselect_all (BaulIconContainer *container)
8271{
8272 if (unselect_all (container))
8273 {
8274 g_signal_emit (container,
8275 signals[SELECTION_CHANGED], 0);
8276 }
8277}
8278
8279/**
8280 * baul_icon_container_get_icon_by_uri:
8281 * @container: An icon container widget.
8282 * @uri: The uri of an icon to find.
8283 *
8284 * Locate an icon, given the URI. The URI must match exactly.
8285 * Later we may have to have some way of figuring out if the
8286 * URI specifies the same object that does not require an exact match.
8287 **/
8288BaulIcon *
8289baul_icon_container_get_icon_by_uri (BaulIconContainer *container,
8290 const char *uri)
8291{
8292 BaulIconContainerDetails *details;
8293 GList *p;
8294
8295 /* Eventually, we must avoid searching the entire icon list,
8296 but it's OK for now.
8297 A hash table mapping uri to icon is one possibility.
8298 */
8299
8300 details = container->details;
8301
8302 for (p = details->icons; p != NULL((void*)0); p = p->next)
8303 {
8304 BaulIcon *icon;
8305 char *icon_uri;
8306 gboolean is_match;
8307
8308 icon = p->data;
8309
8310 icon_uri = baul_icon_container_get_icon_uri
8311 (container, icon);
8312 is_match = strcmp (uri, icon_uri) == 0;
8313 g_free (icon_uri);
8314
8315 if (is_match)
8316 {
8317 return icon;
8318 }
8319 }
8320
8321 return NULL((void*)0);
8322}
8323
8324static BaulIcon *
8325get_nth_selected_icon (BaulIconContainer *container, int index)
8326{
8327 GList *p;
8328 int selection_count;
8329 BaulIcon *icon = NULL((void*)0);
8330
8331 g_assert (index > 0)do { if (index > 0) ; else g_assertion_message_expr (((gchar
*) 0), "baul-icon-container.c", 8331, ((const char*) (__func__
)), "index > 0"); } while (0)
;
8332
8333 /* Find the nth selected icon. */
8334 selection_count = 0;
8335 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8336 {
8337 icon = p->data;
8338 if (icon->is_selected)
8339 {
8340 if (++selection_count == index)
8341 {
8342 return icon;
8343 }
8344 }
8345 }
8346 return NULL((void*)0);
8347}
8348
8349static BaulIcon *
8350get_first_selected_icon (BaulIconContainer *container)
8351{
8352 return get_nth_selected_icon (container, 1);
8353}
8354
8355static gboolean
8356has_multiple_selection (BaulIconContainer *container)
8357{
8358 return get_nth_selected_icon (container, 2) != NULL((void*)0);
8359}
8360
8361static gboolean
8362all_selected (BaulIconContainer *container)
8363{
8364 GList *p;
8365 BaulIcon *icon = NULL((void*)0);
8366
8367 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8368 {
8369 icon = p->data;
8370 if (!icon->is_selected)
8371 {
8372 return FALSE(0);
8373 }
8374 }
8375 return TRUE(!(0));
8376}
8377
8378static gboolean
8379has_selection (BaulIconContainer *container)
8380{
8381 return get_nth_selected_icon (container, 1) != NULL((void*)0);
8382}
8383
8384/**
8385 * baul_icon_container_show_stretch_handles:
8386 * @container: An icon container widget.
8387 *
8388 * Makes stretch handles visible on the first selected icon.
8389 **/
8390void
8391baul_icon_container_show_stretch_handles (BaulIconContainer *container)
8392{
8393 BaulIconContainerDetails *details;
8394 BaulIcon *icon;
8395 guint initial_size;
8396
8397 icon = get_first_selected_icon (container);
8398 if (icon == NULL((void*)0))
8399 {
8400 return;
8401 }
8402
8403 /* Check if it already has stretch handles. */
8404 details = container->details;
8405 if (details->stretch_icon == icon)
8406 {
8407 return;
8408 }
8409
8410 /* Get rid of the existing stretch handles and put them on the new icon. */
8411 if (details->stretch_icon != NULL((void*)0))
8412 {
8413 baul_icon_canvas_item_set_show_stretch_handles
8414 (details->stretch_icon->item, FALSE(0));
8415 ungrab_stretch_icon (container);
8416 emit_stretch_ended (container, details->stretch_icon);
8417 }
8418 baul_icon_canvas_item_set_show_stretch_handles (icon->item, TRUE(!(0)));
8419 details->stretch_icon = icon;
8420
8421 icon_get_size (container, icon, &initial_size);
8422
8423 /* only need to keep size in one dimension, since they are constrained to be the same */
8424 container->details->stretch_initial_x = icon->x;
8425 container->details->stretch_initial_y = icon->y;
8426 container->details->stretch_initial_size = initial_size;
8427
8428 emit_stretch_started (container, icon);
8429}
8430
8431/**
8432 * baul_icon_container_has_stretch_handles
8433 * @container: An icon container widget.
8434 *
8435 * Returns true if the first selected item has stretch handles.
8436 **/
8437gboolean
8438baul_icon_container_has_stretch_handles (BaulIconContainer *container)
8439{
8440 BaulIcon *icon;
8441
8442 icon = get_first_selected_icon (container);
8443 if (icon == NULL((void*)0))
8444 {
8445 return FALSE(0);
8446 }
8447
8448 return icon == container->details->stretch_icon;
8449}
8450
8451/**
8452 * baul_icon_container_is_stretched
8453 * @container: An icon container widget.
8454 *
8455 * Returns true if the any selected item is stretched to a size other than 1.0.
8456 **/
8457gboolean
8458baul_icon_container_is_stretched (BaulIconContainer *container)
8459{
8460 GList *p;
8461 BaulIcon *icon = NULL((void*)0);
8462
8463 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8464 {
8465 icon = p->data;
8466 if (icon->is_selected && icon->scale != 1.0)
8467 {
8468 return TRUE(!(0));
8469 }
8470 }
8471 return FALSE(0);
8472}
8473
8474/**
8475 * baul_icon_container_unstretch
8476 * @container: An icon container widget.
8477 *
8478 * Gets rid of any icon stretching.
8479 **/
8480void
8481baul_icon_container_unstretch (BaulIconContainer *container)
8482{
8483 GList *p;
8484 BaulIcon *icon = NULL((void*)0);
8485
8486 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8487 {
8488 icon = p->data;
8489 if (icon->is_selected)
8490 {
8491 baul_icon_container_move_icon (container, icon,
8492 icon->x, icon->y,
8493 1.0,
8494 FALSE(0), TRUE(!(0)), TRUE(!(0)));
8495 }
8496 }
8497}
8498
8499static void
8500compute_stretch (StretchState *start,
8501 StretchState *current)
8502{
8503 gboolean right, bottom;
8504 int x_stretch, y_stretch;
8505
8506 /* FIXME bugzilla.gnome.org 45390: This doesn't correspond to
8507 * the way the handles are drawn.
8508 */
8509 /* Figure out which handle we are dragging. */
8510 right = start->pointer_x > start->icon_x + (int) start->icon_size / 2;
8511 bottom = start->pointer_y > start->icon_y + (int) start->icon_size / 2;
8512
8513 /* Figure out how big we should stretch. */
8514 x_stretch = start->pointer_x - current->pointer_x;
8515 y_stretch = start->pointer_y - current->pointer_y;
8516 if (right)
8517 {
8518 x_stretch = - x_stretch;
8519 }
8520 if (bottom)
8521 {
8522 y_stretch = - y_stretch;
8523 }
8524 current->icon_size = MAX ((int) start->icon_size + MIN (x_stretch, y_stretch),((((int) start->icon_size + (((x_stretch) < (y_stretch)
) ? (x_stretch) : (y_stretch))) > ((int) 16)) ? ((int) start
->icon_size + (((x_stretch) < (y_stretch)) ? (x_stretch
) : (y_stretch))) : ((int) 16))
8525 (int) BAUL_ICON_SIZE_SMALLEST)((((int) start->icon_size + (((x_stretch) < (y_stretch)
) ? (x_stretch) : (y_stretch))) > ((int) 16)) ? ((int) start
->icon_size + (((x_stretch) < (y_stretch)) ? (x_stretch
) : (y_stretch))) : ((int) 16))
;
8526
8527 /* Figure out where the corner of the icon should be. */
8528 current->icon_x = start->icon_x;
8529 if (!right)
8530 {
8531 current->icon_x += start->icon_size - current->icon_size;
8532 }
8533 current->icon_y = start->icon_y;
8534 if (!bottom)
8535 {
8536 current->icon_y += start->icon_size - current->icon_size;
8537 }
8538}
8539
8540char *
8541baul_icon_container_get_icon_uri (BaulIconContainer *container,
8542 BaulIcon *icon)
8543{
8544 char *uri;
8545
8546 uri = NULL((void*)0);
8547 g_signal_emit (container,
8548 signals[GET_ICON_URI], 0,
8549 icon->data,
8550 &uri);
8551 return uri;
8552}
8553
8554char *
8555baul_icon_container_get_icon_drop_target_uri (BaulIconContainer *container,
8556 BaulIcon *icon)
8557{
8558 char *uri;
8559
8560 uri = NULL((void*)0);
8561 g_signal_emit (container,
8562 signals[GET_ICON_DROP_TARGET_URI], 0,
8563 icon->data,
8564 &uri);
8565 return uri;
8566}
8567
8568/* Call to reset the scroll region only if the container is not empty,
8569 * to avoid having the flag linger until the next file is added.
8570 */
8571static void
8572reset_scroll_region_if_not_empty (BaulIconContainer *container)
8573{
8574 if (!baul_icon_container_is_empty (container))
8575 {
8576 baul_icon_container_reset_scroll_region (container);
8577 }
8578}
8579
8580/* Switch from automatic layout to manual or vice versa.
8581 * If we switch to manual layout, we restore the icon positions from the
8582 * last manual layout.
8583 */
8584void
8585baul_icon_container_set_auto_layout (BaulIconContainer *container,
8586 gboolean auto_layout)
8587{
8588 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8589 g_return_if_fail (auto_layout == FALSE || auto_layout == TRUE)do { if ((auto_layout == (0) || auto_layout == (!(0)))) { } else
{ g_return_if_fail_warning (((gchar*) 0), ((const char*) (__func__
)), "auto_layout == FALSE || auto_layout == TRUE"); return; }
} while (0)
;
8590
8591 if (container->details->auto_layout == auto_layout)
8592 {
8593 return;
8594 }
8595
8596 reset_scroll_region_if_not_empty (container);
8597 container->details->auto_layout = auto_layout;
8598
8599 if (!auto_layout)
8600 {
8601 reload_icon_positions (container);
8602 baul_icon_container_freeze_icon_positions (container);
8603 }
8604
8605 redo_layout (container);
8606
8607 g_signal_emit (container, signals[LAYOUT_CHANGED], 0);
8608}
8609
8610
8611/* Toggle the tighter layout boolean. */
8612void
8613baul_icon_container_set_tighter_layout (BaulIconContainer *container,
8614 gboolean tighter_layout)
8615{
8616 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8617 g_return_if_fail (tighter_layout == FALSE || tighter_layout == TRUE)do { if ((tighter_layout == (0) || tighter_layout == (!(0))))
{ } else { g_return_if_fail_warning (((gchar*) 0), ((const char
*) (__func__)), "tighter_layout == FALSE || tighter_layout == TRUE"
); return; } } while (0)
;
8618
8619 if (container->details->tighter_layout == tighter_layout)
8620 {
8621 return;
8622 }
8623
8624 container->details->tighter_layout = tighter_layout;
8625
8626 if (container->details->auto_layout)
8627 {
8628 invalidate_label_sizes (container);
8629 redo_layout (container);
8630
8631 g_signal_emit (container, signals[LAYOUT_CHANGED], 0);
8632 }
8633 else
8634 {
8635 /* in manual layout, label sizes still change, even though
8636 * the icons don't move.
8637 */
8638 invalidate_label_sizes (container);
8639 baul_icon_container_request_update_all (container);
8640 }
8641}
8642
8643gboolean
8644baul_icon_container_is_keep_aligned (BaulIconContainer *container)
8645{
8646 return container->details->keep_aligned;
8647}
8648
8649static gboolean
8650align_icons_callback (gpointer callback_data)
8651{
8652 BaulIconContainer *container;
8653
8654 container = BAUL_ICON_CONTAINER (callback_data)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((callback_data)), (baul_icon_container_get_type
())))))
;
8655 align_icons (container);
8656 container->details->align_idle_id = 0;
8657
8658 return FALSE(0);
8659}
8660
8661static void
8662unschedule_align_icons (BaulIconContainer *container)
8663{
8664 if (container->details->align_idle_id != 0)
8665 {
8666 g_source_remove (container->details->align_idle_id);
8667 container->details->align_idle_id = 0;
8668 }
8669}
8670
8671static void
8672schedule_align_icons (BaulIconContainer *container)
8673{
8674 if (container->details->align_idle_id == 0
8675 && container->details->has_been_allocated)
8676 {
8677 container->details->align_idle_id = g_idle_add
8678 (align_icons_callback, container);
8679 }
8680}
8681
8682void
8683baul_icon_container_set_keep_aligned (BaulIconContainer *container,
8684 gboolean keep_aligned)
8685{
8686 if (container->details->keep_aligned != keep_aligned)
8687 {
8688 container->details->keep_aligned = keep_aligned;
8689
8690 if (keep_aligned && !container->details->auto_layout)
8691 {
8692 schedule_align_icons (container);
8693 }
8694 else
8695 {
8696 unschedule_align_icons (container);
8697 }
8698 }
8699}
8700
8701void
8702baul_icon_container_set_layout_mode (BaulIconContainer *container,
8703 BaulIconLayoutMode mode)
8704{
8705 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8706
8707 container->details->layout_mode = mode;
8708 invalidate_labels (container);
8709
8710 redo_layout (container);
8711
8712 g_signal_emit (container, signals[LAYOUT_CHANGED], 0);
8713}
8714
8715void
8716baul_icon_container_set_label_position (BaulIconContainer *container,
8717 BaulIconLabelPosition position)
8718{
8719 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
8720
8721 if (container->details->label_position != position)
8722 {
8723 container->details->label_position = position;
8724
8725 invalidate_labels (container);
8726 baul_icon_container_request_update_all (container);
8727
8728 schedule_redo_layout (container);
8729 }
8730}
8731
8732/* Switch from automatic to manual layout, freezing all the icons in their
8733 * current positions instead of restoring icon positions from the last manual
8734 * layout as set_auto_layout does.
8735 */
8736void
8737baul_icon_container_freeze_icon_positions (BaulIconContainer *container)
8738{
8739 gboolean changed;
8740 GList *p;
8741 BaulIcon *icon;
8742 BaulIconPosition position;
8743
8744 changed = container->details->auto_layout;
8745 container->details->auto_layout = FALSE(0);
8746
8747 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
8748 {
8749 icon = p->data;
8750
8751 position.x = icon->saved_ltr_x;
8752 position.y = icon->y;
8753 position.scale = icon->scale;
8754 g_signal_emit (container, signals[ICON_POSITION_CHANGED], 0,
8755 icon->data, &position);
8756 }
8757
8758 if (changed)
8759 {
8760 g_signal_emit (container, signals[LAYOUT_CHANGED], 0);
8761 }
8762}
8763
8764/* Re-sort, switching to automatic layout if it was in manual layout. */
8765void
8766baul_icon_container_sort (BaulIconContainer *container)
8767{
8768 gboolean changed;
8769
8770 changed = !container->details->auto_layout;
8771 container->details->auto_layout = TRUE(!(0));
8772
8773 reset_scroll_region_if_not_empty (container);
8774 redo_layout (container);
8775
8776 if (changed)
8777 {
8778 g_signal_emit (container, signals[LAYOUT_CHANGED], 0);
8779 }
8780}
8781
8782gboolean
8783baul_icon_container_is_auto_layout (BaulIconContainer *container)
8784{
8785 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
8786
8787 return container->details->auto_layout;
8788}
8789
8790gboolean
8791baul_icon_container_is_tighter_layout (BaulIconContainer *container)
8792{
8793 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
8794
8795 return container->details->tighter_layout;
8796}
8797
8798static void
8799pending_icon_to_rename_destroy_callback (BaulIconCanvasItem *item, BaulIconContainer *container)
8800{
8801 g_assert (container->details->pending_icon_to_rename != NULL)do { if (container->details->pending_icon_to_rename != (
(void*)0)) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 8801, ((const char*) (__func__)), "container->details->pending_icon_to_rename != NULL"
); } while (0)
;
8802 g_assert (container->details->pending_icon_to_rename->item == item)do { if (container->details->pending_icon_to_rename->
item == item) ; else g_assertion_message_expr (((gchar*) 0), "baul-icon-container.c"
, 8802, ((const char*) (__func__)), "container->details->pending_icon_to_rename->item == item"
); } while (0)
;
8803 container->details->pending_icon_to_rename = NULL((void*)0);
8804}
8805
8806static BaulIcon*
8807get_pending_icon_to_rename (BaulIconContainer *container)
8808{
8809 return container->details->pending_icon_to_rename;
8810}
8811
8812static void
8813set_pending_icon_to_rename (BaulIconContainer *container, BaulIcon *icon)
8814{
8815 BaulIcon *old_icon;
8816
8817 old_icon = container->details->pending_icon_to_rename;
8818
8819 if (icon == old_icon)
8820 {
8821 return;
8822 }
8823
8824 if (old_icon != NULL((void*)0))
8825 {
8826 g_signal_handlers_disconnect_by_funcg_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_rename_destroy_callback)))
, (container))
8827 (old_icon->item,g_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_rename_destroy_callback)))
, (container))
8828 G_CALLBACK (pending_icon_to_rename_destroy_callback),g_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_rename_destroy_callback)))
, (container))
8829 container)g_signal_handlers_disconnect_matched ((old_icon->item), (GSignalMatchType
) (G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA), 0, 0, ((void*)
0), (((GCallback) (pending_icon_to_rename_destroy_callback)))
, (container))
;
8830 }
8831
8832 if (icon != NULL((void*)0))
8833 {
8834 g_signal_connect (icon->item, "destroy",g_signal_connect_data ((icon->item), ("destroy"), (((GCallback
) (pending_icon_to_rename_destroy_callback))), (container), (
(void*)0), (GConnectFlags) 0)
8835 G_CALLBACK (pending_icon_to_rename_destroy_callback), container)g_signal_connect_data ((icon->item), ("destroy"), (((GCallback
) (pending_icon_to_rename_destroy_callback))), (container), (
(void*)0), (GConnectFlags) 0)
;
8836 }
8837
8838 container->details->pending_icon_to_rename = icon;
8839}
8840
8841static void
8842process_pending_icon_to_rename (BaulIconContainer *container)
8843{
8844 BaulIcon *pending_icon_to_rename;
8845
8846 pending_icon_to_rename = get_pending_icon_to_rename (container);
8847
8848 if (pending_icon_to_rename != NULL((void*)0))
8849 {
8850 if (pending_icon_to_rename->is_selected && !has_multiple_selection (container))
8851 {
8852 baul_icon_container_start_renaming_selected_item (container, FALSE(0));
8853 }
8854 else
8855 {
8856 set_pending_icon_to_rename (container, NULL((void*)0));
8857 }
8858 }
8859}
8860
8861static gboolean
8862is_renaming_pending (BaulIconContainer *container)
8863{
8864 return get_pending_icon_to_rename (container) != NULL((void*)0);
8865}
8866
8867static gboolean
8868is_renaming (BaulIconContainer *container)
8869{
8870 return container->details->renaming;
8871}
8872
8873/**
8874 * baul_icon_container_start_renaming_selected_item
8875 * @container: An icon container widget.
8876 * @select_all: Whether the whole file should initially be selected, or
8877 * only its basename (i.e. everything except its extension).
8878 *
8879 * Displays the edit name widget on the first selected icon
8880 **/
8881void
8882baul_icon_container_start_renaming_selected_item (BaulIconContainer *container,
8883 gboolean select_all)
8884{
8885 BaulIconContainerDetails *details;
8886 BaulIcon *icon;
8887 EelDRect icon_rect;
8888 EelDRect text_rect;
8889 PangoFontDescription *desc;
8890 const char *editable_text;
8891 int x, y, width;
8892 int start_offset, end_offset;
8893
8894 /* Check if it already in renaming mode, if so - select all */
8895 details = container->details;
8896 if (details->renaming)
8897 {
8898 eel_editable_label_select_region (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
,
8899 0,
8900 -1);
8901 return;
8902 }
8903
8904 /* Find selected icon */
8905 icon = get_first_selected_icon (container);
8906 if (icon == NULL((void*)0))
8907 {
8908 return;
8909 }
8910
8911 g_assert (!has_multiple_selection (container))do { if (!has_multiple_selection (container)) ; else g_assertion_message_expr
(((gchar*) 0), "baul-icon-container.c", 8911, ((const char*)
(__func__)), "!has_multiple_selection (container)"); } while
(0)
;
8912
8913
8914 if (!icon_is_positioned (icon))
8915 {
8916 set_pending_icon_to_rename (container, icon);
8917 return;
8918 }
8919
8920 set_pending_icon_to_rename (container, NULL((void*)0));
8921
8922 /* Make a copy of the original editable text for a later compare */
8923 editable_text = baul_icon_canvas_item_get_editable_text (icon->item);
8924
8925 /* This could conceivably be NULL if a rename was triggered really early. */
8926 if (editable_text == NULL((void*)0))
8927 {
8928 return;
8929 }
8930
8931 details->original_text = g_strdup (editable_text)g_strdup_inline (editable_text);
8932
8933 /* Freeze updates so files added while renaming don't cause rename to loose focus, bug #318373 */
8934 baul_icon_container_freeze_updates (container);
8935
8936 /* Create text renaming widget, if it hasn't been created already.
8937 * We deal with the broken icon text item widget by keeping it around
8938 * so its contents can still be cut and pasted as part of the clipboard
8939 */
8940 if (details->rename_widget == NULL((void*)0))
8941 {
8942 details->rename_widget = eel_editable_label_new ("Test text");
8943 eel_editable_label_set_line_wrap (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
, TRUE(!(0)));
8944 eel_editable_label_set_line_wrap_mode (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
, PANGO_WRAP_WORD_CHAR);
8945 eel_editable_label_set_draw_outline (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
, TRUE(!(0)));
8946
8947 if (details->label_position != BAUL_ICON_LABEL_POSITION_BESIDE)
8948 {
8949 eel_editable_label_set_justify (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
, CTK_JUSTIFY_CENTER);
8950 }
8951
8952 ctk_widget_set_margin_start (details->rename_widget, 1);
8953 ctk_widget_set_margin_end (details->rename_widget, 1);
8954 ctk_widget_set_margin_top (details->rename_widget, 1);
8955 ctk_widget_set_margin_bottom (details->rename_widget, 1);
8956 ctk_layout_put (CTK_LAYOUT (container)((((CtkLayout*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_layout_get_type ()))))))
,
8957 details->rename_widget, 0, 0);
8958 }
8959
8960 /* Set the right font */
8961 if (details->font)
8962 {
8963 desc = pango_font_description_from_string (details->font);
8964 }
8965 else
8966 {
8967 PangoContext *context;
8968
8969 context = ctk_widget_get_pango_context (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
8970 desc = pango_font_description_copy (pango_context_get_font_description (context));
8971 pango_font_description_set_size (desc,
8972 pango_font_description_get_size (desc) +
8973 container->details->font_size_table [container->details->zoom_level]);
8974 }
8975 eel_editable_label_set_font_description (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
,
8976 desc);
8977 pango_font_description_free (desc);
8978
8979 icon_rect = baul_icon_canvas_item_get_icon_rectangle (icon->item);
8980 text_rect = baul_icon_canvas_item_get_text_rectangle (icon->item, TRUE(!(0)));
8981
8982 if (baul_icon_container_is_layout_vertical (container) &&
8983 container->details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
8984 {
8985 /* for one-line editables, the width changes dynamically */
8986 width = -1;
8987 }
8988 else
8989 {
8990 width = baul_icon_canvas_item_get_max_text_width (icon->item);
8991 }
8992
8993 if (details->label_position == BAUL_ICON_LABEL_POSITION_BESIDE)
8994 {
8995 eel_canvas_w2c (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
->canvas,
8996 text_rect.x0,
8997 text_rect.y0,
8998 &x, &y);
8999 }
9000 else
9001 {
9002 eel_canvas_w2c (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
->canvas,
9003 (icon_rect.x0 + icon_rect.x1) / 2,
9004 icon_rect.y1,
9005 &x, &y);
9006 x = x - width / 2 - 1;
9007 }
9008
9009 ctk_layout_move (CTK_LAYOUT (container)((((CtkLayout*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_layout_get_type ()))))))
,
9010 details->rename_widget,
9011 x, y);
9012
9013 ctk_widget_set_size_request (details->rename_widget,
9014 width, -1);
9015 eel_editable_label_set_text (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
,
9016 editable_text);
9017 if (select_all)
9018 {
9019 start_offset = 0;
9020 end_offset = -1;
9021 }
9022 else
9023 {
9024 eel_filename_get_rename_region (editable_text, &start_offset, &end_offset);
9025 }
9026 ctk_widget_show (details->rename_widget);
9027 ctk_widget_grab_focus (details->rename_widget);
9028
9029 eel_editable_label_select_region (EEL_EDITABLE_LABEL (details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((details->rename_widget)), (eel_editable_label_get_type
())))))
,
9030 start_offset,
9031 end_offset);
9032 g_signal_emit (container,
9033 signals[RENAMING_ICON], 0,
9034 CTK_EDITABLE (details->rename_widget)((((CtkEditable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((details->rename_widget)), ((ctk_editable_get_type ())
)))))
);
9035
9036 baul_icon_container_update_icon (container, icon);
9037
9038 /* We are in renaming mode */
9039 details->renaming = TRUE(!(0));
9040 baul_icon_canvas_item_set_renaming (icon->item, TRUE(!(0)));
9041}
9042
9043static void
9044end_renaming_mode (BaulIconContainer *container, gboolean commit)
9045{
9046 BaulIcon *icon;
9047
9048 set_pending_icon_to_rename (container, NULL((void*)0));
9049
9050 icon = get_icon_being_renamed (container);
9051 if (icon == NULL((void*)0))
9052 {
9053 return;
9054 }
9055
9056 /* We are not in renaming mode */
9057 container->details->renaming = FALSE(0);
9058 baul_icon_canvas_item_set_renaming (icon->item, FALSE(0));
9059
9060 baul_icon_container_unfreeze_updates (container);
9061
9062 if (commit)
9063 {
9064 set_pending_icon_to_reveal (container, icon);
9065 }
9066
9067 ctk_widget_grab_focus (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
9068
9069 if (commit)
9070 {
9071 const char *changed_text;
9072
9073 /* Verify that text has been modified before signalling change. */
9074 changed_text = eel_editable_label_get_text (EEL_EDITABLE_LABEL (container->details->rename_widget)((((EelEditableLabel*) (void *) g_type_check_instance_cast ((
GTypeInstance*) ((container->details->rename_widget)), (
eel_editable_label_get_type())))))
);
9075 if (strcmp (container->details->original_text, changed_text) != 0)
9076 {
9077 AtkObject *accessible_icon;
9078
9079 g_signal_emit (container,
9080 signals[ICON_TEXT_CHANGED], 0,
9081 icon->data,
9082 changed_text);
9083
9084 accessible_icon = atk_gobject_accessible_for_object (G_OBJECT(icon->item)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), (((GType) ((20) << (2))))))))
);
9085 g_object_notify (G_OBJECT(accessible_icon)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible_icon)), (((GType) ((20) << (2))))))))
, "accessible-name");
9086 }
9087 }
9088
9089 ctk_widget_hide (container->details->rename_widget);
9090
9091 g_free (container->details->original_text);
9092
9093}
9094
9095/* emit preview signal, called by the canvas item */
9096gboolean
9097baul_icon_container_emit_preview_signal (BaulIconContainer *icon_container,
9098 BaulIcon *icon,
9099 gboolean start_flag)
9100{
9101 gboolean result;
9102
9103 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (icon_container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((icon_container)); GType __t = (baul_icon_container_get_type
()); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (icon_container)"
); return ((0)); } } while (0)
;
9104 g_return_val_if_fail (icon != NULL, FALSE)do { if ((icon != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "icon != NULL"); return
((0)); } } while (0)
;
9105 g_return_val_if_fail (start_flag == FALSE || start_flag == TRUE, FALSE)do { if ((start_flag == (0) || start_flag == (!(0)))) { } else
{ g_return_if_fail_warning (((gchar*) 0), ((const char*) (__func__
)), "start_flag == FALSE || start_flag == TRUE"); return ((0)
); } } while (0)
;
9106
9107 result = FALSE(0);
9108 g_signal_emit (icon_container,
9109 signals[PREVIEW], 0,
9110 icon->data,
9111 start_flag,
9112 &result);
9113
9114 return result;
9115}
9116
9117gboolean
9118baul_icon_container_has_stored_icon_positions (BaulIconContainer *container)
9119{
9120 GList *p;
9121 gboolean have_stored_position;
9122 BaulIconPosition position;
9123 BaulIcon *icon = NULL((void*)0);
9124
9125 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
9126 {
9127 icon = p->data;
9128
9129 have_stored_position = FALSE(0);
9130 g_signal_emit (container,
9131 signals[GET_STORED_ICON_POSITION], 0,
9132 icon->data,
9133 &position,
9134 &have_stored_position);
9135 if (have_stored_position)
9136 {
9137 return TRUE(!(0));
9138 }
9139 }
9140 return FALSE(0);
9141}
9142
9143void
9144baul_icon_container_set_single_click_mode (BaulIconContainer *container,
9145 gboolean single_click_mode)
9146{
9147 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9148
9149 container->details->single_click_mode = single_click_mode;
9150}
9151
9152/* Return if the icon container is a fixed size */
9153gboolean
9154baul_icon_container_get_is_fixed_size (BaulIconContainer *container)
9155{
9156 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
9157
9158 return container->details->is_fixed_size;
9159}
9160
9161/* Set the icon container to be a fixed size */
9162void
9163baul_icon_container_set_is_fixed_size (BaulIconContainer *container,
9164 gboolean is_fixed_size)
9165{
9166 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9167
9168 container->details->is_fixed_size = is_fixed_size;
9169}
9170
9171gboolean
9172baul_icon_container_get_is_desktop (BaulIconContainer *container)
9173{
9174 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
9175
9176 return container->details->is_desktop;
9177}
9178
9179void
9180baul_icon_container_set_is_desktop (BaulIconContainer *container,
9181 gboolean is_desktop)
9182{
9183 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9184
9185 container->details->is_desktop = is_desktop;
9186
9187 if (is_desktop) {
9188 CtkStyleContext *context;
9189
9190 context = ctk_widget_get_style_context (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
9191 ctk_style_context_add_class (context, "baul-desktop");
9192 }
9193}
9194
9195void
9196baul_icon_container_set_margins (BaulIconContainer *container,
9197 int left_margin,
9198 int right_margin,
9199 int top_margin,
9200 int bottom_margin)
9201{
9202 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9203
9204 container->details->left_margin = left_margin;
9205 container->details->right_margin = right_margin;
9206 container->details->top_margin = top_margin;
9207 container->details->bottom_margin = bottom_margin;
9208
9209 /* redo layout of icons as the margins have changed */
9210 schedule_redo_layout (container);
9211}
9212
9213void
9214baul_icon_container_set_use_drop_shadows (BaulIconContainer *container,
9215 gboolean use_drop_shadows)
9216{
9217 if (container->details->drop_shadows_requested == use_drop_shadows)
9218 {
9219 return;
9220 }
9221
9222 container->details->drop_shadows_requested = use_drop_shadows;
9223 container->details->use_drop_shadows = use_drop_shadows;
9224
9225 ctk_widget_queue_draw (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
9226}
9227
9228/* handle theme changes */
9229
9230void
9231baul_icon_container_set_font (BaulIconContainer *container,
9232 const char *font)
9233{
9234 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9235
9236 if (g_strcmp0 (container->details->font, font) == 0)
9237 {
9238 return;
9239 }
9240
9241 g_free (container->details->font);
9242 container->details->font = g_strdup (font)g_strdup_inline (font);
9243
9244 invalidate_labels (container);
9245 baul_icon_container_request_update_all (container);
9246 ctk_widget_queue_draw (CTK_WIDGET (container)((((CtkWidget*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((ctk_widget_get_type ()))))))
);
9247}
9248
9249void
9250baul_icon_container_set_font_size_table (BaulIconContainer *container,
9251 const int font_size_table[BAUL_ZOOM_LEVEL_LARGEST + 1])
9252{
9253 int old_font_size;
9254 int i;
9255
9256 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9257 g_return_if_fail (font_size_table != NULL)do { if ((font_size_table != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "font_size_table != NULL"
); return; } } while (0)
;
9258
9259 old_font_size = container->details->font_size_table[container->details->zoom_level];
9260
9261 for (i = 0; i <= BAUL_ZOOM_LEVEL_LARGEST; i++)
9262 {
9263 if (container->details->font_size_table[i] != font_size_table[i])
9264 {
9265 container->details->font_size_table[i] = font_size_table[i];
9266 }
9267 }
9268
9269 if (old_font_size != container->details->font_size_table[container->details->zoom_level])
9270 {
9271 invalidate_labels (container);
9272 baul_icon_container_request_update_all (container);
9273 }
9274}
9275
9276/**
9277 * baul_icon_container_get_icon_description
9278 * @container: An icon container widget.
9279 * @data: Icon data
9280 *
9281 * Gets the description for the icon. This function may return NULL.
9282 **/
9283char*
9284baul_icon_container_get_icon_description (BaulIconContainer *container,
9285 BaulIconData *data)
9286{
9287 BaulIconContainerClass *klass;
9288
9289 klass = BAUL_ICON_CONTAINER_GET_CLASS (container)((((BaulIconContainerClass*) (((GTypeInstance*) ((container))
)->g_class))))
;
9290
9291 if (klass->get_icon_description)
9292 {
9293 return klass->get_icon_description (container, data);
9294 }
9295 else
9296 {
9297 return NULL((void*)0);
9298 }
9299}
9300
9301gboolean
9302baul_icon_container_get_allow_moves (BaulIconContainer *container)
9303{
9304 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
9305
9306 return container->details->drag_allow_moves;
9307}
9308
9309void
9310baul_icon_container_set_allow_moves (BaulIconContainer *container,
9311 gboolean allow_moves)
9312{
9313 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9314
9315 container->details->drag_allow_moves = allow_moves;
9316}
9317
9318void
9319baul_icon_container_set_forced_icon_size (BaulIconContainer *container,
9320 int forced_icon_size)
9321{
9322 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9323
9324 if (forced_icon_size != container->details->forced_icon_size)
9325 {
9326 container->details->forced_icon_size = forced_icon_size;
9327
9328 invalidate_label_sizes (container);
9329 baul_icon_container_request_update_all (container);
9330 }
9331}
9332
9333void
9334baul_icon_container_set_all_columns_same_width (BaulIconContainer *container,
9335 gboolean all_columns_same_width)
9336{
9337 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9338
9339 if (all_columns_same_width != container->details->all_columns_same_width)
9340 {
9341 container->details->all_columns_same_width = all_columns_same_width;
9342
9343 invalidate_labels (container);
9344 baul_icon_container_request_update_all (container);
9345 }
9346}
9347
9348/**
9349 * baul_icon_container_set_highlighted_for_clipboard
9350 * @container: An icon container widget.
9351 * @data: Icon Data associated with all icons that should be highlighted.
9352 * Others will be unhighlighted.
9353 **/
9354void
9355baul_icon_container_set_highlighted_for_clipboard (BaulIconContainer *container,
9356 GList *clipboard_icon_data)
9357{
9358 GList *l;
9359 gboolean highlighted_for_clipboard;
9360 BaulIcon *icon = NULL((void*)0);
9361
9362 g_return_if_fail (BAUL_IS_ICON_CONTAINER (container))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return; } } while (0)
;
9363
9364 for (l = container->details->icons; l != NULL((void*)0); l = l->next)
9365 {
9366 icon = l->data;
9367 highlighted_for_clipboard = (g_list_find (clipboard_icon_data, icon->data) != NULL((void*)0));
9368
9369 eel_canvas_item_set (EEL_CANVAS_ITEM (icon->item)((((EelCanvasItem*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), ((eel_canvas_item_get_type ()))))))
,
9370 "highlighted-for-clipboard", highlighted_for_clipboard,
9371 NULL((void*)0));
9372 }
9373
9374}
9375
9376/* BaulIconContainerAccessible */
9377
9378static BaulIconContainerAccessiblePrivate *
9379accessible_get_priv (AtkObject *accessible)
9380{
9381 BaulIconContainerAccessiblePrivate *priv;
9382
9383 priv = g_object_get_qdata (G_OBJECT (accessible)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), (((GType) ((20) << (2))))))))
,
9384 accessible_private_data_quark);
9385
9386 return priv;
9387}
9388
9389/* AtkAction interface */
9390
9391static gboolean
9392baul_icon_container_accessible_do_action (AtkAction *accessible, int i)
9393{
9394 CtkWidget *widget;
9395 BaulIconContainer *container;
9396 GList *selection;
9397
9398 g_return_val_if_fail (i < LAST_ACTION, FALSE)do { if ((i < LAST_ACTION)) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "i < LAST_ACTION"
); return ((0)); } } while (0)
;
9399
9400 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9401 if (!widget)
9402 {
9403 return FALSE(0);
9404 }
9405
9406 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9407 switch (i)
9408 {
9409 case ACTION_ACTIVATE :
9410 selection = baul_icon_container_get_selection (container);
9411
9412 if (selection)
9413 {
9414 g_signal_emit_by_name (container, "activate", selection);
9415 g_list_free (selection);
9416 }
9417 break;
9418 case ACTION_MENU :
9419 handle_popups (container, NULL((void*)0),"context_click_background");
9420 break;
9421 default :
9422 g_warning ("Invalid action passed to BaulIconContainerAccessible::do_action");
9423 return FALSE(0);
9424 }
9425 return TRUE(!(0));
9426}
9427
9428static int
9429baul_icon_container_accessible_get_n_actions (AtkAction *accessible G_GNUC_UNUSED__attribute__ ((__unused__)))
9430{
9431 return LAST_ACTION;
9432}
9433
9434static const char *
9435baul_icon_container_accessible_action_get_description (AtkAction *accessible,
9436 int i)
9437{
9438 BaulIconContainerAccessiblePrivate *priv;
9439
9440 g_assert (i < LAST_ACTION)do { if (i < LAST_ACTION) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 9440, ((const char*) (
__func__)), "i < LAST_ACTION"); } while (0)
;
9441
9442 priv = accessible_get_priv (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9443
9444 if (priv->action_descriptions[i])
9445 {
9446 return priv->action_descriptions[i];
9447 }
9448 else
9449 {
9450 return baul_icon_container_accessible_action_descriptions[i];
9451 }
9452}
9453
9454static const char *
9455baul_icon_container_accessible_action_get_name (AtkAction *accessible G_GNUC_UNUSED__attribute__ ((__unused__)),
9456 int i)
9457{
9458 g_assert (i < LAST_ACTION)do { if (i < LAST_ACTION) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 9458, ((const char*) (
__func__)), "i < LAST_ACTION"); } while (0)
;
9459
9460 return baul_icon_container_accessible_action_names[i];
9461}
9462
9463static const char *
9464baul_icon_container_accessible_action_get_keybinding (AtkAction *accessible G_GNUC_UNUSED__attribute__ ((__unused__)),
9465 int i)
9466{
9467 g_assert (i < LAST_ACTION)do { if (i < LAST_ACTION) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 9467, ((const char*) (
__func__)), "i < LAST_ACTION"); } while (0)
;
9468
9469 return NULL((void*)0);
9470}
9471
9472static gboolean
9473baul_icon_container_accessible_action_set_description (AtkAction *accessible,
9474 int i,
9475 const char *description)
9476{
9477 BaulIconContainerAccessiblePrivate *priv;
9478
9479 g_assert (i < LAST_ACTION)do { if (i < LAST_ACTION) ; else g_assertion_message_expr (
((gchar*) 0), "baul-icon-container.c", 9479, ((const char*) (
__func__)), "i < LAST_ACTION"); } while (0)
;
9480
9481 priv = accessible_get_priv (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9482
9483 if (priv->action_descriptions[i])
9484 {
9485 g_free (priv->action_descriptions[i]);
9486 }
9487 priv->action_descriptions[i] = g_strdup (description)g_strdup_inline (description);
9488
9489 return FALSE(0);
9490}
9491
9492static void
9493baul_icon_container_accessible_action_interface_init (AtkActionIface *iface)
9494{
9495 iface->do_action = baul_icon_container_accessible_do_action;
9496 iface->get_n_actions = baul_icon_container_accessible_get_n_actions;
9497 iface->get_description = baul_icon_container_accessible_action_get_description;
9498 iface->get_name = baul_icon_container_accessible_action_get_name;
9499 iface->get_keybinding = baul_icon_container_accessible_action_get_keybinding;
9500 iface->set_description = baul_icon_container_accessible_action_set_description;
9501}
9502
9503/* AtkSelection interface */
9504
9505static void
9506baul_icon_container_accessible_update_selection (AtkObject *accessible)
9507{
9508 BaulIconContainer *container;
9509 BaulIconContainerAccessiblePrivate *priv;
9510 GList *l;
9511 BaulIcon *icon = NULL((void*)0);
9512
9513 container = BAUL_ICON_CONTAINER (ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)))((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((ctk_accessible_get_widget (((((CtkAccessible
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((accessible
)), ((ctk_accessible_get_type ()))))))))), (baul_icon_container_get_type
())))))
;
9514
9515 priv = accessible_get_priv (accessible);
9516
9517 if (priv->selection)
9518 {
9519 g_list_free (priv->selection);
9520 priv->selection = NULL((void*)0);
9521 }
9522
9523 for (l = container->details->icons; l != NULL((void*)0); l = l->next)
9524 {
9525 icon = l->data;
9526 if (icon->is_selected)
9527 {
9528 priv->selection = g_list_prepend (priv->selection,
9529 icon);
9530 }
9531 }
9532
9533 priv->selection = g_list_reverse (priv->selection);
9534}
9535
9536static void
9537baul_icon_container_accessible_selection_changed_cb (BaulIconContainer *container G_GNUC_UNUSED__attribute__ ((__unused__)),
9538 gpointer data)
9539{
9540 g_signal_emit_by_name (data, "selection_changed");
9541}
9542
9543static void
9544baul_icon_container_accessible_icon_added_cb (BaulIconContainer *container,
9545 BaulIconData *icon_data,
9546 gpointer data)
9547{
9548 BaulIcon *icon;
9549
9550 // We don't want to emit children_changed signals during any type of load.
9551 if (container->details->is_loading || container->details->is_populating_container)
9552 return;
9553
9554 icon = g_hash_table_lookup (container->details->icon_set, icon_data);
9555 if (icon)
9556 {
9557 AtkObject *atk_parent;
9558 AtkObject *atk_child;
9559 int index;
9560
9561 atk_parent = ATK_OBJECT (data)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((data)), ((atk_object_get_type ()))))))
;
9562 atk_child = atk_gobject_accessible_for_object
9563 (G_OBJECT (icon->item)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), (((GType) ((20) << (2))))))))
);
9564 index = g_list_index (container->details->icons, icon);
9565
9566 g_signal_emit_by_name (atk_parent, "children_changed::add",
9567 index, atk_child, NULL((void*)0));
9568 }
9569}
9570
9571static void
9572baul_icon_container_accessible_icon_removed_cb (BaulIconContainer *container,
9573 BaulIconData *icon_data,
9574 gpointer data)
9575{
9576 BaulIcon *icon;
9577
9578 icon = g_hash_table_lookup (container->details->icon_set, icon_data);
9579 if (icon)
9580 {
9581 AtkObject *atk_parent;
9582 AtkObject *atk_child;
9583 int index;
9584
9585 atk_parent = ATK_OBJECT (data)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((data)), ((atk_object_get_type ()))))))
;
9586 atk_child = atk_gobject_accessible_for_object
9587 (G_OBJECT (icon->item)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), (((GType) ((20) << (2))))))))
);
9588 index = g_list_index (container->details->icons, icon);
9589
9590 g_signal_emit_by_name (atk_parent, "children_changed::remove",
9591 index, atk_child, NULL((void*)0));
9592 }
9593}
9594
9595static void
9596baul_icon_container_accessible_cleared_cb (BaulIconContainer *container G_GNUC_UNUSED__attribute__ ((__unused__)),
9597 gpointer data)
9598{
9599 g_signal_emit_by_name (data, "children_changed", 0, NULL((void*)0), NULL((void*)0));
9600}
9601
9602
9603static gboolean
9604baul_icon_container_accessible_add_selection (AtkSelection *accessible,
9605 int i)
9606{
9607 CtkWidget *widget;
9608 BaulIconContainer *container;
9609 BaulIcon *icon;
9610
9611 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9612 if (!widget)
9613 {
9614 return FALSE(0);
9615 }
9616
9617 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9618
9619 icon = g_list_nth_data (container->details->icons, i);
9620 if (icon)
9621 {
9622 GList *selection;
9623
9624 selection = baul_icon_container_get_selection (container);
9625 selection = g_list_prepend (selection,
9626 icon->data);
9627 baul_icon_container_set_selection (container, selection);
9628
9629 g_list_free (selection);
9630 return TRUE(!(0));
9631 }
9632
9633 return FALSE(0);
9634}
9635
9636static gboolean
9637baul_icon_container_accessible_clear_selection (AtkSelection *accessible)
9638{
9639 CtkWidget *widget;
9640 BaulIconContainer *container;
9641
9642 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9643 if (!widget)
9644 {
9645 return FALSE(0);
9646 }
9647
9648 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9649
9650 baul_icon_container_unselect_all (container);
9651
9652 return TRUE(!(0));
9653}
9654
9655static AtkObject *
9656baul_icon_container_accessible_ref_selection (AtkSelection *accessible,
9657 int i)
9658{
9659 BaulIconContainerAccessiblePrivate *priv;
9660 BaulIcon *icon;
9661
9662 baul_icon_container_accessible_update_selection (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9663 priv = accessible_get_priv (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9664
9665 icon = g_list_nth_data (priv->selection, i);
9666 if (icon)
9667 {
9668 AtkObject *atk_object;
9669
9670 atk_object = atk_gobject_accessible_for_object (G_OBJECT (icon->item)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), (((GType) ((20) << (2))))))))
);
9671 if (atk_object)
9672 {
9673 g_object_ref (atk_object)((__typeof__ (atk_object)) (g_object_ref) (atk_object));
9674 }
9675
9676 return atk_object;
9677 }
9678 else
9679 {
9680 return NULL((void*)0);
9681 }
9682}
9683
9684static int
9685baul_icon_container_accessible_get_selection_count (AtkSelection *accessible)
9686{
9687 int count;
9688 BaulIconContainerAccessiblePrivate *priv;
9689
9690 baul_icon_container_accessible_update_selection (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9691 priv = accessible_get_priv (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9692
9693 count = g_list_length (priv->selection);
9694
9695 return count;
9696}
9697
9698static gboolean
9699baul_icon_container_accessible_is_child_selected (AtkSelection *accessible,
9700 int i)
9701{
9702 BaulIconContainer *container;
9703 BaulIcon *icon;
9704 CtkWidget *widget;
9705
9706 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9707 if (!widget)
9708 {
9709 return FALSE(0);
9710 }
9711
9712 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9713
9714 icon = g_list_nth_data (container->details->icons, i);
9715 return icon ? icon->is_selected : FALSE(0);
9716}
9717
9718static gboolean
9719baul_icon_container_accessible_remove_selection (AtkSelection *accessible,
9720 int i)
9721{
9722 BaulIconContainer *container;
9723 BaulIconContainerAccessiblePrivate *priv;
9724 BaulIcon *icon;
9725 CtkWidget *widget;
9726
9727 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9728 if (!widget)
9729 {
9730 return FALSE(0);
9731 }
9732
9733 baul_icon_container_accessible_update_selection (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9734 priv = accessible_get_priv (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9735
9736 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9737
9738 icon = g_list_nth_data (priv->selection, i);
9739 if (icon)
9740 {
9741 GList *selection;
9742
9743 selection = baul_icon_container_get_selection (container);
9744 selection = g_list_remove (selection, icon->data);
9745 baul_icon_container_set_selection (container, selection);
9746
9747 g_list_free (selection);
9748 return TRUE(!(0));
9749 }
9750
9751 return FALSE(0);
9752}
9753
9754static gboolean
9755baul_icon_container_accessible_select_all_selection (AtkSelection *accessible)
9756{
9757 BaulIconContainer *container;
9758 CtkWidget *widget;
9759
9760 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9761 if (!widget)
9762 {
9763 return FALSE(0);
9764 }
9765
9766 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9767
9768 baul_icon_container_select_all (container);
9769
9770 return TRUE(!(0));
9771}
9772
9773void
9774baul_icon_container_widget_to_file_operation_position (BaulIconContainer *container,
9775 CdkPoint *position)
9776{
9777 double x, y;
9778
9779 g_return_if_fail (position != NULL)do { if ((position != ((void*)0))) { } else { g_return_if_fail_warning
(((gchar*) 0), ((const char*) (__func__)), "position != NULL"
); return; } } while (0)
;
9780
9781 x = position->x;
9782 y = position->y;
9783
9784 eel_canvas_window_to_world (EEL_CANVAS (container)((((EelCanvas*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((container)), ((eel_canvas_get_type ()))))))
, x, y, &x, &y);
9785
9786 position->x = (int) x;
9787 position->y = (int) y;
9788
9789 /* ensure that we end up in the middle of the icon */
9790 position->x -= baul_get_icon_size_for_zoom_level (container->details->zoom_level) / 2;
9791 position->y -= baul_get_icon_size_for_zoom_level (container->details->zoom_level) / 2;
9792}
9793
9794static void
9795baul_icon_container_accessible_selection_interface_init (AtkSelectionIface *iface)
9796{
9797 iface->add_selection = baul_icon_container_accessible_add_selection;
9798 iface->clear_selection = baul_icon_container_accessible_clear_selection;
9799 iface->ref_selection = baul_icon_container_accessible_ref_selection;
9800 iface->get_selection_count = baul_icon_container_accessible_get_selection_count;
9801 iface->is_child_selected = baul_icon_container_accessible_is_child_selected;
9802 iface->remove_selection = baul_icon_container_accessible_remove_selection;
9803 iface->select_all_selection = baul_icon_container_accessible_select_all_selection;
9804}
9805
9806
9807static gint
9808baul_icon_container_accessible_get_n_children (AtkObject *accessible)
9809{
9810 BaulIconContainer *container;
9811 CtkWidget *widget;
9812 gint i;
9813
9814 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9815 if (!widget)
9816 {
9817 return FALSE(0);
9818 }
9819
9820 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9821
9822 i = g_hash_table_size (container->details->icon_set);
9823 if (container->details->rename_widget)
9824 {
9825 i++;
9826 }
9827 return i;
9828}
9829
9830static AtkObject*
9831baul_icon_container_accessible_ref_child (AtkObject *accessible, int i)
9832{
9833 AtkObject *atk_object;
9834 BaulIconContainer *container;
9835 BaulIcon *icon;
9836 CtkWidget *widget;
9837
9838 widget = ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)((((CtkAccessible*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((ctk_accessible_get_type ()))))))
);
9839 if (!widget)
9840 {
9841 return NULL((void*)0);
9842 }
9843
9844 container = BAUL_ICON_CONTAINER (widget)((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((widget)), (baul_icon_container_get_type())
))))
;
9845
9846 icon = g_list_nth_data (container->details->icons, i);
9847 if (icon)
9848 {
9849 atk_object = atk_gobject_accessible_for_object (G_OBJECT (icon->item)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((icon->item)), (((GType) ((20) << (2))))))))
);
9850 g_object_ref (atk_object)((__typeof__ (atk_object)) (g_object_ref) (atk_object));
9851
9852 return atk_object;
9853 }
9854 else
9855 {
9856 if (i == g_list_length (container->details->icons))
9857 {
9858 if (container->details->rename_widget)
9859 {
9860 atk_object = ctk_widget_get_accessible (container->details->rename_widget);
9861 g_object_ref (atk_object)((__typeof__ (atk_object)) (g_object_ref) (atk_object));
9862
9863 return atk_object;
9864 }
9865 }
9866 return NULL((void*)0);
9867 }
9868}
9869
9870static void
9871baul_icon_container_accessible_initialize (AtkObject *accessible,
9872 gpointer data)
9873{
9874 BaulIconContainerAccessiblePrivate *priv;
9875
9876 if (ATK_OBJECT_CLASS (accessible_parent_class)((((AtkObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((accessible_parent_class)), ((atk_object_get_type ())))))
)
->initialize)
9877 {
9878 ATK_OBJECT_CLASS (accessible_parent_class)((((AtkObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((accessible_parent_class)), ((atk_object_get_type ())))))
)
->initialize (accessible, data);
9879 }
9880
9881 priv = g_new0 (BaulIconContainerAccessiblePrivate, 1)((BaulIconContainerAccessiblePrivate *) g_malloc0_n ((1), sizeof
(BaulIconContainerAccessiblePrivate)))
;
9882 g_object_set_qdata (G_OBJECT (accessible)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), (((GType) ((20) << (2))))))))
,
9883 accessible_private_data_quark,
9884 priv);
9885
9886 if (CTK_IS_ACCESSIBLE (accessible)(((__extension__ ({ GTypeInstance *__inst = (GTypeInstance*) (
(accessible)); GType __t = ((ctk_accessible_get_type ())); gboolean
__r; if (!__inst) __r = (0); else if (__inst->g_class &&
__inst->g_class->g_type == __t) __r = (!(0)); else __r
= g_type_check_instance_is_a (__inst, __t); __r; }))))
)
9887 {
9888 BaulIconContainer *container;
9889
9890 baul_icon_container_accessible_update_selection
9891 (ATK_OBJECT (accessible)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((accessible)), ((atk_object_get_type ()))))))
);
9892
9893 container = BAUL_ICON_CONTAINER (ctk_accessible_get_widget (CTK_ACCESSIBLE (accessible)))((((BaulIconContainer*) (void *) g_type_check_instance_cast (
(GTypeInstance*) ((ctk_accessible_get_widget (((((CtkAccessible
*) (void *) g_type_check_instance_cast ((GTypeInstance*) ((accessible
)), ((ctk_accessible_get_type ()))))))))), (baul_icon_container_get_type
())))))
;
9894 g_signal_connect (G_OBJECT (container), "selection_changed",g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("selection_changed"), (((GCallback) (baul_icon_container_accessible_selection_changed_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9895 G_CALLBACK (baul_icon_container_accessible_selection_changed_cb),g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("selection_changed"), (((GCallback) (baul_icon_container_accessible_selection_changed_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9896 accessible)g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("selection_changed"), (((GCallback) (baul_icon_container_accessible_selection_changed_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
;
9897 g_signal_connect (G_OBJECT (container), "icon_added",g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("icon_added"), (((GCallback) (baul_icon_container_accessible_icon_added_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9898 G_CALLBACK (baul_icon_container_accessible_icon_added_cb),g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("icon_added"), (((GCallback) (baul_icon_container_accessible_icon_added_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9899 accessible)g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("icon_added"), (((GCallback) (baul_icon_container_accessible_icon_added_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
;
9900 g_signal_connect (G_OBJECT (container), "icon_removed",g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("icon_removed"), (((GCallback) (baul_icon_container_accessible_icon_removed_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9901 G_CALLBACK (baul_icon_container_accessible_icon_removed_cb),g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("icon_removed"), (((GCallback) (baul_icon_container_accessible_icon_removed_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9902 accessible)g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("icon_removed"), (((GCallback) (baul_icon_container_accessible_icon_removed_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
;
9903 g_signal_connect (G_OBJECT (container), "cleared",g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("cleared"), (((GCallback) (baul_icon_container_accessible_cleared_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9904 G_CALLBACK (baul_icon_container_accessible_cleared_cb),g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("cleared"), (((GCallback) (baul_icon_container_accessible_cleared_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
9905 accessible)g_signal_connect_data ((((((GObject*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((container)), (((GType) ((20) << (2
))))))))), ("cleared"), (((GCallback) (baul_icon_container_accessible_cleared_cb
))), (accessible), ((void*)0), (GConnectFlags) 0)
;
9906 }
9907}
9908
9909static void
9910baul_icon_container_accessible_finalize (GObject *object)
9911{
9912 BaulIconContainerAccessiblePrivate *priv;
9913 int i;
9914
9915 priv = accessible_get_priv (ATK_OBJECT (object)((((AtkObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((object)), ((atk_object_get_type ()))))))
);
9916 if (priv->selection)
9917 {
9918 g_list_free (priv->selection);
9919 }
9920
9921 for (i = 0; i < LAST_ACTION; i++)
9922 {
9923 if (priv->action_descriptions[i])
9924 {
9925 g_free (priv->action_descriptions[i]);
9926 }
9927 }
9928
9929 g_free (priv);
9930
9931 G_OBJECT_CLASS (accessible_parent_class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((accessible_parent_class)), (((GType) ((20) << (2))
))))))
->finalize (object);
9932}
9933
9934G_DEFINE_TYPE_WITH_CODE (BaulIconContainerAccessible,static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
9935 baul_icon_container_accessible,static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
9936 eel_canvas_accessible_get_type (),static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
9937 G_IMPLEMENT_INTERFACE (ATK_TYPE_ACTION,static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
9938 baul_icon_container_accessible_action_interface_init)static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
9939 G_IMPLEMENT_INTERFACE (ATK_TYPE_SELECTION,static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
9940 baul_icon_container_accessible_selection_interface_init))static void baul_icon_container_accessible_init (BaulIconContainerAccessible
*self); static void baul_icon_container_accessible_class_init
(BaulIconContainerAccessibleClass *klass); static GType baul_icon_container_accessible_get_type_once
(void); static gpointer baul_icon_container_accessible_parent_class
= ((void*)0); static gint BaulIconContainerAccessible_private_offset
; static void baul_icon_container_accessible_class_intern_init
(gpointer klass) { baul_icon_container_accessible_parent_class
= g_type_class_peek_parent (klass); if (BaulIconContainerAccessible_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &BaulIconContainerAccessible_private_offset
); baul_icon_container_accessible_class_init ((BaulIconContainerAccessibleClass
*) klass); } __attribute__ ((__unused__)) static inline gpointer
baul_icon_container_accessible_get_instance_private (BaulIconContainerAccessible
*self) { return (((gpointer) ((guint8*) (self) + (glong) (BaulIconContainerAccessible_private_offset
)))); } GType baul_icon_container_accessible_get_type (void) {
static GType static_g_define_type_id = 0; if ((__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); (void) (
0 ? (gpointer) * (&static_g_define_type_id) : ((void*)0))
; (!(__extension__ ({ _Static_assert (sizeof *(&static_g_define_type_id
) == sizeof (gpointer), "Expression evaluates to false"); __typeof__
(*(&static_g_define_type_id)) gapg_temp_newval; __typeof__
((&static_g_define_type_id)) gapg_temp_atomic = (&static_g_define_type_id
); __atomic_load (gapg_temp_atomic, &gapg_temp_newval, 5)
; gapg_temp_newval; })) && g_once_init_enter_pointer (
&static_g_define_type_id)); })) ) { GType g_define_type_id
= baul_icon_container_accessible_get_type_once (); (__extension__
({ _Static_assert (sizeof *(&static_g_define_type_id) ==
sizeof (gpointer), "Expression evaluates to false"); 0 ? (void
) (*(&static_g_define_type_id) = (g_define_type_id)) : (void
) 0; g_once_init_leave_pointer ((&static_g_define_type_id
), (gpointer) (guintptr) (g_define_type_id)); })) ; } return static_g_define_type_id
; } __attribute__ ((__noinline__)) static GType baul_icon_container_accessible_get_type_once
(void) { GType g_define_type_id = g_type_register_static_simple
(eel_canvas_accessible_get_type (), g_intern_static_string (
"BaulIconContainerAccessible"), sizeof (BaulIconContainerAccessibleClass
), (GClassInitFunc)(void (*)(void)) baul_icon_container_accessible_class_intern_init
, sizeof (BaulIconContainerAccessible), (GInstanceInitFunc)(void
(*)(void)) baul_icon_container_accessible_init, (GTypeFlags)
0); { {{ const GInterfaceInfo g_implement_interface_info = {
(GInterfaceInitFunc)(void (*)(void)) baul_icon_container_accessible_action_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_action_get_type ()), &g_implement_interface_info);
} { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc
)(void (*)(void)) baul_icon_container_accessible_selection_interface_init
, ((void*)0), ((void*)0) }; g_type_add_interface_static (g_define_type_id
, (atk_selection_get_type ()), &g_implement_interface_info
); };} } return g_define_type_id; }
;
9941
9942static void
9943baul_icon_container_accessible_init (BaulIconContainerAccessible *accessible G_GNUC_UNUSED__attribute__ ((__unused__)))
9944{
9945}
9946
9947static void
9948baul_icon_container_accessible_class_init (BaulIconContainerAccessibleClass *klass)
9949{
9950 GObjectClass *gobject_class = G_OBJECT_CLASS (klass)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((klass)), (((GType) ((20) << (2))))))))
;
9951 AtkObjectClass *atk_class = ATK_OBJECT_CLASS (klass)((((AtkObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((klass)), ((atk_object_get_type ()))))))
;
9952
9953 accessible_parent_class = g_type_class_peek_parent (klass);
9954
9955 gobject_class->finalize = baul_icon_container_accessible_finalize;
9956
9957 atk_class->get_n_children = baul_icon_container_accessible_get_n_children;
9958 atk_class->ref_child = baul_icon_container_accessible_ref_child;
9959 atk_class->initialize = baul_icon_container_accessible_initialize;
9960
9961 accessible_private_data_quark = g_quark_from_static_string ("icon-container-accessible-private-data");
9962}
9963
9964#if ! defined (BAUL_OMIT_SELF_CHECK)
9965
9966static char *
9967check_compute_stretch (int icon_x, int icon_y, int icon_size,
9968 int start_pointer_x, int start_pointer_y,
9969 int end_pointer_x, int end_pointer_y)
9970{
9971 StretchState start, current;
9972
9973 start.icon_x = icon_x;
9974 start.icon_y = icon_y;
9975 start.icon_size = icon_size;
9976 start.pointer_x = start_pointer_x;
9977 start.pointer_y = start_pointer_y;
9978 current.pointer_x = end_pointer_x;
9979 current.pointer_y = end_pointer_y;
9980
9981 compute_stretch (&start, &current);
9982
9983 return g_strdup_printf ("%d,%d:%d",
9984 current.icon_x,
9985 current.icon_y,
9986 current.icon_size);
9987}
9988
9989void
9990baul_self_check_icon_container (void)
9991{
9992 EEL_CHECK_STRING_RESULT (check_compute_stretch (0, 0, 16, 0, 0, 0, 0), "0,0:16")do { eel_before_check ("check_compute_stretch (0, 0, 16, 0, 0, 0, 0)"
, "baul-icon-container.c", 9992); eel_check_string_result (check_compute_stretch
(0, 0, 16, 0, 0, 0, 0), "0,0:16"); } while (0)
;
9993 EEL_CHECK_STRING_RESULT (check_compute_stretch (0, 0, 16, 16, 16, 17, 17), "0,0:17")do { eel_before_check ("check_compute_stretch (0, 0, 16, 16, 16, 17, 17)"
, "baul-icon-container.c", 9993); eel_check_string_result (check_compute_stretch
(0, 0, 16, 16, 16, 17, 17), "0,0:17"); } while (0)
;
9994 EEL_CHECK_STRING_RESULT (check_compute_stretch (0, 0, 16, 16, 16, 17, 16), "0,0:16")do { eel_before_check ("check_compute_stretch (0, 0, 16, 16, 16, 17, 16)"
, "baul-icon-container.c", 9994); eel_check_string_result (check_compute_stretch
(0, 0, 16, 16, 16, 17, 16), "0,0:16"); } while (0)
;
9995 EEL_CHECK_STRING_RESULT (check_compute_stretch (100, 100, 64, 105, 105, 40, 40), "35,35:129")do { eel_before_check ("check_compute_stretch (100, 100, 64, 105, 105, 40, 40)"
, "baul-icon-container.c", 9995); eel_check_string_result (check_compute_stretch
(100, 100, 64, 105, 105, 40, 40), "35,35:129"); } while (0)
;
9996}
9997#endif /* ! BAUL_OMIT_SELF_CHECK */
9998
9999gboolean
10000baul_icon_container_is_layout_rtl (BaulIconContainer *container)
10001{
10002 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), 0)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return (0); } } while (0)
;
10003
10004 return container->details->layout_mode == BAUL_ICON_LAYOUT_T_B_R_L ||
10005 container->details->layout_mode == BAUL_ICON_LAYOUT_R_L_T_B;
10006}
10007
10008gboolean
10009baul_icon_container_is_layout_vertical (BaulIconContainer *container)
10010{
10011 g_return_val_if_fail (BAUL_IS_ICON_CONTAINER (container), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((container)); GType __t = (baul_icon_container_get_type()
); gboolean __r; if (!__inst) __r = (0); else if (__inst->
g_class && __inst->g_class->g_type == __t) __r =
(!(0)); else __r = g_type_check_instance_is_a (__inst, __t);
__r; })))))) { } else { g_return_if_fail_warning (((gchar*) 0
), ((const char*) (__func__)), "BAUL_IS_ICON_CONTAINER (container)"
); return ((0)); } } while (0)
;
10012
10013 return (container->details->layout_mode == BAUL_ICON_LAYOUT_T_B_L_R ||
10014 container->details->layout_mode == BAUL_ICON_LAYOUT_T_B_R_L);
10015}
10016
10017int
10018baul_icon_container_get_max_layout_lines_for_pango (BaulIconContainer *container)
10019{
10020 int limit;
10021
10022 if (baul_icon_container_get_is_desktop (container))
10023 {
10024 limit = desktop_text_ellipsis_limit;
10025 }
10026 else
10027 {
10028 limit = text_ellipsis_limits[container->details->zoom_level];
10029 }
10030
10031 if (limit <= 0)
10032 {
10033 return G_MININT(-2147483647 -1);
10034 }
10035
10036 return -limit;
10037}
10038
10039int
10040baul_icon_container_get_max_layout_lines (BaulIconContainer *container)
10041{
10042 int limit;
10043
10044 if (baul_icon_container_get_is_desktop (container))
10045 {
10046 limit = desktop_text_ellipsis_limit;
10047 }
10048 else
10049 {
10050 limit = text_ellipsis_limits[container->details->zoom_level];
10051 }
10052
10053 if (limit <= 0)
10054 {
10055 return G_MAXINT2147483647;
10056 }
10057
10058 return limit;
10059}
10060
10061void
10062baul_icon_container_begin_loading (BaulIconContainer *container)
10063{
10064 gboolean dummy;
10065
10066 if (baul_icon_container_get_store_layout_timestamps (container))
10067 {
10068 container->details->layout_timestamp = UNDEFINED_TIME((time_t) (-1));
10069 g_signal_emit (container,
10070 signals[GET_STORED_LAYOUT_TIMESTAMP], 0,
10071 NULL((void*)0), &container->details->layout_timestamp, &dummy);
10072 }
10073}
10074
10075static void
10076store_layout_timestamps_now (BaulIconContainer *container)
10077{
10078 GList *p;
10079 gboolean dummy;
10080 BaulIcon *icon = NULL((void*)0);
10081
10082 container->details->layout_timestamp = time (NULL((void*)0));
10083 g_signal_emit (container,
10084 signals[STORE_LAYOUT_TIMESTAMP], 0,
10085 NULL((void*)0), &container->details->layout_timestamp, &dummy);
10086
10087 for (p = container->details->icons; p != NULL((void*)0); p = p->next)
10088 {
10089 icon = p->data;
10090
10091 g_signal_emit (container,
10092 signals[STORE_LAYOUT_TIMESTAMP], 0,
10093 icon->data, &container->details->layout_timestamp, &dummy);
10094 }
10095}
10096
10097void
10098baul_icon_container_end_loading (BaulIconContainer *container,
10099 gboolean all_icons_added)
10100{
10101 if (all_icons_added &&
10102 baul_icon_container_get_store_layout_timestamps (container))
10103 {
10104 if (container->details->new_icons == NULL((void*)0))
10105 {
10106 store_layout_timestamps_now (container);
10107 }
10108 else
10109 {
10110 container->details->store_layout_timestamps_when_finishing_new_icons = TRUE(!(0));
10111 }
10112 }
10113}
10114
10115gboolean
10116baul_icon_container_get_store_layout_timestamps (BaulIconContainer *container)
10117{
10118 return container->details->store_layout_timestamps;
10119}
10120
10121void
10122baul_icon_container_set_store_layout_timestamps (BaulIconContainer *container,
10123 gboolean store_layout_timestamps)
10124{
10125 container->details->store_layout_timestamps = store_layout_timestamps;
10126}