1 /* GTK - The GIMP Toolkit
2  * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball, Josh MacDonald
3  * Copyright (C) 1997-1998 Jay Painter <jpaint@serv.net><jpaint@gimp.org>
4  *
5  * GtkCMCTree widget for GTK+
6  * Copyright (C) 1998 Lars Hamann and Stefan Jeske
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the
20  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21  * Boston, MA 02111-1307, USA.
22  */
23 
24 /*
25  * Modified by the GTK+ Team and others 1997-2000.  See the AUTHORS
26  * file for a list of people on the GTK+ Team.  See the ChangeLog
27  * files for a list of changes.  These files are distributed with
28  * GTK+ at ftp://ftp.gtk.org/pub/gtk/.
29  */
30 
31 #ifndef __GTK_CMCTREE_H__
32 #define __GTK_CMCTREE_H__
33 
34 #include "gtkcmclist.h"
35 
36 G_BEGIN_DECLS
37 
38 #define GTK_TYPE_CMCTREE            (gtk_cmctree_get_type ())
39 #define GTK_CMCTREE(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_CMCTREE, GtkCMCTree))
40 #define GTK_CMCTREE_CLASS(klass)    (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_CMCTREE, GtkCMCTreeClass))
41 #define GTK_IS_CMCTREE(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_CMCTREE))
42 #define GTK_IS_CMCTREE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_CMCTREE))
43 #define GTK_CMCTREE_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_CMCTREE, GtkCMCTreeClass))
44 
45 #define GTK_CMCTREE_ROW(_node_) ((GtkCMCTreeRow *)(((GList *)(_node_))->data))
46 #define GTK_CMCTREE_NODE(_node_) ((GtkCMCTreeNode *)((_node_)))
47 #define GTK_CMCTREE_NODE_NEXT(_nnode_) ((GtkCMCTreeNode *)(((GList *)(_nnode_))->next))
48 #define GTK_CMCTREE_NODE_PREV(_pnode_) ((GtkCMCTreeNode *)(((GList *)(_pnode_))->prev))
49 #define GTK_CMCTREE_FUNC(_func_) ((GtkCMCTreeFunc)(_func_))
50 
51 #define GTK_TYPE_CMCTREE_NODE (gtk_cmctree_node_get_type ())
52 
53 GType gtk_cmctree_pos_get_type (void) G_GNUC_CONST;
54 #define GTK_TYPE_CMCTREE_POS (gtk_cmctree_pos_get_type())
55 GType gtk_cmctree_line_style_get_type (void) G_GNUC_CONST;
56 #define GTK_TYPE_CMCTREE_LINE_STYLE (gtk_cmctree_line_style_get_type())
57 GType gtk_cmctree_expander_style_get_type (void) G_GNUC_CONST;
58 #define GTK_TYPE_CMCTREE_EXPANDER_STYLE (gtk_cmctree_expander_style_get_type())
59 GType gtk_cmctree_expansion_type_get_type (void) G_GNUC_CONST;
60 #define GTK_TYPE_CMCTREE_EXPANSION_TYPE (gtk_cmctree_expansion_type_get_type())
61 
62 typedef enum
63 {
64   GTK_CMCTREE_POS_BEFORE,
65   GTK_CMCTREE_POS_AS_CHILD,
66   GTK_CMCTREE_POS_AFTER
67 } GtkCMCTreePos;
68 
69 typedef enum
70 {
71   GTK_CMCTREE_LINES_NONE
72 } GtkCMCTreeLineStyle;
73 
74 typedef enum
75 {
76   GTK_CMCTREE_EXPANDER_NONE,
77   GTK_CMCTREE_EXPANDER_TRIANGLE
78 } GtkCMCTreeExpanderStyle;
79 
80 typedef enum
81 {
82   GTK_CMCTREE_EXPANSION_EXPAND,
83   GTK_CMCTREE_EXPANSION_EXPAND_RECURSIVE,
84   GTK_CMCTREE_EXPANSION_COLLAPSE,
85   GTK_CMCTREE_EXPANSION_COLLAPSE_RECURSIVE,
86   GTK_CMCTREE_EXPANSION_TOGGLE,
87   GTK_CMCTREE_EXPANSION_TOGGLE_RECURSIVE
88 } GtkCMCTreeExpansionType;
89 
90 typedef struct _GtkCMCTree      GtkCMCTree;
91 typedef struct _GtkCMCTreeClass GtkCMCTreeClass;
92 typedef struct _GtkCMCTreeRow   GtkCMCTreeRow;
93 typedef struct _GtkCMCTreeNode  GtkCMCTreeNode;
94 
95 typedef void (*GtkCMCTreeFunc) (GtkCMCTree     *ctree,
96 			      GtkCMCTreeNode *node,
97 			      gpointer      data);
98 
99 typedef gboolean (*GtkCMCTreeGNodeFunc) (GtkCMCTree     *ctree,
100                                        guint         depth,
101                                        GNode        *gnode,
102 				       GtkCMCTreeNode *cnode,
103                                        gpointer      data);
104 
105 typedef gboolean (*GtkCMCTreeCompareDragFunc) (GtkCMCTree     *ctree,
106                                              GtkCMCTreeNode *source_node,
107                                              GtkCMCTreeNode *new_parent,
108                                              GtkCMCTreeNode *new_sibling);
109 
110 struct _GtkCMCTree
111 {
112   GtkCMCList clist;
113 
114   gint tree_indent;
115   gint tree_spacing;
116   gint tree_column;
117 
118   guint line_style     : 2;
119   guint expander_style : 2;
120   guint show_stub      : 1;
121 
122   GtkCMCTreeCompareDragFunc drag_compare;
123 };
124 
125 struct _GtkCMCTreeClass
126 {
127   GtkCMCListClass parent_class;
128 
129   void (*tree_select_row)   (GtkCMCTree     *ctree,
130 			     GtkCMCTreeNode *row,
131 			     gint          column);
132   void (*tree_unselect_row) (GtkCMCTree     *ctree,
133 			     GtkCMCTreeNode *row,
134 			     gint          column);
135   void (*tree_expand)       (GtkCMCTree     *ctree,
136 			     GtkCMCTreeNode *node);
137   void (*tree_collapse)     (GtkCMCTree     *ctree,
138 			     GtkCMCTreeNode *node);
139   void (*tree_move)         (GtkCMCTree     *ctree,
140 			     GtkCMCTreeNode *node,
141 			     GtkCMCTreeNode *new_parent,
142 			     GtkCMCTreeNode *new_sibling);
143   void (*change_focus_row_expansion) (GtkCMCTree *ctree,
144 				      GtkCMCTreeExpansionType action);
145 };
146 
147 struct _GtkCMCTreeRow
148 {
149   GtkCMCListRow row;
150 
151   GtkCMCTreeNode *parent;
152   GtkCMCTreeNode *sibling;
153   GtkCMCTreeNode *children;
154 
155   GdkPixbuf *pixbuf_closed;
156   GdkPixbuf *pixbuf_opened;
157 
158   guint16 level;
159 
160   guint is_leaf  : 1;
161   guint expanded : 1;
162 };
163 
164 struct _GtkCMCTreeNode {
165   GList list;
166 };
167 
168 
169 /***********************************************************
170  *           Creation, insertion, deletion                 *
171  ***********************************************************/
172 
173 GType gtk_cmctree_get_type                       (void);
174 GtkWidget * gtk_cmctree_new_with_titles            (gint          columns,
175 						  gint          tree_column,
176 						  gchar        *titles[]);
177 GtkWidget * gtk_cmctree_new                        (gint          columns,
178 						  gint          tree_column);
179 GtkCMCTreeNode * gtk_cmctree_insert_node             (GtkCMCTree     *ctree,
180 						  GtkCMCTreeNode *parent,
181 						  GtkCMCTreeNode *sibling,
182 						  gchar        *text[],
183 						  guint8        spacing,
184 						  GdkPixbuf    *pixbuf_closed,
185 						  GdkPixbuf    *pixbuf_opened,
186 						  gboolean      is_leaf,
187 						  gboolean      expanded);
188 void gtk_cmctree_remove_node                       (GtkCMCTree     *ctree,
189 						  GtkCMCTreeNode *node);
190 GtkCMCTreeNode * gtk_cmctree_insert_gnode            (GtkCMCTree          *ctree,
191 						  GtkCMCTreeNode      *parent,
192 						  GtkCMCTreeNode      *sibling,
193 						  GNode             *gnode,
194 						  GtkCMCTreeGNodeFunc  func,
195 						  gpointer           data);
196 GNode * gtk_cmctree_export_to_gnode                (GtkCMCTree          *ctree,
197 						  GNode             *parent,
198 						  GNode             *sibling,
199 						  GtkCMCTreeNode      *node,
200 						  GtkCMCTreeGNodeFunc  func,
201 						  gpointer           data);
202 
203 /***********************************************************
204  *  Generic recursive functions, querying / finding tree   *
205  *  information                                            *
206  ***********************************************************/
207 
208 void gtk_cmctree_post_recursive                    (GtkCMCTree     *ctree,
209 						  GtkCMCTreeNode *node,
210 						  GtkCMCTreeFunc  func,
211 						  gpointer      data);
212 void gtk_cmctree_post_recursive_to_depth           (GtkCMCTree     *ctree,
213 						  GtkCMCTreeNode *node,
214 						  gint          depth,
215 						  GtkCMCTreeFunc  func,
216 						  gpointer      data);
217 void gtk_cmctree_pre_recursive                     (GtkCMCTree     *ctree,
218 						  GtkCMCTreeNode *node,
219 						  GtkCMCTreeFunc  func,
220 						  gpointer      data);
221 void gtk_cmctree_pre_recursive_to_depth            (GtkCMCTree     *ctree,
222 						  GtkCMCTreeNode *node,
223 						  gint          depth,
224 						  GtkCMCTreeFunc  func,
225 						  gpointer      data);
226 gboolean gtk_cmctree_is_viewable                   (GtkCMCTree     *ctree,
227 					          GtkCMCTreeNode *node);
228 GtkCMCTreeNode * gtk_cmctree_last                    (GtkCMCTree     *ctree,
229 					          GtkCMCTreeNode *node);
230 GtkCMCTreeNode * gtk_cmctree_find_node_ptr           (GtkCMCTree     *ctree,
231 					          GtkCMCTreeRow  *ctree_row);
232 GtkCMCTreeNode * gtk_cmctree_node_nth                (GtkCMCTree     *ctree,
233 						  guint         row);
234 gboolean gtk_cmctree_find                          (GtkCMCTree     *ctree,
235 					          GtkCMCTreeNode *node,
236 					          GtkCMCTreeNode *child);
237 gboolean gtk_cmctree_is_ancestor                   (GtkCMCTree     *ctree,
238 					          GtkCMCTreeNode *node,
239 					          GtkCMCTreeNode *child);
240 GtkCMCTreeNode * gtk_cmctree_find_by_row_data        (GtkCMCTree     *ctree,
241 					          GtkCMCTreeNode *node,
242 					          gpointer      data);
243 /* returns a GList of all GtkCMCTreeNodes with row->data == data. */
244 GList * gtk_cmctree_find_all_by_row_data           (GtkCMCTree     *ctree,
245 						  GtkCMCTreeNode *node,
246 						  gpointer      data);
247 GtkCMCTreeNode * gtk_cmctree_find_by_row_data_custom (GtkCMCTree     *ctree,
248 						  GtkCMCTreeNode *node,
249 						  gpointer      data,
250 						  GCompareFunc  func);
251 /* returns a GList of all GtkCMCTreeNodes with row->data == data. */
252 GList * gtk_cmctree_find_all_by_row_data_custom    (GtkCMCTree     *ctree,
253 						  GtkCMCTreeNode *node,
254 						  gpointer      data,
255 						  GCompareFunc  func);
256 
257 /* This assumes that x and y coordinates are inside the clist_window.
258  * Returns true if the coordinates are inside a tree expander on
259  * one of the rows. */
260 gboolean gtk_cmctree_is_hot_spot                   (GtkCMCTree     *ctree,
261 					          gint          x,
262 					          gint          y);
263 
264 /***********************************************************
265  *   Tree signals : move, expand, collapse, (un)select     *
266  ***********************************************************/
267 
268 void gtk_cmctree_move                              (GtkCMCTree     *ctree,
269 						  GtkCMCTreeNode *node,
270 						  GtkCMCTreeNode *new_parent,
271 						  GtkCMCTreeNode *new_sibling);
272 void gtk_cmctree_expand                            (GtkCMCTree     *ctree,
273 						  GtkCMCTreeNode *node);
274 void gtk_cmctree_expand_recursive                  (GtkCMCTree     *ctree,
275 						  GtkCMCTreeNode *node);
276 void gtk_cmctree_expand_to_depth                   (GtkCMCTree     *ctree,
277 						  GtkCMCTreeNode *node,
278 						  gint          depth);
279 void gtk_cmctree_collapse                          (GtkCMCTree     *ctree,
280 						  GtkCMCTreeNode *node);
281 void gtk_cmctree_collapse_recursive                (GtkCMCTree     *ctree,
282 						  GtkCMCTreeNode *node);
283 void gtk_cmctree_collapse_to_depth                 (GtkCMCTree     *ctree,
284 						  GtkCMCTreeNode *node,
285 						  gint          depth);
286 void gtk_cmctree_toggle_expansion                  (GtkCMCTree     *ctree,
287 						  GtkCMCTreeNode *node);
288 void gtk_cmctree_toggle_expansion_recursive        (GtkCMCTree     *ctree,
289 						  GtkCMCTreeNode *node);
290 void gtk_cmctree_select                            (GtkCMCTree     *ctree,
291 						  GtkCMCTreeNode *node);
292 void gtk_cmctree_select_recursive                  (GtkCMCTree     *ctree,
293 						  GtkCMCTreeNode *node);
294 void gtk_cmctree_unselect                          (GtkCMCTree     *ctree,
295 						  GtkCMCTreeNode *node);
296 void gtk_cmctree_unselect_recursive                (GtkCMCTree     *ctree,
297 						  GtkCMCTreeNode *node);
298 void gtk_cmctree_real_select_recursive             (GtkCMCTree     *ctree,
299 						  GtkCMCTreeNode *node,
300 						  gint          state);
301 
302 /***********************************************************
303  *           Analogons of GtkCMCList functions               *
304  ***********************************************************/
305 
306 void gtk_cmctree_node_set_text                     (GtkCMCTree     *ctree,
307 						  GtkCMCTreeNode *node,
308 						  gint          column,
309 						  const gchar  *text);
310 void gtk_cmctree_node_set_pixbuf                   (GtkCMCTree     *ctree,
311 						  GtkCMCTreeNode *node,
312 						  gint          column,
313 						  GdkPixbuf    *pixbuf);
314 void gtk_cmctree_node_set_pixtext                  (GtkCMCTree     *ctree,
315 						  GtkCMCTreeNode *node,
316 						  gint          column,
317 						  const gchar  *text,
318 						  guint8        spacing,
319 						  GdkPixbuf    *pixbuf);
320 void gtk_cmctree_set_node_info                     (GtkCMCTree     *ctree,
321 						  GtkCMCTreeNode *node,
322 						  const gchar  *text,
323 						  guint8        spacing,
324 						  GdkPixbuf    *pixbuf_closed,
325 						  GdkPixbuf    *pixbuf_opened,
326 						  gboolean      is_leaf,
327 						  gboolean      expanded);
328 void gtk_cmctree_node_set_shift                    (GtkCMCTree     *ctree,
329 						  GtkCMCTreeNode *node,
330 						  gint          column,
331 						  gint          vertical,
332 						  gint          horizontal);
333 void gtk_cmctree_node_set_selectable               (GtkCMCTree     *ctree,
334 						  GtkCMCTreeNode *node,
335 						  gboolean      selectable);
336 gboolean gtk_cmctree_node_get_selectable           (GtkCMCTree     *ctree,
337 						  GtkCMCTreeNode *node);
338 GtkCMCellType gtk_cmctree_node_get_cell_type         (GtkCMCTree     *ctree,
339 						  GtkCMCTreeNode *node,
340 						  gint          column);
341 gboolean gtk_cmctree_node_get_text                 (GtkCMCTree     *ctree,
342 						  GtkCMCTreeNode *node,
343 						  gint          column,
344 						  gchar       **text);
345 gboolean gtk_cmctree_node_get_pixbuf               (GtkCMCTree     *ctree,
346 						  GtkCMCTreeNode *node,
347 						  gint          column,
348 						  GdkPixbuf   **pixbuf);
349 gboolean gtk_cmctree_node_get_pixtext              (GtkCMCTree     *ctree,
350 						  GtkCMCTreeNode *node,
351 						  gint          column,
352 						  gchar       **text,
353 						  guint8       *spacing,
354 						  GdkPixbuf   **pixbuf);
355 gboolean gtk_cmctree_get_node_info                 (GtkCMCTree     *ctree,
356 						  GtkCMCTreeNode *node,
357 						  gchar       **text,
358 						  guint8       *spacing,
359 						  GdkPixbuf   **pixbuf_closed,
360 						  GdkPixbuf   **pixbuf_opened,
361 						  gboolean     *is_leaf,
362 						  gboolean     *expanded);
363 void gtk_cmctree_node_set_row_style                (GtkCMCTree     *ctree,
364 						  GtkCMCTreeNode *node,
365 						  GtkStyle     *style);
366 GtkStyle * gtk_cmctree_node_get_row_style          (GtkCMCTree     *ctree,
367 						  GtkCMCTreeNode *node);
368 void gtk_cmctree_node_set_cell_style               (GtkCMCTree     *ctree,
369 						  GtkCMCTreeNode *node,
370 						  gint          column,
371 						  GtkStyle     *style);
372 GtkStyle * gtk_cmctree_node_get_cell_style         (GtkCMCTree     *ctree,
373 						  GtkCMCTreeNode *node,
374 						  gint          column);
375 void gtk_cmctree_node_set_foreground               (GtkCMCTree       *ctree,
376 						  GtkCMCTreeNode   *node,
377 						  const GdkColor *color);
378 void gtk_cmctree_node_set_background               (GtkCMCTree       *ctree,
379 						  GtkCMCTreeNode   *node,
380 						  const GdkColor *color);
381 void gtk_cmctree_node_set_row_data                 (GtkCMCTree     *ctree,
382 						  GtkCMCTreeNode *node,
383 						  gpointer      data);
384 void gtk_cmctree_node_set_row_data_full            (GtkCMCTree     *ctree,
385 						  GtkCMCTreeNode *node,
386 						  gpointer      data,
387 						  GDestroyNotify destroy);
388 gpointer gtk_cmctree_node_get_row_data             (GtkCMCTree     *ctree,
389 						  GtkCMCTreeNode *node);
390 void gtk_cmctree_node_moveto                       (GtkCMCTree     *ctree,
391 						  GtkCMCTreeNode *node,
392 						  gint          column,
393 						  gfloat        row_align,
394 						  gfloat        col_align);
395 GtkVisibility gtk_cmctree_node_is_visible          (GtkCMCTree     *ctree,
396 						  GtkCMCTreeNode *node);
397 
398 /***********************************************************
399  *             GtkCMCTree specific functions                 *
400  ***********************************************************/
401 
402 void gtk_cmctree_set_indent            (GtkCMCTree                *ctree,
403 				      gint                     indent);
404 void gtk_cmctree_set_spacing           (GtkCMCTree                *ctree,
405 				      gint                     spacing);
406 void gtk_cmctree_set_show_stub         (GtkCMCTree                *ctree,
407 				      gboolean                 show_stub);
408 void gtk_cmctree_set_line_style        (GtkCMCTree                *ctree,
409 				      GtkCMCTreeLineStyle        line_style);
410 void gtk_cmctree_set_expander_style    (GtkCMCTree                *ctree,
411 				      GtkCMCTreeExpanderStyle    expander_style);
412 void gtk_cmctree_set_drag_compare_func (GtkCMCTree     	      *ctree,
413 				      GtkCMCTreeCompareDragFunc  cmp_func);
414 
415 /***********************************************************
416  *             Tree sorting functions                      *
417  ***********************************************************/
418 
419 void gtk_cmctree_sort_node                         (GtkCMCTree     *ctree,
420 						  GtkCMCTreeNode *node);
421 void gtk_cmctree_sort_recursive                    (GtkCMCTree     *ctree,
422 						  GtkCMCTreeNode *node);
423 
424 
425 #define gtk_cmctree_set_reorderable(t,r)                    gtk_cmclist_set_reorderable((GtkCMCList*) (t),(r))
426 
427 /* GType for the GtkCMCTreeNode.  This is a boxed type, although it uses
428  * no-op's for the copy and free routines.  It is defined in order to
429  * provide type information for the signal arguments
430  */
431 GType   gtk_cmctree_node_get_type                  (void) G_GNUC_CONST;
432 
433 G_END_DECLS
434 
435 #endif				/* __GTK_CMCTREE_H__ */
436