]> Creatis software - bbtk.git/blob - kernel/src/ThirdParty/wx/treemultictrl/wxTreeMultiCtrl.h
Feature #1774
[bbtk.git] / kernel / src / ThirdParty / wx / treemultictrl / wxTreeMultiCtrl.h
1 /*
2  # ---------------------------------------------------------------------
3  #
4  # Copyright (c) CREATIS (Centre de Recherche en Acquisition et Traitement de l'Image
5  #                        pour la SantÈ)
6  # Authors : Eduardo Davila, Frederic Cervenansky, Claire Mouton
7  # Previous Authors : Laurent Guigues, Jean-Pierre Roux
8  # CreaTools website : www.creatis.insa-lyon.fr/site/fr/creatools_accueil
9  #
10  #  This software is governed by the CeCILL-B license under French law and
11  #  abiding by the rules of distribution of free software. You can  use,
12  #  modify and/ or redistribute the software under the terms of the CeCILL-B
13  #  license as circulated by CEA, CNRS and INRIA at the following URL
14  #  http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
15  #  or in the file LICENSE.txt.
16  #
17  #  As a counterpart to the access to the source code and  rights to copy,
18  #  modify and redistribute granted by the license, users are provided only
19  #  with a limited warranty  and the software's author,  the holder of the
20  #  economic rights,  and the successive licensors  have only  limited
21  #  liability.
22  #
23  #  The fact that you are presently reading this means that you have had
24  #  knowledge of the CeCILL-B license and that you accept its terms.
25  # ------------------------------------------------------------------------ */
26
27
28 //---------------------------------------------------------------------------
29 // $RCSfile: wxTreeMultiCtrl.h,v $
30 // $Source: /cvs/creatis/bbtk/kernel/src/ThirdParty/wx/treemultictrl/wxTreeMultiCtrl.h,v $
31 // $Revision: 1.3 $
32 // $Date: 2012/11/16 08:49:16 $
33 //---------------------------------------------------------------------------
34 // Author:      Jorgen Bodde
35 // Copyright:   (c) Jorgen Bodde
36 // License:     wxWidgets License
37 //---------------------------------------------------------------------------
38
39 #ifndef __WXTREEMULTICTRL_H__
40 #define __WXTREEMULTICTRL_H__
41
42 /** \author Jorgen Bodde
43     \mainpage
44
45     This is the wxTreeMultiCtrl documentation guide. For the upcoming CodeShop project I am working on, I've
46     created a new control for wxWidgets (http://www.wxwidgets.com), with similar functionality as
47     the wxTreeCtrl. This control allows you to add multiple wxWindow based components in a tree shaped form,
48     with multiple root entries, which can contain multiple sub nodes, which can contain the visual controls
49     in the tree. The tree behaves very much like a wxTreeCtrl, showing all controls in a more structured way.
50
51     wxTreeMultiCtrl is freeware and distributed under the wxWidgets license. wxWidgets is THE toolkit for
52     (cross platform) C++ / Python programming!
53
54     \section how_work How does it work?
55
56     The internals of the wxTreeMultiCtrl are built up from a composite pattern. This pattern forms a recursive
57     tree where each end node can consist of a Window or a Node type. The Node type can consist out of multiple
58     Window or Node types, and the  Window type is an end node which contains an assigned wxWindow to be displayed
59     on the current level.
60
61     The wxTreeMultiCtrl communicates to the developer by using the wxTreeMultiItem class, which is about the same
62     as a wxTreeItemId. The wxTreeMultiItem class can be used in add or delete operations, fold operations, find
63     operations, data get and set methods, and more. It helps the developer build up the tree, and later on,
64     get and set data from it.
65
66     \section what_dp What can it do and what not?
67
68     What it can do:
69
70     - Run-time addition / deletion of nodes, with an unlimited level depth
71     - Inheriting the control makes it possible to respond to the events of the added wxWindow based components
72     - Since all structured controls are owned by the wxTreeMultiCtrl, FindWindow will work, and all events can be captured
73     - Collapsing and expanding of a (or all) sub nodes from a specific location by method or by mouse click
74     - Typesafe getting or setting boolean, text or selection values by simply passing the window ID
75     - Run-time adjustment of spacing between controls
76     - Easy indenting of Window nodes
77     - Contain complex controls per Window node by putting them on a wxPanel, allowing custom behavior of those controls on the wxPanel
78     - Automatic deep background color adjustment of every window added, which means that every control on a wxPanel will be
79       automatically set to the proper background. There is also an exception flag for wxButton controls, so that they remain
80       their original color (if desired).
81
82     What it cannot do:
83
84     - Drag and drop support of individual nodes. Since the purpose was creating a tree shaped / property sheet kind of window,
85       dragging and dropping is not really desired behavior.
86     - No selection possible. Click on the controls to edit, double click on a container node to collapse and expand.
87     - Draw a selection border. Since there is no selection possible, no selection will be drawn
88     - Editing of captions like point and click in wxTreeCtrl. Again this is not desired behavior, because the (sub)
89       items are not really the same as wxTreeCtrl items.
90
91     Special thanks to Phil for testing, Julian Smart et al. for making this great toolkit!
92 */
93
94 #ifdef __GNUG__
95     #pragma interface "wxTreeMultiCtrl.cpp"
96 #endif
97
98 #ifndef WX_PRECOMP
99     #include "wx/wx.h"
100 #endif
101
102 #include <wx/dynarray.h>
103
104
105 // classes for internal tree structure
106 #include "TreeMultiItemRoot.h"
107
108 // Flags for wxTreeMultCtrl use
109 #define wxTMC_DEFAULT_STYLE wxSIMPLE_BORDER
110
111 /** @defgroup wndflags wxTreeMultiWindowItem flags
112     These flags can be used in wxTreeMultiCtrl::AppendWindow as enforced flags, or in wxTreeMultiWindowInfo to set the flags
113     for repetetive adding of Window nodes with the same (or near same) properties.
114     @{
115 */
116 /** When set, this flag will change the background of all the panels
117     and subwindows added to the wxTreeMultiCtrl. */
118 #define wxTMC_BG_ADJUST_CNT   0x000000001
119 /** When set, the background of the wxButton windows will also be changed.
120     This needs wxTMC_ADJUST_BACKGROUND to be set as well. */
121 #define wxTMC_BG_ADJUST_BTN   0x000000002
122 /** When set, all backgrounds from windows and buttons will be adjusted
123     to match the control background */
124 #define wxTMC_BG_ADJUST_ALL   (wxTMC_BG_ADJUST_CNT | wxTMC_BG_ADJUST_BTN)
125 /** When set, the control added is resized horizontally over the complete
126     length. When the user resizes the window, the control is resized as well */
127 #define wxTMC_SPAN_WIDTH      0x000000004
128 /** @}
129 */
130
131
132 #define wxTreeMultiCtrlNameStr wxT("wxTreeMultiCtrl")
133
134 #define WXTMC_GUTTER_DEFAULT 6      // gutter before and after image of [+] or [-]
135 #define WXTMC_YSPACING_DEFAULT 10   // per item 10 pixels spacing extra for every item
136 #define WXTMC_PIXELS_PER_UNIT 10
137
138 /** \defgroup hitflags wxTreeMultiCtrl HitTest flags
139     @{
140 */
141
142 enum
143 {
144     /// wxCoord was found in the gutter of the node (in front of the [+])
145     wxTMC_HITTEST_GUTTER = 1,
146     /// wxCoord was found inside a window, or behind it, on a Window node
147     wxTMC_HITTEST_WINDOW,
148     /// wxCoord was found on a caption of a Node or Root item
149     wxTMC_HITTEST_CAPTION,
150     /// wxCoord was found on a checkbox (only when item really has a checkbox)
151     wxTMC_HITTEST_CHECKBOX
152 };
153
154 /** @}
155 */
156
157 /** @defgroup classes wxTreeMultiCtrl Classes
158     These classes are all the available classes in the wxTreeMultiCtrl you should know about.
159     @{
160
161     @}
162 */
163
164 /** \class wxTreeMultiItem
165     \ingroup classes
166     \brief An intermediate class which is used to return as 'item' value for the wxTreeMultiCtrl. This class
167     is comparable with wxTreeItemId.
168
169     The wxTreeMultiItem is used to pass information to the user about the tree node in question. It can also be used point out where the
170     subnodes should be added.
171
172     For example:
173     \code
174
175         wxTreeMultiItem item = MyMultiTreeCtrl->AddRoot("This is the first root");
176
177         // now add a node to the root
178         if(item.IsOk())
179             MyMultiTreeCtrl->AppendWindow(item, new wxStaticText(MyMultiTreeCtrl, -1, "This is a static text");
180
181
182     \endcode
183
184     The wxTreeMultiItem comes in three internal types which are used in the wxTreeMultiCtrl. For functions such as
185     wxTreeMultiCtrl::AddRoot, a Root item is returned. For functions such as wxTreeMultiCtrl::AppendWindow, a
186     Window node is returned. For functions such as wxTreeMultiCtrl::AppendNode, a Node item is returned.
187
188     \li A Root item represents a top level item. Special operations on this item is adding multiple nodes to it from a
189     top level.
190
191     \li A Node item represents a container item which has multiple sub items which can both be Window items, or Node items.
192     A root item is a special type of Node item, so all operations which are only for Node items, are also for Root items.
193
194     \li A Window node represents an end node, which points to a wxWindow which represents the visual contents of this node.
195     This type of node can hold any wxWindow derived class.
196
197 */
198
199 class wxTreeMultiItem
200 {
201 private:
202     TreeMultiItemBase *_item;
203 public:
204     /** Default declaration constructor, and should be used when declaring an item which gets assigned a new
205         value by e.g. wxTreeMultiCtrl::AppendNode. */
206     wxTreeMultiItem() {
207         _item = 0;
208     };
209
210 #ifndef _NO_DOXYGEN_
211
212     wxTreeMultiItem(TreeMultiItemBase *ptr) {
213         _item = ptr;
214     };
215
216     // Returns the TreeMultiItemBase class. This shoult *NOT* be
217     // used if you don't know what you are doing! This means never use it. */
218     TreeMultiItemBase *GetItem() const {
219         return _item;
220     };
221
222 #endif // _NO_DOXYGEN_
223
224     /** The copy operator. Used in assigning one wxTreeMultiItem to another, usually in returning wxTreeMultiItem
225         classes from the wxTreeMultiCtrl.
226     */
227     void operator=(const wxTreeMultiItem &item) {
228         _item = item._item;
229     };
230
231    /** Equality operator. It returns true if the items are identical or if both items are invalid. */
232     bool operator==(wxTreeMultiItem const& item) const {return (this->GetItem() == item.GetItem());}
233
234    /** Inequality operator. It returns true if the items are different or one of them is invalid. */
235     bool operator!=(wxTreeMultiItem const& item) const {return (this->GetItem() != item.GetItem());}
236
237         /** Returns the parent of the current wxTreeMultiItem. This means the wxTreeMultiNode is returned. It can
238             be useful to check or clear the checkbox at this level. */
239         wxTreeMultiItem GetParent() const{
240                 wxCHECK(IsOk(), wxTreeMultiItem(0));
241                 return wxTreeMultiItem(_item->GetParent());
242         };
243
244     /** Validates if the wxTreeMultiItem is a valid instance to use in the wxTreeMultiCtrl. Returns TRUE when there
245         is a member value is associated with it, or FALSE when not. This value can also be checked when this class is returned from a wxTreeMultiCtrl operation. For example:
246
247         \code
248
249             wxTreeMultiItem item = MyTreeMultiCtrl->FindNode("NAME");
250             if(item.IsOk())
251             {
252                 // Found the node, now do something with it
253             }
254             else
255             {
256                 // Sorry, not found
257             }
258
259         \endcode
260
261     */
262     bool IsOk() const {
263         return _item != 0;
264     };
265
266     /** Returns TRUE when the wxTreeMultiItem is a Window item. This means the item is both valid, and points to a
267         window node. This means it can be used in functions that expect a Window node. If the item is invalid or a Window
268         item, FALSE is returned
269         \sa wxTreeMultiCtrl::AppendWindow
270     */
271     bool IsWindowItem() const {
272         if(_item && _item->IsTreeMultiItemWindow())
273             return true;
274         return false;
275     };
276
277     /** Returns TRUE when the wxTreeMultiItem is a Node item. This means the item is both valid, and points to a
278         node element (i.e. setting the caption, counting node children, etc). If the item is invalid or not a Node
279         item, FALSE is returned.
280         When the item is actually a root item (specialised node type), this also returns TRUE.
281         \sa wxTreeMultiCtrl::AppendNode wxTreeMultiCtrl::AddRoot
282     */
283     bool IsNodeItem() const {
284         if(_item && (_item->IsTreeMultiItemNode() || _item->IsTreeMultiItemRoot()))
285             return true;
286         return false;
287     };
288
289     /** Returns True when the wxTreeMultiItem is a Root (top node) item. This means the item is both valid,
290         and points to a root element (this item is always shown as first node in the tree). A root node is
291         always visible, but can contain other collapsed children. If the item is invalid or not a Root node,
292         FALSE is returned.
293     */
294     bool IsRootItem() const {
295         if(_item && _item->IsTreeMultiItemRoot())
296             return true;
297         return false;
298     };
299
300     /** Returns TRUE if the node is expanded, else FALSE if it is collapsed. If the item is not a Root or Node
301         item, an assertion failure is generated (in debug mode) or FALSE is returned (in release mode).
302
303         \sa wxTreeMultiCtrl::Expand, wxTreeMultiCtrl::Collapse, wxTreeMultiCtrl::CollapseAndReset
304     */
305     bool IsExpanded() const {
306         wxCHECK(_item, false);
307         TreeMultiItemNode *n = _item->IsTreeMultiItemNode();
308         wxCHECK(n, false);
309
310         return n->IsExpanded();
311     };
312
313     /** Returns true if this node is excluded from drawing. Please note that when this node is not visible
314         due to a higher excluded parent node but not literally excluded itself, it will return false (not excluded).
315         Use wxTreeMultiCtrl::GetExcludedParent() to get the node that hides this one. */
316     bool IsExcluded() {
317         wxCHECK(_item, false);
318         return _item->IsExcluded();
319     }
320
321    /** Returns true if the item is selected.
322        Please note that currently only nodes can be selected.
323    */
324     bool IsSelected(void) const
325     {
326       wxCHECK(this->GetItem(),false);
327       return this->GetItem()->IsSelected();
328     }
329     /** Returns true if this node is visible. Please note that when this node is a child node of a collapsed
330         node, it is not visible. Also if this node is a child node of an excluded node, it is also not visible.
331         It does <b>NOT</b> return false when it's drawn somewhere outside of the visible area. */
332     bool IsVisible() {
333         wxCHECK(_item, false);
334         return _item->IsVisible();
335     }
336
337 };
338
339 WX_DECLARE_OBJARRAY(wxTreeMultiItem,wxArrayTreeMultiItem);
340
341 /** \class wxTreeMultiWindowInfo
342     \ingroup classes
343     \brief This class contains information for every Window node to be added.
344
345     This class can be used to modify the behaviour of the Window node to be added, and can be reused to pass along
346     upon every wxTreeMultiCtrl::AppendWindow call. For example:
347
348     \code
349
350         wxTreeMultiWindowInfo wndinfo;
351
352         MyTreeMultiCtrl->AppendWindow(item, new wxStaticText(MyTreeMultiCtrl,
353                                       -1, "Press this button"), "", wndinfo));
354
355         // now adjust the spacing of our next window to add, by indenting
356         // 4 times the indent size
357
358         wndinfo.Indent(4);
359         MyTreeMultiCtrl->AppendWindow(item, new wxButton(MyTreeMultiCtrl,
360                                       -1, "Apply"), "", wndinfo);
361
362     \endcode
363
364     The class is created to prevent long parameter lists in the functions. Other ways to manipulate a newly added
365     Window node are;
366
367     \li Change top spacing of the Window node to be added
368     \li Change front spacing (indent) of the Window node
369     \li Set extra flags for this Window node
370 */
371
372 //-------------------------------------------------------------------------------------------------------------------
373
374 class wxTreeMultiWindowInfo
375 {
376 private:
377     /** Flag that indicates that every window background in the assigned wxWindow needs te be overriden with the
378         current colour of the TreeMultiCtrl. This is a deep adjustment and will do every subwindow until none are
379         left. If 'false' no adjustment is done. For AppendWindow only */
380     int _flags;
381     /** Extra indent for every item that is added. This will add front spacing to the item's x calculation.
382         For AppendNode and AppendWindow. Spacing is added behind the collapse image not in front. */
383     int _frontSpacing,
384         _frontSpacingOrg;
385
386     /** Extra top spacing for every item that is added. This will add top spacing to the item's y calculation */
387     int _topSpacing;
388
389 #if(CHECKBOXVIEW)
390     /** Checkstate for checkboxed property sheets */
391     bool _checkState;
392 #endif
393
394 public:
395 #if(CHECKBOXVIEW)
396     wxTreeMultiWindowInfo(int flags, int frontSpacing, int topSpacing, bool checkState = false)
397         : _flags(flags)
398         , _frontSpacing(frontSpacing)
399         , _frontSpacingOrg(frontSpacing)
400         , _topSpacing(topSpacing)
401         , _checkState(checkState)
402 #else
403     wxTreeMultiWindowInfo(int flags, int frontSpacing, int topSpacing)
404         : _flags(flags)
405         , _frontSpacing(frontSpacing)
406         , _frontSpacingOrg(frontSpacing)
407         , _topSpacing(topSpacing)
408 #endif
409     {
410         // constructor
411     }
412     /** Adds indent to original front spacing and increments it with that value (quick extra indent).
413         The original value of FrontSpacing (see SetFrontSpacing() gets indented by multiplying
414         the 'num' factor (default = 1) times the indent value. So if the FrontSpacing was set to 10,
415         and Indent(2) is called, the new indent will be 30. (10 + 2 * 10). The original FrontSpacing
416         value is remembered, so calling Outdent(2) will bring it back to 10 (30 - (2*10). Calling
417         SetFrontSpacing with a new value, deletes the old indent.
418
419         \sa Outdent, SetFrontSpacing
420     */
421     int Indent(int num = 1) {
422         if(num > 0)
423             _frontSpacing += (_frontSpacingOrg * num);
424         return _frontSpacing;
425     };
426     /** Reduces indent a number of times, by subtracting 'num' times the original FrontSpacing value from
427         the current FrontSpacing value (quick extra indent). Thus if the original FrontSpacing was set to
428         10, and the current indent value is 40, Outdent(2) will do 40 - (2 * 10) = 20
429
430         \sa Indent, SetFrontSpacing
431     */
432     int Outdent(int num = 1) {
433         _frontSpacing -= (_frontSpacingOrg * num);
434         if(_frontSpacing < 0)
435             _frontSpacing = 0;
436         return _frontSpacing;
437     };
438
439     /** Sets FrontSpacing value. This also resets the current indent level.  */
440     void SetFrontSpacing(int frontSpacing) {
441         _frontSpacing = frontSpacing;
442         _frontSpacingOrg = frontSpacing;
443     };
444     /** Gets front spacing. This will return the current indent level set. If Indent or Outdent is used,
445         this level represents the current Indent level.*/
446     int GetFrontSpacing() const {
447         return _frontSpacing;
448     };
449
450     /** Sets top spacing. This means the number of pixels spacing between the last node and the next one to
451         be added.
452     */
453     void SetTopSpacing(int topSpacing) {
454         _topSpacing = topSpacing;
455         if(_topSpacing < 0)
456             _topSpacing = 0;
457     };
458
459     /* Gets top spacing currently set. */
460     int GetTopSpacing() const {
461         return _topSpacing;
462     };
463
464     /** Sets the current flags set, and returns previous flags state.
465         \sa @link wndflags wxTreeMultiWindowInfo flags@endlink
466     */
467     int SetFlags(int flags) {
468         int tmp = _flags;
469         _flags = flags;
470         return tmp;
471     };
472
473     /** Gets the current flags set.
474         \sa @link wndflags wxTreeMultiWindowInfo flags@endlink
475     */
476     int GetFlags() const {
477         return _flags;
478     };
479
480     /** Or's the given flag with the current flagset, and adds it. The
481         old flag set is returned before the OR is applied.
482         \sa @link wndflags wxTreeMultiWindowInfo flags@endlink
483     */
484     int AddFlag(int flag_mask) {
485         int tmp = _flags;
486         _flags |= flag_mask;
487         return tmp;
488     };
489
490     /** And's the given flag in a negated manner and removes this flag set from
491         the current flags.  The old flag set is returned.
492         \sa @link wndflags wxTreeMultiWindowInfo flags@endlink
493     */
494     int RemoveFlag(int flag_mask) {
495         int tmp = _flags;
496         _flags &= ~(flag_mask);
497         return tmp;
498     };
499
500 #if(CHECKBOXVIEW)
501     /** Sets the default checkstate if checkboxes if SetCheckboxView is chosen. For all the
502         items to be added (even captions) this checkstate is chosen. The default checkstate
503         is false. <b>This needs USE_CHECKBOXVIEW set to YES, or CHECKBOXVIEW=1 during compile</b> */
504     void SetDefaultCheckState(bool checkState = true) {
505         _checkState = checkState;
506     };
507
508     /** Gets the default checkstate of the item. <b>This needs USE_CHECKBOXVIEW set to YES, or CHECKBOXVIEW=1 during compile</b>
509         \sa SetDefaultCheckState */
510     bool GetDefaultCheckState() const {
511         return _checkState;
512     };
513 #endif
514 };
515
516 // Default info string
517 #ifndef LINUX
518   #define wxTreeMultiWindowInfoDefault wxTreeMultiWindowInfo(wxTMC_BG_ADJUST_CNT, 8, 0)
519 #else
520   #define wxTreeMultiWindowInfoDefault wxTreeMultiWindowInfo(wxTMC_BG_ADJUST_ALL, 8, 0)
521 #endif
522
523 /** \class wxTreeMultiCtrl
524     \ingroup classes
525     \brief This is the visual control, which will contain all the logic for the tree mechanism.
526
527     The wxTreeMultiCtrl is the container class which can be filled in to get the tree shaped structure in
528     which the controls are displayed. The user can add / delete new nodes at runtime, expand or collapse
529     nodes, perform get or set actions on the controls inside, and iterate over the items.
530
531     A typical usage of the wxTreeCtrl is;
532
533     \code
534     wxTreeMultiCtrl *tmc = new wxTreeMultiCtrl(this, -1);
535
536     // add root
537     wxTreeMultiItem item = tmc->AddRoot("This is the first root");
538
539     // create a wxTreeMultiWindowInfo object for indenting etc
540     wxTreeMultiWindowInfo wndinfo;
541
542     // add subitem to root
543     tmc->AppendWindow(item, new wxButton(tmc, -1, "Press this"), "", wndinfo);
544
545     // indent a few
546     wndinfo.Indent(4);
547
548     // add a new one
549     tmc->AddWindow(item, new wxCheckBox(tmc, ID_MYCHECK, "Check this!"), "", wndinfo);
550
551     // now check the value of the checkbox
552     tmc->SetBooleanValue(ID_MYCHECK, true);
553
554     \endcode
555
556     <b>IMPORTANT:</b> Every control added to the wxTreeMultiCtrl has to be child of the wxTreeMultiCtrl.
557
558 */
559 class wxTreeMultiCtrl: public wxScrolledWindow
560 {
561     DECLARE_DYNAMIC_CLASS(wxTreeMultiCtrl)
562
563     /** \todo When tab is pressed, the focus can get out of sight. This should be resolved by
564        catching the TAB, see what window is focussed, and scroll the window so it's visible */
565 private:
566     TreeMultiItemRoot _root;
567
568     long _style;
569     wxBitmap *_expandBmp, *_collBmp;
570
571     /** Delta Y for bitmap, to center it on the caption */
572     int _iconDeltaY, _checkDeltaY;
573
574     /* Caption height. This is the height of the font of this window */
575     int _captionHeight;
576
577     /** The gutter spacing in front and back of the image. This determines the amount of spacing in front
578         of each item */
579     int _gutterWidth;
580
581     /** The image width of the [+] / [-] icon. This is also calculated in the gutter */
582     int _iconWidth;
583
584     /** The image height of the [+] / [-] icon. This is calculated as minimal size and to allign */
585     int _iconHeight;
586
587     /** Max height. This is either the [+] bitmap or the checkbox */
588     int _maxHeight;
589
590
591     /** Extra Y spacing between the items. */
592     int _spacingY;
593
594     /** Two step create prevention. Something with GetWindowSize freaks out when not actually created */
595     bool _create_called;
596
597 #if(CHECKBOXVIEW)
598     wxBitmap *_checkBmp, *_uncheckBmp, *_tristateBmp;
599
600     /** Toggles checkbox view. If true, every item created (caption or node) will be created with checkbox */
601     bool _checkboxView;
602
603     /** Height and weight for checkbox */
604     int _checkHeight, _checkWidth;
605 #endif
606
607     /** brush for highlighting nodes */
608      wxBrush* m_HilightBrush;
609
610     /** This captionFont is made equal to the font of the wxScrolledWindow. As extra the bold face
611         is set on it when this is wanted by the user (see flags) */
612     wxFont _captionFont;
613
614    /** list of selected items */
615     wxArrayTreeMultiItem m_SelectedItems;
616
617     /** Does the actual collapsing / expanding. So that Expand and Collapse aren't using the same code twice */
618     void DoFold(TreeMultiItemBase *item, bool expand, bool recursive);
619
620     /** Redraws and recalculates the nodes from the current node. It will also clear all 'dirty' flags when
621         they are recalculated */
622     void RedrawFromNode(TreeMultiItemNode *n);
623
624     /** Redraws from parent node of this node */
625     void RedrawFromParentNode(TreeMultiItemBase *b);
626
627     /** Draws checkbox belonging to this node, in the given state */
628     void DrawCheckbox(TreeMultiItemBase *b, wxDC &dc, bool convertScrolled = false);
629
630     /** Recalculate the space needed based on every node. It goes as follows.
631         - A foldable node (TreeMultiItemNode) is as high as the 'Jg' y-size. This type only has a caption plus a
632           picture which explains the state ([+] or [-]), the width will be the caption length
633         - A window node will be as high as the y size of the window. The X size is the total length of the
634           window.
635         - For every child node an indent will be added to the x size.
636
637         Only visible nodes will be recalculated. Non visible (collapsed) children will be skipped  */
638     void RecalculateNodePositions();
639
640     /** Recurses into the whole tree and provides every node with the proper x and y values. All non visible items
641         are skipped (so when it encounters a collapsed node, it's children are not calculated). Returns the last Y */
642     int CalculateNodeDimensions(TreeMultiItemBase *b, int currentY, int level);
643
644     void DrawNode(TreeMultiItemBase *b, wxDC &dc);
645
646     /** Sets background colour of all the windows and subwindows in this wxWindow. This is very handy
647         for wxPanel derived classes which need to be made equal to the background colour of the wxTreeMultiCtrl */
648     void SetWindowBackgroundColour(wxWindow *wnd, const wxColour &col, int flags);
649
650     /** Shows or hides the assigned window (if there is any) */
651     void ShowTreeMultiWindow(TreeMultiItemWindow *window, bool show = true);
652
653     /** Goes down the tree, and if a window is not visible (thus all it's children aren't too) it will hide
654         the window so it is not shown on the control */
655     void UpdateAllWindowVisibility();
656
657     /** Hides tree multi window. It this is a TreeMultiItemNode, hide all subwindows as well. */
658     void UpdateTreeMultiWindowVisibility(TreeMultiItemBase *b, bool show);
659
660     /** Recalculates totally needed virtual size of the wxTreeMultiCtrl. It will scan for
661         the largest window, with the biggest size, and report that back */
662     void RecalculateVirtualSize();
663
664     /** Adjusts scrollbars in window, usually done after virtual size (x,y) is recalculated */
665     using wxScrolledWindow::AdjustScrollbars;
666     virtual void AdjustScrollbars(int x, int y);
667
668     /** Recalculates and accumulates largest x and y */
669     void RecalculateVirtualSizeFromNode(const TreeMultiItemNode *node, int &x, int &y);
670
671     /** Scans for TreeMultiItemBase node that contains x,y and in area returns a hittest constant to
672         indicate what matched */
673     TreeMultiItemBase *FindNodeByPoint(TreeMultiItemBase *b, wxPoint const& pt, int &area);
674
675     /** Scans for TreeMultiItemWindow that holds the wxWindow pointer. Does not scan in panels or does
676         a deep search. Reason, this function is used to advance to next TreeMultiItemWindow for focus
677         on this wxScrolledWindow. If a sub window is found, it will skip other windows on that same level */
678     wxTreeMultiItem FindWindowNode(wxWindow *wnd, TreeMultiItemNode *n = 0);
679
680     /** Finds next visible window item in chain. If not found use FindFirstVisibleItem to start from the
681         beginning */
682     TreeMultiItemWindow *FindNextVisibleWindowItem(TreeMultiItemBase *b, int index = -1);
683
684     /** Adjust the centering of the bitmap icons (collapse / expand) when the caption font changes. They need to
685         be centered in the middle of the font, so a bit of deltaY adjustment is needed */
686     void AdjustIconsDeltaY();
687
688         /** Calculate the spanning of the individual nodes */
689         void CalculateNodeSpanning(TreeMultiItemBase *b);
690
691 #if(CHECKBOXVIEW)
692     /** Recurse to all the children and set the checkbox state (even when there is no checkbox) */
693     void SetRecursiveCheckState(TreeMultiItemNode *n, bool check);
694
695     /** From current checked node, all children will be scanned and the parent node of this node
696         will get tristate if the checked items are scattered (some are some aren't). If all nodes in this
697         node are checked, the parent node gets checked all the way up to the last one that matches
698         criteria. If all are cleared, parent node gets cleared */
699     void ScanTristateCheckstates(TreeMultiItemBase *b);
700 #endif
701
702    /** \name Private add and delete methods
703        @{
704    */
705
706    /** Inserts a node into the parent's node at the specified position.
707        As this is a private method error checking is limited. Therefore, it has to be guaranteed that this method
708        is only called with a valid parent node pointer.
709        The position is zero based. In case the position is equal or larger than the current number of
710        parent's elements the new node is appended.
711        The newly inserted node is being returned.
712    */
713     wxTreeMultiItem InsertNode(TreeMultiItemNode* ParentPtr, size_t Position, wxString const& Caption, wxString const& Name);
714
715    /** Inserts a window into the parent's node at the specified position.
716        As this is a private method error checking is limited. Therefore, it has to be guaranteed that this method
717        is only called with a valid parent node and window pointer.
718        The position is zero based. In case the position is equal or larger than the current number of
719        parent's elements the new node is appended.
720        The newly inserted window is being returned.
721    */
722     wxTreeMultiItem InsertWindow(TreeMultiItemNode* ParentPtr, size_t Position, wxWindow* WindowPtr, wxString const& Name,
723                                  wxTreeMultiWindowInfo const& Info, int Flags);
724
725    /** @}
726    */
727 private:
728     void Init();
729
730     // handlers
731     //---------
732
733     //virtual void OnDraw(wxDC& dc);
734     void OnPaint(wxPaintEvent &event);
735     void OnMouseClick     (wxMouseEvent& event);
736     void OnRightMouseClick(wxMouseEvent& Event);
737     void OnKey(wxKeyEvent &event);
738         void OnSize(wxSizeEvent &event);
739
740         /** Recalculates the spanning controls */
741         void RecalculateSpanSizes();
742
743 public:
744     /** Two step constructor. Call Create when this constructor is called to build up the
745         wxTreeMultiCtrl
746     */
747     wxTreeMultiCtrl()
748         : _create_called(false)
749     {
750
751         Init();
752     }
753
754     /** The default constructor. The style wxTAB_TRAVERSAL is enforced to make sure that the
755         focus handling is being done correctly. The styles to be used are styles valid for
756         the wxWindow and wxScrolledWindow
757     */
758     wxTreeMultiCtrl(wxWindow *parent, wxWindowID id = -1,
759                         const wxPoint& pos = wxDefaultPosition,
760                         const wxSize& size = wxDefaultSize,
761                         long style = wxTMC_DEFAULT_STYLE,
762                         const wxValidator &validator = wxDefaultValidator,
763                         const wxString& name = wxTreeMultiCtrlNameStr)
764         : _style(style | wxTAB_TRAVERSAL)
765         , _create_called(false)
766     {
767         Create(parent, id, pos, size, style, validator, name);
768     }
769
770     /** Destructor */
771     virtual ~wxTreeMultiCtrl();
772
773     /** Two step creation. Whenever the control is created without any parameters, use Create to actually
774         create it. Don't access the control's public methods before this is called
775
776         \sa wxTreeMultiCtrl()
777     */
778     bool Create(wxWindow *parent, wxWindowID id = -1,
779                 const wxPoint& pos = wxDefaultPosition,
780                 const wxSize& size = wxDefaultSize,
781                 long style = wxTMC_DEFAULT_STYLE,
782                 const wxValidator &validator = wxDefaultValidator,
783                 const wxString& name = wxTreeMultiCtrlNameStr);
784
785     // accessors
786     //----------
787
788     /** @name Add and delete methods
789         To add and delete node items like a Root item, Window item or Node item. This allows the user to
790         manipulate the tree, and build it up.
791         @{
792     */
793
794     /** Adds a root node to the wxTreeMultiItem. There can be many root nodes. Use this wxTreeMultiNode pointer to add
795         more subnodes to it. */
796     wxTreeMultiItem AddRoot(const wxString &caption, const wxString &name = wxEmptyString);
797
798     /** Adds a window to the tree control. Use this wxTreeMultiItem method to add a window class to the
799         current wxTreeMultiItem. The wxTreeMultiItem must point to a Node class. If this is not the case
800         an empty wxTreeMultiItem is returned. The mask is used to override the mask settings of the
801         wxTreeMultiWindowInfo class. This can be handy to set or clear extra flags only needed for certain
802         situations */
803     wxTreeMultiItem AppendWindow(const wxTreeMultiItem &ParentItem, wxWindow *window = NULL, const wxString &name = wxEmptyString,
804                                  wxTreeMultiWindowInfo const& info = wxTreeMultiWindowInfoDefault, int flags = 0);
805
806    /** Adds a window to the tree control. Use this method to add a window class at the specified position
807        of the parent's wxTreeMultiItem. In case the position is smaller than the current number of children all elements
808        are shifted upwards, otherwise the new window is appended to the parent's wxTreeMultiItem.
809        The parent wxTreeMultiItem must point to a Node class. If this is not the case an
810        empty wxTreeMultiItem is returned.
811    */
812     wxTreeMultiItem InsertWindow(wxTreeMultiItem const& ParentItem, size_t Position, wxWindow *window = NULL, wxString const& Name = wxEmptyString,
813                                  wxTreeMultiWindowInfo const& info = wxTreeMultiWindowInfoDefault, int flags = 0);
814
815    /** Adds a window to the tree control. Use this method to add a window class as the first element
816        of the parent's wxTreeMultiItem. The parent wxTreeMultiItem must point to a Node class. If this is not the case an
817        empty wxTreeMultiItem is returned.
818    */
819     wxTreeMultiItem PrependWindow(wxTreeMultiItem const& ParentItem, wxWindow *window = NULL, const wxString &name = wxEmptyString,
820                                   wxTreeMultiWindowInfo const& info = wxTreeMultiWindowInfoDefault, int flags = 0);
821
822     /** Adds a node to the tree control. Use this wxTreeMultiItem method to add a recursive subnode class as the last element
823         of the parent's wxTreeMultiItem. The parent wxTreeMultiItem must point to a Node class. If this is not the case
824         an empty wxTreeMultiItem is returned. A node can contain multiple nodes or window classes */
825     wxTreeMultiItem AppendNode(wxTreeMultiItem const& ParentItem, const wxString &caption = wxEmptyString,
826                                const wxString &name = wxEmptyString);
827
828    /** Adds a node to the tree control. Use this method to add a recursive subnode class at the specified position
829        of the parent's wxTreeMultiItem. In case the position is smaller than the current number of nodes all elements
830        are shifted upwards, otherwise the new node is appended to the parent's wxTreeMultiItem.
831        The parent wxTreeMultiItem must point to a Node class. If this is not the case an
832        empty wxTreeMultiItem is returned. A node can contain multiple nodes or window classes.
833    */
834     wxTreeMultiItem InsertNode(wxTreeMultiItem const& ParentItem, size_t Position, wxString const& caption, wxString const& name);
835
836    /** Adds a node to the tree control. Use this method to add a recursive subnode class as the first element
837        of the parent's wxTreeMultiItem. The parent wxTreeMultiItem must point to a Node class. If this is not the case an
838        empty wxTreeMultiItem is returned. A node can contain multiple nodes or window classes.
839    */
840     wxTreeMultiItem PrependNode(wxTreeMultiItem const& ParentItem, wxString const& caption = wxEmptyString,
841                                 wxString const& name = wxEmptyString);
842
843     /** Delete item from the tree control. Whenever it is present, delete it. If not, return false. After
844         deletion the wxTreeMultiItem is 0, thus IsOk will return false */
845     bool Delete(wxTreeMultiItem &item);
846
847     /** Deletes all the items from the wxTreeMultiCtrl. */
848     void DeleteAllItems(void)
849     {
850       this->_root.Clear();
851       this->m_SelectedItems.Clear();
852       Refresh();
853     };
854
855     /** Deletes all children of the current node. The wxTreeMultiItem needs to be of type Node to
856         do this. Call GetParentNode to get the parent wxTreeMultiItem which is always a node. */
857     void DeleteChildren(const wxTreeMultiItem &item);
858
859     /** @}
860     */
861
862     /** @name Expand and collapse methods
863          These methods are all for items of type Node.
864         @{
865     */
866
867     /** Expand all nodes and subnodes. Recursive = true means all subnodes are also expanded. */
868     void ExpandNodes(bool recursive = false);
869
870     /** Collapses all nodes and subnodes. Recursive = true means all subnodes are also expanded. */
871     void CollapseNodes(bool recursive = false);
872
873     /** Expands given node, and with recursive, also the subnodes */
874     void Expand(const wxTreeMultiItem &item, bool recursive);
875
876     /** Collapses given node, and with recursive, also the subnodes. If this item is not a node, but a window.
877         the parent is resolved and that node is collapsed */
878     void Collapse(const wxTreeMultiItem &item, bool recursive);
879
880     /** Collapses this node and removes all children from it. This is only applicable on
881         wxTreeMultiItems which are of type Node / Root. */
882     void CollapseAndReset(const wxTreeMultiItem &item);
883
884     /** Folds the given node. The same as Expand and Collapse, but the state can be
885         given through a parameter */
886     void Fold(const wxTreeMultiItem &item, bool expand = true) {
887         if(expand)
888             Expand(item, false);
889         else
890             Collapse(item, false);
891     };
892
893     /** @}
894     */
895
896     /** @name Selection manipulation
897          These methods allow you to select, unselect or test wxTreeMultiItems on selection.
898          Currently only items of type Node can be manipulated.
899         @{
900     */
901
902    /** Returns the number of selected items. */
903     size_t GetSelectedItemCount(void) const {return this->m_SelectedItems.GetCount();}
904
905    /** Returns the first selected item.
906        If there is no selected item an invalid tree multi item is returned.
907    */
908     wxTreeMultiItem GetFirstSelectedItem(void) const;
909
910    /** Returns the last selected item.
911        If there is no selected item an invalid tree multi item is returned.
912    */
913     wxTreeMultiItem GetLastSelectedItem(void) const;
914
915    /** Returns a selected item with the specified index.
916        If there is no selected item with the passed index an invalide tree multi item is returned.
917    */
918     wxTreeMultiItem GetSelectedItem(size_t Index) const;
919
920    /** Returns the index of the selected item.
921        In case the item is not selected "GetSelectedItemCount()" - which is an invalid index - is returned.
922    */
923     size_t GetSelectedItemIndex(wxTreeMultiItem const& Item) const;
924
925    /** Selects the specified item AND in case
926         - UnselectOthers is set all other selected items are going to be unselected;
927         - ExpandSelection is set all items between the last selected item and the passed item
928           are selected, too (in case there this is the first selection all items between the first root
929           and the passed item are selected).
930        If the passed item is already selected the other parameters are ignored.
931        Please not that currently only nodes can be selected, therefore, if any other item is passed nothing will happen.
932    */
933     void SelectItem(wxTreeMultiItem const& Item, bool UnselectOthers=true, bool ExpandSelection=false);
934
935    /** Unselect all selected items. */
936     void UnselectAll(void);
937
938    /** Unselect specified item */
939     void Unselect(wxTreeMultiItem const& Item);
940
941     /** @}
942     */
943
944
945     /** \name Visibility manipulation
946         These methods allow you to manipulate a certain wxTreeMultiItem to temporarily exclude or to include
947         the node from drawing. Whenever it is excluded, all operations can still be performed, however
948         the node may not be visible.
949         @{
950     */
951
952     /** Excludes this node from drawing. When excluded, the node will dissapear from the control but is still
953         physically present in the tree itself. If this node is a composite node with children, they will all be
954         hidden from the control. */
955     void Exclude(const wxTreeMultiItem &item);
956
957     /** Includes an excluded node. If the node was already present on the drawing, nothing happens. If the
958         node is included after exclusion it will become visible. If the parent node is still excluded or
959         collapsed (not visible) this will not show, until the parent node shows */
960     void Include(const wxTreeMultiItem &item);
961
962     /** Returns the parent that is responsible for excluding this node. If there is no excluded node as parent,
963         the wxTreeMultiItem is zero. */
964     wxTreeMultiItem GetExcludedParent(const wxTreeMultiItem &item);
965
966     /** @}
967     */
968
969     /** Checks if the point is under one of the given areas. The returned areas can be
970         \li wxTMC_HITTEST_GUTTER If the front part of the item is clicked (where the node is)
971         \li wxTMC_HITTEST_WINDOW If located in the window area
972         \li wxTMC_HITTEST_CAPTION If located on the caption of the MultiTreeItemNode
973
974         Returned is the item which is located under the mouse, or none (IsOk = false) if
975         no item under the mouse */
976     wxTreeMultiItem HitTest(wxPoint const& pt, int &flags);
977
978     /** @name Find methods
979          These methods are used for finding a node in the wxTreeMultiCtrl.
980         @{
981     */
982
983     /** Searches for the given name from the given level and lower. It will return a wxTreeMultiItem which needs
984         to be checked with IsOk() to see if it is a correct item. IsRootItem, IsNodeItem and IsWindowItem can be
985         used to determine the type of item. If the search returned an item which doesn't satisfy the query, you can
986         restart the search from here, with skip = true to skip the passed item. */
987     wxTreeMultiItem FindItem(const wxTreeMultiItem &item, const wxString &name, bool ignoreCase = false,
988                              bool skipFirst = false);
989
990     /** Searches all nodes for the given name and returns the one found. This is a specialised method for FindItem */
991     wxTreeMultiItem FindItem(const wxString &name, bool ignoreCase = false) {
992         return FindItem(wxTreeMultiItem(&_root), name, ignoreCase, false);
993     };
994
995     /** @}
996     */
997
998     /** Returns the number of children in this node. If this node is not of type Node, count returns -1. */
999     int GetChildrenCount(const wxTreeMultiItem &item) {
1000         if(item.IsNodeItem())
1001         {
1002             TreeMultiItemNode *n = (TreeMultiItemNode *)item.GetItem();
1003             return n->GetNodeCount();
1004         }
1005
1006         return -1;
1007     };
1008
1009     /** This method finds the current focused window, and returns the wxTreeMultiItem that has this window as pointer.
1010         If the wxTreeMultiItem is not ok, the focused window is on a sub-panel, or not on this control. If the focus is
1011         on a sub-panel, this panel will handle the focusing. If you are still interested in this window, try
1012         wxWindow::FindFocus which will always return with a pointer if a wxWindow has focus */
1013     wxTreeMultiItem GetFocus();
1014
1015     /** @name Smart window Get/Set methods
1016          These methods are used for quickly getting or setting primitive values, like boolean, string, or selections into
1017          primitive wxWindow controls like a wxRadioButton, wxCheckBox, wxTextCtrl, etc.
1018          The methods allow you to quickly set e.g. a boolean value by using the wxWindow ID of the control. A type
1019          check is performed before the value is actually set with the appropiate method for it. If it fails, an assertion
1020          will follow in debug mode. If you want to get values back similar get methods are present to return values.
1021          This allows the user to quickly retrieve or set values by ID, without the fuss of remembering the pointer or
1022          node ID of the wxTreeMultiCtrl.
1023         @{
1024     */
1025
1026     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1027         AppendWindow). When it is found, it is type casted towards a <b>wxCheckBox</b> and <b>wxRadioButton</b>. Whenever
1028         it finds a proper type it will return true or false. Whenever no proper type is found, it will return with false.
1029         In debug mode it will cause an assertion failure as well, to notify the developer something is wrong.
1030
1031         \sa SetBooleanValue
1032     */
1033     bool GetBooleanValue(int wndId);
1034
1035     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1036         AppendWindow). When it is found, it is type casted towards a <b>wxTextCtrl</b>, <b>wxChoice</b> and <b>wxComboBox</b>.
1037         Whenever it finds a proper type it will return the (selected) text in the control. Whenever no proper type is found,
1038         it will return with an empty string. In debug mode it will cause an exception error as well if the cast fails, to notify
1039         the developer something is wrong.
1040
1041         \sa SetTextValue
1042     */
1043     wxString GetTextValue(int wndId);
1044
1045     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1046         AppendWindow). When it is found, it is type casted towards a <b>wxCheckBox</b> and <b>wxRadioButton</b>. Whenever
1047         it finds a proper type it set the control's value to the given boolean parameter. Nothing happens when no proper type
1048         is found, however debug mode it will cause an assertion failure.
1049
1050         \sa GetBooleanValue
1051     */
1052     void SetBooleanValue(int wndId, bool value = true);
1053
1054     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1055         AppendWindow). When it is found, it is type casted towards a <b>wxTextCtrl</b>. If the control is not found or
1056         of the wrong type, an asserion failure (in debug mode) follows. <br><i><b>NOTE: </b></i> this method
1057         does not typecast to wxChoice or wxComboBox and the likes. If a selection in one of those needs to be set, use the
1058         SetSelectionValue / GetSelectionValue combination.
1059         \sa GetTextValue, GetSelectionValue, SetSelectionValue
1060     */
1061     void SetTextValue(int wndId, const wxString &value = wxEmptyString);
1062
1063     /** Retrieves the wxWindow * associated with the wxTreeMultiItem. This only works for Window typed wxTreeMultiItem
1064         classes. If this type does not match or no window is associated, 0 is returned. */
1065     wxWindow *GetWindow(const wxTreeMultiItem &item) {
1066         if(item.IsWindowItem())
1067             return ((TreeMultiItemWindow *)item.GetItem())->GetWindow();
1068         return 0;
1069     };
1070
1071     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1072         AppendWindow). When it is found, it is type casted towards a <b>wxListBox, wxChoice, wxComboBox</b>.
1073         If the control is not found or of the wrong type, an asserion failure (in debug mode) follows. If it is found
1074         the selection is set in the control.
1075     */
1076     void SetSelectionValue(int wndId, int sel);
1077
1078     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1079         AppendWindow). When it is found, it is type casted towards a <b>wxListBox, wxChoice, wxComboBox</b>.
1080         If the control is not found or of the wrong type, an asserion failure (in debug mode) follows. In release mode -1 is
1081         returned. If it is found the selection index is returned.
1082     */
1083     int GetSelectionValue(int wndId);
1084
1085     /** This function calls FindWindow on the wxTreeMultiCtrl to find the window with the given ID (which is added with
1086         AppendWindow). When it is found, it is type casted towards a <b>wxListBox</b>. If the control is not found or
1087         of the wrong type, an asserion failure (in debug mode) follows. In release mode an empty wxArrayInt is returned.
1088         If it is found the selections are stored in the wxArrayInt. This is only valid for wxListBox classes with multiple
1089         selection flag set.
1090     */
1091     void GetSelectionValues(int wndId, wxArrayInt &sels);
1092
1093 #if(CHECKBOXVIEW)
1094     /** Gets the checkbox state of the wxTreeMultiItem pointed out by "item". If the item does not have a checkbox
1095         associated (or the item is not ok), it will return -1. If the checkbox is checked it will return 1,
1096         unchecked is 0, and tri-state (usually only for caption nodes) it will return 2. <b>This needs USE_CHECKBOXVIEW
1097         set to YES, or CHECKBOXVIEW=1 during compile</b>*/
1098     int GetCheckboxState(const wxTreeMultiItem &item, bool WXUNUSED(recursive)) {
1099         wxCHECK(item.IsOk(), -1);
1100
1101         // return the checkbox state
1102         TreeMultiItemBase *b = item.GetItem();
1103         if(b->GetCheckbox())
1104             return b->GetCheckboxState();
1105
1106         return -1;
1107     };
1108
1109     /** Sets the checkbox state of the wxTreeMultiItem pointed out by "item". If the item does not have a checkbox
1110         associated (or the item is not ok), it will simply ignore this. <b>This needs USE_CHECKBOXVIEW
1111         set to YES, or CHECKBOXVIEW=1 during compile</b>. Contributed by Thomas Enickl.*/
1112         void SetCheckboxState( const wxTreeMultiItem &item, int state ) {
1113                 wxCHECK2( item.IsOk(), return );
1114                 TreeMultiItemBase *b = item.GetItem();
1115                 if( b->GetCheckbox() )
1116                         b->SetCheckboxState( state );
1117                 RedrawFromNode( item.GetItem()->GetParent() );
1118         };
1119 #endif
1120
1121     /** @}
1122     */
1123
1124     /** @name Extended visibility and manipulation methods
1125         These methods alter the wxTreeMultiCtrl appearance, or add more functionality like checkboxes before each node.
1126         @{
1127     */
1128
1129     /** Sets the Y spacing of the wxTreeMultiCtrl to a new size. This can be used to give the controls some more
1130         spacing in between */
1131
1132     void SetSpacingY(int spacingY) {
1133         if(spacingY >= 0)
1134         {
1135             _spacingY = spacingY;
1136             RedrawFromNode(0);
1137         }
1138     };
1139
1140     /** Gets the Y spacing of the wxTreeMultiCtrl. */
1141
1142     int GetSpacingY() const {
1143         return _spacingY;
1144     };
1145
1146 #if(CHECKBOXVIEW)
1147     /** This method toggles the checkbox view mode. Whenever set to true, the next window item, or caption node item
1148         will get a checkbox. <b>This needs USE_CHECKBOXVIEW set to YES, or CHECKBOXVIEW=1 during compile</b>
1149         \sa GetCheckboxView, wxTreeMultiWindowInfo::SetDefaultCheckState
1150     */
1151     void SetCheckboxView(bool value) {
1152         _checkboxView = value;
1153     };
1154
1155     /** This method returns the checkbox state currently used. <b>This needs USE_CHECKBOXVIEW set to YES, or
1156         CHECKBOXVIEW=1 during compile</b>
1157         \sa SetCheckboxView, wxTreeMultiWindowInfo::SetDefaultCheckState, wxTreeMultiWindowInfo::GetDefaultCheckState
1158     */
1159     bool GetCheckboxView() const {
1160         return _checkboxView;
1161     };
1162 #endif
1163
1164     /** @}
1165     */
1166
1167     /** @name Iteration methods
1168         Allows the user to iterate through a wxTreeMultiCtrl node, and get all the children or siblings.
1169         To start an iteration from the lowest level the functions GetFirstRoot and GetLastRoot are provided.
1170         @{
1171     */
1172
1173    /** Returns the first root. */
1174     wxTreeMultiItem GetFirstRoot(void) const {return wxTreeMultiItem(this->_root.First());}
1175
1176    /** Returns the last root. */
1177     wxTreeMultiItem GetLastRoot(void) const {return wxTreeMultiItem(this->_root.Last());}
1178
1179    /** Returns the items parent. */
1180     wxTreeMultiItem GetParent(wxTreeMultiItem const& item) const;
1181
1182     /** Returns the first child of this node. The type of wxTreeMultiItem needs to be of Node. Whenever not succesful,
1183         the item returned is not ok (IsOk = false). Upon success, a valid child is returned. The cookie variable doesn't
1184         need to be initialized */
1185     wxTreeMultiItem GetFirstChild(const wxTreeMultiItem &item, int &cookie) const;
1186
1187     /** Returns the next child in the iteration on the level of 'item'. Make sure you called GetFirstChild first
1188         before calling this one */
1189     wxTreeMultiItem GetNextChild(const wxTreeMultiItem &item, int &cookie) const;
1190
1191     /** Returns the last child of this node. The type of 'item' needs to be of Node. Whenever not succesful,
1192         the item returned is not ok (IsOk = false). Upon success, a valid last child is returned. */
1193     wxTreeMultiItem GetLastChild(const wxTreeMultiItem &item) const;
1194
1195    /** Returns the next sibling of the passed item. */
1196     wxTreeMultiItem GetNextSibling(wxTreeMultiItem const& item) const;
1197
1198    /** Returns the previous sibling of the passed item. */
1199     wxTreeMultiItem GetPrevSibling(wxTreeMultiItem const& item) const;
1200
1201    /** Returns the next item. "Next" is defined by the following order:
1202         - in case the current item has a child it is the first child of the current item;
1203         - in case the current item has a next sibling as the next sibling;
1204         - as the parent's (or one of its ancestor's) next sibling.
1205    */
1206     wxTreeMultiItem GetNext(wxTreeMultiItem const& item) const;
1207
1208    /** Returns the previous item. "Previous" is defined by the following order:
1209         - in case the current item has a child it is the last child of the current item;
1210         - in case the current item has a previous sibling it is the previous sibling;
1211         - as the parent's (or one of its ancestor's) previous sibling.
1212    */
1213     wxTreeMultiItem GetPrevious(wxTreeMultiItem const& item) const;
1214
1215
1216     /** @}
1217     */
1218
1219     /** @name Get and set methods
1220         These methods allow you to set or get certain properties of the wxTreeMultiCtrl.
1221         @{
1222     */
1223
1224     /** Get the currently used font for the caption headers in the wxTreeMultiCtrl. If you want to alter this
1225         font, simply obtain it and copy it to a local font. After that, set this font back using SetCaptionFont()
1226     */
1227     const wxFont &GetCaptionFont() const {
1228         return _captionFont;
1229     };
1230
1231     /** Sets the font to be used for the text caption headers. This triggers a complete redraw because x,y sizes can
1232         differ, and ofcourse all nodes need to be updated. You can call this method at any time not only at the
1233         beginning. */
1234     void SetCaptionFont(const wxFont &font);
1235
1236     /** @}
1237     */
1238
1239   void OnDraw(wxDC& dc);
1240
1241 private:
1242     DECLARE_EVENT_TABLE()
1243 };
1244
1245 #endif