]> git.saurik.com Git - wxWidgets.git/blob - samples/widgets/odcombobox.cpp
Make storing non-trivial data in wxThreadSpecificInfo possible.
[wxWidgets.git] / samples / widgets / odcombobox.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Program: wxWidgets Widgets Sample
3 // Name: odcombobox.cpp
4 // Purpose: Part of the widgets sample showing wxOwnerDrawnComboBox
5 // Author: Jaakko Salli (based on combobox page by Vadim Zeitlin)
6 // Created: Jul-28-2006
7 // Copyright: (c) 2006 Jaakko Salli
8 // Licence: wxWindows licence
9 /////////////////////////////////////////////////////////////////////////////
10
11 // ============================================================================
12 // declarations
13 // ============================================================================
14
15 // ----------------------------------------------------------------------------
16 // headers
17 // ----------------------------------------------------------------------------
18
19 // for compilers that support precompilation, includes "wx/wx.h".
20 #include "wx/wxprec.h"
21
22 #ifdef __BORLANDC__
23 #pragma hdrstop
24 #endif
25
26 #if wxUSE_ODCOMBOBOX
27
28 // for all others, include the necessary headers
29 #ifndef WX_PRECOMP
30 #include "wx/log.h"
31
32 #include "wx/bitmap.h"
33 #include "wx/button.h"
34 #include "wx/checkbox.h"
35 #include "wx/combobox.h"
36 #include "wx/radiobox.h"
37 #include "wx/statbox.h"
38 #include "wx/textctrl.h"
39 #endif
40
41 #include "wx/dc.h"
42 #include "wx/dcmemory.h"
43 #include "wx/sizer.h"
44 #include "wx/odcombo.h"
45
46
47 #include "itemcontainer.h"
48 #include "widgets.h"
49
50 #include "icons/odcombobox.xpm"
51
52 // ----------------------------------------------------------------------------
53 // constants
54 // ----------------------------------------------------------------------------
55
56 // control ids
57 enum
58 {
59 ODComboPage_Reset = wxID_HIGHEST,
60 ODComboPage_PopupMinWidth,
61 ODComboPage_PopupHeight,
62 ODComboPage_ButtonWidth,
63 ODComboPage_ButtonHeight,
64 ODComboPage_ButtonSpacing,
65 ODComboPage_CurText,
66 ODComboPage_InsertionPointText,
67 ODComboPage_Insert,
68 ODComboPage_InsertText,
69 ODComboPage_Add,
70 ODComboPage_AddText,
71 ODComboPage_AddSeveral,
72 ODComboPage_AddMany,
73 ODComboPage_Clear,
74 ODComboPage_Change,
75 ODComboPage_ChangeText,
76 ODComboPage_Delete,
77 ODComboPage_DeleteText,
78 ODComboPage_DeleteSel,
79 ODComboPage_Combo,
80 ODComboPage_ContainerTests
81 };
82
83
84 // ----------------------------------------------------------------------------
85 // ODComboboxWidgetsPage
86 // ----------------------------------------------------------------------------
87
88 class ODComboboxWidgetsPage : public ItemContainerWidgetsPage
89 {
90 public:
91 ODComboboxWidgetsPage(WidgetsBookCtrl *book, wxImageList *imaglist);
92
93 virtual wxControl *GetWidget() const { return m_combobox; }
94 virtual wxTextEntryBase *GetTextEntry() const
95 { return m_combobox ? m_combobox->GetTextCtrl() : NULL; }
96 virtual wxItemContainer* GetContainer() const { return m_combobox; }
97 virtual void RecreateWidget() { CreateCombo(); }
98
99 // lazy creation of the content
100 virtual void CreateContent();
101
102 protected:
103 // event handlers
104 void OnButtonReset(wxCommandEvent& event);
105 void OnButtonChange(wxCommandEvent& event);
106 void OnButtonDelete(wxCommandEvent& event);
107 void OnButtonDeleteSel(wxCommandEvent& event);
108 void OnButtonClear(wxCommandEvent& event);
109 void OnButtonInsert(wxCommandEvent &event);
110 void OnButtonAdd(wxCommandEvent& event);
111 void OnButtonAddSeveral(wxCommandEvent& event);
112 void OnButtonAddMany(wxCommandEvent& event);
113
114 void OnComboBox(wxCommandEvent& event);
115 void OnDropDown(wxCommandEvent& event);
116 void OnCloseUp(wxCommandEvent& event);
117 void OnComboText(wxCommandEvent& event);
118
119 void OnCheckOrRadioBox(wxCommandEvent& event);
120
121 void OnTextPopupWidth(wxCommandEvent& event);
122 void OnTextPopupHeight(wxCommandEvent& event);
123 void OnTextButtonAll(wxCommandEvent& event);
124
125 void OnUpdateUICurText(wxUpdateUIEvent& event);
126 void OnUpdateUIInsertionPointText(wxUpdateUIEvent& event);
127
128 void OnUpdateUIInsert(wxUpdateUIEvent& event);
129 void OnUpdateUIAddSeveral(wxUpdateUIEvent& event);
130 void OnUpdateUIClearButton(wxUpdateUIEvent& event);
131 void OnUpdateUIDeleteButton(wxUpdateUIEvent& event);
132 void OnUpdateUIDeleteSelButton(wxUpdateUIEvent& event);
133 void OnUpdateUIResetButton(wxUpdateUIEvent& event);
134
135 // reset the odcombobox parameters
136 void Reset();
137
138 // (re)create the odcombobox
139 void CreateCombo();
140
141 // helper that gets all button values from controls and calls SetButtonPosition
142 void GetButtonPosition();
143
144 // helper to create the button bitmap
145 wxBitmap CreateBitmap(const wxColour& colour);
146
147 // the controls
148 // ------------
149
150 // the checkboxes for styles
151 wxCheckBox *m_chkSort,
152 *m_chkReadonly,
153 *m_chkDclickcycles,
154 *m_chkBitmapbutton,
155 *m_chkStdbutton;
156
157 // the text entries for popup and button adjustment
158 wxTextCtrl *m_textPopupMinWidth,
159 *m_textPopupHeight,
160 *m_textButtonWidth,
161 *m_textButtonHeight,
162 *m_textButtonSpacing;
163
164 // the checkboxes for same
165 wxCheckBox *m_chkAlignpopupright,
166 *m_chkAlignbutleft;
167
168 // the combobox itself and the sizer it is in
169 wxOwnerDrawnComboBox *m_combobox;
170 wxSizer *m_sizerCombo;
171
172 // the text entries for "Add/change string" and "Delete" buttons
173 wxTextCtrl *m_textInsert,
174 *m_textAdd,
175 *m_textChange,
176 *m_textDelete;
177
178 private:
179 DECLARE_EVENT_TABLE()
180 DECLARE_WIDGETS_PAGE(ODComboboxWidgetsPage)
181 };
182
183 // ----------------------------------------------------------------------------
184 // event tables
185 // ----------------------------------------------------------------------------
186
187 BEGIN_EVENT_TABLE(ODComboboxWidgetsPage, WidgetsPage)
188 EVT_BUTTON(ODComboPage_Reset, ODComboboxWidgetsPage::OnButtonReset)
189 EVT_BUTTON(ODComboPage_Change, ODComboboxWidgetsPage::OnButtonChange)
190 EVT_BUTTON(ODComboPage_Delete, ODComboboxWidgetsPage::OnButtonDelete)
191 EVT_BUTTON(ODComboPage_DeleteSel, ODComboboxWidgetsPage::OnButtonDeleteSel)
192 EVT_BUTTON(ODComboPage_Clear, ODComboboxWidgetsPage::OnButtonClear)
193 EVT_BUTTON(ODComboPage_Insert, ODComboboxWidgetsPage::OnButtonInsert)
194 EVT_BUTTON(ODComboPage_Add, ODComboboxWidgetsPage::OnButtonAdd)
195 EVT_BUTTON(ODComboPage_AddSeveral, ODComboboxWidgetsPage::OnButtonAddSeveral)
196 EVT_BUTTON(ODComboPage_AddMany, ODComboboxWidgetsPage::OnButtonAddMany)
197 EVT_BUTTON(ODComboPage_ContainerTests, ItemContainerWidgetsPage::OnButtonTestItemContainer)
198
199 EVT_TEXT_ENTER(ODComboPage_InsertText, ODComboboxWidgetsPage::OnButtonInsert)
200 EVT_TEXT_ENTER(ODComboPage_AddText, ODComboboxWidgetsPage::OnButtonAdd)
201 EVT_TEXT_ENTER(ODComboPage_DeleteText, ODComboboxWidgetsPage::OnButtonDelete)
202
203 EVT_TEXT(ODComboPage_PopupMinWidth, ODComboboxWidgetsPage::OnTextPopupWidth)
204 EVT_TEXT(ODComboPage_PopupHeight, ODComboboxWidgetsPage::OnTextPopupHeight)
205 EVT_TEXT(ODComboPage_ButtonWidth, ODComboboxWidgetsPage::OnTextButtonAll)
206 EVT_TEXT(ODComboPage_ButtonHeight, ODComboboxWidgetsPage::OnTextButtonAll)
207 EVT_TEXT(ODComboPage_ButtonSpacing, ODComboboxWidgetsPage::OnTextButtonAll)
208
209 EVT_UPDATE_UI(ODComboPage_CurText, ODComboboxWidgetsPage::OnUpdateUICurText)
210 EVT_UPDATE_UI(ODComboPage_InsertionPointText, ODComboboxWidgetsPage::OnUpdateUIInsertionPointText)
211
212 EVT_UPDATE_UI(ODComboPage_Reset, ODComboboxWidgetsPage::OnUpdateUIResetButton)
213 EVT_UPDATE_UI(ODComboPage_Insert, ODComboboxWidgetsPage::OnUpdateUIInsert)
214 EVT_UPDATE_UI(ODComboPage_AddSeveral, ODComboboxWidgetsPage::OnUpdateUIAddSeveral)
215 EVT_UPDATE_UI(ODComboPage_Clear, ODComboboxWidgetsPage::OnUpdateUIClearButton)
216 EVT_UPDATE_UI(ODComboPage_DeleteText, ODComboboxWidgetsPage::OnUpdateUIClearButton)
217 EVT_UPDATE_UI(ODComboPage_Delete, ODComboboxWidgetsPage::OnUpdateUIDeleteButton)
218 EVT_UPDATE_UI(ODComboPage_Change, ODComboboxWidgetsPage::OnUpdateUIDeleteSelButton)
219 EVT_UPDATE_UI(ODComboPage_ChangeText, ODComboboxWidgetsPage::OnUpdateUIDeleteSelButton)
220 EVT_UPDATE_UI(ODComboPage_DeleteSel, ODComboboxWidgetsPage::OnUpdateUIDeleteSelButton)
221
222 EVT_COMBOBOX_DROPDOWN(ODComboPage_Combo, ODComboboxWidgetsPage::OnDropDown)
223 EVT_COMBOBOX_CLOSEUP(ODComboPage_Combo, ODComboboxWidgetsPage::OnCloseUp)
224 EVT_COMBOBOX(ODComboPage_Combo, ODComboboxWidgetsPage::OnComboBox)
225 EVT_TEXT(ODComboPage_Combo, ODComboboxWidgetsPage::OnComboText)
226 EVT_TEXT_ENTER(ODComboPage_Combo, ODComboboxWidgetsPage::OnComboText)
227
228 EVT_CHECKBOX(wxID_ANY, ODComboboxWidgetsPage::OnCheckOrRadioBox)
229 EVT_RADIOBOX(wxID_ANY, ODComboboxWidgetsPage::OnCheckOrRadioBox)
230 END_EVENT_TABLE()
231
232 // ============================================================================
233 // implementation
234 // ============================================================================
235
236 //
237 // wxOwnerDrawnComboBox needs to subclassed so that owner-drawing
238 // callbacks can be implemented.
239 class DemoODComboBox : public wxOwnerDrawnComboBox
240 {
241 public:
242 virtual void OnDrawItem(wxDC& dc,
243 const wxRect& rect,
244 int item,
245 int WXUNUSED(flags)) const
246 {
247 if ( item == wxNOT_FOUND )
248 return;
249
250 wxColour txtCol;
251 int mod = item % 4;
252
253 if ( mod == 0 )
254 txtCol = *wxBLACK;
255 else if ( mod == 1 )
256 txtCol = *wxRED;
257 else if ( mod == 2 )
258 txtCol = *wxGREEN;
259 else
260 txtCol = *wxBLUE;
261
262 dc.SetTextForeground(txtCol);
263
264 dc.DrawText(GetString(item),
265 rect.x + 3,
266 rect.y + ((rect.height - dc.GetCharHeight())/2)
267 );
268 }
269
270 virtual void OnDrawBackground(wxDC& dc, const wxRect& rect,
271 int item, int flags ) const
272 {
273
274 // If item is selected or even, or we are painting the
275 // combo control itself, use the default rendering.
276 if ( (flags & (wxODCB_PAINTING_CONTROL|wxODCB_PAINTING_SELECTED)) ||
277 (item & 1) == 0 )
278 {
279 wxOwnerDrawnComboBox::OnDrawBackground(dc,rect,item,flags);
280 return;
281 }
282
283 // Otherwise, draw every other background with different colour.
284 wxColour bgCol(240,240,250);
285 dc.SetBrush(wxBrush(bgCol));
286 dc.SetPen(wxPen(bgCol));
287 dc.DrawRectangle(rect);
288 }
289
290 virtual wxCoord OnMeasureItem(size_t WXUNUSED(item)) const
291 {
292 return 48;
293 }
294
295 virtual wxCoord OnMeasureItemWidth(size_t WXUNUSED(item)) const
296 {
297 return -1; // default - will be measured from text width
298 }
299 };
300
301
302 IMPLEMENT_WIDGETS_PAGE(ODComboboxWidgetsPage, wxT("OwnerDrawnCombobox"),
303 GENERIC_CTRLS | WITH_ITEMS_CTRLS | COMBO_CTRLS
304 );
305
306 ODComboboxWidgetsPage::ODComboboxWidgetsPage(WidgetsBookCtrl *book,
307 wxImageList *imaglist)
308 : ItemContainerWidgetsPage(book, imaglist, odcombobox_xpm)
309 {
310 // init everything
311 m_chkSort =
312 m_chkReadonly =
313 m_chkDclickcycles = (wxCheckBox *)NULL;
314
315 m_combobox = (wxOwnerDrawnComboBox *)NULL;
316 m_sizerCombo = (wxSizer *)NULL;
317 }
318
319 void ODComboboxWidgetsPage::CreateContent()
320 {
321 /*
322 What we create here is a frame having 3 panes: style pane is the
323 leftmost one, in the middle the pane with buttons allowing to perform
324 miscellaneous combobox operations and the pane containing the combobox
325 itself to the right
326 */
327 wxTextCtrl *text;
328 wxSizer *sizerRow;
329
330 wxSizer *sizerTop = new wxBoxSizer(wxHORIZONTAL);
331
332 wxSizer *sizerLeft = new wxBoxSizer(wxVERTICAL);
333
334 // left pane - style box
335 wxStaticBox *box = new wxStaticBox(this, wxID_ANY, wxT("&Set style"));
336
337 wxSizer *sizerStyle = new wxStaticBoxSizer(box, wxVERTICAL);
338
339 m_chkSort = CreateCheckBoxAndAddToSizer(sizerStyle, wxT("&Sort items"));
340 m_chkReadonly = CreateCheckBoxAndAddToSizer(sizerStyle, wxT("&Read only"));
341 m_chkDclickcycles = CreateCheckBoxAndAddToSizer(sizerStyle, wxT("&Double-click Cycles"));
342
343 sizerStyle->AddSpacer(4);
344
345 m_chkBitmapbutton = CreateCheckBoxAndAddToSizer(sizerStyle, wxT("&Bitmap button"));
346 m_chkStdbutton = CreateCheckBoxAndAddToSizer(sizerStyle, wxT("B&lank button background"));
347
348 wxButton *btn = new wxButton(this, ODComboPage_Reset, wxT("&Reset"));
349 sizerStyle->Add(btn, 0, wxALIGN_CENTRE_HORIZONTAL | wxALL, 3);
350
351 sizerLeft->Add(sizerStyle, 0, wxGROW | wxALIGN_CENTRE_HORIZONTAL);
352
353 // left pane - popup adjustment box
354 box = new wxStaticBox(this, wxID_ANY, wxT("Adjust &popup"));
355
356 wxSizer *sizerPopupPos = new wxStaticBoxSizer(box, wxVERTICAL);
357
358 sizerRow = CreateSizerWithTextAndLabel(wxT("Min. Width:"),
359 ODComboPage_PopupMinWidth,
360 &m_textPopupMinWidth);
361 m_textPopupMinWidth->SetValue(wxT("-1"));
362 sizerPopupPos->Add(sizerRow, 0, wxALL | wxGROW, 5);
363
364 sizerRow = CreateSizerWithTextAndLabel(wxT("Max. Height:"),
365 ODComboPage_PopupHeight,
366 &m_textPopupHeight);
367 m_textPopupHeight->SetValue(wxT("-1"));
368 sizerPopupPos->Add(sizerRow, 0, wxALL | wxGROW, 5);
369
370 m_chkAlignpopupright = CreateCheckBoxAndAddToSizer(sizerPopupPos, wxT("Align Right"));
371
372 sizerLeft->Add(sizerPopupPos, 0, wxGROW | wxALIGN_CENTRE_HORIZONTAL | wxTOP, 2);
373
374 // left pane - button adjustment box
375 box = new wxStaticBox(this, wxID_ANY, wxT("Adjust &button"));
376
377 wxSizer *sizerButtonPos = new wxStaticBoxSizer(box, wxVERTICAL);
378
379 sizerRow = CreateSizerWithTextAndLabel(wxT("Width:"),
380 ODComboPage_ButtonWidth,
381 &m_textButtonWidth);
382 m_textButtonWidth->SetValue(wxT("-1"));
383 sizerButtonPos->Add(sizerRow, 0, wxALL | wxGROW, 5);
384
385 sizerRow = CreateSizerWithTextAndLabel(wxT("VSpacing:"),
386 ODComboPage_ButtonSpacing,
387 &m_textButtonSpacing);
388 m_textButtonSpacing->SetValue(wxT("0"));
389 sizerButtonPos->Add(sizerRow, 0, wxALL | wxGROW, 5);
390
391 sizerRow = CreateSizerWithTextAndLabel(wxT("Height:"),
392 ODComboPage_ButtonHeight,
393 &m_textButtonHeight);
394 m_textButtonHeight->SetValue(wxT("-1"));
395 sizerButtonPos->Add(sizerRow, 0, wxALL | wxGROW, 5);
396
397 m_chkAlignbutleft = CreateCheckBoxAndAddToSizer(sizerButtonPos, wxT("Align Left"));
398
399 sizerLeft->Add(sizerButtonPos, 0, wxGROW | wxALIGN_CENTRE_HORIZONTAL | wxTOP, 2);
400
401 // middle pane
402 wxStaticBox *box2 = new wxStaticBox(this, wxID_ANY,
403 wxT("&Change combobox contents"));
404 wxSizer *sizerMiddle = new wxStaticBoxSizer(box2, wxVERTICAL);
405
406 btn = new wxButton(this, ODComboPage_ContainerTests, wxT("Run &tests"));
407 sizerMiddle->Add(btn, 0, wxALL | wxGROW, 5);
408
409 sizerRow = CreateSizerWithTextAndLabel(wxT("Current selection"),
410 ODComboPage_CurText,
411 &text);
412 text->SetEditable(false);
413
414 sizerMiddle->Add(sizerRow, 0, wxALL | wxGROW, 5);
415
416 sizerRow = CreateSizerWithTextAndLabel(wxT("Insertion Point"),
417 ODComboPage_InsertionPointText,
418 &text);
419 text->SetEditable(false);
420
421 sizerMiddle->Add(sizerRow, 0, wxALL | wxGROW, 5);
422
423 sizerRow = CreateSizerWithTextAndButton(ODComboPage_Insert,
424 wxT("&Insert this string"),
425 ODComboPage_InsertText,
426 &m_textInsert);
427 sizerMiddle->Add(sizerRow, 0, wxALL | wxGROW, 5);
428
429 sizerRow = CreateSizerWithTextAndButton(ODComboPage_Add,
430 wxT("&Add this string"),
431 ODComboPage_AddText,
432 &m_textAdd);
433 sizerMiddle->Add(sizerRow, 0, wxALL | wxGROW, 5);
434
435 btn = new wxButton(this, ODComboPage_AddSeveral, wxT("&Append a few strings"));
436 sizerMiddle->Add(btn, 0, wxALL | wxGROW, 5);
437
438 btn = new wxButton(this, ODComboPage_AddMany, wxT("Append &many strings"));
439 sizerMiddle->Add(btn, 0, wxALL | wxGROW, 5);
440
441 sizerRow = CreateSizerWithTextAndButton(ODComboPage_Change,
442 wxT("C&hange current"),
443 ODComboPage_ChangeText,
444 &m_textChange);
445 sizerMiddle->Add(sizerRow, 0, wxALL | wxGROW, 5);
446
447 sizerRow = CreateSizerWithTextAndButton(ODComboPage_Delete,
448 wxT("&Delete this item"),
449 ODComboPage_DeleteText,
450 &m_textDelete);
451 sizerMiddle->Add(sizerRow, 0, wxALL | wxGROW, 5);
452
453 btn = new wxButton(this, ODComboPage_DeleteSel, wxT("Delete &selection"));
454 sizerMiddle->Add(btn, 0, wxALL | wxGROW, 5);
455
456 btn = new wxButton(this, ODComboPage_Clear, wxT("&Clear"));
457 sizerMiddle->Add(btn, 0, wxALL | wxGROW, 5);
458
459 // right pane
460 wxSizer *sizerRight = new wxBoxSizer(wxVERTICAL);
461 m_combobox = new DemoODComboBox();
462 m_combobox->Create(this, ODComboPage_Combo, wxEmptyString,
463 wxDefaultPosition, wxDefaultSize,
464 0, NULL,
465 0);
466 sizerRight->Add(m_combobox, 0, wxGROW | wxALL, 5);
467 sizerRight->SetMinSize(150, 0);
468 m_sizerCombo = sizerRight; // save it to modify it later
469
470 // the 3 panes panes compose the window
471 sizerTop->Add(sizerLeft, 4, wxGROW | (wxALL & ~wxLEFT), 10);
472 sizerTop->Add(sizerMiddle, 5, wxGROW | wxALL, 10);
473 sizerTop->Add(sizerRight, 4, wxGROW | (wxALL & ~wxRIGHT), 10);
474
475 // final initializations
476 Reset();
477
478 SetSizer(sizerTop);
479 }
480
481 // ----------------------------------------------------------------------------
482 // operations
483 // ----------------------------------------------------------------------------
484
485 void ODComboboxWidgetsPage::Reset()
486 {
487 m_chkSort->SetValue(false);
488 m_chkReadonly->SetValue(false);
489 m_chkDclickcycles->SetValue(false);
490 m_chkDclickcycles->Enable(false);
491 m_chkBitmapbutton->SetValue(false);
492 m_chkStdbutton->SetValue(false);
493 m_chkStdbutton->Enable(false);
494 }
495
496 void ODComboboxWidgetsPage::CreateCombo()
497 {
498 int flags = ms_defaultFlags;
499
500 if ( m_chkSort->GetValue() )
501 flags |= wxCB_SORT;
502 if ( m_chkReadonly->GetValue() )
503 flags |= wxCB_READONLY;
504 if ( m_chkDclickcycles->GetValue() )
505 flags |= wxODCB_DCLICK_CYCLES;
506
507 wxArrayString items;
508 if ( m_combobox )
509 {
510 unsigned int count = m_combobox->GetCount();
511 for ( unsigned int n = 0; n < count; n++ )
512 {
513 items.Add(m_combobox->GetString(n));
514 }
515
516 m_sizerCombo->Detach( m_combobox );
517 delete m_combobox;
518 }
519
520 m_combobox = new DemoODComboBox();
521 m_combobox->Create(this, ODComboPage_Combo, wxEmptyString,
522 wxDefaultPosition, wxDefaultSize,
523 0, NULL,
524 flags);
525
526 unsigned int count = items.GetCount();
527 for ( unsigned int n = 0; n < count; n++ )
528 {
529 m_combobox->Append(items[n]);
530 }
531
532 // Update from controls that edit popup position etc.
533
534 wxUpdateUIEvent tempEvt;
535 OnTextPopupWidth(tempEvt);
536 OnTextPopupHeight(tempEvt);
537 GetButtonPosition();
538
539 m_combobox->SetPopupAnchor( m_chkAlignpopupright->GetValue() ? wxRIGHT : wxLEFT );
540
541 if ( m_chkBitmapbutton->GetValue() )
542 {
543 wxBitmap bmpNormal = CreateBitmap(*wxBLUE);
544 wxBitmap bmpPressed = CreateBitmap(wxColour(0,0,128));
545 wxBitmap bmpHover = CreateBitmap(wxColour(128,128,255));
546 m_combobox->SetButtonBitmaps(bmpNormal,m_chkStdbutton->GetValue(),bmpPressed,bmpHover);
547 }
548
549 m_sizerCombo->Add(m_combobox, 0, wxGROW | wxALL, 5);
550 m_sizerCombo->Layout();
551 }
552
553 // ----------------------------------------------------------------------------
554 // event handlers
555 // ----------------------------------------------------------------------------
556
557 void ODComboboxWidgetsPage::OnButtonReset(wxCommandEvent& WXUNUSED(event))
558 {
559 Reset();
560
561 CreateCombo();
562 }
563
564 void ODComboboxWidgetsPage::OnButtonChange(wxCommandEvent& WXUNUSED(event))
565 {
566 int sel = m_combobox->GetSelection();
567 if ( sel != wxNOT_FOUND )
568 {
569 #ifndef __WXGTK__
570 m_combobox->SetString(sel, m_textChange->GetValue());
571 #else
572 wxLogMessage(wxT("Not implemented in wxGTK"));
573 #endif
574 }
575 }
576
577 void ODComboboxWidgetsPage::OnButtonDelete(wxCommandEvent& WXUNUSED(event))
578 {
579 unsigned long n;
580 if ( !m_textDelete->GetValue().ToULong(&n) ||
581 (n >= m_combobox->GetCount()) )
582 {
583 return;
584 }
585
586 m_combobox->Delete(n);
587 }
588
589 void ODComboboxWidgetsPage::OnButtonDeleteSel(wxCommandEvent& WXUNUSED(event))
590 {
591 int sel = m_combobox->GetSelection();
592 if ( sel != wxNOT_FOUND )
593 {
594 m_combobox->Delete(sel);
595 }
596 }
597
598 void ODComboboxWidgetsPage::OnButtonClear(wxCommandEvent& WXUNUSED(event))
599 {
600 m_combobox->Clear();
601 }
602
603 void ODComboboxWidgetsPage::OnButtonInsert(wxCommandEvent& WXUNUSED(event))
604 {
605 static unsigned int s_item = 0;
606
607 wxString s = m_textInsert->GetValue();
608 if ( !m_textInsert->IsModified() )
609 {
610 // update the default string
611 m_textInsert->SetValue(wxString::Format(wxT("test item %u"), ++s_item));
612 }
613
614 if (m_combobox->GetSelection() >= 0)
615 m_combobox->Insert(s, m_combobox->GetSelection());
616 }
617
618 void ODComboboxWidgetsPage::OnButtonAdd(wxCommandEvent& WXUNUSED(event))
619 {
620 static unsigned int s_item = 0;
621
622 wxString s = m_textAdd->GetValue();
623 if ( !m_textAdd->IsModified() )
624 {
625 // update the default string
626 m_textAdd->SetValue(wxString::Format(wxT("test item %u"), ++s_item));
627 }
628
629 m_combobox->Append(s);
630 }
631
632 void ODComboboxWidgetsPage::OnButtonAddMany(wxCommandEvent& WXUNUSED(event))
633 {
634 // "many" means 1000 here
635 for ( unsigned int n = 0; n < 1000; n++ )
636 {
637 m_combobox->Append(wxString::Format(wxT("item #%u"), n));
638 }
639 }
640
641 void ODComboboxWidgetsPage::OnButtonAddSeveral(wxCommandEvent& WXUNUSED(event))
642 {
643 m_combobox->Append(wxT("First"));
644 m_combobox->Append(wxT("another one"));
645 m_combobox->Append(wxT("and the last (very very very very very very very very very very long) one"));
646 }
647
648 void ODComboboxWidgetsPage::OnTextPopupWidth(wxCommandEvent& WXUNUSED(event))
649 {
650 long l = 0;
651
652 m_textPopupMinWidth->GetValue().ToLong(&l);
653
654 if (m_combobox && l > 0)
655 {
656 m_combobox->SetPopupMinWidth(l);
657 }
658 }
659
660 void ODComboboxWidgetsPage::OnTextPopupHeight(wxCommandEvent& WXUNUSED(event))
661 {
662 long l = 0;
663
664 m_textPopupHeight->GetValue().ToLong(&l);
665
666 if (m_combobox && l > 0)
667 {
668 m_combobox->SetPopupMaxHeight(l);
669 }
670 }
671
672 void ODComboboxWidgetsPage::GetButtonPosition()
673 {
674 long w = -1;
675 long h = -1;
676 long spacing = 0;
677
678 m_textButtonWidth->GetValue().ToLong(&w);
679 m_textButtonSpacing->GetValue().ToLong(&spacing);
680 m_textButtonHeight->GetValue().ToLong(&h);
681 int align = m_chkAlignbutleft->GetValue() ?
682 wxLEFT : wxRIGHT;
683
684 m_combobox->SetButtonPosition(w,h,align,spacing);
685 }
686
687 void ODComboboxWidgetsPage::OnTextButtonAll(wxCommandEvent& WXUNUSED(event))
688 {
689 if (m_combobox)
690 {
691 if ( m_chkBitmapbutton->GetValue() )
692 CreateCombo();
693 else
694 GetButtonPosition();
695 }
696 }
697
698 void ODComboboxWidgetsPage::OnUpdateUICurText(wxUpdateUIEvent& event)
699 {
700 if (m_combobox)
701 event.SetText( wxString::Format(wxT("%d"), m_combobox->GetSelection()) );
702 }
703
704 void ODComboboxWidgetsPage::OnUpdateUIInsertionPointText(wxUpdateUIEvent& event)
705 {
706 if (m_combobox)
707 event.SetText( wxString::Format(wxT("%ld"), m_combobox->GetInsertionPoint()) );
708 }
709
710 void ODComboboxWidgetsPage::OnUpdateUIResetButton(wxUpdateUIEvent& event)
711 {
712 if (m_combobox)
713 event.Enable( m_chkSort->GetValue() || m_chkReadonly->GetValue() ||
714 m_chkBitmapbutton->GetValue() );
715 }
716
717 void ODComboboxWidgetsPage::OnUpdateUIInsert(wxUpdateUIEvent& event)
718 {
719 if (m_combobox)
720 {
721 bool enable = !(m_combobox->GetWindowStyle() & wxCB_SORT) &&
722 (m_combobox->GetSelection() >= 0);
723
724 event.Enable(enable);
725 }
726 }
727
728 void ODComboboxWidgetsPage::OnUpdateUIDeleteButton(wxUpdateUIEvent& event)
729 {
730 if (m_combobox)
731 {
732 unsigned long n;
733 event.Enable(m_textDelete->GetValue().ToULong(&n) &&
734 (n < (unsigned)m_combobox->GetCount()));
735 }
736 }
737
738 void ODComboboxWidgetsPage::OnUpdateUIDeleteSelButton(wxUpdateUIEvent& event)
739 {
740 if (m_combobox)
741 event.Enable(m_combobox->GetSelection() != wxNOT_FOUND);
742 }
743
744 void ODComboboxWidgetsPage::OnUpdateUIClearButton(wxUpdateUIEvent& event)
745 {
746 if (m_combobox)
747 event.Enable(m_combobox->GetCount() != 0);
748 }
749
750 void ODComboboxWidgetsPage::OnUpdateUIAddSeveral(wxUpdateUIEvent& event)
751 {
752 if (m_combobox)
753 event.Enable(!(m_combobox->GetWindowStyle() & wxCB_SORT));
754 }
755
756 void ODComboboxWidgetsPage::OnComboText(wxCommandEvent& event)
757 {
758 if (!m_combobox)
759 return;
760
761 wxString s = event.GetString();
762
763 wxASSERT_MSG( s == m_combobox->GetValue(),
764 wxT("event and combobox values should be the same") );
765
766 if (event.GetEventType() == wxEVT_TEXT_ENTER)
767 {
768 wxLogMessage(wxT("OwnerDrawnCombobox enter pressed (now '%s')"), s.c_str());
769 }
770 else
771 {
772 wxLogMessage(wxT("OwnerDrawnCombobox text changed (now '%s')"), s.c_str());
773 }
774 }
775
776 void ODComboboxWidgetsPage::OnComboBox(wxCommandEvent& event)
777 {
778 long sel = event.GetInt();
779 m_textDelete->SetValue(wxString::Format(wxT("%ld"), sel));
780
781 wxLogMessage(wxT("OwnerDrawnCombobox item %ld selected"), sel);
782
783 wxLogMessage(wxT("OwnerDrawnCombobox GetValue(): %s"), m_combobox->GetValue().c_str() );
784 }
785
786 void ODComboboxWidgetsPage::OnCheckOrRadioBox(wxCommandEvent& event)
787 {
788 wxObject* ctrl = event.GetEventObject();
789
790 // Double-click cycles only applies to read-only combobox
791 if ( ctrl == (wxObject*) m_chkReadonly )
792 {
793 m_chkDclickcycles->Enable( m_chkReadonly->GetValue() );
794 }
795 else if ( ctrl == (wxObject*) m_chkBitmapbutton )
796 {
797 m_chkStdbutton->Enable( m_chkBitmapbutton->GetValue() );
798 }
799 else if ( ctrl == (wxObject*) m_chkAlignbutleft )
800 {
801 wxUpdateUIEvent tempEvt;
802 OnTextButtonAll(tempEvt);
803 }
804
805 CreateCombo();
806 }
807
808 wxBitmap ODComboboxWidgetsPage::CreateBitmap(const wxColour& colour)
809 {
810 int ch = m_combobox->GetClientSize().y - 1;
811 int h0 = ch - 5;
812
813 long w = -1;
814 long h = -1;
815
816 m_textButtonWidth->GetValue().ToLong(&w);
817 m_textButtonHeight->GetValue().ToLong(&h);
818
819 if ( w <= 0 )
820 w = h0 - 1;
821 if ( h <= 0 )
822 h = h0;
823 if ( h > ch )
824 h = ch;
825
826 wxMemoryDC dc;
827 wxBitmap bmp(w,h);
828 dc.SelectObject(bmp);
829
830 // Draw transparent background
831 wxColour magic(255,0,255);
832 wxBrush magicBrush(magic);
833 dc.SetBrush(magicBrush);
834 dc.SetPen(*wxTRANSPARENT_PEN);
835 dc.DrawRectangle(0,0,bmp.GetWidth(),bmp.GetHeight());
836
837 // Draw image content
838 dc.SetBrush(wxBrush(colour));
839 dc.DrawCircle(h/2,h/2+1,(h/2));
840
841 dc.SelectObject(wxNullBitmap);
842
843 // Finalize transparency with a mask
844 wxMask *mask = new wxMask(bmp, magic);
845 bmp.SetMask(mask);
846
847 return bmp;
848 }
849
850 void ODComboboxWidgetsPage::OnDropDown(wxCommandEvent& WXUNUSED(event))
851 {
852 wxLogMessage(wxT("Combobox dropped down"));
853 }
854
855 void ODComboboxWidgetsPage::OnCloseUp(wxCommandEvent& WXUNUSED(event))
856 {
857 wxLogMessage(wxT("Combobox closed up"));
858 }
859
860 #endif //wxUSE_ODCOMBOBOX