added tests for setting fg/bg colours
[wxWidgets.git] / samples / widgets / radiobox.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Program: wxWidgets Widgets Sample
3 // Name: radiobox.cpp
4 // Purpose: Part of the widgets sample showing wxRadioBox
5 // Author: Vadim Zeitlin
6 // Created: 15.04.01
7 // Id: $Id$
8 // Copyright: (c) 2001 Vadim Zeitlin
9 // License: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
11
12 // ============================================================================
13 // declarations
14 // ============================================================================
15
16 // ----------------------------------------------------------------------------
17 // headers
18 // ----------------------------------------------------------------------------
19
20 // for compilers that support precompilation, includes "wx/wx.h".
21 #include "wx/wxprec.h"
22
23 #ifdef __BORLANDC__
24 #pragma hdrstop
25 #endif
26
27 // for all others, include the necessary headers
28 #ifndef WX_PRECOMP
29 #include "wx/log.h"
30
31 #include "wx/bitmap.h"
32 #include "wx/button.h"
33 #include "wx/checkbox.h"
34 #include "wx/radiobox.h"
35 #include "wx/statbox.h"
36 #include "wx/textctrl.h"
37 #endif
38
39 #include "wx/sizer.h"
40
41 #include "widgets.h"
42 #if 1
43 #include "icons/radiobox.xpm"
44
45 // ----------------------------------------------------------------------------
46 // constants
47 // ----------------------------------------------------------------------------
48
49 // control ids
50 enum
51 {
52 RadioPage_Reset = 100,
53 RadioPage_Update,
54 RadioPage_Selection,
55 RadioPage_Label,
56 RadioPage_LabelBtn,
57 RadioPage_Radio
58 };
59
60 // layout direction radiobox selections
61 enum
62 {
63 RadioDir_Default,
64 RadioDir_LtoR,
65 RadioDir_TtoB
66 };
67
68 // default values for the number of radiobox items
69 static const unsigned int DEFAULT_NUM_ENTRIES = 12;
70 static const unsigned int DEFAULT_MAJOR_DIM = 3;
71
72 // ----------------------------------------------------------------------------
73 // RadioWidgetsPage
74 // ----------------------------------------------------------------------------
75
76 class RadioWidgetsPage : public WidgetsPage
77 {
78 public:
79 RadioWidgetsPage(wxNotebook *notebook, wxImageList *imaglist);
80 virtual ~RadioWidgetsPage(){};
81
82 virtual wxControl *GetWidget() const { return m_radio; }
83
84 protected:
85 // event handlers
86 void OnCheckOrRadioBox(wxCommandEvent& event);
87 void OnRadioBox(wxCommandEvent& event);
88
89 void OnButtonReset(wxCommandEvent& event);
90 void OnButtonRecreate(wxCommandEvent& event);
91
92 void OnButtonSelection(wxCommandEvent& event);
93 void OnButtonSetLabel(wxCommandEvent& event);
94
95 void OnUpdateUIReset(wxUpdateUIEvent& event);
96 void OnUpdateUIUpdate(wxUpdateUIEvent& event);
97 void OnUpdateUISelection(wxUpdateUIEvent& event);
98
99 // reset the wxRadioBox parameters
100 void Reset();
101
102 // (re)create the wxRadioBox
103 void CreateRadio();
104
105 // the controls
106 // ------------
107
108 // the check/radio boxes for styles
109 wxCheckBox *m_chkVert;
110 wxRadioBox *m_radioDir;
111
112 // the gauge itself and the sizer it is in
113 wxRadioBox *m_radio;
114 wxSizer *m_sizerRadio;
115
116 // the text entries for command parameters
117 wxTextCtrl *m_textNumBtns,
118 *m_textMajorDim,
119 *m_textCurSel,
120 *m_textSel,
121 *m_textLabel,
122 *m_textLabelBtns;
123
124 private:
125 DECLARE_EVENT_TABLE()
126 DECLARE_WIDGETS_PAGE(RadioWidgetsPage)
127 };
128
129 // ----------------------------------------------------------------------------
130 // event tables
131 // ----------------------------------------------------------------------------
132
133 BEGIN_EVENT_TABLE(RadioWidgetsPage, WidgetsPage)
134 EVT_BUTTON(RadioPage_Reset, RadioWidgetsPage::OnButtonReset)
135
136 EVT_BUTTON(RadioPage_Update, RadioWidgetsPage::OnButtonRecreate)
137 EVT_BUTTON(RadioPage_LabelBtn, RadioWidgetsPage::OnButtonRecreate)
138
139 EVT_BUTTON(RadioPage_Selection, RadioWidgetsPage::OnButtonSelection)
140 EVT_BUTTON(RadioPage_Label, RadioWidgetsPage::OnButtonSetLabel)
141
142 EVT_UPDATE_UI(RadioPage_Update, RadioWidgetsPage::OnUpdateUIUpdate)
143 EVT_UPDATE_UI(RadioPage_Selection, RadioWidgetsPage::OnUpdateUISelection)
144
145 EVT_RADIOBOX(RadioPage_Radio, RadioWidgetsPage::OnRadioBox)
146
147 EVT_CHECKBOX(wxID_ANY, RadioWidgetsPage::OnCheckOrRadioBox)
148 EVT_RADIOBOX(wxID_ANY, RadioWidgetsPage::OnCheckOrRadioBox)
149 END_EVENT_TABLE()
150
151 // ============================================================================
152 // implementation
153 // ============================================================================
154
155 IMPLEMENT_WIDGETS_PAGE(RadioWidgetsPage, _T("Radio"));
156
157 RadioWidgetsPage::RadioWidgetsPage(wxNotebook *notebook,
158 wxImageList *imaglist)
159 : WidgetsPage(notebook)
160 {
161 imaglist->Add(wxBitmap(radio_xpm));
162
163 // init everything
164 m_chkVert = (wxCheckBox *)NULL;
165
166 m_textNumBtns =
167 m_textLabelBtns =
168 m_textLabel = (wxTextCtrl *)NULL;
169
170 m_radio =
171 m_radioDir = (wxRadioBox *)NULL;
172 m_sizerRadio = (wxSizer *)NULL;
173
174 wxSizer *sizerTop = new wxBoxSizer(wxHORIZONTAL);
175
176 // left pane
177 wxStaticBox *box = new wxStaticBox(this, wxID_ANY, _T("&Set style"));
178
179 wxSizer *sizerLeft = new wxStaticBoxSizer(box, wxVERTICAL);
180
181 m_chkVert = CreateCheckBoxAndAddToSizer(sizerLeft, _T("&Vertical layout"));
182
183 static const wxString layoutDir[] =
184 {
185 _T("default"),
186 _T("left to right"),
187 _T("top to bottom")
188 };
189
190 m_radioDir = new wxRadioBox(this, wxID_ANY, _T("Numbering:"),
191 wxDefaultPosition, wxDefaultSize,
192 WXSIZEOF(layoutDir), layoutDir,
193 1, wxRA_SPECIFY_COLS);
194 sizerLeft->Add(m_radioDir, 0, wxGROW | wxALL, 5);
195
196 // if it's not defined, we can't change the radiobox direction
197 #ifndef wxRA_LEFTTORIGHT
198 m_radioDir->Disable();
199 #endif // wxRA_LEFTTORIGHT
200
201 wxSizer *sizerRow;
202 sizerRow = CreateSizerWithTextAndLabel(_T("&Major dimension:"),
203 wxID_ANY,
204 &m_textMajorDim);
205 sizerLeft->Add(sizerRow, 0, wxGROW | wxALL, 5);
206
207 sizerRow = CreateSizerWithTextAndLabel(_T("&Number of buttons:"),
208 wxID_ANY,
209 &m_textNumBtns);
210 sizerLeft->Add(sizerRow, 0, wxGROW | wxALL, 5);
211
212 wxButton *btn;
213 btn = new wxButton(this, RadioPage_Update, _T("&Update"));
214 sizerLeft->Add(btn, 0, wxALIGN_CENTRE_HORIZONTAL | wxALL, 5);
215
216 sizerLeft->Add(5, 5, 0, wxGROW | wxALL, 5); // spacer
217
218 btn = new wxButton(this, RadioPage_Reset, _T("&Reset"));
219 sizerLeft->Add(btn, 0, wxALIGN_CENTRE_HORIZONTAL | wxALL, 15);
220
221 // middle pane
222 wxStaticBox *box2 = new wxStaticBox(this, wxID_ANY, _T("&Change parameters"));
223 wxSizer *sizerMiddle = new wxStaticBoxSizer(box2, wxVERTICAL);
224
225 sizerRow = CreateSizerWithTextAndLabel(_T("Current selection:"),
226 wxID_ANY,
227 &m_textCurSel);
228 sizerMiddle->Add(sizerRow, 0, wxGROW | wxALL, 5);
229
230 sizerRow = CreateSizerWithTextAndButton(RadioPage_Selection,
231 _T("&Change selection:"),
232 wxID_ANY,
233 &m_textSel);
234 sizerMiddle->Add(sizerRow, 0, wxGROW | wxALL, 5);
235
236 sizerRow = CreateSizerWithTextAndButton(RadioPage_Label,
237 _T("&Label for box:"),
238 wxID_ANY,
239 &m_textLabel);
240 sizerMiddle->Add(sizerRow, 0, wxGROW | wxALL, 5);
241
242 sizerRow = CreateSizerWithTextAndButton(RadioPage_LabelBtn,
243 _T("&Label for buttons:"),
244 wxID_ANY,
245 &m_textLabelBtns);
246 sizerMiddle->Add(sizerRow, 0, wxGROW | wxALL, 5);
247
248 // right pane
249 wxSizer *sizerRight = new wxBoxSizer(wxHORIZONTAL);
250 sizerRight->SetMinSize(150, 0);
251 m_sizerRadio = sizerRight; // save it to modify it later
252
253 Reset();
254 CreateRadio();
255
256 // the 3 panes panes compose the window
257 sizerTop->Add(sizerLeft, 0, wxGROW | (wxALL & ~wxLEFT), 10);
258 sizerTop->Add(sizerMiddle, 1, wxGROW | wxALL, 10);
259 sizerTop->Add(sizerRight, 0, wxGROW | (wxALL & ~wxRIGHT), 10);
260
261 // final initializations
262 SetSizer(sizerTop);
263
264 sizerTop->Fit(this);
265 }
266
267 // ----------------------------------------------------------------------------
268 // operations
269 // ----------------------------------------------------------------------------
270
271 void RadioWidgetsPage::Reset()
272 {
273 m_textMajorDim->SetValue(wxString::Format(_T("%u"), DEFAULT_MAJOR_DIM));
274 m_textNumBtns->SetValue(wxString::Format(_T("%u"), DEFAULT_NUM_ENTRIES));
275 m_textLabel->SetValue(_T("I'm a radiobox"));
276 m_textLabelBtns->SetValue(_T("item"));
277
278 m_chkVert->SetValue(false);
279 m_radioDir->SetSelection(RadioDir_Default);
280 }
281
282 void RadioWidgetsPage::CreateRadio()
283 {
284 int sel;
285 if ( m_radio )
286 {
287 sel = m_radio->GetSelection();
288
289 m_sizerRadio->Detach( m_radio );
290
291 delete m_radio;
292 }
293 else // first time creation, no old selection to preserve
294 {
295 sel = -1;
296 }
297
298 unsigned long count;
299 if ( !m_textNumBtns->GetValue().ToULong(&count) )
300 {
301 wxLogWarning(_T("Should have a valid number for number of items."));
302
303 // fall back to default
304 count = DEFAULT_NUM_ENTRIES;
305 }
306
307 unsigned long majorDim;
308 if ( !m_textMajorDim->GetValue().ToULong(&majorDim) )
309 {
310 wxLogWarning(_T("Should have a valid major dimension number."));
311
312 // fall back to default
313 majorDim = DEFAULT_MAJOR_DIM;
314 }
315
316 wxString *items = new wxString[count];
317
318 wxString labelBtn = m_textLabelBtns->GetValue();
319 for ( size_t n = 0; n < count; n++ )
320 {
321 items[n] = wxString::Format(_T("%s %lu"),
322 labelBtn.c_str(), (unsigned long)n + 1);
323 }
324
325 int flags = m_chkVert->GetValue() ? wxRA_VERTICAL
326 : wxRA_HORIZONTAL;
327
328 #ifdef wxRA_LEFTTORIGHT
329 switch ( m_radioDir->GetSelection() )
330 {
331 default:
332 wxFAIL_MSG( _T("unexpected wxRadioBox layout direction") );
333 // fall through
334
335 case RadioDir_Default:
336 break;
337
338 case RadioDir_LtoR:
339 flags |= wxRA_LEFTTORIGHT;
340 break;
341
342 case RadioDir_TtoB:
343 flags |= wxRA_TOPTOBOTTOM;
344 break;
345 }
346 #endif // wxRA_LEFTTORIGHT
347
348 m_radio = new wxRadioBox(this, RadioPage_Radio,
349 m_textLabel->GetValue(),
350 wxDefaultPosition, wxDefaultSize,
351 count, items,
352 majorDim,
353 flags);
354
355 delete [] items;
356
357 if ( sel >= 0 && (size_t)sel < count )
358 {
359 m_radio->SetSelection(sel);
360 }
361
362 m_sizerRadio->Add(m_radio, 1, wxGROW);
363 m_sizerRadio->Layout();
364 }
365
366 // ----------------------------------------------------------------------------
367 // event handlers
368 // ----------------------------------------------------------------------------
369
370 void RadioWidgetsPage::OnButtonReset(wxCommandEvent& WXUNUSED(event))
371 {
372 Reset();
373
374 CreateRadio();
375 }
376
377 void RadioWidgetsPage::OnCheckOrRadioBox(wxCommandEvent& WXUNUSED(event))
378 {
379 CreateRadio();
380 }
381
382 void RadioWidgetsPage::OnRadioBox(wxCommandEvent& event)
383 {
384 int sel = m_radio->GetSelection();
385 int event_sel = event.GetSelection();
386 wxUnusedVar(event_sel);
387
388 wxLogMessage(_T("Radiobox selection changed, now %d"), sel);
389
390 wxASSERT_MSG( sel == event_sel,
391 _T("selection should be the same in event and radiobox") );
392
393 m_textCurSel->SetValue(wxString::Format(_T("%d"), sel));
394 }
395
396 void RadioWidgetsPage::OnButtonRecreate(wxCommandEvent& WXUNUSED(event))
397 {
398 CreateRadio();
399 }
400
401 void RadioWidgetsPage::OnButtonSetLabel(wxCommandEvent& WXUNUSED(event))
402 {
403 m_radio->wxControl::SetLabel(m_textLabel->GetValue());
404 }
405
406 void RadioWidgetsPage::OnButtonSelection(wxCommandEvent& WXUNUSED(event))
407 {
408 unsigned long sel;
409 if ( !m_textSel->GetValue().ToULong(&sel) ||
410 (sel >= (size_t)m_radio->GetCount()) )
411 {
412 wxLogWarning(_T("Invalid number specified as new selection."));
413 }
414 else
415 {
416 m_radio->SetSelection(sel);
417 }
418 }
419
420 void RadioWidgetsPage::OnUpdateUIUpdate(wxUpdateUIEvent& event)
421 {
422 unsigned long n;
423 event.Enable( m_textNumBtns->GetValue().ToULong(&n) &&
424 m_textMajorDim->GetValue().ToULong(&n) );
425 }
426
427 void RadioWidgetsPage::OnUpdateUISelection(wxUpdateUIEvent& event)
428 {
429 unsigned long n;
430 event.Enable( m_textSel->GetValue().ToULong(&n) &&
431 (n < (size_t)m_radio->GetCount()) );
432 }
433
434 void RadioWidgetsPage::OnUpdateUIReset(wxUpdateUIEvent& event)
435 {
436 // only enable it if something is not set to default
437 bool enable = m_chkVert->GetValue();
438
439 if ( !enable )
440 {
441 unsigned long numEntries;
442
443 enable = !m_textNumBtns->GetValue().ToULong(&numEntries) ||
444 numEntries != DEFAULT_NUM_ENTRIES;
445
446 if ( !enable )
447 {
448 unsigned long majorDim;
449
450 enable = !m_textMajorDim->GetValue().ToULong(&majorDim) ||
451 majorDim != DEFAULT_MAJOR_DIM;
452 }
453 }
454
455 event.Enable(enable);
456 }
457
458 #endif