Bug Summary

File:ctk/ctktreestore.c
Warning:line 429, column 29
Use of memory allocated with size zero

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 ctktreestore.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 -fcoverage-compilation-dir=/rootdir/ctk -resource-dir /usr/lib/llvm-16/lib/clang/16 -D HAVE_CONFIG_H -I . -I .. -D G_LOG_DOMAIN="Ctk" -D G_LOG_USE_STRUCTURED=1 -D CTK_VERSION="3.25.5" -D CTK_BINARY_VERSION="3.0.0" -D CTK_COMPILATION -D CTK_PRINT_BACKEND_ENABLE_UNSUPPORTED -D CTK_LIBDIR="/usr/lib" -D CTK_LOCALEDIR="/usr/share/locale" -D CTK_DATADIR="/usr/share" -D CTK_DATA_PREFIX="/usr" -D CTK_SYSCONFDIR="/usr/etc" -D CTK_HOST="x86_64-pc-linux-gnu" -D CTK_PRINT_BACKENDS="file,cups" -D X11_DATA_PREFIX="/usr" -D ISO_CODES_PREFIX="" -I .. -I ../ctk -I .. -I ../cdk -I /usr/include/glib-2.0 -I /usr/lib/x86_64-linux-gnu/glib-2.0/include -I /usr/include/sysprof-6 -D G_ENABLE_DEBUG -D G_ENABLE_CONSISTENCY_CHECKS -D GLIB_MIN_REQUIRED_VERSION=GLIB_VERSION_2_66 -D GLIB_MAX_ALLOWED_VERSION=GLIB_VERSION_2_66 -I /usr/include/pango-1.0 -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/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/atk-1.0 -I /usr/include/gdk-pixbuf-2.0 -I /usr/include/x86_64-linux-gnu -I /usr/include/webp -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/gio-unix-2.0 -I /usr/include/harfbuzz -I /usr/include/freetype2 -I /usr/include/libpng16 -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/pango-1.0 -I /usr/include/libmount -I /usr/include/blkid -I /usr/include/fribidi -I /usr/include/cairo -I /usr/include/pixman-1 -D PIC -internal-isystem /usr/lib/llvm-16/lib/clang/16/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 -fdebug-compilation-dir=/rootdir/ctk -ferror-limit 19 -fvisibility=hidden -fgnuc-version=4.2.1 -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.core.SizeofPtr -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/2024-09-19-170505-43637-1 -x c ctktreestore.c
1/* ctktreestore.c
2 * Copyright (C) 2000 Red Hat, Inc., Jonathan Blandford <jrb@redhat.com>
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
13 *
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "config.h"
19#include <string.h>
20#include <gobject/gvaluecollector.h>
21#include "ctktreemodel.h"
22#include "ctktreestore.h"
23#include "ctktreedatalist.h"
24#include "ctktreednd.h"
25#include "ctkbuildable.h"
26#include "ctkbuilderprivate.h"
27#include "ctkdebug.h"
28#include "ctkintl.h"
29
30
31/**
32 * SECTION:ctktreestore
33 * @Short_description: A tree-like data structure that can be used with the CtkTreeView
34 * @Title: CtkTreeStore
35 * @See_also: #CtkTreeModel
36 *
37 * The #CtkTreeStore object is a list model for use with a #CtkTreeView
38 * widget. It implements the #CtkTreeModel interface, and consequentially,
39 * can use all of the methods available there. It also implements the
40 * #CtkTreeSortable interface so it can be sorted by the view. Finally,
41 * it also implements the tree
42 * [drag and drop][ctk3-CtkTreeView-drag-and-drop]
43 * interfaces.
44 *
45 * # CtkTreeStore as CtkBuildable
46 *
47 * The CtkTreeStore implementation of the #CtkBuildable interface allows
48 * to specify the model columns with a <columns> element that may contain
49 * multiple <column> elements, each specifying one model column. The “type”
50 * attribute specifies the data type for the column.
51 *
52 * An example of a UI Definition fragment for a tree store:
53 * |[
54 * <object class="CtkTreeStore">
55 * <columns>
56 * <column type="gchararray"/>
57 * <column type="gchararray"/>
58 * <column type="gint"/>
59 * </columns>
60 * </object>
61 * ]|
62 */
63
64struct _CtkTreeStorePrivate
65{
66 gint stamp;
67 CtkSortType order;
68 gpointer root;
69 gpointer last;
70 gint n_columns;
71 gint sort_column_id;
72 GList *sort_list;
73 GType *column_headers;
74 CtkTreeIterCompareFunc default_sort_func;
75 gpointer default_sort_data;
76 GDestroyNotify default_sort_destroy;
77 guint columns_dirty : 1;
78};
79
80
81#define G_NODE(node)((GNode *)node) ((GNode *)node)
82#define CTK_TREE_STORE_IS_SORTED(tree)(((CtkTreeStore*)(tree))->priv->sort_column_id != (-2)) (((CtkTreeStore*)(tree))->priv->sort_column_id != CTK_TREE_SORTABLE_UNSORTED_SORT_COLUMN_ID(-2))
83#define VALID_ITER(iter, tree_store)((iter)!= ((void*)0) && (iter)->user_data != ((void
*)0) && ((CtkTreeStore*)(tree_store))->priv->stamp
== (iter)->stamp)
((iter)!= NULL((void*)0) && (iter)->user_data != NULL((void*)0) && ((CtkTreeStore*)(tree_store))->priv->stamp == (iter)->stamp)
84
85static void ctk_tree_store_tree_model_init (CtkTreeModelIface *iface);
86static void ctk_tree_store_drag_source_init(CtkTreeDragSourceIface *iface);
87static void ctk_tree_store_drag_dest_init (CtkTreeDragDestIface *iface);
88static void ctk_tree_store_sortable_init (CtkTreeSortableIface *iface);
89static void ctk_tree_store_buildable_init (CtkBuildableIface *iface);
90static void ctk_tree_store_finalize (GObject *object);
91static CtkTreeModelFlags ctk_tree_store_get_flags (CtkTreeModel *tree_model);
92static gint ctk_tree_store_get_n_columns (CtkTreeModel *tree_model);
93static GType ctk_tree_store_get_column_type (CtkTreeModel *tree_model,
94 gint index);
95static gboolean ctk_tree_store_get_iter (CtkTreeModel *tree_model,
96 CtkTreeIter *iter,
97 CtkTreePath *path);
98static CtkTreePath *ctk_tree_store_get_path (CtkTreeModel *tree_model,
99 CtkTreeIter *iter);
100static void ctk_tree_store_get_value (CtkTreeModel *tree_model,
101 CtkTreeIter *iter,
102 gint column,
103 GValue *value);
104static gboolean ctk_tree_store_iter_next (CtkTreeModel *tree_model,
105 CtkTreeIter *iter);
106static gboolean ctk_tree_store_iter_previous (CtkTreeModel *tree_model,
107 CtkTreeIter *iter);
108static gboolean ctk_tree_store_iter_children (CtkTreeModel *tree_model,
109 CtkTreeIter *iter,
110 CtkTreeIter *parent);
111static gboolean ctk_tree_store_iter_has_child (CtkTreeModel *tree_model,
112 CtkTreeIter *iter);
113static gint ctk_tree_store_iter_n_children (CtkTreeModel *tree_model,
114 CtkTreeIter *iter);
115static gboolean ctk_tree_store_iter_nth_child (CtkTreeModel *tree_model,
116 CtkTreeIter *iter,
117 CtkTreeIter *parent,
118 gint n);
119static gboolean ctk_tree_store_iter_parent (CtkTreeModel *tree_model,
120 CtkTreeIter *iter,
121 CtkTreeIter *child);
122
123
124static void ctk_tree_store_set_n_columns (CtkTreeStore *tree_store,
125 gint n_columns);
126static void ctk_tree_store_set_column_type (CtkTreeStore *tree_store,
127 gint column,
128 GType type);
129
130static void ctk_tree_store_increment_stamp (CtkTreeStore *tree_store);
131
132
133/* DND interfaces */
134static gboolean real_ctk_tree_store_row_draggable (CtkTreeDragSource *drag_source,
135 CtkTreePath *path);
136static gboolean ctk_tree_store_drag_data_delete (CtkTreeDragSource *drag_source,
137 CtkTreePath *path);
138static gboolean ctk_tree_store_drag_data_get (CtkTreeDragSource *drag_source,
139 CtkTreePath *path,
140 CtkSelectionData *selection_data);
141static gboolean ctk_tree_store_drag_data_received (CtkTreeDragDest *drag_dest,
142 CtkTreePath *dest,
143 CtkSelectionData *selection_data);
144static gboolean ctk_tree_store_row_drop_possible (CtkTreeDragDest *drag_dest,
145 CtkTreePath *dest_path,
146 CtkSelectionData *selection_data);
147
148/* Sortable Interfaces */
149
150static void ctk_tree_store_sort (CtkTreeStore *tree_store);
151static void ctk_tree_store_sort_iter_changed (CtkTreeStore *tree_store,
152 CtkTreeIter *iter,
153 gint column,
154 gboolean emit_signal);
155static gboolean ctk_tree_store_get_sort_column_id (CtkTreeSortable *sortable,
156 gint *sort_column_id,
157 CtkSortType *order);
158static void ctk_tree_store_set_sort_column_id (CtkTreeSortable *sortable,
159 gint sort_column_id,
160 CtkSortType order);
161static void ctk_tree_store_set_sort_func (CtkTreeSortable *sortable,
162 gint sort_column_id,
163 CtkTreeIterCompareFunc func,
164 gpointer data,
165 GDestroyNotify destroy);
166static void ctk_tree_store_set_default_sort_func (CtkTreeSortable *sortable,
167 CtkTreeIterCompareFunc func,
168 gpointer data,
169 GDestroyNotify destroy);
170static gboolean ctk_tree_store_has_default_sort_func (CtkTreeSortable *sortable);
171
172
173/* buildable */
174
175static gboolean ctk_tree_store_buildable_custom_tag_start (CtkBuildable *buildable,
176 CtkBuilder *builder,
177 GObject *child,
178 const gchar *tagname,
179 GMarkupParser *parser,
180 gpointer *data);
181static void ctk_tree_store_buildable_custom_finished (CtkBuildable *buildable,
182 CtkBuilder *builder,
183 GObject *child,
184 const gchar *tagname,
185 gpointer user_data);
186
187static void ctk_tree_store_move (CtkTreeStore *tree_store,
188 CtkTreeIter *iter,
189 CtkTreeIter *position,
190 gboolean before);
191
192
193#ifdef G_ENABLE_DEBUG1
194static void validate_gnode (GNode *node);
195
196static inline void
197validate_tree (CtkTreeStore *tree_store)
198{
199 if (CTK_DEBUG_CHECK (TREE)(ctk_get_debug_flags () & CTK_DEBUG_TREE))
200 {
201 g_assert (G_NODE (tree_store->priv->root)->parent == NULL)do { if (((GNode *)tree_store->priv->root)->parent ==
((void*)0)) ; else g_assertion_message_expr ("Ctk", "ctktreestore.c"
, 201, ((const char*) (__func__)), "G_NODE (tree_store->priv->root)->parent == NULL"
); } while (0)
;
202 validate_gnode (G_NODE (tree_store->priv->root)((GNode *)tree_store->priv->root));
203 }
204}
205#else
206#define validate_tree(store)
207#endif
208
209G_DEFINE_TYPE_WITH_CODE (CtkTreeStore, ctk_tree_store, G_TYPE_OBJECT,static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
210 G_ADD_PRIVATE (CtkTreeStore)static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
211 G_IMPLEMENT_INTERFACE (CTK_TYPE_TREE_MODEL,static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
212 ctk_tree_store_tree_model_init)static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
213 G_IMPLEMENT_INTERFACE (CTK_TYPE_TREE_DRAG_SOURCE,static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
214 ctk_tree_store_drag_source_init)static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
215 G_IMPLEMENT_INTERFACE (CTK_TYPE_TREE_DRAG_DEST,static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
216 ctk_tree_store_drag_dest_init)static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
217 G_IMPLEMENT_INTERFACE (CTK_TYPE_TREE_SORTABLE,static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
218 ctk_tree_store_sortable_init)static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
219 G_IMPLEMENT_INTERFACE (CTK_TYPE_BUILDABLE,static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
220 ctk_tree_store_buildable_init))static void ctk_tree_store_init (CtkTreeStore *self); static void
ctk_tree_store_class_init (CtkTreeStoreClass *klass); static
GType ctk_tree_store_get_type_once (void); static gpointer ctk_tree_store_parent_class
= ((void*)0); static gint CtkTreeStore_private_offset; static
void ctk_tree_store_class_intern_init (gpointer klass) { ctk_tree_store_parent_class
= g_type_class_peek_parent (klass); if (CtkTreeStore_private_offset
!= 0) g_type_class_adjust_private_offset (klass, &CtkTreeStore_private_offset
); ctk_tree_store_class_init ((CtkTreeStoreClass*) klass); } __attribute__
((__unused__)) static inline gpointer ctk_tree_store_get_instance_private
(CtkTreeStore *self) { return (((gpointer) ((guint8*) (self)
+ (glong) (CtkTreeStore_private_offset)))); } GType ctk_tree_store_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
= ctk_tree_store_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 ctk_tree_store_get_type_once (void
) { GType g_define_type_id = g_type_register_static_simple ((
(GType) ((20) << (2))), g_intern_static_string ("CtkTreeStore"
), sizeof (CtkTreeStoreClass), (GClassInitFunc)(void (*)(void
)) ctk_tree_store_class_intern_init, sizeof (CtkTreeStore), (
GInstanceInitFunc)(void (*)(void)) ctk_tree_store_init, (GTypeFlags
) 0); { {{ CtkTreeStore_private_offset = g_type_add_instance_private
(g_define_type_id, sizeof (CtkTreeStorePrivate)); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_tree_model_init, ((void*)0), ((void*)0
) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_model_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_source_init, ((void*)0), ((void*)
0) }; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_source_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_drag_dest_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_tree_drag_dest_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_sortable_init, ((void*)0), ((void*)0) }
; g_type_add_interface_static (g_define_type_id, (ctk_tree_sortable_get_type
()), &g_implement_interface_info); } { const GInterfaceInfo
g_implement_interface_info = { (GInterfaceInitFunc)(void (*)
(void)) ctk_tree_store_buildable_init, ((void*)0), ((void*)0)
}; g_type_add_interface_static (g_define_type_id, (ctk_buildable_get_type
()), &g_implement_interface_info); };} } return g_define_type_id
; }
221
222static void
223ctk_tree_store_class_init (CtkTreeStoreClass *class)
224{
225 GObjectClass *object_class;
226
227 object_class = (GObjectClass *) class;
228
229 object_class->finalize = ctk_tree_store_finalize;
230}
231
232static void
233ctk_tree_store_tree_model_init (CtkTreeModelIface *iface)
234{
235 iface->get_flags = ctk_tree_store_get_flags;
236 iface->get_n_columns = ctk_tree_store_get_n_columns;
237 iface->get_column_type = ctk_tree_store_get_column_type;
238 iface->get_iter = ctk_tree_store_get_iter;
239 iface->get_path = ctk_tree_store_get_path;
240 iface->get_value = ctk_tree_store_get_value;
241 iface->iter_next = ctk_tree_store_iter_next;
242 iface->iter_previous = ctk_tree_store_iter_previous;
243 iface->iter_children = ctk_tree_store_iter_children;
244 iface->iter_has_child = ctk_tree_store_iter_has_child;
245 iface->iter_n_children = ctk_tree_store_iter_n_children;
246 iface->iter_nth_child = ctk_tree_store_iter_nth_child;
247 iface->iter_parent = ctk_tree_store_iter_parent;
248}
249
250static void
251ctk_tree_store_drag_source_init (CtkTreeDragSourceIface *iface)
252{
253 iface->row_draggable = real_ctk_tree_store_row_draggable;
254 iface->drag_data_delete = ctk_tree_store_drag_data_delete;
255 iface->drag_data_get = ctk_tree_store_drag_data_get;
256}
257
258static void
259ctk_tree_store_drag_dest_init (CtkTreeDragDestIface *iface)
260{
261 iface->drag_data_received = ctk_tree_store_drag_data_received;
262 iface->row_drop_possible = ctk_tree_store_row_drop_possible;
263}
264
265static void
266ctk_tree_store_sortable_init (CtkTreeSortableIface *iface)
267{
268 iface->get_sort_column_id = ctk_tree_store_get_sort_column_id;
269 iface->set_sort_column_id = ctk_tree_store_set_sort_column_id;
270 iface->set_sort_func = ctk_tree_store_set_sort_func;
271 iface->set_default_sort_func = ctk_tree_store_set_default_sort_func;
272 iface->has_default_sort_func = ctk_tree_store_has_default_sort_func;
273}
274
275void
276ctk_tree_store_buildable_init (CtkBuildableIface *iface)
277{
278 iface->custom_tag_start = ctk_tree_store_buildable_custom_tag_start;
279 iface->custom_finished = ctk_tree_store_buildable_custom_finished;
280}
281
282static void
283ctk_tree_store_init (CtkTreeStore *tree_store)
284{
285 CtkTreeStorePrivate *priv;
286
287 priv = ctk_tree_store_get_instance_private (tree_store);
288 tree_store->priv = priv;
289 priv->root = g_node_new (NULL((void*)0));
290 /* While the odds are against us getting 0... */
291 do
292 {
293 priv->stamp = g_random_int ();
294 }
295 while (priv->stamp == 0);
296
297 priv->sort_list = NULL((void*)0);
298 priv->sort_column_id = CTK_TREE_SORTABLE_UNSORTED_SORT_COLUMN_ID(-2);
299 priv->columns_dirty = FALSE(0);
300}
301
302/**
303 * ctk_tree_store_new:
304 * @n_columns: number of columns in the tree store
305 * @...: all #GType types for the columns, from first to last
306 *
307 * Creates a new tree store as with @n_columns columns each of the types passed
308 * in. Note that only types derived from standard GObject fundamental types
309 * are supported.
310 *
311 * As an example, `ctk_tree_store_new (3, G_TYPE_INT, G_TYPE_STRING,
312 * GDK_TYPE_PIXBUF);` will create a new #CtkTreeStore with three columns, of type
313 * #gint, #gchararray, and #GdkPixbuf respectively.
314 *
315 * Returns: a new #CtkTreeStore
316 **/
317CtkTreeStore *
318ctk_tree_store_new (gint n_columns,
319 ...)
320{
321 CtkTreeStore *retval;
322 va_list args;
323 gint i;
324
325 g_return_val_if_fail (n_columns > 0, NULL)do { if ((n_columns > 0)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "n_columns > 0"); return
(((void*)0)); } } while (0)
;
326
327 retval = g_object_new (CTK_TYPE_TREE_STORE(ctk_tree_store_get_type ()), NULL((void*)0));
328 ctk_tree_store_set_n_columns (retval, n_columns);
329
330 va_start (args, n_columns)__builtin_va_start(args, n_columns);
331
332 for (i = 0; i < n_columns; i++)
333 {
334 GType type = va_arg (args, GType)__builtin_va_arg(args, GType);
335 if (! _ctk_tree_data_list_check_type (type))
336 {
337 g_warning ("%s: Invalid type %s", G_STRLOC"ctktreestore.c" ":" "337", g_type_name (type));
338 g_object_unref (retval);
339 va_end (args)__builtin_va_end(args);
340 return NULL((void*)0);
341 }
342 ctk_tree_store_set_column_type (retval, i, type);
343 }
344 va_end (args)__builtin_va_end(args);
345
346 return retval;
347}
348/**
349 * ctk_tree_store_newv: (rename-to ctk_tree_store_new)
350 * @n_columns: number of columns in the tree store
351 * @types: (array length=n_columns): an array of #GType types for the columns, from first to last
352 *
353 * Non vararg creation function. Used primarily by language bindings.
354 *
355 * Returns: (transfer full): a new #CtkTreeStore
356 **/
357CtkTreeStore *
358ctk_tree_store_newv (gint n_columns,
359 GType *types)
360{
361 CtkTreeStore *retval;
362 gint i;
363
364 g_return_val_if_fail (n_columns > 0, NULL)do { if ((n_columns > 0)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "n_columns > 0"); return
(((void*)0)); } } while (0)
;
365
366 retval = g_object_new (CTK_TYPE_TREE_STORE(ctk_tree_store_get_type ()), NULL((void*)0));
367 ctk_tree_store_set_n_columns (retval, n_columns);
368
369 for (i = 0; i < n_columns; i++)
370 {
371 if (! _ctk_tree_data_list_check_type (types[i]))
372 {
373 g_warning ("%s: Invalid type %s", G_STRLOC"ctktreestore.c" ":" "373", g_type_name (types[i]));
374 g_object_unref (retval);
375 return NULL((void*)0);
376 }
377 ctk_tree_store_set_column_type (retval, i, types[i]);
378 }
379
380 return retval;
381}
382
383
384/**
385 * ctk_tree_store_set_column_types:
386 * @tree_store: A #CtkTreeStore
387 * @n_columns: Number of columns for the tree store
388 * @types: (array length=n_columns): An array of #GType types, one for each column
389 *
390 * This function is meant primarily for #GObjects that inherit from
391 * #CtkTreeStore, and should only be used when constructing a new
392 * #CtkTreeStore. It will not function after a row has been added,
393 * or a method on the #CtkTreeModel interface is called.
394 **/
395void
396ctk_tree_store_set_column_types (CtkTreeStore *tree_store,
397 gint n_columns,
398 GType *types)
399{
400 gint i;
401
402 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
7
Assuming '__inst' is non-null
8
Taking false branch
9
Assuming field 'g_class' is null
10
Assuming the condition is true
11
Taking true branch
12
Loop condition is false. Exiting loop
403 g_return_if_fail (tree_store->priv->columns_dirty == 0)do { if ((tree_store->priv->columns_dirty == 0)) { } else
{ g_return_if_fail_warning ("Ctk", ((const char*) (__func__)
), "tree_store->priv->columns_dirty == 0"); return; } }
while (0)
;
13
Assuming field 'columns_dirty' is equal to 0
14
Taking true branch
15
Loop condition is false. Exiting loop
404
405 ctk_tree_store_set_n_columns (tree_store, n_columns);
16
Calling 'ctk_tree_store_set_n_columns'
406 for (i = 0; i < n_columns; i++)
407 {
408 if (! _ctk_tree_data_list_check_type (types[i]))
409 {
410 g_warning ("%s: Invalid type %s", G_STRLOC"ctktreestore.c" ":" "410", g_type_name (types[i]));
411 continue;
412 }
413 ctk_tree_store_set_column_type (tree_store, i, types[i]);
414 }
415}
416
417static void
418ctk_tree_store_set_n_columns (CtkTreeStore *tree_store,
419 gint n_columns)
420{
421 CtkTreeStorePrivate *priv = tree_store->priv;
422 int i;
423
424 if (priv->n_columns == n_columns)
17
Assuming 'n_columns' is not equal to field 'n_columns'
18
Taking false branch
425 return;
426
427 priv->column_headers = g_renew (GType, priv->column_headers, n_columns)((GType *) g_realloc_n (priv->column_headers, (n_columns),
sizeof (GType)))
;
428 for (i = priv->n_columns; i < n_columns; i++)
19
Assuming 'i' is < 'n_columns'
20
Loop condition is true. Entering loop body
429 priv->column_headers[i] = G_TYPE_INVALID((GType) ((0) << (2)));
21
Use of memory allocated with size zero
430 priv->n_columns = n_columns;
431
432 if (priv->sort_list)
433 _ctk_tree_data_list_header_free (priv->sort_list);
434
435 priv->sort_list = _ctk_tree_data_list_header_new (n_columns, priv->column_headers);
436}
437
438/**
439 * ctk_tree_store_set_column_type:
440 * @tree_store: a #CtkTreeStore
441 * @column: column number
442 * @type: type of the data to be stored in @column
443 *
444 * Supported types include: %G_TYPE_UINT, %G_TYPE_INT, %G_TYPE_UCHAR,
445 * %G_TYPE_CHAR, %G_TYPE_BOOLEAN, %G_TYPE_POINTER, %G_TYPE_FLOAT,
446 * %G_TYPE_DOUBLE, %G_TYPE_STRING, %G_TYPE_OBJECT, and %G_TYPE_BOXED, along with
447 * subclasses of those types such as %GDK_TYPE_PIXBUF.
448 *
449 **/
450static void
451ctk_tree_store_set_column_type (CtkTreeStore *tree_store,
452 gint column,
453 GType type)
454{
455 CtkTreeStorePrivate *priv = tree_store->priv;
456
457 if (!_ctk_tree_data_list_check_type (type))
458 {
459 g_warning ("%s: Invalid type %s", G_STRLOC"ctktreestore.c" ":" "459", g_type_name (type));
460 return;
461 }
462 priv->column_headers[column] = type;
463}
464
465static gboolean
466node_free (GNode *node, gpointer data)
467{
468 if (node->data)
469 _ctk_tree_data_list_free (node->data, (GType*)data);
470 node->data = NULL((void*)0);
471
472 return FALSE(0);
473}
474
475static void
476ctk_tree_store_finalize (GObject *object)
477{
478 CtkTreeStore *tree_store = CTK_TREE_STORE (object)((((CtkTreeStore*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((object)), ((ctk_tree_store_get_type ()))))))
;
479 CtkTreeStorePrivate *priv = tree_store->priv;
480
481 g_node_traverse (priv->root, G_POST_ORDER, G_TRAVERSE_ALL, -1,
482 node_free, priv->column_headers);
483 g_node_destroy (priv->root);
484 _ctk_tree_data_list_header_free (priv->sort_list);
485 g_free (priv->column_headers);
486
487 if (priv->default_sort_destroy)
488 {
489 GDestroyNotify d = priv->default_sort_destroy;
490
491 priv->default_sort_destroy = NULL((void*)0);
492 d (priv->default_sort_data);
493 priv->default_sort_data = NULL((void*)0);
494 }
495
496 /* must chain up */
497 G_OBJECT_CLASS (ctk_tree_store_parent_class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass
*) ((ctk_tree_store_parent_class)), (((GType) ((20) << (
2))))))))
->finalize (object);
498}
499
500/* fulfill the CtkTreeModel requirements */
501/* NOTE: CtkTreeStore::root is a GNode, that acts as the parent node. However,
502 * it is not visible to the tree or to the user., and the path “0” refers to the
503 * first child of CtkTreeStore::root.
504 */
505
506
507static CtkTreeModelFlags
508ctk_tree_store_get_flags (CtkTreeModel *tree_model G_GNUC_UNUSED__attribute__ ((__unused__)))
509{
510 return CTK_TREE_MODEL_ITERS_PERSIST;
511}
512
513static gint
514ctk_tree_store_get_n_columns (CtkTreeModel *tree_model)
515{
516 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
517 CtkTreeStorePrivate *priv = tree_store->priv;
518
519 priv->columns_dirty = TRUE(!(0));
520
521 return priv->n_columns;
522}
523
524static GType
525ctk_tree_store_get_column_type (CtkTreeModel *tree_model,
526 gint index)
527{
528 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
529 CtkTreeStorePrivate *priv = tree_store->priv;
530
531 g_return_val_if_fail (index < priv->n_columns, G_TYPE_INVALID)do { if ((index < priv->n_columns)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "index < priv->n_columns"
); return (((GType) ((0) << (2)))); } } while (0)
;
532
533 priv->columns_dirty = TRUE(!(0));
534
535 return priv->column_headers[index];
536}
537
538static gboolean
539ctk_tree_store_get_iter (CtkTreeModel *tree_model,
540 CtkTreeIter *iter,
541 CtkTreePath *path)
542{
543 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
544 CtkTreeStorePrivate *priv = tree_store->priv;
545 CtkTreeIter parent;
546 gint *indices;
547 gint depth, i;
548
549 priv->columns_dirty = TRUE(!(0));
550
551 indices = ctk_tree_path_get_indices (path);
552 depth = ctk_tree_path_get_depth (path);
553
554 g_return_val_if_fail (depth > 0, FALSE)do { if ((depth > 0)) { } else { g_return_if_fail_warning (
"Ctk", ((const char*) (__func__)), "depth > 0"); return ((
0)); } } while (0)
;
555
556 parent.stamp = priv->stamp;
557 parent.user_data = priv->root;
558
559 if (!ctk_tree_store_iter_nth_child (tree_model, iter, &parent, indices[0]))
560 {
561 iter->stamp = 0;
562 return FALSE(0);
563 }
564
565 for (i = 1; i < depth; i++)
566 {
567 parent = *iter;
568 if (!ctk_tree_store_iter_nth_child (tree_model, iter, &parent, indices[i]))
569 {
570 iter->stamp = 0;
571 return FALSE(0);
572 }
573 }
574
575 return TRUE(!(0));
576}
577
578static CtkTreePath *
579ctk_tree_store_get_path (CtkTreeModel *tree_model,
580 CtkTreeIter *iter)
581{
582 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
583 CtkTreeStorePrivate *priv = tree_store->priv;
584 CtkTreePath *retval;
585 GNode *tmp_node;
586 gint i = 0;
587
588 g_return_val_if_fail (iter->user_data != NULL, NULL)do { if ((iter->user_data != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->user_data != NULL"
); return (((void*)0)); } } while (0)
;
589 g_return_val_if_fail (iter->stamp == priv->stamp, NULL)do { if ((iter->stamp == priv->stamp)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->stamp == priv->stamp"
); return (((void*)0)); } } while (0)
;
590
591 validate_tree (tree_store);
592
593 if (G_NODE (iter->user_data)((GNode *)iter->user_data)->parent == NULL((void*)0) &&
594 G_NODE (iter->user_data)((GNode *)iter->user_data) == priv->root)
595 return ctk_tree_path_new ();
596 g_assert (G_NODE (iter->user_data)->parent != NULL)do { if (((GNode *)iter->user_data)->parent != ((void*)
0)) ; else g_assertion_message_expr ("Ctk", "ctktreestore.c",
596, ((const char*) (__func__)), "G_NODE (iter->user_data)->parent != NULL"
); } while (0)
;
597
598 if (G_NODE (iter->user_data)((GNode *)iter->user_data)->parent == G_NODE (priv->root)((GNode *)priv->root))
599 {
600 retval = ctk_tree_path_new ();
601 tmp_node = G_NODE (priv->root)((GNode *)priv->root)->children;
602 }
603 else
604 {
605 CtkTreeIter tmp_iter = *iter;
606
607 tmp_iter.user_data = G_NODE (iter->user_data)((GNode *)iter->user_data)->parent;
608
609 retval = ctk_tree_store_get_path (tree_model, &tmp_iter);
610 tmp_node = G_NODE (iter->user_data)((GNode *)iter->user_data)->parent->children;
611 }
612
613 if (retval == NULL((void*)0))
614 return NULL((void*)0);
615
616 if (tmp_node == NULL((void*)0))
617 {
618 ctk_tree_path_free (retval);
619 return NULL((void*)0);
620 }
621
622 for (; tmp_node; tmp_node = tmp_node->next)
623 {
624 if (tmp_node == G_NODE (iter->user_data)((GNode *)iter->user_data))
625 break;
626 i++;
627 }
628
629 if (tmp_node == NULL((void*)0))
630 {
631 /* We couldn't find node, meaning it's prolly not ours */
632 /* Perhaps I should do a g_return_if_fail here. */
633 ctk_tree_path_free (retval);
634 return NULL((void*)0);
635 }
636
637 ctk_tree_path_append_index (retval, i);
638
639 return retval;
640}
641
642
643static void
644ctk_tree_store_get_value (CtkTreeModel *tree_model,
645 CtkTreeIter *iter,
646 gint column,
647 GValue *value)
648{
649 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
650 CtkTreeStorePrivate *priv = tree_store->priv;
651 CtkTreeDataList *list;
652 gint tmp_column = column;
653
654 g_return_if_fail (column < priv->n_columns)do { if ((column < priv->n_columns)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "column < priv->n_columns"
); return; } } while (0)
;
655 g_return_if_fail (VALID_ITER (iter, tree_store))do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return; } } while (0)
;
656
657 list = G_NODE (iter->user_data)((GNode *)iter->user_data)->data;
658
659 while (tmp_column-- > 0 && list)
660 list = list->next;
661
662 if (list)
663 {
664 _ctk_tree_data_list_node_to_value (list,
665 priv->column_headers[column],
666 value);
667 }
668 else
669 {
670 /* We want to return an initialized but empty (default) value */
671 g_value_init (value, priv->column_headers[column]);
672 }
673}
674
675static gboolean
676ctk_tree_store_iter_next (CtkTreeModel *tree_model,
677 CtkTreeIter *iter)
678{
679 g_return_val_if_fail (iter->user_data != NULL, FALSE)do { if ((iter->user_data != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->user_data != NULL"
); return ((0)); } } while (0)
;
680 g_return_val_if_fail (iter->stamp == CTK_TREE_STORE (tree_model)->priv->stamp, FALSE)do { if ((iter->stamp == ((((CtkTreeStore*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((tree_model)), ((ctk_tree_store_get_type (
)))))))->priv->stamp)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->stamp == CTK_TREE_STORE (tree_model)->priv->stamp"
); return ((0)); } } while (0)
;
681
682 if (G_NODE (iter->user_data)((GNode *)iter->user_data)->next == NULL((void*)0))
683 {
684 iter->stamp = 0;
685 return FALSE(0);
686 }
687
688 iter->user_data = G_NODE (iter->user_data)((GNode *)iter->user_data)->next;
689
690 return TRUE(!(0));
691}
692
693static gboolean
694ctk_tree_store_iter_previous (CtkTreeModel *tree_model,
695 CtkTreeIter *iter)
696{
697 g_return_val_if_fail (iter->user_data != NULL, FALSE)do { if ((iter->user_data != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->user_data != NULL"
); return ((0)); } } while (0)
;
698 g_return_val_if_fail (iter->stamp == CTK_TREE_STORE (tree_model)->priv->stamp, FALSE)do { if ((iter->stamp == ((((CtkTreeStore*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((tree_model)), ((ctk_tree_store_get_type (
)))))))->priv->stamp)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->stamp == CTK_TREE_STORE (tree_model)->priv->stamp"
); return ((0)); } } while (0)
;
699
700 if (G_NODE (iter->user_data)((GNode *)iter->user_data)->prev == NULL((void*)0))
701 {
702 iter->stamp = 0;
703 return FALSE(0);
704 }
705
706 iter->user_data = G_NODE (iter->user_data)((GNode *)iter->user_data)->prev;
707
708 return TRUE(!(0));
709}
710
711static gboolean
712ctk_tree_store_iter_children (CtkTreeModel *tree_model,
713 CtkTreeIter *iter,
714 CtkTreeIter *parent)
715{
716 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
717 CtkTreeStorePrivate *priv = tree_store->priv;
718 GNode *children;
719
720 if (parent)
721 g_return_val_if_fail (VALID_ITER (parent, tree_store), FALSE)do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return ((0)); } } while (0)
;
722
723 if (parent)
724 children = G_NODE (parent->user_data)((GNode *)parent->user_data)->children;
725 else
726 children = G_NODE (priv->root)((GNode *)priv->root)->children;
727
728 if (children)
729 {
730 iter->stamp = priv->stamp;
731 iter->user_data = children;
732 return TRUE(!(0));
733 }
734 else
735 {
736 iter->stamp = 0;
737 return FALSE(0);
738 }
739}
740
741static gboolean
742ctk_tree_store_iter_has_child (CtkTreeModel *tree_model,
743 CtkTreeIter *iter)
744{
745 g_return_val_if_fail (iter->user_data != NULL, FALSE)do { if ((iter->user_data != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter->user_data != NULL"
); return ((0)); } } while (0)
;
746 g_return_val_if_fail (VALID_ITER (iter, tree_model), FALSE)do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_model))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_model)"
); return ((0)); } } while (0)
;
747
748 return G_NODE (iter->user_data)((GNode *)iter->user_data)->children != NULL((void*)0);
749}
750
751static gint
752ctk_tree_store_iter_n_children (CtkTreeModel *tree_model,
753 CtkTreeIter *iter)
754{
755 GNode *node;
756 gint i = 0;
757
758 g_return_val_if_fail (iter == NULL || iter->user_data != NULL, 0)do { if ((iter == ((void*)0) || iter->user_data != ((void*
)0))) { } else { g_return_if_fail_warning ("Ctk", ((const char
*) (__func__)), "iter == NULL || iter->user_data != NULL")
; return (0); } } while (0)
;
759
760 if (iter == NULL((void*)0))
761 node = G_NODE (CTK_TREE_STORE (tree_model)->priv->root)((GNode *)((((CtkTreeStore*) (void *) g_type_check_instance_cast
((GTypeInstance*) ((tree_model)), ((ctk_tree_store_get_type (
)))))))->priv->root)
->children;
762 else
763 node = G_NODE (iter->user_data)((GNode *)iter->user_data)->children;
764
765 while (node)
766 {
767 i++;
768 node = node->next;
769 }
770
771 return i;
772}
773
774static gboolean
775ctk_tree_store_iter_nth_child (CtkTreeModel *tree_model,
776 CtkTreeIter *iter,
777 CtkTreeIter *parent,
778 gint n)
779{
780 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
781 CtkTreeStorePrivate *priv = tree_store->priv;
782 GNode *parent_node;
783 GNode *child;
784
785 g_return_val_if_fail (parent == NULL || parent->user_data != NULL, FALSE)do { if ((parent == ((void*)0) || parent->user_data != ((void
*)0))) { } else { g_return_if_fail_warning ("Ctk", ((const char
*) (__func__)), "parent == NULL || parent->user_data != NULL"
); return ((0)); } } while (0)
;
786
787 if (parent == NULL((void*)0))
788 parent_node = priv->root;
789 else
790 parent_node = parent->user_data;
791
792 child = g_node_nth_child (parent_node, n);
793
794 if (child)
795 {
796 iter->user_data = child;
797 iter->stamp = priv->stamp;
798 return TRUE(!(0));
799 }
800 else
801 {
802 iter->stamp = 0;
803 return FALSE(0);
804 }
805}
806
807static gboolean
808ctk_tree_store_iter_parent (CtkTreeModel *tree_model,
809 CtkTreeIter *iter,
810 CtkTreeIter *child)
811{
812 CtkTreeStore *tree_store = (CtkTreeStore *) tree_model;
813 CtkTreeStorePrivate *priv = tree_store->priv;
814 GNode *parent;
815
816 g_return_val_if_fail (iter != NULL, FALSE)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return (
(0)); } } while (0)
;
817 g_return_val_if_fail (VALID_ITER (child, tree_store), FALSE)do { if ((((child)!= ((void*)0) && (child)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (child)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (child, tree_store)"
); return ((0)); } } while (0)
;
818
819 parent = G_NODE (child->user_data)((GNode *)child->user_data)->parent;
820
821 g_assert (parent != NULL)do { if (parent != ((void*)0)) ; else g_assertion_message_expr
("Ctk", "ctktreestore.c", 821, ((const char*) (__func__)), "parent != NULL"
); } while (0)
;
822
823 if (parent != priv->root)
824 {
825 iter->user_data = parent;
826 iter->stamp = priv->stamp;
827 return TRUE(!(0));
828 }
829 else
830 {
831 iter->stamp = 0;
832 return FALSE(0);
833 }
834}
835
836
837/* Does not emit a signal */
838static gboolean
839ctk_tree_store_real_set_value (CtkTreeStore *tree_store,
840 CtkTreeIter *iter,
841 gint column,
842 GValue *value,
843 gboolean sort)
844{
845 CtkTreeStorePrivate *priv = tree_store->priv;
846 CtkTreeDataList *list;
847 CtkTreeDataList *prev;
848 gint old_column = column;
849 GValue real_value = G_VALUE_INIT{ 0, { { 0 } } };
850 gboolean converted = FALSE(0);
851 gboolean retval = FALSE(0);
852
853 if (! g_type_is_a (G_VALUE_TYPE (value), priv->column_headers[column])(((((GValue*) (value))->g_type)) == (priv->column_headers
[column]) || (g_type_is_a) (((((GValue*) (value))->g_type)
), (priv->column_headers[column])))
)
854 {
855 if (! (g_value_type_transformable (G_VALUE_TYPE (value)(((GValue*) (value))->g_type), priv->column_headers[column])))
856 {
857 g_warning ("%s: Unable to convert from %s to %s",
858 G_STRLOC"ctktreestore.c" ":" "858",
859 g_type_name (G_VALUE_TYPE (value)(((GValue*) (value))->g_type)),
860 g_type_name (priv->column_headers[column]));
861 return retval;
862 }
863
864 g_value_init (&real_value, priv->column_headers[column]);
865 if (!g_value_transform (value, &real_value))
866 {
867 g_warning ("%s: Unable to make conversion from %s to %s",
868 G_STRLOC"ctktreestore.c" ":" "868",
869 g_type_name (G_VALUE_TYPE (value)(((GValue*) (value))->g_type)),
870 g_type_name (priv->column_headers[column]));
871 g_value_unset (&real_value);
872 return retval;
873 }
874 converted = TRUE(!(0));
875 }
876
877 prev = list = G_NODE (iter->user_data)((GNode *)iter->user_data)->data;
878
879 while (list != NULL((void*)0))
880 {
881 if (column == 0)
882 {
883 if (converted)
884 _ctk_tree_data_list_value_to_node (list, &real_value);
885 else
886 _ctk_tree_data_list_value_to_node (list, value);
887 retval = TRUE(!(0));
888 if (converted)
889 g_value_unset (&real_value);
890 if (sort && CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
891 ctk_tree_store_sort_iter_changed (tree_store, iter, old_column, TRUE(!(0)));
892 return retval;
893 }
894
895 column--;
896 prev = list;
897 list = list->next;
898 }
899
900 if (G_NODE (iter->user_data)((GNode *)iter->user_data)->data == NULL((void*)0))
901 {
902 G_NODE (iter->user_data)((GNode *)iter->user_data)->data = list = _ctk_tree_data_list_alloc ();
903 list->next = NULL((void*)0);
904 }
905 else
906 {
907 list = prev->next = _ctk_tree_data_list_alloc ();
908 list->next = NULL((void*)0);
909 }
910
911 while (column != 0)
912 {
913 list->next = _ctk_tree_data_list_alloc ();
914 list = list->next;
915 list->next = NULL((void*)0);
916 column --;
917 }
918
919 if (converted)
920 _ctk_tree_data_list_value_to_node (list, &real_value);
921 else
922 _ctk_tree_data_list_value_to_node (list, value);
923
924 retval = TRUE(!(0));
925 if (converted)
926 g_value_unset (&real_value);
927
928 if (sort && CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
929 ctk_tree_store_sort_iter_changed (tree_store, iter, old_column, TRUE(!(0)));
930
931 return retval;
932}
933
934/**
935 * ctk_tree_store_set_value:
936 * @tree_store: a #CtkTreeStore
937 * @iter: A valid #CtkTreeIter for the row being modified
938 * @column: column number to modify
939 * @value: new value for the cell
940 *
941 * Sets the data in the cell specified by @iter and @column.
942 * The type of @value must be convertible to the type of the
943 * column.
944 *
945 **/
946void
947ctk_tree_store_set_value (CtkTreeStore *tree_store,
948 CtkTreeIter *iter,
949 gint column,
950 GValue *value)
951{
952 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
953 g_return_if_fail (VALID_ITER (iter, tree_store))do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return; } } while (0)
;
954 g_return_if_fail (column >= 0 && column < tree_store->priv->n_columns)do { if ((column >= 0 && column < tree_store->
priv->n_columns)) { } else { g_return_if_fail_warning ("Ctk"
, ((const char*) (__func__)), "column >= 0 && column < tree_store->priv->n_columns"
); return; } } while (0)
;
955 g_return_if_fail (G_IS_VALUE (value))do { if (((((g_type_check_value ((GValue*) (value))))))) { } else
{ g_return_if_fail_warning ("Ctk", ((const char*) (__func__)
), "G_IS_VALUE (value)"); return; } } while (0)
;
956
957 if (ctk_tree_store_real_set_value (tree_store, iter, column, value, TRUE(!(0))))
958 {
959 CtkTreePath *path;
960
961 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
962 ctk_tree_model_row_changed (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
963 ctk_tree_path_free (path);
964 }
965}
966
967static CtkTreeIterCompareFunc
968ctk_tree_store_get_compare_func (CtkTreeStore *tree_store)
969{
970 CtkTreeStorePrivate *priv = tree_store->priv;
971 CtkTreeIterCompareFunc func = NULL((void*)0);
972
973 if (CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
974 {
975 if (priv->sort_column_id != -1)
976 {
977 CtkTreeDataSortHeader *header;
978 header = _ctk_tree_data_list_get_header (priv->sort_list,
979 priv->sort_column_id);
980 g_return_val_if_fail (header != NULL, NULL)do { if ((header != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header != NULL"); return
(((void*)0)); } } while (0)
;
981 g_return_val_if_fail (header->func != NULL, NULL)do { if ((header->func != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header->func != NULL"
); return (((void*)0)); } } while (0)
;
982 func = header->func;
983 }
984 else
985 {
986 func = priv->default_sort_func;
987 }
988 }
989
990 return func;
991}
992
993static void
994ctk_tree_store_set_vector_internal (CtkTreeStore *tree_store,
995 CtkTreeIter *iter,
996 gboolean *emit_signal,
997 gboolean *maybe_need_sort,
998 gint *columns,
999 GValue *values,
1000 gint n_values)
1001{
1002 CtkTreeStorePrivate *priv = tree_store->priv;
1003 gint i;
1004 CtkTreeIterCompareFunc func = NULL((void*)0);
1005
1006 func = ctk_tree_store_get_compare_func (tree_store);
1007 if (func != _ctk_tree_data_list_compare_func)
1008 *maybe_need_sort = TRUE(!(0));
1009
1010 for (i = 0; i < n_values; i++)
1011 {
1012 *emit_signal = ctk_tree_store_real_set_value (tree_store, iter,
1013 columns[i], &values[i],
1014 FALSE(0)) || *emit_signal;
1015
1016 if (func == _ctk_tree_data_list_compare_func &&
1017 columns[i] == priv->sort_column_id)
1018 *maybe_need_sort = TRUE(!(0));
1019 }
1020}
1021
1022static void
1023ctk_tree_store_set_valist_internal (CtkTreeStore *tree_store,
1024 CtkTreeIter *iter,
1025 gboolean *emit_signal,
1026 gboolean *maybe_need_sort,
1027 va_list var_args)
1028{
1029 CtkTreeStorePrivate *priv = tree_store->priv;
1030 gint column;
1031 CtkTreeIterCompareFunc func = NULL((void*)0);
1032
1033 column = va_arg (var_args, gint)__builtin_va_arg(var_args, gint);
1034
1035 func = ctk_tree_store_get_compare_func (tree_store);
1036 if (func != _ctk_tree_data_list_compare_func)
1037 *maybe_need_sort = TRUE(!(0));
1038
1039 while (column != -1)
1040 {
1041 GValue value = G_VALUE_INIT{ 0, { { 0 } } };
1042 gchar *error = NULL((void*)0);
1043
1044 if (column < 0 || column >= priv->n_columns)
1045 {
1046 g_warning ("%s: Invalid column number %d added to iter (remember to end your list of columns with a -1)", G_STRLOC"ctktreestore.c" ":" "1046", column);
1047 break;
1048 }
1049
1050 G_VALUE_COLLECT_INIT (&value, priv->column_headers[column],do { GTypeValueTable *g_vci_vtab; do { GValue *g_vci_val = (&
value); guint g_vci_flags = (0); const gchar *g_vci_collect_format
; GTypeCValue g_vci_cvalues[(8)] = { { 0, }, }; guint g_vci_n_values
= 0; g_vci_vtab = g_type_value_table_peek (priv->column_headers
[column]); g_vci_collect_format = g_vci_vtab->collect_format
; g_vci_val->g_type = priv->column_headers[column]; while
(*g_vci_collect_format) { GTypeCValue *g_vci_cvalue = g_vci_cvalues
+ g_vci_n_values++; switch (*g_vci_collect_format++) { case G_VALUE_COLLECT_INT
: g_vci_cvalue->v_int = __builtin_va_arg((var_args), gint)
; break; case G_VALUE_COLLECT_LONG: g_vci_cvalue->v_long =
__builtin_va_arg((var_args), glong); break; case G_VALUE_COLLECT_INT64
: g_vci_cvalue->v_int64 = __builtin_va_arg((var_args), gint64
); break; case G_VALUE_COLLECT_DOUBLE: g_vci_cvalue->v_double
= __builtin_va_arg((var_args), gdouble); break; case G_VALUE_COLLECT_POINTER
: g_vci_cvalue->v_pointer = __builtin_va_arg((var_args), gpointer
); break; default: do { g_assertion_message_expr ("Ctk", "ctktreestore.c"
, 1051, ((const char*) (__func__)), ((void*)0)); } while (0);
} } *(&error) = g_vci_vtab->collect_value (g_vci_val,
g_vci_n_values, g_vci_cvalues, g_vci_flags); } while (0); } while
(0)
1051 var_args, 0, &error)do { GTypeValueTable *g_vci_vtab; do { GValue *g_vci_val = (&
value); guint g_vci_flags = (0); const gchar *g_vci_collect_format
; GTypeCValue g_vci_cvalues[(8)] = { { 0, }, }; guint g_vci_n_values
= 0; g_vci_vtab = g_type_value_table_peek (priv->column_headers
[column]); g_vci_collect_format = g_vci_vtab->collect_format
; g_vci_val->g_type = priv->column_headers[column]; while
(*g_vci_collect_format) { GTypeCValue *g_vci_cvalue = g_vci_cvalues
+ g_vci_n_values++; switch (*g_vci_collect_format++) { case G_VALUE_COLLECT_INT
: g_vci_cvalue->v_int = __builtin_va_arg((var_args), gint)
; break; case G_VALUE_COLLECT_LONG: g_vci_cvalue->v_long =
__builtin_va_arg((var_args), glong); break; case G_VALUE_COLLECT_INT64
: g_vci_cvalue->v_int64 = __builtin_va_arg((var_args), gint64
); break; case G_VALUE_COLLECT_DOUBLE: g_vci_cvalue->v_double
= __builtin_va_arg((var_args), gdouble); break; case G_VALUE_COLLECT_POINTER
: g_vci_cvalue->v_pointer = __builtin_va_arg((var_args), gpointer
); break; default: do { g_assertion_message_expr ("Ctk", "ctktreestore.c"
, 1051, ((const char*) (__func__)), ((void*)0)); } while (0);
} } *(&error) = g_vci_vtab->collect_value (g_vci_val,
g_vci_n_values, g_vci_cvalues, g_vci_flags); } while (0); } while
(0)
;
1052 if (error)
1053 {
1054 g_warning ("%s: %s", G_STRLOC"ctktreestore.c" ":" "1054", error);
1055 g_free (error);
1056
1057 /* we purposely leak the value here, it might not be
1058 * in a sane state if an error condition occoured
1059 */
1060 break;
1061 }
1062
1063 *emit_signal = ctk_tree_store_real_set_value (tree_store,
1064 iter,
1065 column,
1066 &value,
1067 FALSE(0)) || *emit_signal;
1068
1069 if (func == _ctk_tree_data_list_compare_func &&
1070 column == priv->sort_column_id)
1071 *maybe_need_sort = TRUE(!(0));
1072
1073 g_value_unset (&value);
1074
1075 column = va_arg (var_args, gint)__builtin_va_arg(var_args, gint);
1076 }
1077}
1078
1079/**
1080 * ctk_tree_store_set_valuesv: (rename-to ctk_tree_store_set)
1081 * @tree_store: A #CtkTreeStore
1082 * @iter: A valid #CtkTreeIter for the row being modified
1083 * @columns: (array length=n_values): an array of column numbers
1084 * @values: (array length=n_values): an array of GValues
1085 * @n_values: the length of the @columns and @values arrays
1086 *
1087 * A variant of ctk_tree_store_set_valist() which takes
1088 * the columns and values as two arrays, instead of varargs. This
1089 * function is mainly intended for language bindings or in case
1090 * the number of columns to change is not known until run-time.
1091 *
1092 * Since: 2.12
1093 **/
1094void
1095ctk_tree_store_set_valuesv (CtkTreeStore *tree_store,
1096 CtkTreeIter *iter,
1097 gint *columns,
1098 GValue *values,
1099 gint n_values)
1100{
1101 CtkTreeStorePrivate *priv = tree_store->priv;
1102 gboolean emit_signal = FALSE(0);
1103 gboolean maybe_need_sort = FALSE(0);
1104
1105 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1106 g_return_if_fail (VALID_ITER (iter, tree_store))do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return; } } while (0)
;
1107
1108 ctk_tree_store_set_vector_internal (tree_store, iter,
1109 &emit_signal,
1110 &maybe_need_sort,
1111 columns, values, n_values);
1112
1113 if (maybe_need_sort && CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
1114 ctk_tree_store_sort_iter_changed (tree_store, iter, priv->sort_column_id, TRUE(!(0)));
1115
1116 if (emit_signal)
1117 {
1118 CtkTreePath *path;
1119
1120 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1121 ctk_tree_model_row_changed (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1122 ctk_tree_path_free (path);
1123 }
1124}
1125
1126/**
1127 * ctk_tree_store_set_valist:
1128 * @tree_store: A #CtkTreeStore
1129 * @iter: A valid #CtkTreeIter for the row being modified
1130 * @var_args: va_list of column/value pairs
1131 *
1132 * See ctk_tree_store_set(); this version takes a va_list for
1133 * use by language bindings.
1134 *
1135 **/
1136void
1137ctk_tree_store_set_valist (CtkTreeStore *tree_store,
1138 CtkTreeIter *iter,
1139 va_list var_args)
1140{
1141 CtkTreeStorePrivate *priv = tree_store->priv;
1142 gboolean emit_signal = FALSE(0);
1143 gboolean maybe_need_sort = FALSE(0);
1144
1145 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1146 g_return_if_fail (VALID_ITER (iter, tree_store))do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return; } } while (0)
;
1147
1148 ctk_tree_store_set_valist_internal (tree_store, iter,
1149 &emit_signal,
1150 &maybe_need_sort,
1151 var_args);
1152
1153 if (maybe_need_sort && CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
1154 ctk_tree_store_sort_iter_changed (tree_store, iter, priv->sort_column_id, TRUE(!(0)));
1155
1156 if (emit_signal)
1157 {
1158 CtkTreePath *path;
1159
1160 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1161 ctk_tree_model_row_changed (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1162 ctk_tree_path_free (path);
1163 }
1164}
1165
1166/**
1167 * ctk_tree_store_set:
1168 * @tree_store: A #CtkTreeStore
1169 * @iter: A valid #CtkTreeIter for the row being modified
1170 * @...: pairs of column number and value, terminated with -1
1171 *
1172 * Sets the value of one or more cells in the row referenced by @iter.
1173 * The variable argument list should contain integer column numbers,
1174 * each column number followed by the value to be set.
1175 * The list is terminated by a -1. For example, to set column 0 with type
1176 * %G_TYPE_STRING to “Foo”, you would write
1177 * `ctk_tree_store_set (store, iter, 0, "Foo", -1)`.
1178 *
1179 * The value will be referenced by the store if it is a %G_TYPE_OBJECT, and it
1180 * will be copied if it is a %G_TYPE_STRING or %G_TYPE_BOXED.
1181 **/
1182void
1183ctk_tree_store_set (CtkTreeStore *tree_store,
1184 CtkTreeIter *iter,
1185 ...)
1186{
1187 va_list var_args;
1188
1189 va_start (var_args, iter)__builtin_va_start(var_args, iter);
1190 ctk_tree_store_set_valist (tree_store, iter, var_args);
1191 va_end (var_args)__builtin_va_end(var_args);
1192}
1193
1194/**
1195 * ctk_tree_store_remove:
1196 * @tree_store: A #CtkTreeStore
1197 * @iter: A valid #CtkTreeIter
1198 *
1199 * Removes @iter from @tree_store. After being removed, @iter is set to the
1200 * next valid row at that level, or invalidated if it previously pointed to the
1201 * last one.
1202 *
1203 * Returns: %TRUE if @iter is still valid, %FALSE if not.
1204 **/
1205gboolean
1206ctk_tree_store_remove (CtkTreeStore *tree_store,
1207 CtkTreeIter *iter)
1208{
1209 CtkTreeStorePrivate *priv = tree_store->priv;
1210 CtkTreePath *path;
1211 CtkTreeIter new_iter = {0,};
1212 GNode *parent;
1213 GNode *next_node;
1214
1215 g_return_val_if_fail (CTK_IS_TREE_STORE (tree_store), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return ((0
)); } } while (0)
;
1216 g_return_val_if_fail (VALID_ITER (iter, tree_store), FALSE)do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return ((0)); } } while (0)
;
1217
1218 parent = G_NODE (iter->user_data)((GNode *)iter->user_data)->parent;
1219
1220 g_assert (parent != NULL)do { if (parent != ((void*)0)) ; else g_assertion_message_expr
("Ctk", "ctktreestore.c", 1220, ((const char*) (__func__)), "parent != NULL"
); } while (0)
;
1221 next_node = G_NODE (iter->user_data)((GNode *)iter->user_data)->next;
1222
1223 if (G_NODE (iter->user_data)((GNode *)iter->user_data)->data)
1224 g_node_traverse (G_NODE (iter->user_data)((GNode *)iter->user_data), G_POST_ORDER, G_TRAVERSE_ALL,
1225 -1, node_free, priv->column_headers);
1226
1227 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1228 g_node_destroy (G_NODE (iter->user_data)((GNode *)iter->user_data));
1229
1230 ctk_tree_model_row_deleted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path);
1231
1232 if (parent != G_NODE (priv->root)((GNode *)priv->root))
1233 {
1234 /* child_toggled */
1235 if (parent->children == NULL((void*)0))
1236 {
1237 ctk_tree_path_up (path);
1238
1239 new_iter.stamp = priv->stamp;
1240 new_iter.user_data = parent;
1241 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, &new_iter);
1242 }
1243 }
1244 ctk_tree_path_free (path);
1245
1246 /* revalidate iter */
1247 if (next_node != NULL((void*)0))
1248 {
1249 iter->stamp = priv->stamp;
1250 iter->user_data = next_node;
1251 return TRUE(!(0));
1252 }
1253 else
1254 {
1255 iter->stamp = 0;
1256 iter->user_data = NULL((void*)0);
1257 }
1258
1259 return FALSE(0);
1260}
1261
1262/**
1263 * ctk_tree_store_insert:
1264 * @tree_store: A #CtkTreeStore
1265 * @iter: (out): An unset #CtkTreeIter to set to the new row
1266 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1267 * @position: position to insert the new row, or -1 for last
1268 *
1269 * Creates a new row at @position. If parent is non-%NULL, then the row will be
1270 * made a child of @parent. Otherwise, the row will be created at the toplevel.
1271 * If @position is -1 or is larger than the number of rows at that level, then
1272 * the new row will be inserted to the end of the list. @iter will be changed
1273 * to point to this new row. The row will be empty after this function is
1274 * called. To fill in values, you need to call ctk_tree_store_set() or
1275 * ctk_tree_store_set_value().
1276 *
1277 **/
1278void
1279ctk_tree_store_insert (CtkTreeStore *tree_store,
1280 CtkTreeIter *iter,
1281 CtkTreeIter *parent,
1282 gint position)
1283{
1284 CtkTreeStorePrivate *priv = tree_store->priv;
1285 CtkTreePath *path;
1286 GNode *parent_node;
1287 GNode *new_node;
1288
1289 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1290 g_return_if_fail (iter != NULL)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return;
} } while (0)
;
1291 if (parent)
1292 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1293
1294 if (parent)
1295 parent_node = parent->user_data;
1296 else
1297 parent_node = priv->root;
1298
1299 priv->columns_dirty = TRUE(!(0));
1300
1301 new_node = g_node_new (NULL((void*)0));
1302
1303 iter->stamp = priv->stamp;
1304 iter->user_data = new_node;
1305 g_node_insert (parent_node, position, new_node);
1306
1307 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1308 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1309
1310 if (parent_node != priv->root)
1311 {
1312 if (new_node->prev == NULL((void*)0) && new_node->next == NULL((void*)0))
1313 {
1314 ctk_tree_path_up (path);
1315 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, parent);
1316 }
1317 }
1318
1319 ctk_tree_path_free (path);
1320
1321 validate_tree ((CtkTreeStore*)tree_store);
1322}
1323
1324/**
1325 * ctk_tree_store_insert_before:
1326 * @tree_store: A #CtkTreeStore
1327 * @iter: (out): An unset #CtkTreeIter to set to the new row
1328 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1329 * @sibling: (allow-none): A valid #CtkTreeIter, or %NULL
1330 *
1331 * Inserts a new row before @sibling. If @sibling is %NULL, then the row will
1332 * be appended to @parent ’s children. If @parent and @sibling are %NULL, then
1333 * the row will be appended to the toplevel. If both @sibling and @parent are
1334 * set, then @parent must be the parent of @sibling. When @sibling is set,
1335 * @parent is optional.
1336 *
1337 * @iter will be changed to point to this new row. The row will be empty after
1338 * this function is called. To fill in values, you need to call
1339 * ctk_tree_store_set() or ctk_tree_store_set_value().
1340 *
1341 **/
1342void
1343ctk_tree_store_insert_before (CtkTreeStore *tree_store,
1344 CtkTreeIter *iter,
1345 CtkTreeIter *parent,
1346 CtkTreeIter *sibling)
1347{
1348 CtkTreeStorePrivate *priv = tree_store->priv;
1349 CtkTreePath *path;
1350 GNode *parent_node = NULL((void*)0);
1351 GNode *new_node;
1352
1353 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1354 g_return_if_fail (iter != NULL)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return;
} } while (0)
;
1355 if (parent != NULL((void*)0))
1356 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1357 if (sibling != NULL((void*)0))
1358 g_return_if_fail (VALID_ITER (sibling, tree_store))do { if ((((sibling)!= ((void*)0) && (sibling)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (sibling)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (sibling, tree_store)"
); return; } } while (0)
;
1359
1360 if (parent == NULL((void*)0) && sibling == NULL((void*)0))
1361 parent_node = priv->root;
1362 else if (parent == NULL((void*)0))
1363 parent_node = G_NODE (sibling->user_data)((GNode *)sibling->user_data)->parent;
1364 else if (sibling == NULL((void*)0))
1365 parent_node = G_NODE (parent->user_data)((GNode *)parent->user_data);
1366 else
1367 {
1368 g_return_if_fail (G_NODE (sibling->user_data)->parent == G_NODE (parent->user_data))do { if ((((GNode *)sibling->user_data)->parent == ((GNode
*)parent->user_data))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "G_NODE (sibling->user_data)->parent == G_NODE (parent->user_data)"
); return; } } while (0)
;
1369 parent_node = G_NODE (parent->user_data)((GNode *)parent->user_data);
1370 }
1371
1372 priv->columns_dirty = TRUE(!(0));
1373
1374 new_node = g_node_new (NULL((void*)0));
1375
1376 g_node_insert_before (parent_node,
1377 sibling ? G_NODE (sibling->user_data)((GNode *)sibling->user_data) : NULL((void*)0),
1378 new_node);
1379
1380 iter->stamp = priv->stamp;
1381 iter->user_data = new_node;
1382
1383 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1384 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1385
1386 if (parent_node != priv->root)
1387 {
1388 if (new_node->prev == NULL((void*)0) && new_node->next == NULL((void*)0))
1389 {
1390 CtkTreeIter parent_iter;
1391
1392 parent_iter.stamp = priv->stamp;
1393 parent_iter.user_data = parent_node;
1394
1395 ctk_tree_path_up (path);
1396 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, &parent_iter);
1397 }
1398 }
1399
1400 ctk_tree_path_free (path);
1401
1402 validate_tree (tree_store);
1403}
1404
1405/**
1406 * ctk_tree_store_insert_after:
1407 * @tree_store: A #CtkTreeStore
1408 * @iter: (out): An unset #CtkTreeIter to set to the new row
1409 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1410 * @sibling: (allow-none): A valid #CtkTreeIter, or %NULL
1411 *
1412 * Inserts a new row after @sibling. If @sibling is %NULL, then the row will be
1413 * prepended to @parent ’s children. If @parent and @sibling are %NULL, then
1414 * the row will be prepended to the toplevel. If both @sibling and @parent are
1415 * set, then @parent must be the parent of @sibling. When @sibling is set,
1416 * @parent is optional.
1417 *
1418 * @iter will be changed to point to this new row. The row will be empty after
1419 * this function is called. To fill in values, you need to call
1420 * ctk_tree_store_set() or ctk_tree_store_set_value().
1421 *
1422 **/
1423void
1424ctk_tree_store_insert_after (CtkTreeStore *tree_store,
1425 CtkTreeIter *iter,
1426 CtkTreeIter *parent,
1427 CtkTreeIter *sibling)
1428{
1429 CtkTreeStorePrivate *priv = tree_store->priv;
1430 CtkTreePath *path;
1431 GNode *parent_node;
1432 GNode *new_node;
1433
1434 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1435 g_return_if_fail (iter != NULL)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return;
} } while (0)
;
1436 if (parent != NULL((void*)0))
1437 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1438 if (sibling != NULL((void*)0))
1439 g_return_if_fail (VALID_ITER (sibling, tree_store))do { if ((((sibling)!= ((void*)0) && (sibling)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (sibling)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (sibling, tree_store)"
); return; } } while (0)
;
1440
1441 if (parent == NULL((void*)0) && sibling == NULL((void*)0))
1442 parent_node = priv->root;
1443 else if (parent == NULL((void*)0))
1444 parent_node = G_NODE (sibling->user_data)((GNode *)sibling->user_data)->parent;
1445 else if (sibling == NULL((void*)0))
1446 parent_node = G_NODE (parent->user_data)((GNode *)parent->user_data);
1447 else
1448 {
1449 g_return_if_fail (G_NODE (sibling->user_data)->parent ==do { if ((((GNode *)sibling->user_data)->parent == ((GNode
*)parent->user_data))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "G_NODE (sibling->user_data)->parent == G_NODE (parent->user_data)"
); return; } } while (0)
1450 G_NODE (parent->user_data))do { if ((((GNode *)sibling->user_data)->parent == ((GNode
*)parent->user_data))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "G_NODE (sibling->user_data)->parent == G_NODE (parent->user_data)"
); return; } } while (0)
;
1451 parent_node = G_NODE (parent->user_data)((GNode *)parent->user_data);
1452 }
1453
1454 priv->columns_dirty = TRUE(!(0));
1455
1456 new_node = g_node_new (NULL((void*)0));
1457
1458 g_node_insert_after (parent_node,
1459 sibling ? G_NODE (sibling->user_data)((GNode *)sibling->user_data) : NULL((void*)0),
1460 new_node);
1461
1462 iter->stamp = priv->stamp;
1463 iter->user_data = new_node;
1464
1465 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1466 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1467
1468 if (parent_node != priv->root)
1469 {
1470 if (new_node->prev == NULL((void*)0) && new_node->next == NULL((void*)0))
1471 {
1472 CtkTreeIter parent_iter;
1473
1474 parent_iter.stamp = priv->stamp;
1475 parent_iter.user_data = parent_node;
1476
1477 ctk_tree_path_up (path);
1478 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, &parent_iter);
1479 }
1480 }
1481
1482 ctk_tree_path_free (path);
1483
1484 validate_tree (tree_store);
1485}
1486
1487/**
1488 * ctk_tree_store_insert_with_values:
1489 * @tree_store: A #CtkTreeStore
1490 * @iter: (out) (allow-none): An unset #CtkTreeIter to set the new row, or %NULL.
1491 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1492 * @position: position to insert the new row, or -1 to append after existing rows
1493 * @...: pairs of column number and value, terminated with -1
1494 *
1495 * Creates a new row at @position. @iter will be changed to point to this
1496 * new row. If @position is -1, or larger than the number of rows on the list, then
1497 * the new row will be appended to the list. The row will be filled with
1498 * the values given to this function.
1499 *
1500 * Calling
1501 * `ctk_tree_store_insert_with_values (tree_store, iter, position, ...)`
1502 * has the same effect as calling
1503 * |[<!-- language="C" -->
1504 * ctk_tree_store_insert (tree_store, iter, position);
1505 * ctk_tree_store_set (tree_store, iter, ...);
1506 * ]|
1507 * with the different that the former will only emit a row_inserted signal,
1508 * while the latter will emit row_inserted, row_changed and if the tree store
1509 * is sorted, rows_reordered. Since emitting the rows_reordered signal
1510 * repeatedly can affect the performance of the program,
1511 * ctk_tree_store_insert_with_values() should generally be preferred when
1512 * inserting rows in a sorted tree store.
1513 *
1514 * Since: 2.10
1515 */
1516void
1517ctk_tree_store_insert_with_values (CtkTreeStore *tree_store,
1518 CtkTreeIter *iter,
1519 CtkTreeIter *parent,
1520 gint position,
1521 ...)
1522{
1523 CtkTreeStorePrivate *priv = tree_store->priv;
1524 CtkTreePath *path;
1525 GNode *parent_node;
1526 GNode *new_node;
1527 CtkTreeIter tmp_iter;
1528 va_list var_args;
1529 gboolean changed = FALSE(0);
1530 gboolean maybe_need_sort = FALSE(0);
1531
1532 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1533
1534 if (!iter)
1535 iter = &tmp_iter;
1536
1537 if (parent)
1538 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1539
1540 if (parent)
1541 parent_node = parent->user_data;
1542 else
1543 parent_node = priv->root;
1544
1545 priv->columns_dirty = TRUE(!(0));
1546
1547 new_node = g_node_new (NULL((void*)0));
1548
1549 iter->stamp = priv->stamp;
1550 iter->user_data = new_node;
1551 g_node_insert (parent_node, position, new_node);
1552
1553 va_start (var_args, position)__builtin_va_start(var_args, position);
1554 ctk_tree_store_set_valist_internal (tree_store, iter,
1555 &changed, &maybe_need_sort,
1556 var_args);
1557 va_end (var_args)__builtin_va_end(var_args);
1558
1559 if (maybe_need_sort && CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
1560 ctk_tree_store_sort_iter_changed (tree_store, iter, priv->sort_column_id, FALSE(0));
1561
1562 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1563 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1564
1565 if (parent_node != priv->root)
1566 {
1567 if (new_node->prev == NULL((void*)0) && new_node->next == NULL((void*)0))
1568 {
1569 ctk_tree_path_up (path);
1570 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, parent);
1571 }
1572 }
1573
1574 ctk_tree_path_free (path);
1575
1576 validate_tree ((CtkTreeStore *)tree_store);
1577}
1578
1579/**
1580 * ctk_tree_store_insert_with_valuesv: (rename-to ctk_tree_store_insert_with_values)
1581 * @tree_store: A #CtkTreeStore
1582 * @iter: (out) (allow-none): An unset #CtkTreeIter to set the new row, or %NULL.
1583 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1584 * @position: position to insert the new row, or -1 for last
1585 * @columns: (array length=n_values): an array of column numbers
1586 * @values: (array length=n_values): an array of GValues
1587 * @n_values: the length of the @columns and @values arrays
1588 *
1589 * A variant of ctk_tree_store_insert_with_values() which takes
1590 * the columns and values as two arrays, instead of varargs. This
1591 * function is mainly intended for language bindings.
1592 *
1593 * Since: 2.10
1594 */
1595void
1596ctk_tree_store_insert_with_valuesv (CtkTreeStore *tree_store,
1597 CtkTreeIter *iter,
1598 CtkTreeIter *parent,
1599 gint position,
1600 gint *columns,
1601 GValue *values,
1602 gint n_values)
1603{
1604 CtkTreeStorePrivate *priv = tree_store->priv;
1605 CtkTreePath *path;
1606 GNode *parent_node;
1607 GNode *new_node;
1608 CtkTreeIter tmp_iter;
1609 gboolean changed = FALSE(0);
1610 gboolean maybe_need_sort = FALSE(0);
1611
1612 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1613
1614 if (!iter)
1615 iter = &tmp_iter;
1616
1617 if (parent)
1618 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1619
1620 if (parent)
1621 parent_node = parent->user_data;
1622 else
1623 parent_node = priv->root;
1624
1625 priv->columns_dirty = TRUE(!(0));
1626
1627 new_node = g_node_new (NULL((void*)0));
1628
1629 iter->stamp = priv->stamp;
1630 iter->user_data = new_node;
1631 g_node_insert (parent_node, position, new_node);
1632
1633 ctk_tree_store_set_vector_internal (tree_store, iter,
1634 &changed, &maybe_need_sort,
1635 columns, values, n_values);
1636
1637 if (maybe_need_sort && CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
1638 ctk_tree_store_sort_iter_changed (tree_store, iter, priv->sort_column_id, FALSE(0));
1639
1640 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1641 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1642
1643 if (parent_node != priv->root)
1644 {
1645 if (new_node->prev == NULL((void*)0) && new_node->next == NULL((void*)0))
1646 {
1647 ctk_tree_path_up (path);
1648 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, parent);
1649 }
1650 }
1651
1652 ctk_tree_path_free (path);
1653
1654 validate_tree ((CtkTreeStore *)tree_store);
1655}
1656
1657/**
1658 * ctk_tree_store_prepend:
1659 * @tree_store: A #CtkTreeStore
1660 * @iter: (out): An unset #CtkTreeIter to set to the prepended row
1661 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1662 *
1663 * Prepends a new row to @tree_store. If @parent is non-%NULL, then it will prepend
1664 * the new row before the first child of @parent, otherwise it will prepend a row
1665 * to the top level. @iter will be changed to point to this new row. The row
1666 * will be empty after this function is called. To fill in values, you need to
1667 * call ctk_tree_store_set() or ctk_tree_store_set_value().
1668 **/
1669void
1670ctk_tree_store_prepend (CtkTreeStore *tree_store,
1671 CtkTreeIter *iter,
1672 CtkTreeIter *parent)
1673{
1674 CtkTreeStorePrivate *priv = tree_store->priv;
1675 GNode *parent_node;
1676
1677 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1678 g_return_if_fail (iter != NULL)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return;
} } while (0)
;
1679 if (parent != NULL((void*)0))
1680 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1681
1682 priv->columns_dirty = TRUE(!(0));
1683
1684 if (parent == NULL((void*)0))
1685 parent_node = priv->root;
1686 else
1687 parent_node = parent->user_data;
1688
1689 if (parent_node->children == NULL((void*)0))
1690 {
1691 CtkTreePath *path;
1692
1693 iter->stamp = priv->stamp;
1694 iter->user_data = g_node_new (NULL((void*)0));
1695
1696 g_node_prepend (parent_node, G_NODE (iter->user_data)((GNode *)iter->user_data));
1697
1698 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1699 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1700
1701 if (parent_node != priv->root)
1702 {
1703 ctk_tree_path_up (path);
1704 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, parent);
1705 }
1706 ctk_tree_path_free (path);
1707 }
1708 else
1709 {
1710 ctk_tree_store_insert_after (tree_store, iter, parent, NULL((void*)0));
1711 }
1712
1713 validate_tree (tree_store);
1714}
1715
1716/**
1717 * ctk_tree_store_append:
1718 * @tree_store: A #CtkTreeStore
1719 * @iter: (out): An unset #CtkTreeIter to set to the appended row
1720 * @parent: (allow-none): A valid #CtkTreeIter, or %NULL
1721 *
1722 * Appends a new row to @tree_store. If @parent is non-%NULL, then it will append the
1723 * new row after the last child of @parent, otherwise it will append a row to
1724 * the top level. @iter will be changed to point to this new row. The row will
1725 * be empty after this function is called. To fill in values, you need to call
1726 * ctk_tree_store_set() or ctk_tree_store_set_value().
1727 **/
1728void
1729ctk_tree_store_append (CtkTreeStore *tree_store,
1730 CtkTreeIter *iter,
1731 CtkTreeIter *parent)
1732{
1733 CtkTreeStorePrivate *priv = tree_store->priv;
1734 GNode *parent_node;
1735
1736 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1737 g_return_if_fail (iter != NULL)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return;
} } while (0)
;
1738 if (parent != NULL((void*)0))
1739 g_return_if_fail (VALID_ITER (parent, tree_store))do { if ((((parent)!= ((void*)0) && (parent)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (parent)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (parent, tree_store)"
); return; } } while (0)
;
1740
1741 if (parent == NULL((void*)0))
1742 parent_node = priv->root;
1743 else
1744 parent_node = parent->user_data;
1745
1746 priv->columns_dirty = TRUE(!(0));
1747
1748 if (parent_node->children == NULL((void*)0))
1749 {
1750 CtkTreePath *path;
1751
1752 iter->stamp = priv->stamp;
1753 iter->user_data = g_node_new (NULL((void*)0));
1754
1755 g_node_append (parent_node, G_NODE (iter->user_data))g_node_insert_before ((parent_node), ((void*)0), (((GNode *)iter
->user_data)))
;
1756
1757 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
1758 ctk_tree_model_row_inserted (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, iter);
1759
1760 if (parent_node != priv->root)
1761 {
1762 ctk_tree_path_up (path);
1763 ctk_tree_model_row_has_child_toggled (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, parent);
1764 }
1765 ctk_tree_path_free (path);
1766 }
1767 else
1768 {
1769 ctk_tree_store_insert_before (tree_store, iter, parent, NULL((void*)0));
1770 }
1771
1772 validate_tree (tree_store);
1773}
1774
1775/**
1776 * ctk_tree_store_is_ancestor:
1777 * @tree_store: A #CtkTreeStore
1778 * @iter: A valid #CtkTreeIter
1779 * @descendant: A valid #CtkTreeIter
1780 *
1781 * Returns %TRUE if @iter is an ancestor of @descendant. That is, @iter is the
1782 * parent (or grandparent or great-grandparent) of @descendant.
1783 *
1784 * Returns: %TRUE, if @iter is an ancestor of @descendant
1785 **/
1786gboolean
1787ctk_tree_store_is_ancestor (CtkTreeStore *tree_store,
1788 CtkTreeIter *iter,
1789 CtkTreeIter *descendant)
1790{
1791 g_return_val_if_fail (CTK_IS_TREE_STORE (tree_store), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return ((0
)); } } while (0)
;
1792 g_return_val_if_fail (VALID_ITER (iter, tree_store), FALSE)do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return ((0)); } } while (0)
;
1793 g_return_val_if_fail (VALID_ITER (descendant, tree_store), FALSE)do { if ((((descendant)!= ((void*)0) && (descendant)->
user_data != ((void*)0) && ((CtkTreeStore*)(tree_store
))->priv->stamp == (descendant)->stamp))) { } else {
g_return_if_fail_warning ("Ctk", ((const char*) (__func__)),
"VALID_ITER (descendant, tree_store)"); return ((0)); } } while
(0)
;
1794
1795 return g_node_is_ancestor (G_NODE (iter->user_data)((GNode *)iter->user_data),
1796 G_NODE (descendant->user_data)((GNode *)descendant->user_data));
1797}
1798
1799
1800/**
1801 * ctk_tree_store_iter_depth:
1802 * @tree_store: A #CtkTreeStore
1803 * @iter: A valid #CtkTreeIter
1804 *
1805 * Returns the depth of @iter. This will be 0 for anything on the root level, 1
1806 * for anything down a level, etc.
1807 *
1808 * Returns: The depth of @iter
1809 **/
1810gint
1811ctk_tree_store_iter_depth (CtkTreeStore *tree_store,
1812 CtkTreeIter *iter)
1813{
1814 g_return_val_if_fail (CTK_IS_TREE_STORE (tree_store), 0)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return (0)
; } } while (0)
;
1815 g_return_val_if_fail (VALID_ITER (iter, tree_store), 0)do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return (0); } } while (0)
;
1816
1817 return g_node_depth (G_NODE (iter->user_data)((GNode *)iter->user_data)) - 2;
1818}
1819
1820/* simple ripoff from g_node_traverse_post_order */
1821static gboolean
1822ctk_tree_store_clear_traverse (GNode *node,
1823 CtkTreeStore *store)
1824{
1825 CtkTreeIter iter;
1826
1827 if (node->children)
1828 {
1829 GNode *child;
1830
1831 child = node->children;
1832 while (child)
1833 {
1834 register GNode *current;
1835
1836 current = child;
1837 child = current->next;
1838 if (ctk_tree_store_clear_traverse (current, store))
1839 return TRUE(!(0));
1840 }
1841
1842 if (node->parent)
1843 {
1844 iter.stamp = store->priv->stamp;
1845 iter.user_data = node;
1846
1847 ctk_tree_store_remove (store, &iter);
1848 }
1849 }
1850 else if (node->parent)
1851 {
1852 iter.stamp = store->priv->stamp;
1853 iter.user_data = node;
1854
1855 ctk_tree_store_remove (store, &iter);
1856 }
1857
1858 return FALSE(0);
1859}
1860
1861static void
1862ctk_tree_store_increment_stamp (CtkTreeStore *tree_store)
1863{
1864 CtkTreeStorePrivate *priv = tree_store->priv;
1865 do
1866 {
1867 priv->stamp++;
1868 }
1869 while (priv->stamp == 0);
1870}
1871
1872/**
1873 * ctk_tree_store_clear:
1874 * @tree_store: a #CtkTreeStore
1875 *
1876 * Removes all rows from @tree_store
1877 **/
1878void
1879ctk_tree_store_clear (CtkTreeStore *tree_store)
1880{
1881 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
1882
1883 ctk_tree_store_clear_traverse (tree_store->priv->root, tree_store);
1884 ctk_tree_store_increment_stamp (tree_store);
1885}
1886
1887static gboolean
1888ctk_tree_store_iter_is_valid_helper (CtkTreeIter *iter,
1889 GNode *first)
1890{
1891 GNode *node;
1892
1893 node = first;
1894
1895 do
1896 {
1897 if (node == iter->user_data)
1898 return TRUE(!(0));
1899
1900 if (node->children)
1901 if (ctk_tree_store_iter_is_valid_helper (iter, node->children))
1902 return TRUE(!(0));
1903
1904 node = node->next;
1905 }
1906 while (node);
1907
1908 return FALSE(0);
1909}
1910
1911/**
1912 * ctk_tree_store_iter_is_valid:
1913 * @tree_store: A #CtkTreeStore.
1914 * @iter: A #CtkTreeIter.
1915 *
1916 * WARNING: This function is slow. Only use it for debugging and/or testing
1917 * purposes.
1918 *
1919 * Checks if the given iter is a valid iter for this #CtkTreeStore.
1920 *
1921 * Returns: %TRUE if the iter is valid, %FALSE if the iter is invalid.
1922 *
1923 * Since: 2.2
1924 **/
1925gboolean
1926ctk_tree_store_iter_is_valid (CtkTreeStore *tree_store,
1927 CtkTreeIter *iter)
1928{
1929 g_return_val_if_fail (CTK_IS_TREE_STORE (tree_store), FALSE)do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return ((0
)); } } while (0)
;
1930 g_return_val_if_fail (iter != NULL, FALSE)do { if ((iter != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "iter != NULL"); return (
(0)); } } while (0)
;
1931
1932 if (!VALID_ITER (iter, tree_store)((iter)!= ((void*)0) && (iter)->user_data != ((void
*)0) && ((CtkTreeStore*)(tree_store))->priv->stamp
== (iter)->stamp)
)
1933 return FALSE(0);
1934
1935 return ctk_tree_store_iter_is_valid_helper (iter, tree_store->priv->root);
1936}
1937
1938/* DND */
1939
1940
1941static gboolean real_ctk_tree_store_row_draggable (CtkTreeDragSource *drag_source G_GNUC_UNUSED__attribute__ ((__unused__)),
1942 CtkTreePath *path G_GNUC_UNUSED__attribute__ ((__unused__)))
1943{
1944 return TRUE(!(0));
1945}
1946
1947static gboolean
1948ctk_tree_store_drag_data_delete (CtkTreeDragSource *drag_source,
1949 CtkTreePath *path)
1950{
1951 CtkTreeIter iter;
1952
1953 if (ctk_tree_store_get_iter (CTK_TREE_MODEL (drag_source)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_source)), ((ctk_tree_model_get_type ()))))))
,
1954 &iter,
1955 path))
1956 {
1957 ctk_tree_store_remove (CTK_TREE_STORE (drag_source)((((CtkTreeStore*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_source)), ((ctk_tree_store_get_type ()))))))
,
1958 &iter);
1959 return TRUE(!(0));
1960 }
1961 else
1962 {
1963 return FALSE(0);
1964 }
1965}
1966
1967static gboolean
1968ctk_tree_store_drag_data_get (CtkTreeDragSource *drag_source,
1969 CtkTreePath *path,
1970 CtkSelectionData *selection_data)
1971{
1972 /* Note that we don't need to handle the CTK_TREE_MODEL_ROW
1973 * target, because the default handler does it for us, but
1974 * we do anyway for the convenience of someone maybe overriding the
1975 * default handler.
1976 */
1977
1978 if (ctk_tree_set_row_drag_data (selection_data,
1979 CTK_TREE_MODEL (drag_source)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_source)), ((ctk_tree_model_get_type ()))))))
,
1980 path))
1981 {
1982 return TRUE(!(0));
1983 }
1984 else
1985 {
1986 /* FIXME handle text targets at least. */
1987 }
1988
1989 return FALSE(0);
1990}
1991
1992static void
1993copy_node_data (CtkTreeStore *tree_store,
1994 CtkTreeIter *src_iter,
1995 CtkTreeIter *dest_iter)
1996{
1997 CtkTreeDataList *dl = G_NODE (src_iter->user_data)((GNode *)src_iter->user_data)->data;
1998 CtkTreeDataList *copy_head = NULL((void*)0);
1999 CtkTreeDataList *copy_prev = NULL((void*)0);
2000 CtkTreeDataList *copy_iter = NULL((void*)0);
2001 CtkTreePath *path;
2002 gint col;
2003
2004 col = 0;
2005 while (dl)
2006 {
2007 copy_iter = _ctk_tree_data_list_node_copy (dl, tree_store->priv->column_headers[col]);
2008
2009 if (copy_head == NULL((void*)0))
2010 copy_head = copy_iter;
2011
2012 if (copy_prev)
2013 copy_prev->next = copy_iter;
2014
2015 copy_prev = copy_iter;
2016
2017 dl = dl->next;
2018 ++col;
2019 }
2020
2021 G_NODE (dest_iter->user_data)((GNode *)dest_iter->user_data)->data = copy_head;
2022
2023 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, dest_iter);
2024 ctk_tree_model_row_changed (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path, dest_iter);
2025 ctk_tree_path_free (path);
2026}
2027
2028static void
2029recursive_node_copy (CtkTreeStore *tree_store,
2030 CtkTreeIter *src_iter,
2031 CtkTreeIter *dest_iter)
2032{
2033 CtkTreeIter child;
2034 CtkTreeModel *model;
2035
2036 model = CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
;
2037
2038 copy_node_data (tree_store, src_iter, dest_iter);
2039
2040 if (ctk_tree_store_iter_children (model,
2041 &child,
2042 src_iter))
2043 {
2044 /* Need to create children and recurse. Note our
2045 * dependence on persistent iterators here.
2046 */
2047 do
2048 {
2049 CtkTreeIter copy;
2050
2051 /* Gee, a really slow algorithm... ;-) FIXME */
2052 ctk_tree_store_append (tree_store,
2053 &copy,
2054 dest_iter);
2055
2056 recursive_node_copy (tree_store, &child, &copy);
2057 }
2058 while (ctk_tree_store_iter_next (model, &child));
2059 }
2060}
2061
2062static gboolean
2063ctk_tree_store_drag_data_received (CtkTreeDragDest *drag_dest,
2064 CtkTreePath *dest,
2065 CtkSelectionData *selection_data)
2066{
2067 CtkTreeModel *tree_model;
2068 CtkTreeStore *tree_store;
2069 CtkTreeModel *src_model = NULL((void*)0);
2070 CtkTreePath *src_path = NULL((void*)0);
2071 gboolean retval = FALSE(0);
2072
2073 tree_model = CTK_TREE_MODEL (drag_dest)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_dest)), ((ctk_tree_model_get_type ()))))))
;
2074 tree_store = CTK_TREE_STORE (drag_dest)((((CtkTreeStore*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_dest)), ((ctk_tree_store_get_type ()))))))
;
2075
2076 validate_tree (tree_store);
2077
2078 if (ctk_tree_get_row_drag_data (selection_data,
2079 &src_model,
2080 &src_path) &&
2081 src_model == tree_model)
2082 {
2083 /* Copy the given row to a new position */
2084 CtkTreeIter src_iter;
2085 CtkTreeIter dest_iter;
2086 CtkTreePath *prev;
2087
2088 if (!ctk_tree_store_get_iter (src_model,
2089 &src_iter,
2090 src_path))
2091 {
2092 goto out;
2093 }
2094
2095 /* Get the path to insert _after_ (dest is the path to insert _before_) */
2096 prev = ctk_tree_path_copy (dest);
2097
2098 if (!ctk_tree_path_prev (prev))
2099 {
2100 CtkTreeIter dest_parent;
2101 CtkTreePath *parent;
2102 CtkTreeIter *dest_parent_p;
2103
2104 /* dest was the first spot at the current depth; which means
2105 * we are supposed to prepend.
2106 */
2107
2108 /* Get the parent, NULL if parent is the root */
2109 dest_parent_p = NULL((void*)0);
2110 parent = ctk_tree_path_copy (dest);
2111 if (ctk_tree_path_up (parent) &&
2112 ctk_tree_path_get_depth (parent) > 0)
2113 {
2114 ctk_tree_store_get_iter (tree_model,
2115 &dest_parent,
2116 parent);
2117 dest_parent_p = &dest_parent;
2118 }
2119 ctk_tree_path_free (parent);
2120 parent = NULL((void*)0);
2121
2122 ctk_tree_store_prepend (tree_store,
2123 &dest_iter,
2124 dest_parent_p);
2125
2126 retval = TRUE(!(0));
2127 }
2128 else
2129 {
2130 if (ctk_tree_store_get_iter (tree_model, &dest_iter, prev))
2131 {
2132 CtkTreeIter tmp_iter = dest_iter;
2133
2134 ctk_tree_store_insert_after (tree_store, &dest_iter, NULL((void*)0),
2135 &tmp_iter);
2136
2137 retval = TRUE(!(0));
2138 }
2139 }
2140
2141 ctk_tree_path_free (prev);
2142
2143 /* If we succeeded in creating dest_iter, walk src_iter tree branch,
2144 * duplicating it below dest_iter.
2145 */
2146
2147 if (retval)
2148 {
2149 recursive_node_copy (tree_store,
2150 &src_iter,
2151 &dest_iter);
2152 }
2153 }
2154 else
2155 {
2156 /* FIXME maybe add some data targets eventually, or handle text
2157 * targets in the simple case.
2158 */
2159
2160 }
2161
2162 out:
2163
2164 if (src_path)
2165 ctk_tree_path_free (src_path);
2166
2167 return retval;
2168}
2169
2170static gboolean
2171ctk_tree_store_row_drop_possible (CtkTreeDragDest *drag_dest,
2172 CtkTreePath *dest_path,
2173 CtkSelectionData *selection_data)
2174{
2175 CtkTreeModel *src_model = NULL((void*)0);
2176 CtkTreePath *src_path = NULL((void*)0);
2177 CtkTreePath *tmp = NULL((void*)0);
2178 gboolean retval = FALSE(0);
2179
2180 /* don't accept drops if the tree has been sorted */
2181 if (CTK_TREE_STORE_IS_SORTED (drag_dest)(((CtkTreeStore*)(drag_dest))->priv->sort_column_id != (
-2))
)
2182 return FALSE(0);
2183
2184 if (!ctk_tree_get_row_drag_data (selection_data,
2185 &src_model,
2186 &src_path))
2187 goto out;
2188
2189 /* can only drag to ourselves */
2190 if (src_model != CTK_TREE_MODEL (drag_dest)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_dest)), ((ctk_tree_model_get_type ()))))))
)
2191 goto out;
2192
2193 /* Can't drop into ourself. */
2194 if (ctk_tree_path_is_ancestor (src_path,
2195 dest_path))
2196 goto out;
2197
2198 /* Can't drop if dest_path's parent doesn't exist */
2199 {
2200 CtkTreeIter iter;
2201
2202 if (ctk_tree_path_get_depth (dest_path) > 1)
2203 {
2204 tmp = ctk_tree_path_copy (dest_path);
2205 ctk_tree_path_up (tmp);
2206
2207 if (!ctk_tree_store_get_iter (CTK_TREE_MODEL (drag_dest)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((drag_dest)), ((ctk_tree_model_get_type ()))))))
,
2208 &iter, tmp))
2209 goto out;
2210 }
2211 }
2212
2213 /* Can otherwise drop anywhere. */
2214 retval = TRUE(!(0));
2215
2216 out:
2217
2218 if (src_path)
2219 ctk_tree_path_free (src_path);
2220 if (tmp)
2221 ctk_tree_path_free (tmp);
2222
2223 return retval;
2224}
2225
2226/* Sorting and reordering */
2227typedef struct _SortTuple
2228{
2229 gint offset;
2230 GNode *node;
2231} SortTuple;
2232
2233/* Reordering */
2234static gint
2235ctk_tree_store_reorder_func (gconstpointer a,
2236 gconstpointer b,
2237 gpointer user_data G_GNUC_UNUSED__attribute__ ((__unused__)))
2238{
2239 SortTuple *a_reorder;
2240 SortTuple *b_reorder;
2241
2242 a_reorder = (SortTuple *)a;
2243 b_reorder = (SortTuple *)b;
2244
2245 if (a_reorder->offset < b_reorder->offset)
2246 return -1;
2247 if (a_reorder->offset > b_reorder->offset)
2248 return 1;
2249
2250 return 0;
2251}
2252
2253/**
2254 * ctk_tree_store_reorder: (skip)
2255 * @tree_store: A #CtkTreeStore
2256 * @parent: (nullable): A #CtkTreeIter, or %NULL
2257 * @new_order: (array): an array of integers mapping the new position of each child
2258 * to its old position before the re-ordering,
2259 * i.e. @new_order`[newpos] = oldpos`.
2260 *
2261 * Reorders the children of @parent in @tree_store to follow the order
2262 * indicated by @new_order. Note that this function only works with
2263 * unsorted stores.
2264 *
2265 * Since: 2.2
2266 **/
2267void
2268ctk_tree_store_reorder (CtkTreeStore *tree_store,
2269 CtkTreeIter *parent,
2270 gint *new_order)
2271{
2272 gint i, length = 0;
2273 GNode *level, *node;
2274 CtkTreePath *path;
2275 SortTuple *sort_array;
2276
2277 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
2278 g_return_if_fail (!CTK_TREE_STORE_IS_SORTED (tree_store))do { if ((!(((CtkTreeStore*)(tree_store))->priv->sort_column_id
!= (-2)))) { } else { g_return_if_fail_warning ("Ctk", ((const
char*) (__func__)), "!CTK_TREE_STORE_IS_SORTED (tree_store)"
); return; } } while (0)
;
2279 g_return_if_fail (parent == NULL || VALID_ITER (parent, tree_store))do { if ((parent == ((void*)0) || ((parent)!= ((void*)0) &&
(parent)->user_data != ((void*)0) && ((CtkTreeStore
*)(tree_store))->priv->stamp == (parent)->stamp))) {
} else { g_return_if_fail_warning ("Ctk", ((const char*) (__func__
)), "parent == NULL || VALID_ITER (parent, tree_store)"); return
; } } while (0)
;
2280 g_return_if_fail (new_order != NULL)do { if ((new_order != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "new_order != NULL"); return
; } } while (0)
;
2281
2282 if (!parent)
2283 level = G_NODE (tree_store->priv->root)((GNode *)tree_store->priv->root)->children;
2284 else
2285 level = G_NODE (parent->user_data)((GNode *)parent->user_data)->children;
2286
2287 if (G_UNLIKELY (!level)(!level))
2288 {
2289 g_warning ("%s: Cannot reorder, parent has no children", G_STRLOC"ctktreestore.c" ":" "2289");
2290 return;
2291 }
2292
2293 /* count nodes */
2294 node = level;
2295 while (node)
2296 {
2297 length++;
2298 node = node->next;
2299 }
2300
2301 /* set up sortarray */
2302 sort_array = g_new (SortTuple, length)((SortTuple *) g_malloc_n ((length), sizeof (SortTuple)));
2303
2304 node = level;
2305 for (i = 0; i < length; i++)
2306 {
2307 sort_array[new_order[i]].offset = i;
2308 sort_array[i].node = node;
2309
2310 node = node->next;
2311 }
2312
2313 g_qsort_with_data (sort_array,
2314 length,
2315 sizeof (SortTuple),
2316 ctk_tree_store_reorder_func,
2317 NULL((void*)0));
2318
2319 /* fix up level */
2320 for (i = 0; i < length - 1; i++)
2321 {
2322 sort_array[i].node->next = sort_array[i+1].node;
2323 sort_array[i+1].node->prev = sort_array[i].node;
2324 }
2325
2326 sort_array[length-1].node->next = NULL((void*)0);
2327 sort_array[0].node->prev = NULL((void*)0);
2328 if (parent)
2329 G_NODE (parent->user_data)((GNode *)parent->user_data)->children = sort_array[0].node;
2330 else
2331 G_NODE (tree_store->priv->root)((GNode *)tree_store->priv->root)->children = sort_array[0].node;
2332
2333 /* emit signal */
2334 if (parent)
2335 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, parent);
2336 else
2337 path = ctk_tree_path_new ();
2338 ctk_tree_model_rows_reordered (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path,
2339 parent, new_order);
2340 ctk_tree_path_free (path);
2341 g_free (sort_array);
2342}
2343
2344/**
2345 * ctk_tree_store_swap:
2346 * @tree_store: A #CtkTreeStore.
2347 * @a: A #CtkTreeIter.
2348 * @b: Another #CtkTreeIter.
2349 *
2350 * Swaps @a and @b in the same level of @tree_store. Note that this function
2351 * only works with unsorted stores.
2352 *
2353 * Since: 2.2
2354 **/
2355void
2356ctk_tree_store_swap (CtkTreeStore *tree_store,
2357 CtkTreeIter *a,
2358 CtkTreeIter *b)
2359{
2360 GNode *tmp, *node_a, *node_b, *parent_node;
2361 GNode *a_prev, *a_next, *b_prev, *b_next;
2362 gint i, a_count, b_count, length, *order;
2363 CtkTreePath *path_a, *path_b;
2364 CtkTreeIter parent;
2365
2366 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
2367 g_return_if_fail (VALID_ITER (a, tree_store))do { if ((((a)!= ((void*)0) && (a)->user_data != (
(void*)0) && ((CtkTreeStore*)(tree_store))->priv->
stamp == (a)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (a, tree_store)"
); return; } } while (0)
;
2368 g_return_if_fail (VALID_ITER (b, tree_store))do { if ((((b)!= ((void*)0) && (b)->user_data != (
(void*)0) && ((CtkTreeStore*)(tree_store))->priv->
stamp == (b)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (b, tree_store)"
); return; } } while (0)
;
2369
2370 node_a = G_NODE (a->user_data)((GNode *)a->user_data);
2371 node_b = G_NODE (b->user_data)((GNode *)b->user_data);
2372
2373 /* basic sanity checking */
2374 if (node_a == node_b)
2375 return;
2376
2377 path_a = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, a);
2378 path_b = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, b);
2379
2380 g_return_if_fail (path_a && path_b)do { if ((path_a && path_b)) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "path_a && path_b"
); return; } } while (0)
;
2381
2382 ctk_tree_path_up (path_a);
2383 ctk_tree_path_up (path_b);
2384
2385 if (ctk_tree_path_get_depth (path_a) == 0
2386 || ctk_tree_path_get_depth (path_b) == 0)
2387 {
2388 if (ctk_tree_path_get_depth (path_a) != ctk_tree_path_get_depth (path_b))
2389 {
2390 ctk_tree_path_free (path_a);
2391 ctk_tree_path_free (path_b);
2392
2393 g_warning ("Given children are not in the same level\n");
2394 return;
2395 }
2396 parent_node = G_NODE (tree_store->priv->root)((GNode *)tree_store->priv->root);
2397 }
2398 else
2399 {
2400 if (ctk_tree_path_compare (path_a, path_b))
2401 {
2402 ctk_tree_path_free (path_a);
2403 ctk_tree_path_free (path_b);
2404
2405 g_warning ("Given children don't have a common parent\n");
2406 return;
2407 }
2408 ctk_tree_store_get_iter (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &parent,
2409 path_a);
2410 parent_node = G_NODE (parent.user_data)((GNode *)parent.user_data);
2411 }
2412 ctk_tree_path_free (path_b);
2413
2414 /* old links which we have to keep around */
2415 a_prev = node_a->prev;
2416 a_next = node_a->next;
2417
2418 b_prev = node_b->prev;
2419 b_next = node_b->next;
2420
2421 /* fix up links if the nodes are next to eachother */
2422 if (a_prev == node_b)
2423 a_prev = node_a;
2424 if (a_next == node_b)
2425 a_next = node_a;
2426
2427 if (b_prev == node_a)
2428 b_prev = node_b;
2429 if (b_next == node_a)
2430 b_next = node_b;
2431
2432 /* counting nodes */
2433 tmp = parent_node->children;
2434 i = a_count = b_count = 0;
2435 while (tmp)
2436 {
2437 if (tmp == node_a)
2438 a_count = i;
2439 if (tmp == node_b)
2440 b_count = i;
2441
2442 tmp = tmp->next;
2443 i++;
2444 }
2445 length = i;
2446
2447 /* hacking the tree */
2448 if (!a_prev)
2449 parent_node->children = node_b;
2450 else
2451 a_prev->next = node_b;
2452
2453 if (a_next)
2454 a_next->prev = node_b;
2455
2456 if (!b_prev)
2457 parent_node->children = node_a;
2458 else
2459 b_prev->next = node_a;
2460
2461 if (b_next)
2462 b_next->prev = node_a;
2463
2464 node_a->prev = b_prev;
2465 node_a->next = b_next;
2466
2467 node_b->prev = a_prev;
2468 node_b->next = a_next;
2469
2470 /* emit signal */
2471 order = g_new (gint, length)((gint *) g_malloc_n ((length), sizeof (gint)));
2472 for (i = 0; i < length; i++)
2473 if (i == a_count)
2474 order[i] = b_count;
2475 else if (i == b_count)
2476 order[i] = a_count;
2477 else
2478 order[i] = i;
2479
2480 ctk_tree_model_rows_reordered (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, path_a,
2481 parent_node == tree_store->priv->root
2482 ? NULL((void*)0) : &parent, order);
2483 ctk_tree_path_free (path_a);
2484 g_free (order);
2485}
2486
2487/* WARNING: this function is *incredibly* fragile. Please smashtest after
2488 * making changes here.
2489 * -Kris
2490 */
2491static void
2492ctk_tree_store_move (CtkTreeStore *tree_store,
2493 CtkTreeIter *iter,
2494 CtkTreeIter *position,
2495 gboolean before)
2496{
2497 GNode *parent, *node, *a, *b, *tmp, *tmp_a, *tmp_b;
2498 gint old_pos, new_pos, length, i, *order;
2499 CtkTreePath *path = NULL((void*)0), *tmppath, *pos_path = NULL((void*)0);
2500 CtkTreeIter parent_iter, dst_a, dst_b;
2501 gint depth = 0;
2502 gboolean handle_b = TRUE(!(0));
2503
2504 g_return_if_fail (CTK_IS_TREE_STORE (tree_store))do { if (((((__extension__ ({ GTypeInstance *__inst = (GTypeInstance
*) ((tree_store)); GType __t = ((ctk_tree_store_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 ("Ctk", ((const char
*) (__func__)), "CTK_IS_TREE_STORE (tree_store)"); return; } }
while (0)
;
2505 g_return_if_fail (!CTK_TREE_STORE_IS_SORTED (tree_store))do { if ((!(((CtkTreeStore*)(tree_store))->priv->sort_column_id
!= (-2)))) { } else { g_return_if_fail_warning ("Ctk", ((const
char*) (__func__)), "!CTK_TREE_STORE_IS_SORTED (tree_store)"
); return; } } while (0)
;
2506 g_return_if_fail (VALID_ITER (iter, tree_store))do { if ((((iter)!= ((void*)0) && (iter)->user_data
!= ((void*)0) && ((CtkTreeStore*)(tree_store))->priv
->stamp == (iter)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (iter, tree_store)"
); return; } } while (0)
;
2507 if (position)
2508 g_return_if_fail (VALID_ITER (position, tree_store))do { if ((((position)!= ((void*)0) && (position)->
user_data != ((void*)0) && ((CtkTreeStore*)(tree_store
))->priv->stamp == (position)->stamp))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "VALID_ITER (position, tree_store)"
); return; } } while (0)
;
2509
2510 a = b = NULL((void*)0);
2511
2512 /* sanity checks */
2513 if (position)
2514 {
2515 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
2516 pos_path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2517 position);
2518
2519 /* if before:
2520 * moving the iter before path or "path + 1" doesn't make sense
2521 * else
2522 * moving the iter before path or "path - 1" doesn't make sense
2523 */
2524 if (!ctk_tree_path_compare (path, pos_path))
2525 goto free_paths_and_out;
2526
2527 if (before)
2528 ctk_tree_path_next (path);
2529 else
2530 ctk_tree_path_prev (path);
2531
2532 if (!ctk_tree_path_compare (path, pos_path))
2533 goto free_paths_and_out;
2534
2535 if (before)
2536 ctk_tree_path_prev (path);
2537 else
2538 ctk_tree_path_next (path);
2539
2540 if (ctk_tree_path_get_depth (path) != ctk_tree_path_get_depth (pos_path))
2541 {
2542 g_warning ("Given children are not in the same level\n");
2543
2544 goto free_paths_and_out;
2545 }
2546
2547 tmppath = ctk_tree_path_copy (pos_path);
2548 ctk_tree_path_up (path);
2549 ctk_tree_path_up (tmppath);
2550
2551 if (ctk_tree_path_get_depth (path) > 0 &&
2552 ctk_tree_path_compare (path, tmppath))
2553 {
2554 g_warning ("Given children are not in the same level\n");
2555
2556 ctk_tree_path_free (tmppath);
2557 goto free_paths_and_out;
2558 }
2559
2560 ctk_tree_path_free (tmppath);
2561 }
2562
2563 if (!path)
2564 {
2565 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter);
2566 ctk_tree_path_up (path);
2567 }
2568
2569 depth = ctk_tree_path_get_depth (path);
2570
2571 if (depth)
2572 {
2573 ctk_tree_store_get_iter (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2574 &parent_iter, path);
2575
2576 parent = G_NODE (parent_iter.user_data)((GNode *)parent_iter.user_data);
2577 }
2578 else
2579 parent = G_NODE (tree_store->priv->root)((GNode *)tree_store->priv->root);
2580
2581 /* yes, I know that this can be done shorter, but I'm doing it this way
2582 * so the code is also maintainable
2583 */
2584
2585 if (before && position)
2586 {
2587 b = G_NODE (position->user_data)((GNode *)position->user_data);
2588
2589 if (ctk_tree_path_get_indices (pos_path)[ctk_tree_path_get_depth (pos_path) - 1] > 0)
2590 {
2591 ctk_tree_path_prev (pos_path);
2592 if (ctk_tree_store_get_iter (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2593 &dst_a, pos_path))
2594 a = G_NODE (dst_a.user_data)((GNode *)dst_a.user_data);
2595 else
2596 a = NULL((void*)0);
2597 ctk_tree_path_next (pos_path);
2598 }
2599
2600 /* if b is NULL, a is NULL too -- we are at the beginning of the list
2601 * yes and we leak memory here ...
2602 */
2603 g_return_if_fail (b)do { if ((b)) { } else { g_return_if_fail_warning ("Ctk", ((const
char*) (__func__)), "b"); return; } } while (0)
;
2604 }
2605 else if (before && !position)
2606 {
2607 /* move before without position is appending */
2608 a = NULL((void*)0);
2609 b = NULL((void*)0);
2610 }
2611 else /* !before */
2612 {
2613 if (position)
2614 a = G_NODE (position->user_data)((GNode *)position->user_data);
2615 else
2616 a = NULL((void*)0);
2617
2618 if (position)
2619 {
2620 ctk_tree_path_next (pos_path);
2621 if (ctk_tree_store_get_iter (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &dst_b, pos_path))
2622 b = G_NODE (dst_b.user_data)((GNode *)dst_b.user_data);
2623 else
2624 b = NULL((void*)0);
2625 ctk_tree_path_prev (pos_path);
2626 }
2627 else
2628 {
2629 /* move after without position is prepending */
2630 if (depth)
2631 ctk_tree_store_iter_children (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &dst_b,
2632 &parent_iter);
2633 else
2634 ctk_tree_store_iter_children (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &dst_b,
2635 NULL((void*)0));
2636
2637 b = G_NODE (dst_b.user_data)((GNode *)dst_b.user_data);
2638 }
2639
2640 /* if a is NULL, b is NULL too -- we are at the end of the list
2641 * yes and we leak memory here ...
2642 */
2643 if (position)
2644 g_return_if_fail (a)do { if ((a)) { } else { g_return_if_fail_warning ("Ctk", ((const
char*) (__func__)), "a"); return; } } while (0)
;
2645 }
2646
2647 /* counting nodes */
2648 tmp = parent->children;
2649
2650 length = old_pos = 0;
2651 while (tmp)
2652 {
2653 if (tmp == iter->user_data)
2654 old_pos = length;
2655
2656 tmp = tmp->next;
2657 length++;
2658 }
2659
2660 /* remove node from list */
2661 node = G_NODE (iter->user_data)((GNode *)iter->user_data);
2662 tmp_a = node->prev;
2663 tmp_b = node->next;
2664
2665 if (tmp_a)
2666 tmp_a->next = tmp_b;
2667 else
2668 parent->children = tmp_b;
2669
2670 if (tmp_b)
2671 tmp_b->prev = tmp_a;
2672
2673 /* and reinsert the node */
2674 if (a)
2675 {
2676 tmp = a->next;
2677
2678 a->next = node;
2679 node->next = tmp;
2680 node->prev = a;
2681 }
2682 else if (!a && !before)
2683 {
2684 tmp = parent->children;
2685
2686 node->prev = NULL((void*)0);
2687 parent->children = node;
2688
2689 node->next = tmp;
2690 if (tmp)
2691 tmp->prev = node;
2692
2693 handle_b = FALSE(0);
2694 }
2695 else if (!a && before)
2696 {
2697 if (!position)
2698 {
2699 node->parent = NULL((void*)0);
2700 node->next = node->prev = NULL((void*)0);
2701
2702 /* before with sibling = NULL appends */
2703 g_node_insert_before (parent, NULL((void*)0), node);
2704 }
2705 else
2706 {
2707 node->parent = NULL((void*)0);
2708 node->next = node->prev = NULL((void*)0);
2709
2710 /* after with sibling = NULL prepends */
2711 g_node_insert_after (parent, NULL((void*)0), node);
2712 }
2713
2714 handle_b = FALSE(0);
2715 }
2716
2717 if (handle_b)
2718 {
2719 if (b)
2720 {
2721 tmp = b->prev;
2722
2723 b->prev = node;
2724 node->prev = tmp;
2725 node->next = b;
2726 }
2727 else if (!(!a && before)) /* !a && before is completely handled above */
2728 node->next = NULL((void*)0);
2729 }
2730
2731 /* emit signal */
2732 if (position)
2733 new_pos = ctk_tree_path_get_indices (pos_path)[ctk_tree_path_get_depth (pos_path)-1];
2734 else if (before)
2735 {
2736 if (depth)
2737 new_pos = ctk_tree_store_iter_n_children (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2738 &parent_iter) - 1;
2739 else
2740 new_pos = ctk_tree_store_iter_n_children (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2741 NULL((void*)0)) - 1;
2742 }
2743 else
2744 new_pos = 0;
2745
2746 if (new_pos > old_pos)
2747 {
2748 if (before && position)
2749 new_pos--;
2750 }
2751 else
2752 {
2753 if (!before && position)
2754 new_pos++;
2755 }
2756
2757 order = g_new (gint, length)((gint *) g_malloc_n ((length), sizeof (gint)));
2758 if (new_pos > old_pos)
2759 {
2760 for (i = 0; i < length; i++)
2761 if (i < old_pos)
2762 order[i] = i;
2763 else if (i >= old_pos && i < new_pos)
2764 order[i] = i + 1;
2765 else if (i == new_pos)
2766 order[i] = old_pos;
2767 else
2768 order[i] = i;
2769 }
2770 else
2771 {
2772 for (i = 0; i < length; i++)
2773 if (i == new_pos)
2774 order[i] = old_pos;
2775 else if (i > new_pos && i <= old_pos)
2776 order[i] = i - 1;
2777 else
2778 order[i] = i;
2779 }
2780
2781 if (depth)
2782 {
2783 tmppath = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2784 &parent_iter);
2785 ctk_tree_model_rows_reordered (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2786 tmppath, &parent_iter, order);
2787 }
2788 else
2789 {
2790 tmppath = ctk_tree_path_new ();
2791 ctk_tree_model_rows_reordered (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2792 tmppath, NULL((void*)0), order);
2793 }
2794
2795 ctk_tree_path_free (tmppath);
2796 ctk_tree_path_free (path);
2797 if (position)
2798 ctk_tree_path_free (pos_path);
2799 g_free (order);
2800
2801 return;
2802
2803free_paths_and_out:
2804 ctk_tree_path_free (path);
2805 ctk_tree_path_free (pos_path);
2806}
2807
2808/**
2809 * ctk_tree_store_move_before:
2810 * @tree_store: A #CtkTreeStore.
2811 * @iter: A #CtkTreeIter.
2812 * @position: (allow-none): A #CtkTreeIter or %NULL.
2813 *
2814 * Moves @iter in @tree_store to the position before @position. @iter and
2815 * @position should be in the same level. Note that this function only
2816 * works with unsorted stores. If @position is %NULL, @iter will be
2817 * moved to the end of the level.
2818 *
2819 * Since: 2.2
2820 **/
2821void
2822ctk_tree_store_move_before (CtkTreeStore *tree_store,
2823 CtkTreeIter *iter,
2824 CtkTreeIter *position)
2825{
2826 ctk_tree_store_move (tree_store, iter, position, TRUE(!(0)));
2827}
2828
2829/**
2830 * ctk_tree_store_move_after:
2831 * @tree_store: A #CtkTreeStore.
2832 * @iter: A #CtkTreeIter.
2833 * @position: (allow-none): A #CtkTreeIter.
2834 *
2835 * Moves @iter in @tree_store to the position after @position. @iter and
2836 * @position should be in the same level. Note that this function only
2837 * works with unsorted stores. If @position is %NULL, @iter will be moved
2838 * to the start of the level.
2839 *
2840 * Since: 2.2
2841 **/
2842void
2843ctk_tree_store_move_after (CtkTreeStore *tree_store,
2844 CtkTreeIter *iter,
2845 CtkTreeIter *position)
2846{
2847 ctk_tree_store_move (tree_store, iter, position, FALSE(0));
2848}
2849
2850/* Sorting */
2851static gint
2852ctk_tree_store_compare_func (gconstpointer a,
2853 gconstpointer b,
2854 gpointer user_data)
2855{
2856 CtkTreeStore *tree_store = user_data;
2857 CtkTreeStorePrivate *priv = tree_store->priv;
2858 GNode *node_a;
2859 GNode *node_b;
2860 CtkTreeIterCompareFunc func;
2861 gpointer data;
2862
2863 CtkTreeIter iter_a;
2864 CtkTreeIter iter_b;
2865 gint retval;
2866
2867 if (priv->sort_column_id != -1)
2868 {
2869 CtkTreeDataSortHeader *header;
2870
2871 header = _ctk_tree_data_list_get_header (priv->sort_list,
2872 priv->sort_column_id);
2873 g_return_val_if_fail (header != NULL, 0)do { if ((header != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header != NULL"); return
(0); } } while (0)
;
2874 g_return_val_if_fail (header->func != NULL, 0)do { if ((header->func != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header->func != NULL"
); return (0); } } while (0)
;
2875
2876 func = header->func;
2877 data = header->data;
2878 }
2879 else
2880 {
2881 g_return_val_if_fail (priv->default_sort_func != NULL, 0)do { if ((priv->default_sort_func != ((void*)0))) { } else
{ g_return_if_fail_warning ("Ctk", ((const char*) (__func__)
), "priv->default_sort_func != NULL"); return (0); } } while
(0)
;
2882 func = priv->default_sort_func;
2883 data = priv->default_sort_data;
2884 }
2885
2886 node_a = ((SortTuple *) a)->node;
2887 node_b = ((SortTuple *) b)->node;
2888
2889 iter_a.stamp = priv->stamp;
2890 iter_a.user_data = node_a;
2891 iter_b.stamp = priv->stamp;
2892 iter_b.user_data = node_b;
2893
2894 retval = (* func) (CTK_TREE_MODEL (user_data)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((user_data)), ((ctk_tree_model_get_type ()))))))
, &iter_a, &iter_b, data);
2895
2896 if (priv->order == CTK_SORT_DESCENDING)
2897 {
2898 if (retval > 0)
2899 retval = -1;
2900 else if (retval < 0)
2901 retval = 1;
2902 }
2903 return retval;
2904}
2905
2906static void
2907ctk_tree_store_sort_helper (CtkTreeStore *tree_store,
2908 GNode *parent,
2909 gboolean recurse)
2910{
2911 CtkTreeIter iter;
2912 GArray *sort_array;
2913 GNode *node;
2914 GNode *tmp_node;
2915 gint list_length;
2916 gint i;
2917 gint *new_order;
2918 CtkTreePath *path;
2919
2920 node = parent->children;
2921 if (node == NULL((void*)0) || node->next == NULL((void*)0))
2922 {
2923 if (recurse && node && node->children)
2924 ctk_tree_store_sort_helper (tree_store, node, TRUE(!(0)));
2925
2926 return;
2927 }
2928
2929 list_length = 0;
2930 for (tmp_node = node; tmp_node; tmp_node = tmp_node->next)
2931 list_length++;
2932
2933 sort_array = g_array_sized_new (FALSE(0), FALSE(0), sizeof (SortTuple), list_length);
2934
2935 i = 0;
2936 for (tmp_node = node; tmp_node; tmp_node = tmp_node->next)
2937 {
2938 SortTuple tuple;
2939
2940 tuple.offset = i;
2941 tuple.node = tmp_node;
2942 g_array_append_val (sort_array, tuple)g_array_append_vals (sort_array, &(tuple), 1);
2943 i++;
2944 }
2945
2946 /* Sort the array */
2947 g_array_sort_with_data (sort_array, ctk_tree_store_compare_func, tree_store);
2948
2949 for (i = 0; i < list_length - 1; i++)
2950 {
2951 g_array_index (sort_array, SortTuple, i)(((SortTuple*) (void *) (sort_array)->data) [(i)]).node->next =
2952 g_array_index (sort_array, SortTuple, i + 1)(((SortTuple*) (void *) (sort_array)->data) [(i + 1)]).node;
2953 g_array_index (sort_array, SortTuple, i + 1)(((SortTuple*) (void *) (sort_array)->data) [(i + 1)]).node->prev =
2954 g_array_index (sort_array, SortTuple, i)(((SortTuple*) (void *) (sort_array)->data) [(i)]).node;
2955 }
2956 g_array_index (sort_array, SortTuple, list_length - 1)(((SortTuple*) (void *) (sort_array)->data) [(list_length -
1)])
.node->next = NULL((void*)0);
2957 g_array_index (sort_array, SortTuple, 0)(((SortTuple*) (void *) (sort_array)->data) [(0)]).node->prev = NULL((void*)0);
2958 parent->children = g_array_index (sort_array, SortTuple, 0)(((SortTuple*) (void *) (sort_array)->data) [(0)]).node;
2959
2960 /* Let the world know about our new order */
2961 new_order = g_new (gint, list_length)((gint *) g_malloc_n ((list_length), sizeof (gint)));
2962 for (i = 0; i < list_length; i++)
2963 new_order[i] = g_array_index (sort_array, SortTuple, i)(((SortTuple*) (void *) (sort_array)->data) [(i)]).offset;
2964
2965 iter.stamp = tree_store->priv->stamp;
2966 iter.user_data = parent;
2967 path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &iter);
2968 ctk_tree_model_rows_reordered (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
2969 path, &iter, new_order);
2970 ctk_tree_path_free (path);
2971 g_free (new_order);
2972 g_array_free (sort_array, TRUE(!(0)));
2973
2974 if (recurse)
2975 {
2976 for (tmp_node = parent->children; tmp_node; tmp_node = tmp_node->next)
2977 {
2978 if (tmp_node->children)
2979 ctk_tree_store_sort_helper (tree_store, tmp_node, TRUE(!(0)));
2980 }
2981 }
2982}
2983
2984static void
2985ctk_tree_store_sort (CtkTreeStore *tree_store)
2986{
2987 CtkTreeStorePrivate *priv = tree_store->priv;
2988
2989 if (!CTK_TREE_STORE_IS_SORTED (tree_store)(((CtkTreeStore*)(tree_store))->priv->sort_column_id !=
(-2))
)
2990 return;
2991
2992 if (priv->sort_column_id != -1)
2993 {
2994 CtkTreeDataSortHeader *header = NULL((void*)0);
2995
2996 header = _ctk_tree_data_list_get_header (priv->sort_list,
2997 priv->sort_column_id);
2998
2999 /* We want to make sure that we have a function */
3000 g_return_if_fail (header != NULL)do { if ((header != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header != NULL"); return
; } } while (0)
;
3001 g_return_if_fail (header->func != NULL)do { if ((header->func != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header->func != NULL"
); return; } } while (0)
;
3002 }
3003 else
3004 {
3005 g_return_if_fail (priv->default_sort_func != NULL)do { if ((priv->default_sort_func != ((void*)0))) { } else
{ g_return_if_fail_warning ("Ctk", ((const char*) (__func__)
), "priv->default_sort_func != NULL"); return; } } while (
0)
;
3006 }
3007
3008 ctk_tree_store_sort_helper (tree_store, G_NODE (priv->root)((GNode *)priv->root), TRUE(!(0)));
3009}
3010
3011static void
3012ctk_tree_store_sort_iter_changed (CtkTreeStore *tree_store,
3013 CtkTreeIter *iter,
3014 gint column,
3015 gboolean emit_signal)
3016{
3017 CtkTreeStorePrivate *priv = tree_store->priv;
3018 GNode *prev = NULL((void*)0);
3019 GNode *next = NULL((void*)0);
3020 GNode *node;
3021 CtkTreePath *tmp_path;
3022 CtkTreeIter tmp_iter;
3023 gint cmp_a = 0;
3024 gint cmp_b = 0;
3025 gint i;
3026 gint old_location;
3027 gint new_location;
3028 gint *new_order;
3029 gint length;
3030 CtkTreeIterCompareFunc func;
3031 gpointer data;
3032
3033 g_return_if_fail (G_NODE (iter->user_data)->parent != NULL)do { if ((((GNode *)iter->user_data)->parent != ((void*
)0))) { } else { g_return_if_fail_warning ("Ctk", ((const char
*) (__func__)), "G_NODE (iter->user_data)->parent != NULL"
); return; } } while (0)
;
3034
3035 tmp_iter.stamp = priv->stamp;
3036 if (priv->sort_column_id != -1)
3037 {
3038 CtkTreeDataSortHeader *header;
3039 header = _ctk_tree_data_list_get_header (priv->sort_list,
3040 priv->sort_column_id);
3041 g_return_if_fail (header != NULL)do { if ((header != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header != NULL"); return
; } } while (0)
;
3042 g_return_if_fail (header->func != NULL)do { if ((header->func != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header->func != NULL"
); return; } } while (0)
;
3043 func = header->func;
3044 data = header->data;
3045 }
3046 else
3047 {
3048 g_return_if_fail (priv->default_sort_func != NULL)do { if ((priv->default_sort_func != ((void*)0))) { } else
{ g_return_if_fail_warning ("Ctk", ((const char*) (__func__)
), "priv->default_sort_func != NULL"); return; } } while (
0)
;
3049 func = priv->default_sort_func;
3050 data = priv->default_sort_data;
3051 }
3052
3053 /* If it's the built in function, we don't sort. */
3054 if (func == _ctk_tree_data_list_compare_func &&
3055 priv->sort_column_id != column)
3056 return;
3057
3058 old_location = 0;
3059 node = G_NODE (iter->user_data)((GNode *)iter->user_data)->parent->children;
3060 /* First we find the iter, its prev, and its next */
3061 while (node)
3062 {
3063 if (node == G_NODE (iter->user_data)((GNode *)iter->user_data))
3064 break;
3065 old_location++;
3066 node = node->next;
3067 }
3068 g_assert (node != NULL)do { if (node != ((void*)0)) ; else g_assertion_message_expr (
"Ctk", "ctktreestore.c", 3068, ((const char*) (__func__)), "node != NULL"
); } while (0)
;
3069
3070 prev = node->prev;
3071 next = node->next;
3072
3073 /* Check the common case, where we don't need to sort it moved. */
3074 if (prev != NULL((void*)0))
3075 {
3076 tmp_iter.user_data = prev;
3077 cmp_a = (* func) (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &tmp_iter, iter, data);
3078 }
3079
3080 if (next != NULL((void*)0))
3081 {
3082 tmp_iter.user_data = next;
3083 cmp_b = (* func) (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter, &tmp_iter, data);
3084 }
3085
3086 if (priv->order == CTK_SORT_DESCENDING)
3087 {
3088 if (cmp_a < 0)
3089 cmp_a = 1;
3090 else if (cmp_a > 0)
3091 cmp_a = -1;
3092
3093 if (cmp_b < 0)
3094 cmp_b = 1;
3095 else if (cmp_b > 0)
3096 cmp_b = -1;
3097 }
3098
3099 if (prev == NULL((void*)0) && cmp_b <= 0)
3100 return;
3101 else if (next == NULL((void*)0) && cmp_a <= 0)
3102 return;
3103 else if (prev != NULL((void*)0) && next != NULL((void*)0) &&
3104 cmp_a <= 0 && cmp_b <= 0)
3105 return;
3106
3107 /* We actually need to sort it */
3108 /* First, remove the old link. */
3109
3110 if (prev)
3111 prev->next = next;
3112 else
3113 node->parent->children = next;
3114
3115 if (next)
3116 next->prev = prev;
3117
3118 node->prev = NULL((void*)0);
3119 node->next = NULL((void*)0);
3120
3121 /* FIXME: as an optimization, we can potentially start at next */
3122 prev = NULL((void*)0);
3123 node = node->parent->children;
3124 new_location = 0;
3125 tmp_iter.user_data = node;
3126 if (priv->order == CTK_SORT_DESCENDING)
3127 cmp_a = (* func) (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &tmp_iter, iter, data);
3128 else
3129 cmp_a = (* func) (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter, &tmp_iter, data);
3130
3131 while ((node->next) && (cmp_a > 0))
3132 {
3133 prev = node;
3134 node = node->next;
3135 new_location++;
3136 tmp_iter.user_data = node;
3137 if (priv->order == CTK_SORT_DESCENDING)
3138 cmp_a = (* func) (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &tmp_iter, iter, data);
3139 else
3140 cmp_a = (* func) (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, iter, &tmp_iter, data);
3141 }
3142
3143 if ((!node->next) && (cmp_a > 0))
3144 {
3145 new_location++;
3146 node->next = G_NODE (iter->user_data)((GNode *)iter->user_data);
3147 node->next->prev = node;
3148 }
3149 else if (prev)
3150 {
3151 prev->next = G_NODE (iter->user_data)((GNode *)iter->user_data);
3152 prev->next->prev = prev;
3153 G_NODE (iter->user_data)((GNode *)iter->user_data)->next = node;
3154 G_NODE (iter->user_data)((GNode *)iter->user_data)->next->prev = G_NODE (iter->user_data)((GNode *)iter->user_data);
3155 }
3156 else
3157 {
3158 G_NODE (iter->user_data)((GNode *)iter->user_data)->next = G_NODE (iter->user_data)((GNode *)iter->user_data)->parent->children;
3159 G_NODE (iter->user_data)((GNode *)iter->user_data)->next->prev = G_NODE (iter->user_data)((GNode *)iter->user_data);
3160 G_NODE (iter->user_data)((GNode *)iter->user_data)->parent->children = G_NODE (iter->user_data)((GNode *)iter->user_data);
3161 }
3162
3163 if (!emit_signal)
3164 return;
3165
3166 /* Emit the reordered signal. */
3167 length = g_node_n_children (node->parent);
3168 new_order = g_new (int, length)((int *) g_malloc_n ((length), sizeof (int)));
3169 if (old_location < new_location)
3170 for (i = 0; i < length; i++)
3171 {
3172 if (i < old_location ||
3173 i > new_location)
3174 new_order[i] = i;
3175 else if (i >= old_location &&
3176 i < new_location)
3177 new_order[i] = i + 1;
3178 else if (i == new_location)
3179 new_order[i] = old_location;
3180 }
3181 else
3182 for (i = 0; i < length; i++)
3183 {
3184 if (i < new_location ||
3185 i > old_location)
3186 new_order[i] = i;
3187 else if (i > new_location &&
3188 i <= old_location)
3189 new_order[i] = i - 1;
3190 else if (i == new_location)
3191 new_order[i] = old_location;
3192 }
3193
3194 tmp_iter.user_data = node->parent;
3195 tmp_path = ctk_tree_store_get_path (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
, &tmp_iter);
3196
3197 ctk_tree_model_rows_reordered (CTK_TREE_MODEL (tree_store)((((CtkTreeModel*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((tree_store)), ((ctk_tree_model_get_type ()))))))
,
3198 tmp_path, &tmp_iter,
3199 new_order);
3200
3201 ctk_tree_path_free (tmp_path);
3202 g_free (new_order);
3203}
3204
3205
3206static gboolean
3207ctk_tree_store_get_sort_column_id (CtkTreeSortable *sortable,
3208 gint *sort_column_id,
3209 CtkSortType *order)
3210{
3211 CtkTreeStore *tree_store = (CtkTreeStore *) sortable;
3212 CtkTreeStorePrivate *priv = tree_store->priv;
3213
3214 if (sort_column_id)
3215 * sort_column_id = priv->sort_column_id;
3216 if (order)
3217 * order = priv->order;
3218
3219 if (priv->sort_column_id == CTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID(-1) ||
3220 priv->sort_column_id == CTK_TREE_SORTABLE_UNSORTED_SORT_COLUMN_ID(-2))
3221 return FALSE(0);
3222
3223 return TRUE(!(0));
3224}
3225
3226static void
3227ctk_tree_store_set_sort_column_id (CtkTreeSortable *sortable,
3228 gint sort_column_id,
3229 CtkSortType order)
3230{
3231 CtkTreeStore *tree_store = (CtkTreeStore *) sortable;
3232 CtkTreeStorePrivate *priv = tree_store->priv;
3233
3234 if ((priv->sort_column_id == sort_column_id) &&
3235 (priv->order == order))
3236 return;
3237
3238 if (sort_column_id != CTK_TREE_SORTABLE_UNSORTED_SORT_COLUMN_ID(-2))
3239 {
3240 if (sort_column_id != CTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID(-1))
3241 {
3242 CtkTreeDataSortHeader *header = NULL((void*)0);
3243
3244 header = _ctk_tree_data_list_get_header (priv->sort_list,
3245 sort_column_id);
3246
3247 /* We want to make sure that we have a function */
3248 g_return_if_fail (header != NULL)do { if ((header != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header != NULL"); return
; } } while (0)
;
3249 g_return_if_fail (header->func != NULL)do { if ((header->func != ((void*)0))) { } else { g_return_if_fail_warning
("Ctk", ((const char*) (__func__)), "header->func != NULL"
); return; } } while (0)
;
3250 }
3251 else
3252 {
3253 g_return_if_fail (priv->default_sort_func != NULL)do { if ((priv->default_sort_func != ((void*)0))) { } else
{ g_return_if_fail_warning ("Ctk", ((const char*) (__func__)
), "priv->default_sort_func != NULL"); return; } } while (
0)
;
3254 }
3255 }
3256
3257 priv->sort_column_id = sort_column_id;
3258 priv->order = order;
3259
3260 ctk_tree_sortable_sort_column_changed (sortable);
3261
3262 ctk_tree_store_sort (tree_store);
3263}
3264
3265static void
3266ctk_tree_store_set_sort_func (CtkTreeSortable *sortable,
3267 gint sort_column_id,
3268 CtkTreeIterCompareFunc func,
3269 gpointer data,
3270 GDestroyNotify destroy)
3271{
3272 CtkTreeStore *tree_store = (CtkTreeStore *) sortable;
3273 CtkTreeStorePrivate *priv = tree_store->priv;
3274
3275 priv->sort_list = _ctk_tree_data_list_set_header (priv->sort_list,
3276 sort_column_id,
3277 func, data, destroy);
3278
3279 if (priv->sort_column_id == sort_column_id)
3280 ctk_tree_store_sort (tree_store);
3281}
3282
3283static void
3284ctk_tree_store_set_default_sort_func (CtkTreeSortable *sortable,
3285 CtkTreeIterCompareFunc func,
3286 gpointer data,
3287 GDestroyNotify destroy)
3288{
3289 CtkTreeStore *tree_store = (CtkTreeStore *) sortable;
3290 CtkTreeStorePrivate *priv = tree_store->priv;
3291
3292 if (priv->default_sort_destroy)
3293 {
3294 GDestroyNotify d = priv->default_sort_destroy;
3295
3296 priv->default_sort_destroy = NULL((void*)0);
3297 d (priv->default_sort_data);
3298 }
3299
3300 priv->default_sort_func = func;
3301 priv->default_sort_data = data;
3302 priv->default_sort_destroy = destroy;
3303
3304 if (priv->sort_column_id == CTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID(-1))
3305 ctk_tree_store_sort (tree_store);
3306}
3307
3308static gboolean
3309ctk_tree_store_has_default_sort_func (CtkTreeSortable *sortable)
3310{
3311 CtkTreeStore *tree_store = (CtkTreeStore *) sortable;
3312
3313 return (tree_store->priv->default_sort_func != NULL((void*)0));
3314}
3315
3316#ifdef G_ENABLE_DEBUG1
3317static void
3318validate_gnode (GNode* node)
3319{
3320 GNode *iter;
3321
3322 iter = node->children;
3323 while (iter != NULL((void*)0))
3324 {
3325 g_assert (iter->parent == node)do { if (iter->parent == node) ; else g_assertion_message_expr
("Ctk", "ctktreestore.c", 3325, ((const char*) (__func__)), "iter->parent == node"
); } while (0)
;
3326 if (iter->prev)
3327 g_assert (iter->prev->next == iter)do { if (iter->prev->next == iter) ; else g_assertion_message_expr
("Ctk", "ctktreestore.c", 3327, ((const char*) (__func__)), "iter->prev->next == iter"
); } while (0)
;
3328 validate_gnode (iter);
3329 iter = iter->next;
3330 }
3331}
3332#endif
3333
3334/* CtkBuildable custom tag implementation
3335 *
3336 * <columns>
3337 * <column type="..."/>
3338 * <column type="..."/>
3339 * </columns>
3340 */
3341typedef struct {
3342 CtkBuilder *builder;
3343 GObject *object;
3344 GSList *items;
3345} GSListSubParserData;
3346
3347static void
3348tree_model_start_element (GMarkupParseContext *context,
3349 const gchar *element_name,
3350 const gchar **names,
3351 const gchar **values,
3352 gpointer user_data,
3353 GError **error)
3354{
3355 GSListSubParserData *data = (GSListSubParserData*)user_data;
3356
3357 if (strcmp (element_name, "columns") == 0)
3358 {
3359 if (!_ctk_builder_check_parent (data->builder, context, "object", error))
3360 return;
3361
3362 if (!g_markup_collect_attributes (element_name, names, values, error,
3363 G_MARKUP_COLLECT_INVALID, NULL((void*)0), NULL((void*)0),
3364 G_MARKUP_COLLECT_INVALID))
3365 _ctk_builder_prefix_error (data->builder, context, error);
3366
3367 }
3368 else if (strcmp (element_name, "column") == 0)
3369 {
3370 const gchar *type;
3371
3372 if (!_ctk_builder_check_parent (data->builder, context, "columns", error))
3373 return;
3374
3375 if (!g_markup_collect_attributes (element_name, names, values, error,
3376 G_MARKUP_COLLECT_STRING, "type", &type,
3377 G_MARKUP_COLLECT_INVALID))
3378 {
3379 _ctk_builder_prefix_error (data->builder, context, error);
3380 return;
3381 }
3382
3383 data->items = g_slist_prepend (data->items, g_strdup (type)g_strdup_inline (type));
3384 }
3385 else
3386 {
3387 _ctk_builder_error_unhandled_tag (data->builder, context,
3388 "CtkTreeStore", element_name,
3389 error);
3390 }
3391}
3392
3393static void
3394tree_model_end_element (GMarkupParseContext *context G_GNUC_UNUSED__attribute__ ((__unused__)),
3395 const gchar *element_name,
3396 gpointer user_data,
3397 GError **error G_GNUC_UNUSED__attribute__ ((__unused__)))
3398{
3399 GSListSubParserData *data = (GSListSubParserData*)user_data;
3400
3401 g_assert(data->builder)do { if (data->builder) ; else g_assertion_message_expr ("Ctk"
, "ctktreestore.c", 3401, ((const char*) (__func__)), "data->builder"
); } while (0)
;
1
Assuming field 'builder' is non-null
2
Taking true branch
3
Loop condition is false. Exiting loop
3402
3403 if (strcmp (element_name, "columns") == 0)
4
Taking true branch
3404 {
3405 GSList *l;
3406 GType *types;
3407 int i;
3408 GType type;
3409
3410 data = (GSListSubParserData*)user_data;
3411 data->items = g_slist_reverse (data->items);
3412 types = g_new0 (GType, g_slist_length (data->items))((GType *) g_malloc0_n ((g_slist_length (data->items)), sizeof
(GType)))
;
3413
3414 for (l = data->items, i = 0; l; l = l->next, i++)
5
Loop condition is false. Execution continues on line 3429
3415 {
3416 type = ctk_builder_get_type_from_name (data->builder, l->data);
3417 if (type == G_TYPE_INVALID((GType) ((0) << (2))))
3418 {
3419 g_warning ("Unknown type %s specified in treemodel %s",
3420 (const gchar*)l->data,
3421 ctk_buildable_get_name (CTK_BUILDABLE (data->object)((((CtkBuildable*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((data->object)), ((ctk_buildable_get_type ()))))))
));
3422 continue;
3423 }
3424 types[i] = type;
3425
3426 g_free (l->data);
3427 }
3428
3429 ctk_tree_store_set_column_types (CTK_TREE_STORE (data->object)((((CtkTreeStore*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((data->object)), ((ctk_tree_store_get_type ()))))))
, i, types)
;
6
Calling 'ctk_tree_store_set_column_types'
3430
3431 g_free (types);
3432 }
3433}
3434
3435static const GMarkupParser tree_model_parser =
3436 {
3437 .start_element = tree_model_start_element,
3438 .end_element = tree_model_end_element
3439 };
3440
3441
3442static gboolean
3443ctk_tree_store_buildable_custom_tag_start (CtkBuildable *buildable,
3444 CtkBuilder *builder,
3445 GObject *child,
3446 const gchar *tagname,
3447 GMarkupParser *parser,
3448 gpointer *parser_data)
3449{
3450 GSListSubParserData *data;
3451
3452 if (child)
3453 return FALSE(0);
3454
3455 if (strcmp (tagname, "columns") == 0)
3456 {
3457 data = g_slice_new0 (GSListSubParserData)((GSListSubParserData*) g_slice_alloc0 (sizeof (GSListSubParserData
)))
;
3458 data->builder = builder;
3459 data->items = NULL((void*)0);
3460 data->object = G_OBJECT (buildable)((((GObject*) (void *) g_type_check_instance_cast ((GTypeInstance
*) ((buildable)), (((GType) ((20) << (2))))))))
;
3461
3462 *parser = tree_model_parser;
3463 *parser_data = data;
3464
3465 return TRUE(!(0));
3466 }
3467
3468 return FALSE(0);
3469}
3470
3471static void
3472ctk_tree_store_buildable_custom_finished (CtkBuildable *buildable G_GNUC_UNUSED__attribute__ ((__unused__)),
3473 CtkBuilder *builder G_GNUC_UNUSED__attribute__ ((__unused__)),
3474 GObject *child G_GNUC_UNUSED__attribute__ ((__unused__)),
3475 const gchar *tagname,
3476 gpointer user_data)
3477{
3478 GSListSubParserData *data;
3479
3480 if (strcmp (tagname, "columns"))
3481 return;
3482
3483 data = (GSListSubParserData*)user_data;
3484
3485 g_slist_free (data->items);
3486 g_slice_free (GSListSubParserData, data)do { if (1) g_slice_free1 (sizeof (GSListSubParserData), (data
)); else (void) ((GSListSubParserData*) 0 == (data)); } while
(0)
;
3487}