]> git.saurik.com Git - wxWidgets.git/blob - samples/combo/combo.cpp
fix for potential crash when conversion fails
[wxWidgets.git] / samples / combo / combo.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: combo.cpp
3 // Purpose: wxComboCtrl sample
4 // Author: Jaakko Salli
5 // Modified by:
6 // Created: Apr-30-2006
7 // RCS-ID: $Id$
8 // Copyright: (c) Jaakko Salli
9 // Licence: wxWindows licence
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 (this file is usually all you
28 // need because it includes almost all "standard" wxWidgets headers)
29 #ifndef WX_PRECOMP
30 #include "wx/wx.h"
31 #endif
32
33 #if !wxUSE_COMBOCTRL
34 #error "Please set wxUSE_COMBOCTRL to 1 and rebuild the library."
35 #endif
36
37 #include "wx/image.h"
38
39 #include "wx/combo.h"
40 #include "wx/odcombo.h"
41
42 // ----------------------------------------------------------------------------
43 // resources
44 // ----------------------------------------------------------------------------
45
46 // the application icon (under Windows and OS/2 it is in resources and even
47 // though we could still include the XPM here it would be unused)
48 #if !defined(__WXMSW__) && !defined(__WXPM__)
49 #include "../sample.xpm"
50 #endif
51
52 // ----------------------------------------------------------------------------
53 // private classes
54 // ----------------------------------------------------------------------------
55
56 // Define a new application type, each program should derive a class from wxApp
57 class MyApp : public wxApp
58 {
59 public:
60 // override base class virtuals
61 // ----------------------------
62
63 // this one is called on application startup and is a good place for the app
64 // initialization (doing it here and not in the ctor allows to have an error
65 // return: if OnInit() returns false, the application terminates)
66 virtual bool OnInit();
67 };
68
69 // Define a new frame type: this is going to be our main frame
70 class MyFrame : public wxFrame
71 {
72 public:
73 // ctor and dtor
74 MyFrame(const wxString& title);
75 ~MyFrame();
76
77 // event handlers (these functions should _not_ be virtual)
78 void OnQuit(wxCommandEvent& event);
79 void OnAbout(wxCommandEvent& event);
80
81 // log wxComboCtrl events
82 void OnComboBoxUpdate( wxCommandEvent& event );
83
84 protected:
85 wxTextCtrl* m_logWin;
86 wxLog* m_logOld;
87
88 private:
89 // any class wishing to process wxWidgets events must use this macro
90 DECLARE_EVENT_TABLE()
91 };
92
93 // ----------------------------------------------------------------------------
94 // constants
95 // ----------------------------------------------------------------------------
96
97 // IDs for the controls and the menu commands
98 enum
99 {
100 // menu items
101 ComboControl_Quit = wxID_EXIT,
102
103 // it is important for the id corresponding to the "About" command to have
104 // this standard value as otherwise it won't be handled properly under Mac
105 // (where it is special and put into the "Apple" menu)
106 ComboControl_About = wxID_ABOUT
107 };
108
109 // ----------------------------------------------------------------------------
110 // event tables and other macros for wxWidgets
111 // ----------------------------------------------------------------------------
112
113 // the event tables connect the wxWidgets events with the functions (event
114 // handlers) which process them. It can be also done at run-time, but for the
115 // simple menu events like this the static method is much simpler.
116 BEGIN_EVENT_TABLE(MyFrame, wxFrame)
117 EVT_TEXT(wxID_ANY,MyFrame::OnComboBoxUpdate)
118 EVT_COMBOBOX(wxID_ANY,MyFrame::OnComboBoxUpdate)
119
120 EVT_MENU(ComboControl_Quit, MyFrame::OnQuit)
121 EVT_MENU(ComboControl_About, MyFrame::OnAbout)
122 END_EVENT_TABLE()
123
124 // Create a new application object: this macro will allow wxWidgets to create
125 // the application object during program execution (it's better than using a
126 // static object for many reasons) and also implements the accessor function
127 // wxGetApp() which will return the reference of the right type (i.e. MyApp and
128 // not wxApp)
129 IMPLEMENT_APP(MyApp)
130
131 // ============================================================================
132 // implementation
133 // ============================================================================
134
135 // ----------------------------------------------------------------------------
136 // the application class
137 // ----------------------------------------------------------------------------
138
139 // 'Main program' equivalent: the program execution "starts" here
140 bool MyApp::OnInit()
141 {
142 // create the main application window
143 MyFrame *frame = new MyFrame(_T("wxComboCtrl Sample"));
144
145 // and show it (the frames, unlike simple controls, are not shown when
146 // created initially)
147 frame->Show(true);
148
149 // success: wxApp::OnRun() will be called which will enter the main message
150 // loop and the application will run. If we returned false here, the
151 // application would exit immediately.
152 return true;
153 }
154
155
156 // ----------------------------------------------------------------------------
157 // wxListView Custom popup interface
158 // ----------------------------------------------------------------------------
159
160 #include <wx/listctrl.h>
161
162 class ListViewComboPopup : public wxListView, public wxComboPopup
163 {
164 public:
165
166 /*
167 ListViewComboPopup(wxComboCtrlBase* combo)
168 : wxListView(), wxComboPopup(combo)
169 {
170 m_value = -1;
171 m_itemHere = -1; // hot item in list
172 }
173 */
174 virtual void Init()
175 {
176 m_value = -1;
177 m_itemHere = -1; // hot item in list
178 }
179
180 virtual bool Create( wxWindow* parent )
181 {
182 return wxListView::Create(parent,1,
183 wxPoint(0,0),wxDefaultSize,
184 wxLC_LIST|wxLC_SINGLE_SEL|
185 wxLC_SORT_ASCENDING|wxSIMPLE_BORDER);
186 }
187
188 virtual wxWindow *GetControl() { return this; }
189
190 virtual void SetStringValue( const wxString& s )
191 {
192 int n = wxListView::FindItem(-1,s);
193 if ( n >= 0 && n < GetItemCount() )
194 wxListView::Select(n);
195 }
196
197 virtual wxString GetStringValue() const
198 {
199 if ( m_value >= 0 )
200 return wxListView::GetItemText(m_value);
201 return wxEmptyString;
202 }
203
204 //
205 // Popup event handlers
206 //
207
208 // Mouse hot-tracking
209 void OnMouseMove(wxMouseEvent& event)
210 {
211 // Move selection to cursor if it is inside the popup
212
213 int resFlags;
214 int itemHere = HitTest(event.GetPosition(),resFlags);
215 if ( itemHere >= 0 )
216 {
217 wxListView::Select(itemHere,true);
218 m_itemHere = itemHere;
219 }
220 event.Skip();
221 }
222
223 // On mouse left, set the value and close the popup
224 void OnMouseClick(wxMouseEvent& WXUNUSED(event))
225 {
226 m_value = m_itemHere;
227 // TODO: Send event
228 Dismiss();
229 }
230
231 //
232 // Utilies for item manipulation
233 //
234
235 void AddSelection( const wxString& selstr )
236 {
237 wxListView::InsertItem(GetItemCount(),selstr);
238 }
239
240 protected:
241
242 int m_value; // current item index
243 int m_itemHere; // hot item in popup
244
245 private:
246 DECLARE_EVENT_TABLE()
247 };
248
249 BEGIN_EVENT_TABLE(ListViewComboPopup, wxListView)
250 EVT_MOTION(ListViewComboPopup::OnMouseMove)
251 // NOTE: Left down event is used instead of left up right now
252 // since MSW wxListCtrl doesn't seem to emit left ups
253 // consistently.
254 EVT_LEFT_DOWN(ListViewComboPopup::OnMouseClick)
255 END_EVENT_TABLE()
256
257
258 // ----------------------------------------------------------------------------
259 // wxTreeCtrl Custom popup interface
260 // ----------------------------------------------------------------------------
261
262 #include <wx/treectrl.h>
263
264 class TreeCtrlComboPopup : public wxTreeCtrl, public wxComboPopup
265 {
266 public:
267
268 /*
269 TreeCtrlComboPopup(wxComboCtrlBase* combo)
270 : wxTreeCtrl(), wxComboPopup(combo)
271 {
272 }
273 */
274
275 virtual void Init()
276 {
277 }
278
279 virtual bool Create( wxWindow* parent )
280 {
281 return wxTreeCtrl::Create(parent,1,
282 wxPoint(0,0),wxDefaultSize,
283 wxTR_HIDE_ROOT|wxTR_HAS_BUTTONS|
284 wxTR_SINGLE|wxTR_LINES_AT_ROOT|
285 wxSIMPLE_BORDER);
286 }
287
288 virtual void OnShow()
289 {
290 // make sure selected item is visible
291 if ( m_value.IsOk() )
292 EnsureVisible(m_value);
293 }
294
295 virtual wxSize GetAdjustedSize( int minWidth,
296 int WXUNUSED(prefHeight),
297 int maxHeight )
298 {
299 return wxSize(wxMax(300,minWidth),wxMin(250,maxHeight));
300 }
301
302 virtual wxWindow *GetControl() { return this; }
303
304 // Needed by SetStringValue
305 wxTreeItemId FindItemByText( wxTreeItemId parent, const wxString& text )
306 {
307 wxTreeItemIdValue cookie;
308 wxTreeItemId child = GetFirstChild(parent,cookie);
309 while ( child.IsOk() )
310 {
311 if ( GetItemText(child) == text )
312 {
313 return child;
314 }
315 if ( ItemHasChildren(child) )
316 {
317 wxTreeItemId found = FindItemByText(child,text);
318 if ( found.IsOk() )
319 return found;
320 }
321 child = GetNextChild(parent,cookie);
322 }
323 return wxTreeItemId();
324 }
325
326 virtual void SetStringValue( const wxString& s )
327 {
328 wxTreeItemId root = GetRootItem();
329 if ( !root.IsOk() )
330 return;
331
332 wxTreeItemId found = FindItemByText(root,s);
333 if ( found.IsOk() )
334 {
335 m_value = m_itemHere = found;
336 wxTreeCtrl::SelectItem(found);
337 }
338 }
339
340 virtual wxString GetStringValue() const
341 {
342 if ( m_value.IsOk() )
343 return wxTreeCtrl::GetItemText(m_value);
344 return wxEmptyString;
345 }
346
347 //
348 // Popup event handlers
349 //
350
351 // Mouse hot-tracking
352 void OnMouseMove(wxMouseEvent& event)
353 {
354 int resFlags;
355 wxTreeItemId itemHere = HitTest(event.GetPosition(),resFlags);
356 if ( itemHere.IsOk() && (resFlags & wxTREE_HITTEST_ONITEMLABEL) )
357 {
358 wxTreeCtrl::SelectItem(itemHere,true);
359 m_itemHere = itemHere;
360 }
361 event.Skip();
362 }
363
364 // On mouse left, set the value and close the popup
365 void OnMouseClick(wxMouseEvent& event)
366 {
367 int resFlags;
368 wxTreeItemId itemHere = HitTest(event.GetPosition(),resFlags);
369 if ( itemHere.IsOk() && (resFlags & wxTREE_HITTEST_ONITEMLABEL) )
370 {
371 m_itemHere = itemHere;
372 m_value = itemHere;
373 Dismiss();
374 // TODO: Send event
375 }
376 event.Skip();
377 }
378
379 protected:
380
381 wxTreeItemId m_value; // current item index
382 wxTreeItemId m_itemHere; // hot item in popup
383
384 private:
385 DECLARE_EVENT_TABLE()
386 };
387
388 BEGIN_EVENT_TABLE(TreeCtrlComboPopup, wxTreeCtrl)
389 EVT_MOTION(TreeCtrlComboPopup::OnMouseMove)
390 // NOTE: Left down event is used instead of left up right now
391 // since MSW wxTreeCtrl doesn't seem to emit left ups
392 // consistently.
393 EVT_LEFT_DOWN(TreeCtrlComboPopup::OnMouseClick)
394 END_EVENT_TABLE()
395
396 // ----------------------------------------------------------------------------
397 // wxOwnerDrawnComboBox with custom paint list items
398 // ----------------------------------------------------------------------------
399
400 class wxPenStyleComboBox : public wxOwnerDrawnComboBox
401 {
402 public:
403 virtual void OnDrawItem( wxDC& dc,
404 const wxRect& rect,
405 int item,
406 int flags ) const
407 {
408 if ( item == wxNOT_FOUND )
409 return;
410
411 wxRect r(rect);
412 r.Deflate(3);
413 r.height -= 2;
414
415 int pen_style = wxSOLID;
416 if ( item == 1 )
417 pen_style = wxTRANSPARENT;
418 else if ( item == 2 )
419 pen_style = wxDOT;
420 else if ( item == 3 )
421 pen_style = wxLONG_DASH;
422 else if ( item == 4 )
423 pen_style = wxSHORT_DASH;
424 else if ( item == 5 )
425 pen_style = wxDOT_DASH;
426 else if ( item == 6 )
427 pen_style = wxBDIAGONAL_HATCH;
428 else if ( item == 7 )
429 pen_style = wxCROSSDIAG_HATCH;
430 else if ( item == 8 )
431 pen_style = wxFDIAGONAL_HATCH;
432 else if ( item == 9 )
433 pen_style = wxCROSS_HATCH;
434 else if ( item == 10 )
435 pen_style = wxHORIZONTAL_HATCH;
436 else if ( item == 11 )
437 pen_style = wxVERTICAL_HATCH;
438
439 wxPen pen( dc.GetTextForeground(), 3, pen_style );
440
441 // Get text colour as pen colour
442 dc.SetPen ( pen );
443
444 if ( !(flags & wxODCB_PAINTING_CONTROL) )
445 {
446 dc.DrawText(GetString( item ),
447 r.x + 3,
448 (r.y + 0) + ( (r.height/2) - dc.GetCharHeight() )/2
449 );
450
451 dc.DrawLine( r.x+5, r.y+((r.height/4)*3), r.x+r.width - 5, r.y+((r.height/4)*3) );
452 }
453 else
454 {
455 dc.DrawLine( r.x+5, r.y+r.height/2, r.x+r.width - 5, r.y+r.height/2 );
456 }
457 }
458
459 virtual wxCoord OnMeasureItem( size_t WXUNUSED(item) ) const
460 {
461 return 24;
462 }
463
464 virtual wxCoord OnMeasureItemWidth( size_t WXUNUSED(item) ) const
465 {
466 return -1; // default - will be measured from text width
467 }
468
469 };
470
471 // ----------------------------------------------------------------------------
472 // wxComboCtrl with entirely custom button action (opens file dialog)
473 // ----------------------------------------------------------------------------
474
475 class wxFileSelectorCombo : public wxComboCtrl
476 {
477 public:
478 wxFileSelectorCombo() : wxComboCtrl() { Init(); }
479
480 wxFileSelectorCombo(wxWindow *parent,
481 wxWindowID id = wxID_ANY,
482 const wxString& value = wxEmptyString,
483 const wxPoint& pos = wxDefaultPosition,
484 const wxSize& size = wxDefaultSize,
485 long style = 0,
486 const wxValidator& validator = wxDefaultValidator,
487 const wxString& name = wxComboBoxNameStr)
488 : wxComboCtrl()
489 {
490 Init();
491 Create(parent,id,value,
492 pos,size,
493 // Style flag wxCC_STD_BUTTON makes the button
494 // behave more like a standard push button.
495 style | wxCC_STD_BUTTON,
496 validator,name);
497
498 //
499 // Prepare custom button bitmap (just '...' text)
500 wxMemoryDC dc;
501 wxBitmap bmp(12,16);
502 dc.SelectObject(bmp);
503
504 // Draw transparent background
505 wxColour magic(255,0,255);
506 wxBrush magicBrush(magic);
507 dc.SetBrush( magicBrush );
508 dc.SetPen( *wxTRANSPARENT_PEN );
509 dc.DrawRectangle(0,0,bmp.GetWidth(),bmp.GetHeight());
510
511 // Draw text
512 wxString str = wxT("...");
513 int w,h;
514 dc.GetTextExtent(str, &w, &h, 0, 0);
515 dc.DrawText(str, (bmp.GetWidth()-w)/2, (bmp.GetHeight()-h)/2);
516
517 dc.SelectObject( wxNullBitmap );
518
519 // Finalize transparency with a mask
520 wxMask *mask = new wxMask( bmp, magic );
521 bmp.SetMask( mask );
522
523 SetButtonBitmaps(bmp,true);
524 }
525
526 virtual void OnButtonClick()
527 {
528 // Show standard wxFileDialog on button click
529
530 wxFileDialog dlg(this,
531 wxT("Choose File"),
532 wxEmptyString,
533 GetValue(),
534 wxT("All files (*.*)|*.*"),
535 wxFD_OPEN);
536
537 if ( dlg.ShowModal() == wxID_OK )
538 {
539 SetValue(dlg.GetPath());
540 }
541 }
542
543 private:
544 void Init()
545 {
546 // Initialize member variables here
547 }
548 };
549
550 // ----------------------------------------------------------------------------
551 // main frame
552 // ----------------------------------------------------------------------------
553
554 // frame constructor
555 MyFrame::MyFrame(const wxString& title)
556 : wxFrame(NULL, wxID_ANY, title)
557 {
558 wxBoxSizer* topSizer;
559 wxBoxSizer* topRowSizer;
560 wxBoxSizer* colSizer;
561 wxBoxSizer* rowSizer;
562 wxStaticBoxSizer* groupSizer;
563
564 // set the frame icon
565 SetIcon(wxICON(sample));
566
567 #if wxUSE_MENUS
568 // create a menu bar
569 wxMenu *fileMenu = new wxMenu;
570
571 // the "About" item should be in the help menu
572 wxMenu *helpMenu = new wxMenu;
573 helpMenu->Append(ComboControl_About, _T("&About...\tF1"), _T("Show about dialog"));
574
575 fileMenu->Append(ComboControl_Quit, _T("E&xit\tAlt-X"), _T("Quit this program"));
576
577 // now append the freshly created menu to the menu bar...
578 wxMenuBar *menuBar = new wxMenuBar();
579 menuBar->Append(fileMenu, _T("&File"));
580 menuBar->Append(helpMenu, _T("&Help"));
581
582 // ... and attach this menu bar to the frame
583 SetMenuBar(menuBar);
584 #endif // wxUSE_MENUS
585
586 wxPanel* panel = new wxPanel(this);
587
588 // Prepare log window right away since it shows EVT_TEXTs
589 m_logWin = new wxTextCtrl( panel, 105, wxEmptyString, wxDefaultPosition,
590 wxSize(-1,125), wxTE_MULTILINE|wxFULL_REPAINT_ON_RESIZE );
591 m_logWin->SetEditable(false);
592 wxLogTextCtrl* logger = new wxLogTextCtrl( m_logWin );
593 m_logOld = logger->SetActiveTarget( logger );
594 logger->SetTimestamp( NULL );
595
596
597 topSizer = new wxBoxSizer( wxVERTICAL );
598
599 topRowSizer = new wxBoxSizer( wxHORIZONTAL );
600
601 colSizer = new wxBoxSizer( wxVERTICAL );
602
603
604 // Make sure GetFeatures is implemented
605 int features = wxComboCtrl::GetFeatures();
606 wxLogDebug(wxT("wxComboCtrl features: 0x%X (all features: 0x%X)"),
607 features,wxComboCtrlFeatures::All);
608
609
610 wxComboBox* cb;
611 wxComboCtrl* cc;
612 wxGenericComboControl* gcc;
613 wxOwnerDrawnComboBox* odc;
614
615 // Create common strings array
616 wxArrayString arrItems;
617 arrItems.Add( wxT("Solid") );
618 arrItems.Add( wxT("Transparent") );
619 arrItems.Add( wxT("Dot") );
620 arrItems.Add( wxT("Long Dash") );
621 arrItems.Add( wxT("Short Dash") );
622 arrItems.Add( wxT("Dot Dash") );
623 arrItems.Add( wxT("Backward Diagonal Hatch") );
624 arrItems.Add( wxT("Cross-diagonal Hatch") );
625 arrItems.Add( wxT("Forward Diagonal Hatch") );
626 arrItems.Add( wxT("Cross Hatch") );
627 arrItems.Add( wxT("Horizontal Hatch") );
628 arrItems.Add( wxT("Vertical Hatch") );
629
630 int border = 4;
631
632 //
633 // Show some wxOwnerDrawComboBoxes for comparison
634 //
635 rowSizer = new wxBoxSizer(wxHORIZONTAL);
636
637 groupSizer = new wxStaticBoxSizer(new wxStaticBox(panel,wxID_ANY,wxT(" wxOwnerDrawnComboBox ")),
638 wxVERTICAL);
639
640 groupSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Writable, sorted:")), 0,
641 wxALIGN_CENTER_VERTICAL|wxRIGHT|wxEXPAND, border );
642
643 odc = new wxOwnerDrawnComboBox(panel,wxID_ANY,wxEmptyString,
644 wxDefaultPosition, wxDefaultSize,
645 arrItems,
646 wxCB_SORT // wxNO_BORDER|wxCB_READONLY
647 );
648
649 odc->Append(wxT("H - Appended Item")); // test sorting in append
650
651 odc->SetValue(wxT("Dot Dash"));
652
653 groupSizer->Add( odc, 1, wxALIGN_CENTER_VERTICAL|wxEXPAND|wxALL, border );
654
655 //
656 // Readonly ODComboBox
657 groupSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Read-only:")), 0,
658 wxALIGN_CENTER_VERTICAL|wxRIGHT, border );
659
660 odc = new wxOwnerDrawnComboBox(panel,wxID_ANY,wxEmptyString,
661 wxDefaultPosition, wxDefaultSize,
662 arrItems,
663 wxCB_SORT|wxCB_READONLY // wxNO_BORDER|wxCB_READONLY
664 );
665
666 odc->SetValue(wxT("Dot Dash"));
667 odc->SetText(wxT("Dot Dash (Testing SetText)"));
668
669 groupSizer->Add( odc, 1, wxALIGN_CENTER_VERTICAL|wxEXPAND|wxALL, border );
670
671 //
672 // Disabled ODComboBox
673 groupSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Disabled:")), 0,
674 wxALIGN_CENTER_VERTICAL|wxRIGHT, border );
675
676 odc = new wxOwnerDrawnComboBox(panel,wxID_ANY,wxEmptyString,
677 wxDefaultPosition, wxDefaultSize,
678 arrItems,
679 wxCB_SORT|wxCB_READONLY // wxNO_BORDER|wxCB_READONLY
680 );
681
682 odc->SetValue(wxT("Dot Dash"));
683 odc->Enable(false);
684
685 groupSizer->Add( odc, 1, wxALIGN_CENTER_VERTICAL|wxEXPAND|wxALL, border );
686
687 rowSizer->Add( groupSizer, 1, wxEXPAND|wxALL, border );
688
689
690 groupSizer = new wxStaticBoxSizer(new wxStaticBox(panel,wxID_ANY,wxT(" wxComboBox ")),
691 wxVERTICAL);
692
693 //
694 // wxComboBox
695 //
696 groupSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Writable, sorted:")), 0,
697 wxALIGN_CENTER_VERTICAL|wxRIGHT|wxEXPAND, border );
698
699 cb = new wxComboBox(panel,wxID_ANY,wxEmptyString,
700 wxDefaultPosition, wxDefaultSize,
701 arrItems,
702 wxCB_SORT // wxNO_BORDER|wxCB_READONLY
703 );
704
705 cb->Append(wxT("H - Appended Item")); // test sorting in append
706
707 cb->SetValue(wxT("Dot Dash"));
708
709 groupSizer->Add( cb, 1, wxALIGN_CENTER_VERTICAL|wxEXPAND|wxALL, border );
710
711 //
712 // Readonly wxComboBox
713 groupSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Read-only:")), 0,
714 wxALIGN_CENTER_VERTICAL|wxRIGHT, border );
715
716 cb = new wxComboBox(panel,wxID_ANY,wxEmptyString,
717 wxDefaultPosition, wxDefaultSize,
718 arrItems,
719 wxCB_SORT|wxCB_READONLY // wxNO_BORDER|wxCB_READONLY
720 );
721
722 cb->SetValue(wxT("Dot Dash"));
723
724 groupSizer->Add( cb, 1, wxALIGN_CENTER_VERTICAL|wxEXPAND|wxALL, border );
725
726 //
727 // Disabled wxComboBox
728 groupSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Disabled:")), 0,
729 wxALIGN_CENTER_VERTICAL|wxRIGHT, border );
730
731 cb = new wxComboBox(panel,wxID_ANY,wxEmptyString,
732 wxDefaultPosition, wxDefaultSize,
733 arrItems,
734 wxCB_SORT|wxCB_READONLY // wxNO_BORDER|wxCB_READONLY
735 );
736
737 cb->SetValue(wxT("Dot Dash"));
738 cb->Enable(false);
739
740 groupSizer->Add( cb, 1, wxALIGN_CENTER_VERTICAL|wxEXPAND|wxALL, border );
741
742 rowSizer->Add( groupSizer, 1, wxEXPAND|wxALL, border );
743
744
745 colSizer->Add( rowSizer, 1, wxEXPAND|wxALL, border );
746
747
748 //
749 // Pen selector ODComboBox with application painted items
750 //
751 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
752 rowSizer->Add( new wxStaticText(panel,wxID_ANY,
753 wxT("OwnerDrawnComboBox with Custom Paint Items and Button Placing:")), 1,
754 wxALIGN_CENTER_VERTICAL|wxRIGHT, 4 );
755 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
756
757 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
758
759 // When defining derivative class for callbacks, we need
760 // to use two-stage creation (or redefine the common wx
761 // constructor).
762 odc = new wxPenStyleComboBox();
763 odc->Create(panel,wxID_ANY,wxEmptyString,
764 wxDefaultPosition, wxDefaultSize,
765 arrItems,
766 wxCB_READONLY //wxNO_BORDER | wxCB_READONLY
767 );
768
769 odc->SetSelection(0);
770 odc->SetButtonPosition(-2, // width adjustment
771 -6, // height adjustment
772 wxLEFT, // side
773 2 // horizontal spacing
774 );
775
776 rowSizer->Add( odc, 1, wxALIGN_CENTER_VERTICAL|wxALL, 4 );
777 rowSizer->AddStretchSpacer(1);
778 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
779
780
781 //
782 // List View wxComboCtrl
783 //
784
785 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
786 rowSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("List View wxComboCtrl:")), 1,
787 wxALIGN_CENTER_VERTICAL|wxRIGHT, 4 );
788 rowSizer->Add( new wxStaticText(panel,wxID_ANY,wxT("Tree Ctrl wxGenericComboControl:")), 1,
789 wxALIGN_CENTER_VERTICAL|wxRIGHT, 4 );
790 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
791
792 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
793 cc = new wxComboCtrl(panel,2,wxEmptyString,
794 wxDefaultPosition, wxDefaultSize);
795
796 cc->SetPopupMinWidth(300);
797
798 ListViewComboPopup* iface = new ListViewComboPopup();
799 cc->SetPopupControl(iface);
800
801 iface->AddSelection( wxT("Cabbage") );
802 iface->AddSelection( wxT("Potato") );
803 iface->AddSelection( wxT("Onion") );
804 iface->AddSelection( wxT("Carrot") );
805 iface->AddSelection( wxT("Cauliflower") );
806 iface->AddSelection( wxT("Bean") );
807 iface->AddSelection( wxT("Raddish") );
808 iface->AddSelection( wxT("Banana") );
809 iface->AddSelection( wxT("Apple") );
810 iface->AddSelection( wxT("Orange") );
811 iface->AddSelection( wxT("Kiwi") );
812 iface->AddSelection( wxT("Strawberry") );
813 iface->AddSelection( wxT("Cucumber") );
814 iface->AddSelection( wxT("Blackberry") );
815 iface->AddSelection( wxT("Melon") );
816 iface->AddSelection( wxT("Cherry") );
817 iface->AddSelection( wxT("Pea") );
818 iface->AddSelection( wxT("Pear") );
819
820 rowSizer->Add( cc, 1, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
821
822
823 //
824 // Tree Ctrl wxComboCtrl
825 //
826
827 // Note that we test that wxGenericComboControl works
828 gcc = new wxGenericComboControl(panel,wxID_ANY,wxEmptyString,
829 wxDefaultPosition, wxDefaultSize);
830
831 // Set popup interface right away, otherwise some of the calls
832 // below may fail
833 TreeCtrlComboPopup* tcPopup = new TreeCtrlComboPopup();
834 gcc->SetPopupControl(tcPopup);
835
836 // Add items using wxTreeCtrl methods directly
837 wxTreeItemId rootId = tcPopup->AddRoot(wxT("<hidden_root>"));
838
839 wxTreeItemId groupId;
840
841 groupId = tcPopup->AppendItem(rootId,wxT("Controls"));
842 tcPopup->AppendItem(groupId,wxT("wxButton"));
843 tcPopup->AppendItem(groupId,wxT("wxCheckBox"));
844 tcPopup->AppendItem(groupId,wxT("wxListCtrl"));
845 tcPopup->AppendItem(groupId,wxT("wxStaticBox"));
846 tcPopup->AppendItem(groupId,wxT("wxStaticText"));
847 tcPopup->AppendItem(groupId,wxT("wxTextCtrl"));
848 tcPopup->AppendItem(groupId,wxT("wxTreeCtrl"));
849 groupId = tcPopup->AppendItem(rootId,wxT("Dialogs"));
850 tcPopup->AppendItem(groupId,wxT("wxDirDialog"));
851 tcPopup->AppendItem(groupId,wxT("wxFileDialog"));
852 tcPopup->AppendItem(groupId,wxT("wxWizard"));
853
854 gcc->SetValue(wxT("wxStaticBox"));
855
856 // Move button to left - it makes more sense for a tree ctrl
857 gcc->SetButtonPosition(0, // width adjustment
858 0, // height adjustment
859 wxLEFT, // side
860 0 // horizontal spacing
861 );
862
863 rowSizer->Add( gcc, 1, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
864
865 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
866
867 #if wxUSE_IMAGE
868 wxInitAllImageHandlers();
869
870 //
871 // Custom Dropbutton Bitmaps
872 // (second one uses blank button background)
873 //
874 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
875 rowSizer->Add( new wxStaticText(panel,wxID_ANY,
876 wxT("OwnerDrawnComboBox with simple dropbutton graphics:")), 1,
877 wxALIGN_CENTER_VERTICAL|wxRIGHT, 4 );
878
879 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
880
881 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
882
883 odc = new wxOwnerDrawnComboBox(panel,wxID_ANY,wxEmptyString,
884 wxDefaultPosition, wxDefaultSize,
885 arrItems,
886 (long)0 // wxCB_SORT // wxNO_BORDER | wxCB_READONLY
887 );
888
889 wxOwnerDrawnComboBox* odc2;
890 odc2 = new wxOwnerDrawnComboBox(panel,wxID_ANY,wxEmptyString,
891 wxDefaultPosition, wxDefaultSize,
892 arrItems,
893 (long)0 // wxCB_SORT // wxNO_BORDER | wxCB_READONLY
894 );
895
896 // Load images from disk
897 wxImage imgNormal(wxT("dropbutn.png"));
898 wxImage imgPressed(wxT("dropbutp.png"));
899 wxImage imgHover(wxT("dropbuth.png"));
900
901 if ( imgNormal.Ok() && imgPressed.Ok() && imgHover.Ok() )
902 {
903 wxBitmap bmpNormal(imgNormal);
904 wxBitmap bmpPressed(imgPressed);
905 wxBitmap bmpHover(imgHover);
906 odc->SetButtonBitmaps(bmpNormal,false,bmpPressed,bmpHover);
907 odc2->SetButtonBitmaps(bmpNormal,true,bmpPressed,bmpHover);
908 }
909 else
910 wxLogError(wxT("Dropbutton images not found"));
911
912 //odc2->SetButtonPosition(0, // width adjustment
913 // 0, // height adjustment
914 // wxLEFT, // side
915 // 0 // horizontal spacing
916 // );
917
918 rowSizer->Add( odc, 1, wxALIGN_CENTER_VERTICAL|wxALL, 4 );
919 rowSizer->Add( odc2, 1, wxALIGN_CENTER_VERTICAL|wxALL, 4 );
920 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
921 #endif
922
923
924 //
925 // wxComboCtrl with totally custom button action (open file dialog)
926 //
927 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
928 rowSizer->Add( new wxStaticText(panel,wxID_ANY,
929 wxT("wxComboCtrl with custom button action:")), 1,
930 wxALIGN_CENTER_VERTICAL|wxRIGHT, 4 );
931
932
933 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
934
935 rowSizer = new wxBoxSizer ( wxHORIZONTAL );
936 wxFileSelectorCombo* fsc;
937
938 fsc = new wxFileSelectorCombo(panel,wxID_ANY,wxEmptyString,
939 wxDefaultPosition, wxDefaultSize,
940 (long)0
941 );
942
943 rowSizer->Add( fsc, 1, wxALIGN_CENTER_VERTICAL|wxALL, 4 );
944 colSizer->Add( rowSizer, 0, wxEXPAND|wxALL, 5 );
945
946
947 topRowSizer->Add( colSizer, 1, wxALL, 2 );
948
949 topRowSizer->Add( m_logWin, 1, wxEXPAND|wxALL, 5 );
950 topSizer->Add( topRowSizer, 1, wxEXPAND );
951
952 panel->SetSizer( topSizer );
953 topSizer->SetSizeHints( panel );
954
955 SetSize(740,480);
956 Centre();
957 }
958
959 MyFrame::~MyFrame()
960 {
961 delete wxLog::SetActiveTarget(m_logOld);
962 }
963
964 // event handlers
965
966 void MyFrame::OnComboBoxUpdate( wxCommandEvent& event )
967 {
968 // Don't show messages for the log output window (it'll crash)
969 if ( event.GetId() == 105 )
970 return;
971
972 if ( event.GetEventType() == wxEVT_COMMAND_COMBOBOX_SELECTED )
973 wxLogDebug(wxT("EVT_COMBOBOX(id=%i,selection=%i)"),event.GetId(),event.GetSelection());
974 else if ( event.GetEventType() == wxEVT_COMMAND_TEXT_UPDATED )
975 wxLogDebug(wxT("EVT_TEXT(id=%i,string=\"%s\")"),event.GetId(),event.GetString().c_str());
976 }
977
978 void MyFrame::OnQuit(wxCommandEvent& WXUNUSED(event))
979 {
980 // true is to force the frame to close
981 Close(true);
982 }
983
984 void MyFrame::OnAbout(wxCommandEvent& WXUNUSED(event))
985 {
986 wxMessageBox(wxString::Format(
987 _T("Welcome to %s!\n")
988 _T("\n")
989 _T("This is the wxWidgets wxComboCtrl sample\n")
990 _T("running under %s."),
991 wxVERSION_STRING,
992 wxGetOsDescription().c_str()
993 ),
994 _T("About wxComboCtrl sample"),
995 wxOK | wxICON_INFORMATION,
996 this);
997 }