]>
Commit | Line | Data |
---|---|---|
957f5ab7 | 1 | ///////////////////////////////////////////////////////////////////////////// |
c2a41978 WS |
2 | // Name: foldpanelbar.h |
3 | // Purpose: wxFoldPanel | |
4 | // Author: Jorgen Bodde | |
5 | // Modified by: | |
6 | // Created: 22/06/2004 | |
7 | // RCS-ID: $Id$ | |
8 | // Copyright: (c) Jorgen Bodde | |
9 | // Licence: wxWindows licence | |
957f5ab7 VZ |
10 | ///////////////////////////////////////////////////////////////////////////// |
11 | ||
12 | #ifndef __WXFOLDPANELBAR_H__ | |
13 | #define __WXFOLDPANELBAR_H__ | |
14 | ||
15 | #ifndef WX_PRECOMP | |
16 | #include "wx/wx.h" | |
17 | #endif | |
18 | ||
19 | #include "foldpanelitem.h" | |
20 | ||
21 | /** Not yet supported but added for future reference. Single fold forces other panels to close when | |
22 | they are open, and only opens the current panel. This will allow the open panel to gain the full | |
c2a41978 | 23 | size left in the client area */ |
8fa4d6b8 | 24 | #define wxFPB_SINGLE_FOLD 0x0001 |
957f5ab7 VZ |
25 | |
26 | /** All panels are stacked to the bottom. When they are expanded again they show up at the top */ | |
8fa4d6b8 | 27 | #define wxFPB_COLLAPSE_TO_BOTTOM 0x0002 |
957f5ab7 VZ |
28 | |
29 | /** Not yet supported, but added for future reference. Single fold plus panels will be stacked at the bottom */ | |
c2a41978 | 30 | #define wxFPB_EXCLUSIVE_FOLD wxFPB_SINGLE_FOLD | wxFPB_COLLAPSE_TO_BOTTOM |
957f5ab7 VZ |
31 | |
32 | /** Default style of the wxFoldPanelBar */ | |
c2a41978 | 33 | #define wxFPB_DEFAULT_EXTRASTYLE 0 |
957f5ab7 | 34 | |
c2a41978 | 35 | #define wxFPB_DEFAULT_STYLE wxTAB_TRAVERSAL | wxNO_BORDER |
957f5ab7 VZ |
36 | |
37 | /** \class wxFoldPanel | |
c2a41978 | 38 | This class is used to return a reference to the fold panel that is added by wxFoldPanelBar::AddFoldPanel(). Use |
8fa4d6b8 | 39 | wxFoldPanel::IsOk() to check wether the result is ok to be used in further operations. Use wxFoldPanel::GetItem() |
c2a41978 | 40 | to obtain a parent window reference to create the controls on you want to add with wxFoldPanelBar::AddFoldPanelWindow().<br><br> |
957f5ab7 VZ |
41 | */ |
42 | ||
43 | class wxFoldPanel | |
44 | { | |
45 | private: | |
c2a41978 | 46 | wxFoldPanelItem *_item; |
957f5ab7 VZ |
47 | |
48 | public: | |
c2a41978 | 49 | /** Constructor, usually not directly used by the developer. */ |
8fa4d6b8 | 50 | wxFoldPanel(wxFoldPanelItem *item) |
c2a41978 WS |
51 | : _item(item) |
52 | { | |
53 | } | |
54 | ||
55 | /** Returns true if this is a valid wxFoldPanelItem reference. */ | |
56 | bool IsOk() const { | |
57 | return (_item != 0); | |
58 | }; | |
59 | ||
60 | /** Copy operator to assign one instance to the other, this is needed because these classes are passed | |
61 | as instance not by reference. */ | |
62 | virtual void operator=(const wxFoldPanel &item) { | |
63 | _item = item._item; | |
64 | }; | |
957f5ab7 VZ |
65 | |
66 | #ifndef _NO_DOXYGEN_ | |
c2a41978 WS |
67 | // not allowed to be seen by doxygen |
68 | wxFoldPanelItem *GetItem() const { | |
69 | return _item; | |
70 | }; | |
957f5ab7 | 71 | #endif |
8fa4d6b8 | 72 | |
c2a41978 | 73 | /** Use this method to obtain the wxPanel derived class to which you need to add your components. For example;<br> |
957f5ab7 | 74 | |
c2a41978 WS |
75 | \code |
76 | wxFoldPanel item = _pnl->AddFoldPanel(wxT("Test me"), false); | |
8fa4d6b8 | 77 | _pnl->AddFoldPanelWindow(item, new wxButton(item.GetParent(), wxID_ANY, wxT("Press Me"))); |
c2a41978 WS |
78 | \endcode |
79 | */ | |
80 | wxFoldPanelItem *GetParent() const { | |
81 | wxASSERT(_item); | |
82 | return _item; | |
83 | }; | |
957f5ab7 VZ |
84 | |
85 | ||
86 | }; | |
87 | ||
88 | #include <wx/dynarray.h> | |
78727daa | 89 | WX_DEFINE_ARRAY_PTR(wxFoldPanelItem *, wxFoldPanelItemArray); |
957f5ab7 VZ |
90 | |
91 | /** \class wxFoldPanelBar | |
c2a41978 WS |
92 | The wxFoldPanelBar is a class which can maintain a list of collapsable panels. Once a panel is collapsed, only |
93 | it's panel bar is visible to the user. This will provide more space for the other panels, or allow the user to | |
94 | close panels which are not used often to get the most out of the work area. | |
95 | ||
8fa4d6b8 | 96 | This control is easy to use. Simply create it as a child for a panel or sash window, and populate panels with |
c2a41978 | 97 | wxFoldPanelBar::AddFoldPanel(). Then use the wxFoldPanelBar::AddFoldPanelWindow() to add wxWindow derived controls |
8fa4d6b8 | 98 | to the current fold panel. Use wxFoldPanelBar::AddFoldPanelSeperator() to put separators between the groups of |
c2a41978 | 99 | controls that need a visual separator to group them together. After all is constructed, the user can fold |
8fa4d6b8 | 100 | the panels by doubleclicking on the bar or single click on the arrow, which will indicate the collapsed or |
c2a41978 | 101 | expanded state. |
957f5ab7 VZ |
102 | */ |
103 | ||
104 | class wxFoldPanelBar: public wxPanel | |
105 | { | |
106 | private: | |
107 | DECLARE_CLASS( wxFoldPanelBar ) | |
108 | DECLARE_EVENT_TABLE() | |
109 | ||
c2a41978 WS |
110 | wxImageList *_images; |
111 | wxFoldPanelItemArray _panels; | |
112 | wxBoxSizer* _panelSizer; | |
113 | wxPanel *_foldPanel, *_bottomPanel; | |
114 | wxFlexGridSizer* _mainSizer; | |
115 | bool _controlCreated; | |
116 | wxBitmap *_moreBmp; | |
117 | int _extraStyle; | |
957f5ab7 VZ |
118 | |
119 | private: | |
c2a41978 WS |
120 | /** Refreshes all the panels from given index down to last one */ |
121 | void RefreshPanelsFrom(size_t i); | |
957f5ab7 | 122 | |
c2a41978 WS |
123 | /** Refreshes all the panels from given pointer down to last one in the list */ |
124 | void RefreshPanelsFrom(wxFoldPanelItem *item); | |
8fa4d6b8 | 125 | |
c2a41978 WS |
126 | /** Returns the height of the panels that are expanded and collapsed. This is useful to determine |
127 | quickly what size is used to display, and what is left at the bottom to allign | |
128 | the collapsed panels. */ | |
129 | int GetPanelsHeight(int &collapsed, int &expanded); | |
957f5ab7 | 130 | |
c2a41978 WS |
131 | /** Reposition all the collapsed panels to the bottom. When it is not possible to |
132 | allign them to the bottom, stick them behind the visible panels. The Rect holds the | |
133 | slack area left between last repositioned panel and the bottom panels. This needs to | |
134 | get a refresh */ | |
135 | wxRect RepositionCollapsedToBottom(); | |
957f5ab7 VZ |
136 | |
137 | public: | |
8fa4d6b8 | 138 | /** Two step constructor used for XRC. Use wxFoldPanelBar::Create() to create the panel. Do not call |
c2a41978 | 139 | any other methods before the control is fully created! */ |
957f5ab7 VZ |
140 | wxFoldPanelBar(); |
141 | /** One step creation. Look at wxPanel for the argument and style flags. The extraStyle flags are | |
142 | - wxFPB_DEFAULT_EXTRASTYLE : Takes default styles. | |
143 | - wxFPB_COLLAPSE_TO_BOTTOM : When panels are collapsed, they are put at the bottom of the area. */ | |
c2a41978 | 144 | wxFoldPanelBar( wxWindow *parent, wxWindowID id = wxID_ANY, const wxPoint& pos = wxDefaultPosition, |
8fa4d6b8 | 145 | const wxSize& size = wxDefaultSize, long style = wxFPB_DEFAULT_STYLE, |
c2a41978 | 146 | long extraStyle = wxFPB_DEFAULT_EXTRASTYLE); |
8fa4d6b8 | 147 | |
c2a41978 WS |
148 | /** wxFoldPanelBar destructor */ |
149 | virtual ~wxFoldPanelBar(); | |
8fa4d6b8 WS |
150 | |
151 | /** Two step create call. Use this when the control is not created using the wxPanel derived constructor. | |
c2a41978 | 152 | WARNING: Do not create this component more then once! */ |
8fa4d6b8 | 153 | virtual void Create( wxWindow *parent, wxWindowID id = wxID_ANY, const wxPoint& pos = wxDefaultPosition, |
c2a41978 WS |
154 | const wxSize& size = wxDefaultSize, long style = wxFPB_DEFAULT_STYLE, |
155 | long extraStyle = wxFPB_DEFAULT_EXTRASTYLE); | |
8fa4d6b8 | 156 | |
c2a41978 | 157 | /** Adds a fold panel to the list of panels. If the flag collapsedInitially is set to true, the panel |
8fa4d6b8 | 158 | is collapsed initially. The wxFoldPanel item which is returned, can be used as a reference to |
c2a41978 | 159 | perform actions upon the fold panel like collapsing it, expanding it, or deleting it from the list. |
8fa4d6b8 WS |
160 | |
161 | Use this foldpanel to add windows to it. Please consult wxFoldPanelBar::AddFoldPanelWindow() and | |
c2a41978 | 162 | wxFoldPanelBar::AddFoldPanelSeparator() how to add wxWindow items to the panels. */ |
8fa4d6b8 | 163 | wxFoldPanel AddFoldPanel(const wxString &caption, bool collapsedInitially = false, |
c2a41978 WS |
164 | const wxCaptionBarStyle &style = wxEmptyCaptionBarStyle); |
165 | ||
166 | ||
167 | /** Adds a wxWindow derived class to the referenced wxFoldPanel. IMPORTANT: Make the to be created window, | |
168 | child of the wxFoldPanel. See example that follows. The flags to be used are: | |
8fa4d6b8 WS |
169 | - wxFPB_ALIGN_WIDTH: Which means the wxWindow to be added will be alligned to fit the width of the |
170 | wxFoldPanel when it is resized. Very handy for sizer items, buttons and text boxes. | |
957f5ab7 VZ |
171 | - wxFPB_ALIGN_LEFT: Alligns left instead of fitting the width of the child window to be added. Use either |
172 | this one or wxFPB_ALIGN_WIDTH. | |
8fa4d6b8 | 173 | |
c2a41978 WS |
174 | The wxWindow to be added can be slightly indented from left and right so it is more visibly placed |
175 | in the wxFoldPanel. Use ySpacing > 0 to give the control an y offset from the previous wxWindow added, | |
176 | use leftSpacing to give it a slight indent from the left, and rightSpacing also reserves a little space | |
8fa4d6b8 | 177 | on the right so the wxWindow can be properly placed in the wxFoldPanel. |
c2a41978 | 178 | |
8fa4d6b8 | 179 | The following example adds a wxFoldPanel to the wxFoldPanelBar and adds two wxWindow derived controls |
c2a41978 WS |
180 | to the wxFoldPanel: |
181 | ||
182 | \code | |
183 | ||
184 | // create the wxFoldPanelBar | |
185 | _pnl = new wxFoldPanelBar(this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxFPB_DEFAULT_STYLE, wxFPB_COLLAPSE_TO_BOTTOM); | |
186 | ||
187 | // add a foldpanel to the control. "Test me" is the caption and it is initially not collapsed. | |
188 | wxFoldPanel item = _pnl->AddFoldPanel(wxT("Test me"), false); | |
189 | ||
8fa4d6b8 WS |
190 | // now add a button to the fold panel. Mind that the button should be made child of the |
191 | // wxFoldPanel and not of the main form. | |
c2a41978 WS |
192 | _pnl->AddFoldPanelWindow(item, new wxButton(item.GetParent(), ID_COLLAPSEME, wxT("Collapse Me"))); |
193 | ||
194 | // add a separator between the two controls. This is purely a visual line that can have a certain | |
195 | // color and also the indents and width alligning like a control. | |
196 | _pnl->AddFoldPanelSeperator(item); | |
197 | ||
198 | // now add a text ctrl. Also very easy. Allign this on width so that when the control gets wider | |
199 | // the text control also sizes along. | |
8fa4d6b8 | 200 | _pnl->AddFoldPanelWindow(item, new wxTextCtrl(item.GetParent(), wxID_ANY, wxT("Comment")), wxFPB_ALIGN_WIDTH, wxFPB_DEFAULT_YSPACING, 20); |
c2a41978 WS |
201 | |
202 | \endcode | |
203 | */ | |
8fa4d6b8 WS |
204 | int AddFoldPanelWindow(const wxFoldPanel &panel, wxWindow *window, int flags = wxFPB_ALIGN_WIDTH, |
205 | int ySpacing = wxFPB_DEFAULT_YSPACING, int leftSpacing = wxFPB_DEFAULT_LEFTSPACING, | |
c2a41978 WS |
206 | int rightSpacing = wxFPB_DEFAULT_RIGHTSPACING); |
207 | ||
8fa4d6b8 WS |
208 | /** Adds a seperator line to the current wxFoldPanel. The seperator is a simple line which is drawn and is no |
209 | real component. It can be used to seperate groups of controls which belong to eachother. The colour is | |
c2a41978 | 210 | adjustable, and it takes the same ySpacing, leftSpacing and rightSpacing as AddFoldPanelWindow(). */ |
8fa4d6b8 WS |
211 | int AddFoldPanelSeperator(const wxFoldPanel &panel, const wxColour &color = wxColour(167,167,167), |
212 | int ySpacing = wxFPB_DEFAULT_YSPACING, int leftSpacing = wxFPB_DEFAULT_LEFTLINESPACING, | |
c2a41978 WS |
213 | int rightSpacing = wxFPB_DEFAULT_RIGHTLINESPACING); |
214 | ||
8fa4d6b8 | 215 | /** Returns the number of panels currently present in the wxFoldPanelBar. This is independent if they are |
c2a41978 WS |
216 | visible or hidden. */ |
217 | size_t GetCount() const { | |
218 | return _panels.GetCount(); | |
219 | }; | |
220 | ||
221 | /** Returns the wxFoldPanel reference belonging to the current index. An empty panel is returned when the | |
222 | index is out of bounds. Use GetCount() to get the amount of panels present. Collapsing and folding the | |
223 | panel does not change the order in which they are indexed. So it is safe enough to keep a reference | |
224 | to the panel by number. */ | |
225 | wxFoldPanel Item(size_t i) { | |
8fa4d6b8 | 226 | wxCHECK((int)i >= 0 && i < GetCount(), wxFoldPanel(0)); |
c2a41978 WS |
227 | return wxFoldPanel(_panels.Item(i)); |
228 | }; | |
229 | ||
230 | /** Collapses the given wxFoldPanel reference, and updates the foldpanel bar. In the wxFPB_COLLAPSE_TO_BOTTOM | |
231 | style, all collapsed captions are put at the bottom of the control. In the normal mode, they stay where | |
232 | they are */ | |
233 | void Collapse(const wxFoldPanel &item) { | |
234 | wxCHECK2(item.IsOk(), return); | |
235 | item.GetItem()->Collapse(); | |
8fa4d6b8 | 236 | |
c2a41978 WS |
237 | RefreshPanelsFrom(item.GetItem()); |
238 | }; | |
239 | ||
8fa4d6b8 | 240 | /** Expands the given wxFoldPanel reference, and updates the foldpanel bar. In the wxFPB_COLLAPSE_TO_BOTTOM |
c2a41978 WS |
241 | they will be removed from the bottom and the order where the panel originally was placed is restored. */ |
242 | void Expand(const wxFoldPanel &item) { | |
243 | wxCHECK2(item.IsOk(), return); | |
244 | item.GetItem()->Expand(); | |
8fa4d6b8 | 245 | |
c2a41978 WS |
246 | RefreshPanelsFrom(item.GetItem()); |
247 | }; | |
957f5ab7 VZ |
248 | |
249 | /** Sets the style of the caption bar (called wxCaptionBar) of the wxFoldPanel. The changes are applied immediately. | |
c2a41978 WS |
250 | All styles not set in the wxCaptionBarStyle class are not applied. Use the wxCaptionBar reference to indicate |
251 | what captionbar you want to apply the style to. To apply one style to all wxCaptionBar items, use | |
252 | ApplyCaptionStyleAll() */ | |
253 | void ApplyCaptionStyle(wxFoldPanel &fp, const wxCaptionBarStyle &style) { | |
254 | wxCHECK2(fp.IsOk(), return); | |
255 | fp.GetItem()->ApplyCaptionStyle(style); | |
256 | }; | |
257 | ||
258 | /** Sets the style of all the caption bars of the wxFoldPanel. The changes are applied immediately */ | |
259 | void ApplyCaptionStyleAll(const wxCaptionBarStyle &style) { | |
260 | for(size_t i = 0; i < GetCount(); i++) | |
261 | { | |
262 | wxFoldPanel item = Item(i); | |
263 | ApplyCaptionStyle(item, style); | |
264 | } | |
265 | }; | |
266 | ||
8fa4d6b8 | 267 | /** Returns the currently used caption style for the wxFoldPanel. It is returned as a wxCaptionBarStyle class. |
c2a41978 WS |
268 | after modifying it, it can be set again */ |
269 | wxCaptionBarStyle GetCaptionStyle(wxFoldPanel &fp) const { | |
270 | wxCHECK2(fp.IsOk(), wxEmptyCaptionBarStyle); | |
271 | return fp.GetItem()->GetCaptionStyle(); | |
272 | }; | |
957f5ab7 VZ |
273 | |
274 | ||
275 | private: | |
c2a41978 WS |
276 | void OnPressCaption(wxCaptionBarEvent &event); |
277 | void OnSizePanel(wxSizeEvent &event); | |
957f5ab7 | 278 | |
c2a41978 WS |
279 | /** Resize the fold panels so they match the width */ |
280 | void RedisplayFoldPanelItems(); | |
957f5ab7 | 281 | |
c2a41978 | 282 | void OnPaint(wxPaintEvent &event); |
957f5ab7 VZ |
283 | }; |
284 | ||
285 | #endif // __WXFOLDPANELBAR_H__ |