]> git.saurik.com Git - wxWidgets.git/blob - samples/widgets/widgets.cpp
Continuation of 'widgets' sample improvements.
[wxWidgets.git] / samples / widgets / widgets.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Program: wxWidgets Widgets Sample
3 // Name: samples/widgets/widgets.cpp
4 // Purpose: Sample showing most of the simple wxWidgets widgets
5 // Author: Vadim Zeitlin
6 // Created: 27.03.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/app.h"
30 #include "wx/log.h"
31 #include "wx/frame.h"
32 #include "wx/menu.h"
33
34 #include "wx/button.h"
35 #include "wx/checkbox.h"
36 #include "wx/listbox.h"
37 #include "wx/statbox.h"
38 #include "wx/stattext.h"
39 #include "wx/textctrl.h"
40 #include "wx/msgdlg.h"
41 #endif
42
43 #include "wx/sysopt.h"
44 #include "wx/bookctrl.h"
45 #include "wx/treebook.h"
46 #include "wx/sizer.h"
47 #include "wx/colordlg.h"
48 #include "wx/fontdlg.h"
49 #include "wx/textdlg.h"
50
51 #include "widgets.h"
52
53 #include "../sample.xpm"
54
55 // ----------------------------------------------------------------------------
56 // constants
57 // ----------------------------------------------------------------------------
58
59 // control ids
60 enum
61 {
62 Widgets_ClearLog = 100,
63 Widgets_Quit,
64
65 Widgets_BookCtrl,
66
67 #if wxUSE_TOOLTIPS
68 Widgets_SetTooltip,
69 #endif // wxUSE_TOOLTIPS
70 Widgets_SetFgColour,
71 Widgets_SetBgColour,
72 Widgets_SetFont,
73 Widgets_Enable,
74
75 Widgets_BorderNone,
76 Widgets_BorderStatic,
77 Widgets_BorderSimple,
78 Widgets_BorderRaised,
79 Widgets_BorderSunken,
80 Widgets_BorderDouble,
81 Widgets_BorderDefault,
82
83 Widgets_GoToPage,
84 Widgets_GoToPageLast = Widgets_GoToPage + 100
85 };
86
87 const wxChar *WidgetsCategories[MAX_PAGES] = {
88 #if defined(__WXUNIVERSAL__)
89 wxT("Universal"),
90 #else
91 wxT("Native"),
92 #endif
93 wxT("Generic"),
94 wxT("Pickers"),
95 wxT("Comboboxes"),
96 wxT("With items"),
97 wxT("Editable"),
98 wxT("Books"),
99 wxT("All controls")
100 };
101
102 // ----------------------------------------------------------------------------
103 // our classes
104 // ----------------------------------------------------------------------------
105
106 // Define a new application type, each program should derive a class from wxApp
107 class WidgetsApp : public wxApp
108 {
109 public:
110 // override base class virtuals
111 // ----------------------------
112
113 // this one is called on application startup and is a good place for the app
114 // initialization (doing it here and not in the ctor allows to have an error
115 // return: if OnInit() returns false, the application terminates)
116 virtual bool OnInit();
117 };
118
119 // Define a new frame type: this is going to be our main frame
120 class WidgetsFrame : public wxFrame
121 {
122 public:
123 // ctor(s) and dtor
124 WidgetsFrame(const wxString& title);
125 virtual ~WidgetsFrame();
126
127 protected:
128 // event handlers
129 #if USE_LOG
130 void OnButtonClearLog(wxCommandEvent& event);
131 #endif // USE_LOG
132 void OnExit(wxCommandEvent& event);
133
134 #if wxUSE_MENUS
135 void OnPageChanged(WidgetsBookCtrlEvent& event);
136 void OnGoToPage(wxCommandEvent& event);
137
138 #if wxUSE_TOOLTIPS
139 void OnSetTooltip(wxCommandEvent& event);
140 #endif // wxUSE_TOOLTIPS
141 void OnSetFgCol(wxCommandEvent& event);
142 void OnSetBgCol(wxCommandEvent& event);
143 void OnSetFont(wxCommandEvent& event);
144 void OnEnable(wxCommandEvent& event);
145 void OnSetBorder(wxCommandEvent& event);
146 #endif // wxUSE_MENUS
147
148 // initialize the book: add all pages to it
149 void InitBook();
150
151 // finding current page assuming book inside book
152 WidgetsPage *CurrentPage();
153
154 private:
155 // the panel containing everything
156 wxPanel *m_panel;
157
158 #if USE_LOG
159 // the listbox for logging messages
160 wxListBox *m_lboxLog;
161
162 // the log target we use to redirect messages to the listbox
163 wxLog *m_logTarget;
164 #endif // USE_LOG
165
166 // the book containing the test pages
167 WidgetsBookCtrl *m_book;
168
169 #if wxUSE_MENUS
170 // last chosen fg/bg colours and font
171 wxColour m_colFg,
172 m_colBg;
173 wxFont m_font;
174 #endif // wxUSE_MENUS
175
176 // any class wishing to process wxWidgets events must use this macro
177 DECLARE_EVENT_TABLE()
178 };
179
180 #if USE_LOG
181 // A log target which just redirects the messages to a listbox
182 class LboxLogger : public wxLog
183 {
184 public:
185 LboxLogger(wxListBox *lbox, wxLog *logOld)
186 {
187 m_lbox = lbox;
188 //m_lbox->Disable(); -- looks ugly under MSW
189 m_logOld = logOld;
190 }
191
192 virtual ~LboxLogger()
193 {
194 wxLog::SetActiveTarget(m_logOld);
195 }
196
197 private:
198 // implement sink functions
199 virtual void DoLog(wxLogLevel level, const wxChar *szString, time_t t)
200 {
201 // don't put trace messages into listbox or we can get into infinite
202 // recursion
203 if ( level == wxLOG_Trace )
204 {
205 if ( m_logOld )
206 {
207 // cast is needed to call protected method
208 ((LboxLogger *)m_logOld)->DoLog(level, szString, t);
209 }
210 }
211 else
212 {
213 wxLog::DoLog(level, szString, t);
214 }
215 }
216
217 virtual void DoLogString(const wxChar *szString, time_t WXUNUSED(t))
218 {
219 wxString msg;
220 TimeStamp(&msg);
221 msg += szString;
222
223 #ifdef __WXUNIVERSAL__
224 m_lbox->AppendAndEnsureVisible(msg);
225 #else // other ports don't have this method yet
226 m_lbox->Append(msg);
227 m_lbox->SetFirstItem(m_lbox->GetCount() - 1);
228 #endif
229 }
230
231 // the control we use
232 wxListBox *m_lbox;
233
234 // the old log target
235 wxLog *m_logOld;
236 };
237 #endif // USE_LOG
238
239 // array of pages
240 WX_DEFINE_ARRAY_PTR(WidgetsPage *, ArrayWidgetsPage);
241
242 // ----------------------------------------------------------------------------
243 // misc macros
244 // ----------------------------------------------------------------------------
245
246 IMPLEMENT_APP(WidgetsApp)
247
248 // ----------------------------------------------------------------------------
249 // event tables
250 // ----------------------------------------------------------------------------
251
252 BEGIN_EVENT_TABLE(WidgetsFrame, wxFrame)
253 #if USE_LOG
254 EVT_BUTTON(Widgets_ClearLog, WidgetsFrame::OnButtonClearLog)
255 #endif // USE_LOG
256 EVT_BUTTON(Widgets_Quit, WidgetsFrame::OnExit)
257
258 #if wxUSE_TOOLTIPS
259 EVT_MENU(Widgets_SetTooltip, WidgetsFrame::OnSetTooltip)
260 #endif // wxUSE_TOOLTIPS
261
262 #if wxUSE_MENUS
263 EVT_WIDGETS_PAGE_CHANGED(wxID_ANY, WidgetsFrame::OnPageChanged)
264 EVT_MENU_RANGE(Widgets_GoToPage, Widgets_GoToPageLast,
265 WidgetsFrame::OnGoToPage)
266
267 EVT_MENU(Widgets_SetFgColour, WidgetsFrame::OnSetFgCol)
268 EVT_MENU(Widgets_SetBgColour, WidgetsFrame::OnSetBgCol)
269 EVT_MENU(Widgets_SetFont, WidgetsFrame::OnSetFont)
270 EVT_MENU(Widgets_Enable, WidgetsFrame::OnEnable)
271
272 EVT_MENU_RANGE(Widgets_BorderNone, Widgets_BorderDefault,
273 WidgetsFrame::OnSetBorder)
274
275 EVT_MENU(wxID_EXIT, WidgetsFrame::OnExit)
276 #endif // wxUSE_MENUS
277 END_EVENT_TABLE()
278
279 // ============================================================================
280 // implementation
281 // ============================================================================
282
283 // ----------------------------------------------------------------------------
284 // app class
285 // ----------------------------------------------------------------------------
286
287 bool WidgetsApp::OnInit()
288 {
289 if ( !wxApp::OnInit() )
290 return false;
291
292 // the reason for having these ifdef's is that I often run two copies of
293 // this sample side by side and it is useful to see which one is which
294 wxString title;
295 #if defined(__WXUNIVERSAL__)
296 title = _T("wxUniv/");
297 #endif
298
299 #if defined(__WXMSW__)
300 title += _T("wxMSW");
301 #elif defined(__WXGTK__)
302 title += _T("wxGTK");
303 #elif defined(__WXMAC__)
304 title += _T("wxMAC");
305 #elif defined(__WXMOTIF__)
306 title += _T("wxMOTIF");
307 #else
308 title += _T("wxWidgets");
309 #endif
310
311 wxFrame *frame = new WidgetsFrame(title + _T(" widgets demo"));
312 frame->Show();
313
314 //wxLog::AddTraceMask(_T("listbox"));
315 //wxLog::AddTraceMask(_T("scrollbar"));
316 //wxLog::AddTraceMask(_T("focus"));
317
318 return true;
319 }
320
321 // ----------------------------------------------------------------------------
322 // WidgetsFrame construction
323 // ----------------------------------------------------------------------------
324
325 WidgetsFrame::WidgetsFrame(const wxString& title)
326 : wxFrame(NULL, wxID_ANY, title,
327 wxPoint(0, 50), wxDefaultSize,
328 wxDEFAULT_FRAME_STYLE |
329 wxNO_FULL_REPAINT_ON_RESIZE |
330 wxCLIP_CHILDREN |
331 wxTAB_TRAVERSAL)
332 {
333 // set the frame icon
334 SetIcon(wxICON(sample));
335
336 // init everything
337 #if USE_LOG
338 m_lboxLog = (wxListBox *)NULL;
339 m_logTarget = (wxLog *)NULL;
340 #endif // USE_LOG
341 m_book = (WidgetsBookCtrl *)NULL;
342
343 #if wxUSE_MENUS
344 // create the menubar
345 wxMenuBar *mbar = new wxMenuBar;
346 wxMenu *menuWidget = new wxMenu;
347 #if wxUSE_TOOLTIPS
348 menuWidget->Append(Widgets_SetTooltip, _T("Set &tooltip...\tCtrl-T"));
349 menuWidget->AppendSeparator();
350 #endif // wxUSE_TOOLTIPS
351 menuWidget->Append(Widgets_SetFgColour, _T("Set &foreground...\tCtrl-F"));
352 menuWidget->Append(Widgets_SetBgColour, _T("Set &background...\tCtrl-B"));
353 menuWidget->Append(Widgets_SetFont, _T("Set f&ont...\tCtrl-O"));
354 menuWidget->AppendCheckItem(Widgets_Enable, _T("&Enable/disable\tCtrl-E"));
355
356 wxMenu *menuBorders = new wxMenu;
357 menuBorders->AppendRadioItem(Widgets_BorderDefault, _T("De&fault\tCtrl-Shift-9"));
358 menuBorders->AppendRadioItem(Widgets_BorderNone, _T("&None\tCtrl-Shift-0"));
359 menuBorders->AppendRadioItem(Widgets_BorderSimple, _T("&Simple\tCtrl-Shift-1"));
360 menuBorders->AppendRadioItem(Widgets_BorderDouble, _T("&Double\tCtrl-Shift-2"));
361 menuBorders->AppendRadioItem(Widgets_BorderStatic, _T("Stati&c\tCtrl-Shift-3"));
362 menuBorders->AppendRadioItem(Widgets_BorderRaised, _T("&Raised\tCtrl-Shift-4"));
363 menuBorders->AppendRadioItem(Widgets_BorderSunken, _T("S&unken\tCtrl-Shift-5"));
364 menuWidget->AppendSubMenu(menuBorders, _T("Set &border"));
365
366 menuWidget->AppendSeparator();
367 menuWidget->Append(wxID_EXIT, _T("&Quit\tCtrl-Q"));
368 mbar->Append(menuWidget, _T("&Widget"));
369 SetMenuBar(mbar);
370
371 mbar->Check(Widgets_Enable, true);
372 #endif // wxUSE_MENUS
373
374 // create controls
375 m_panel = new wxPanel(this, wxID_ANY,
376 wxDefaultPosition, wxDefaultSize, wxCLIP_CHILDREN);
377
378 wxSizer *sizerTop = new wxBoxSizer(wxVERTICAL);
379
380 // we have 2 panes: book with pages demonstrating the controls in the
381 // upper one and the log window with some buttons in the lower
382
383 int style = wxNO_FULL_REPAINT_ON_RESIZE|wxCLIP_CHILDREN|wxBK_DEFAULT;
384 // Uncomment to suppress page theme (draw in solid colour)
385 //style |= wxNB_NOPAGETHEME;
386
387 m_book = new WidgetsBookCtrl(m_panel, Widgets_BookCtrl, wxDefaultPosition,
388 #ifdef __WXMOTIF__
389 wxSize(500, wxDefaultCoord), // under Motif, height is a function of the width...
390 #else
391 wxDefaultSize,
392 #endif
393 style);
394 InitBook();
395
396 #ifndef __SMARTPHONE__
397 // the lower one only has the log listbox and a button to clear it
398 #if USE_LOG
399 wxSizer *sizerDown = new wxStaticBoxSizer(
400 new wxStaticBox( m_panel, wxID_ANY, _T("&Log window") ),
401 wxVERTICAL);
402
403 m_lboxLog = new wxListBox(m_panel, wxID_ANY);
404 sizerDown->Add(m_lboxLog, 1, wxGROW | wxALL, 5);
405 sizerDown->SetMinSize(100, 150);
406 #else
407 wxSizer *sizerDown = new wxBoxSizer(wxVERTICAL);
408 #endif // USE_LOG
409
410 wxBoxSizer *sizerBtns = new wxBoxSizer(wxHORIZONTAL);
411 wxButton *btn;
412 #if USE_LOG
413 btn = new wxButton(m_panel, Widgets_ClearLog, _T("Clear &log"));
414 sizerBtns->Add(btn);
415 sizerBtns->Add(10, 0); // spacer
416 #endif // USE_LOG
417 btn = new wxButton(m_panel, Widgets_Quit, _T("E&xit"));
418 sizerBtns->Add(btn);
419 sizerDown->Add(sizerBtns, 0, wxALL | wxALIGN_RIGHT, 5);
420
421 // put everything together
422 sizerTop->Add(m_book, 1, wxGROW | (wxALL & ~(wxTOP | wxBOTTOM)), 10);
423 sizerTop->Add(0, 5, 0, wxGROW); // spacer in between
424 sizerTop->Add(sizerDown, 0, wxGROW | (wxALL & ~wxTOP), 10);
425
426 #else // !__SMARTPHONE__/__SMARTPHONE__
427
428 sizerTop->Add(m_book, 1, wxGROW | wxALL );
429
430 #endif // __SMARTPHONE__
431
432 m_panel->SetSizer(sizerTop);
433
434 sizerTop->Fit(this);
435 sizerTop->SetSizeHints(this);
436
437 #if USE_LOG && !defined(__WXCOCOA__)
438 // wxCocoa's listbox is too flakey to use for logging right now
439 // now that everything is created we can redirect the log messages to the
440 // listbox
441 m_logTarget = new LboxLogger(m_lboxLog, wxLog::GetActiveTarget());
442 wxLog::SetActiveTarget(m_logTarget);
443 #endif
444 }
445
446 void WidgetsFrame::InitBook()
447 {
448 wxImageList *imageList = new wxImageList(32, 32);
449
450 imageList->Add(wxBitmap(sample_xpm));
451
452 #if !USE_TREEBOOK
453 WidgetsBookCtrl *books[MAX_PAGES];
454 #endif
455
456 ArrayWidgetsPage pages[MAX_PAGES];
457 wxArrayString labels[MAX_PAGES];
458
459 wxMenu *menuPages = new wxMenu;
460 unsigned int nPage = 0, nFKey = 0;
461 int cat, imageId = 1;
462
463 // we need to first create all pages and only then add them to the book
464 // as we need the image list first
465 //
466 // we also construct the pages menu during this first iteration
467 for ( cat = 0; cat < MAX_PAGES; cat++ )
468 {
469 #if USE_TREEBOOK
470 nPage++; // increase for parent page
471 #else
472 books[cat] = new WidgetsBookCtrl( m_book, wxID_ANY );
473 #endif
474
475 for ( WidgetsPageInfo *info = WidgetsPage::ms_widgetPages;
476 info;
477 info = info->GetNext() )
478 {
479 if( (info->GetCategories() & ( 1 << cat )) == 0)
480 continue;
481
482 WidgetsPage *page = (*info->GetCtor())(
483 #if USE_TREEBOOK
484 m_book
485 #else
486 books[cat]
487 #endif
488 , imageList);
489 pages[cat].Add(page);
490
491 labels[cat].Add(info->GetLabel());
492 if ( cat == ALL_PAGE )
493 {
494 wxString radioLabel(info->GetLabel());
495 nFKey++;
496 if ( nFKey <= 12 )
497 {
498 radioLabel << wxT("\tF" ) << nFKey;
499 }
500
501 menuPages->AppendRadioItem(
502 Widgets_GoToPage + nPage,
503 radioLabel
504 );
505 #if !USE_TREEBOOK
506 // consider only for book in book architecture
507 nPage++;
508 #endif
509 }
510
511 #if USE_TREEBOOK
512 // consider only for treebook architecture (with subpages)
513 nPage++;
514 #endif
515 }
516 }
517
518 GetMenuBar()->Append(menuPages, _T("&Page"));
519
520 m_book->AssignImageList(imageList);
521
522 for ( cat = 0; cat < MAX_PAGES; cat++ )
523 {
524 #if USE_TREEBOOK
525 m_book->AddPage(NULL,WidgetsCategories[cat],false,0);
526 #else
527 m_book->AddPage(books[cat],WidgetsCategories[cat],false,0);
528 books[cat]->SetImageList(imageList);
529 #endif
530
531 // now do add them
532 size_t count = pages[cat].GetCount();
533 for ( size_t n = 0; n < count; n++ )
534 {
535 #if USE_TREEBOOK
536 m_book->AddSubPage(
537 #else
538 books[cat]->AddPage(
539 #endif
540 pages[cat][n],
541 labels[cat][n],
542 false, // don't select
543 imageId++
544 );
545 }
546 }
547
548 #if USE_TREEBOOK
549 // for treebook page #0 is empty parent page only
550 m_book->SetSelection(1);
551 m_book->SetSelection(0);
552 #endif
553 }
554
555 WidgetsPage *WidgetsFrame::CurrentPage()
556 {
557 #if USE_TREEBOOK
558 return wxStaticCast(m_book->GetCurrentPage(), WidgetsPage);
559 #else
560 WidgetsBookCtrl *book = wxStaticCast(m_book->GetCurrentPage(), WidgetsBookCtrl);
561 if (!book) return NULL;
562 return wxStaticCast(book->GetCurrentPage(), WidgetsPage);
563 #endif
564 }
565
566 WidgetsFrame::~WidgetsFrame()
567 {
568 #if USE_LOG
569 delete m_logTarget;
570 #endif // USE_LOG
571 }
572
573 // ----------------------------------------------------------------------------
574 // WidgetsFrame event handlers
575 // ----------------------------------------------------------------------------
576
577 void WidgetsFrame::OnExit(wxCommandEvent& WXUNUSED(event))
578 {
579 Close();
580 }
581
582 #if USE_LOG
583 void WidgetsFrame::OnButtonClearLog(wxCommandEvent& WXUNUSED(event))
584 {
585 m_lboxLog->Clear();
586 }
587 #endif // USE_LOG
588
589 #if wxUSE_MENUS
590
591 void WidgetsFrame::OnPageChanged(WidgetsBookCtrlEvent& event)
592 {
593 wxMenuItem *item = GetMenuBar()->FindItem(Widgets_GoToPage + event.GetSelection());
594 if (item) item->Check();
595 event.Skip();
596 }
597
598 void WidgetsFrame::OnGoToPage(wxCommandEvent& event)
599 {
600 #if USE_TREEBOOK
601 m_book->SetSelection(event.GetId() - Widgets_GoToPage);
602 #else
603 m_book->SetSelection(m_book->GetPageCount()-1);
604 WidgetsBookCtrl *book = wxStaticCast(m_book->GetCurrentPage(), WidgetsBookCtrl);
605 book->SetSelection(event.GetId() - Widgets_GoToPage);
606 #endif
607 }
608
609 #if wxUSE_TOOLTIPS
610
611 void WidgetsFrame::OnSetTooltip(wxCommandEvent& WXUNUSED(event))
612 {
613 static wxString s_tip = _T("This is a tooltip");
614
615 wxTextEntryDialog dialog
616 (
617 this,
618 _T("Tooltip text (may use \\n, leave empty to remove): "),
619 _T("Widgets sample"),
620 s_tip
621 );
622
623 if ( dialog.ShowModal() != wxID_OK )
624 return;
625
626 s_tip = dialog.GetValue();
627 s_tip.Replace(_T("\\n"), _T("\n"));
628
629 WidgetsPage *page = CurrentPage();
630 page->GetWidget()->SetToolTip(s_tip);
631
632 wxControl *ctrl2 = page->GetWidget2();
633 if ( ctrl2 )
634 ctrl2->SetToolTip(s_tip);
635 }
636
637 #endif // wxUSE_TOOLTIPS
638
639 void WidgetsFrame::OnSetFgCol(wxCommandEvent& WXUNUSED(event))
640 {
641 #if wxUSE_COLOURDLG
642 // allow for debugging the default colour the first time this is called
643 WidgetsPage *page = CurrentPage();
644 if (!m_colFg.Ok())
645 m_colFg = page->GetForegroundColour();
646
647 wxColour col = wxGetColourFromUser(this, m_colFg);
648 if ( !col.Ok() )
649 return;
650
651 m_colFg = col;
652
653 page->GetWidget()->SetForegroundColour(m_colFg);
654 page->GetWidget()->Refresh();
655
656 wxControl *ctrl2 = page->GetWidget2();
657 if ( ctrl2 )
658 {
659 ctrl2->SetForegroundColour(m_colFg);
660 ctrl2->Refresh();
661 }
662 #else
663 wxLogMessage(_T("Colour selection dialog not available in current build."));
664 #endif
665 }
666
667 void WidgetsFrame::OnSetBgCol(wxCommandEvent& WXUNUSED(event))
668 {
669 #if wxUSE_COLOURDLG
670 WidgetsPage *page = CurrentPage();
671 if ( !m_colBg.Ok() )
672 m_colBg = page->GetBackgroundColour();
673
674 wxColour col = wxGetColourFromUser(this, m_colBg);
675 if ( !col.Ok() )
676 return;
677
678 m_colBg = col;
679
680 page->GetWidget()->SetBackgroundColour(m_colBg);
681 page->GetWidget()->Refresh();
682
683 wxControl *ctrl2 = page->GetWidget2();
684 if ( ctrl2 )
685 {
686 ctrl2->SetBackgroundColour(m_colFg);
687 ctrl2->Refresh();
688 }
689 #else
690 wxLogMessage(_T("Colour selection dialog not available in current build."));
691 #endif
692 }
693
694 void WidgetsFrame::OnSetFont(wxCommandEvent& WXUNUSED(event))
695 {
696 #if wxUSE_FONTDLG
697 WidgetsPage *page = CurrentPage();
698 if (!m_font.Ok())
699 m_font = page->GetFont();
700
701 wxFont font = wxGetFontFromUser(this, m_font);
702 if ( !font.Ok() )
703 return;
704
705 m_font = font;
706
707 page->GetWidget()->SetFont(m_font);
708 page->GetWidget()->Refresh();
709
710 wxControl *ctrl2 = page->GetWidget2();
711 if ( ctrl2 )
712 {
713 ctrl2->SetFont(m_font);
714 ctrl2->Refresh();
715 }
716 #else
717 wxLogMessage(_T("Font selection dialog not available in current build."));
718 #endif
719 }
720
721 void WidgetsFrame::OnEnable(wxCommandEvent& event)
722 {
723 WidgetsPage *page = CurrentPage();
724 page->GetWidget()->Enable(event.IsChecked());
725 }
726
727 void WidgetsFrame::OnSetBorder(wxCommandEvent& event)
728 {
729 int border;
730 switch ( event.GetId() )
731 {
732 case Widgets_BorderNone: border = wxBORDER_NONE; break;
733 case Widgets_BorderStatic: border = wxBORDER_STATIC; break;
734 case Widgets_BorderSimple: border = wxBORDER_SIMPLE; break;
735 case Widgets_BorderRaised: border = wxBORDER_RAISED; break;
736 case Widgets_BorderSunken: border = wxBORDER_SUNKEN; break;
737 case Widgets_BorderDouble: border = wxBORDER_DOUBLE; break;
738
739 default:
740 wxFAIL_MSG( _T("unknown border style") );
741 // fall through
742
743 case Widgets_BorderDefault: border = wxBORDER_DEFAULT; break;
744 }
745
746 WidgetsPage::ms_defaultFlags &= ~wxBORDER_MASK;
747 WidgetsPage::ms_defaultFlags |= border;
748
749 WidgetsPage *page = CurrentPage();
750 page->RecreateWidget();
751 }
752
753 #endif // wxUSE_MENUS
754
755 // ----------------------------------------------------------------------------
756 // WidgetsPageInfo
757 // ----------------------------------------------------------------------------
758
759 WidgetsPageInfo::WidgetsPageInfo(Constructor ctor, const wxChar *label, int categories)
760 : m_label(label)
761 , m_categories(categories)
762 {
763 m_ctor = ctor;
764
765 m_next = NULL;
766
767 // dummy sorting: add and immediately sort in the list according to label
768 if ( WidgetsPage::ms_widgetPages )
769 {
770 WidgetsPageInfo *node_prev = WidgetsPage::ms_widgetPages;
771 if ( wxStrcmp(label, node_prev->GetLabel().c_str()) < 0 )
772 {
773 // add as first
774 m_next = node_prev;
775 WidgetsPage::ms_widgetPages = this;
776 }
777 else
778 {
779 WidgetsPageInfo *node_next;
780 do
781 {
782 node_next = node_prev->GetNext();
783 if ( node_next )
784 {
785 // add if between two
786 if ( wxStrcmp(label, node_next->GetLabel().c_str()) < 0 )
787 {
788 node_prev->SetNext(this);
789 m_next = node_next;
790 // force to break loop
791 node_next = NULL;
792 }
793 }
794 else
795 {
796 // add as last
797 node_prev->SetNext(this);
798 m_next = node_next;
799 }
800 node_prev = node_next;
801 }
802 while ( node_next );
803 }
804 }
805 else
806 {
807 // add when first
808 WidgetsPage::ms_widgetPages = this;
809 }
810 }
811
812 // ----------------------------------------------------------------------------
813 // WidgetsPage
814 // ----------------------------------------------------------------------------
815
816 int WidgetsPage::ms_defaultFlags = wxBORDER_DEFAULT;
817 WidgetsPageInfo *WidgetsPage::ms_widgetPages = NULL;
818
819 WidgetsPage::WidgetsPage(WidgetsBookCtrl *book)
820 : wxPanel(book, wxID_ANY,
821 wxDefaultPosition, wxDefaultSize,
822 wxNO_FULL_REPAINT_ON_RESIZE |
823 wxCLIP_CHILDREN |
824 wxTAB_TRAVERSAL)
825 {
826 }
827
828 wxSizer *WidgetsPage::CreateSizerWithText(wxControl *control,
829 wxWindowID id,
830 wxTextCtrl **ppText)
831 {
832 wxSizer *sizerRow = new wxBoxSizer(wxHORIZONTAL);
833 wxTextCtrl *text = new wxTextCtrl(this, id, wxEmptyString,
834 wxDefaultPosition, wxDefaultSize, wxTE_PROCESS_ENTER);
835
836 sizerRow->Add(control, 0, wxRIGHT | wxALIGN_CENTRE_VERTICAL, 5);
837 sizerRow->Add(text, 1, wxLEFT | wxALIGN_CENTRE_VERTICAL, 5);
838
839 if ( ppText )
840 *ppText = text;
841
842 return sizerRow;
843 }
844
845 // create a sizer containing a label and a text ctrl
846 wxSizer *WidgetsPage::CreateSizerWithTextAndLabel(const wxString& label,
847 wxWindowID id,
848 wxTextCtrl **ppText)
849 {
850 return CreateSizerWithText(new wxStaticText(this, wxID_ANY, label),
851 id, ppText);
852 }
853
854 // create a sizer containing a button and a text ctrl
855 wxSizer *WidgetsPage::CreateSizerWithTextAndButton(wxWindowID idBtn,
856 const wxString& label,
857 wxWindowID id,
858 wxTextCtrl **ppText)
859 {
860 return CreateSizerWithText(new wxButton(this, idBtn, label), id, ppText);
861 }
862
863 wxCheckBox *WidgetsPage::CreateCheckBoxAndAddToSizer(wxSizer *sizer,
864 const wxString& label,
865 wxWindowID id)
866 {
867 wxCheckBox *checkbox = new wxCheckBox(this, id, label);
868 sizer->Add(checkbox, 0, wxLEFT | wxRIGHT, 5);
869 sizer->Add(0, 2, 0, wxGROW); // spacer
870
871 return checkbox;
872 }