]> git.saurik.com Git - wxWidgets.git/blame_incremental - src/common/valgen.cpp
fixing overrelease and out-of-bounds write, fixes #13725
[wxWidgets.git] / src / common / valgen.cpp
... / ...
CommitLineData
1/////////////////////////////////////////////////////////////////////////////
2// Name: src/common/valgen.cpp
3// Purpose: wxGenericValidator class
4// Author: Kevin Smith
5// Modified by:
6// Created: Jan 22 1999
7// RCS-ID: $Id$
8// Copyright: (c) 1999 Kevin Smith
9// Licence: wxWindows licence
10/////////////////////////////////////////////////////////////////////////////
11
12// For compilers that support precompilation, includes "wx.h".
13#include "wx/wxprec.h"
14
15#ifdef __BORLANDC__
16 #pragma hdrstop
17#endif
18
19#if wxUSE_VALIDATORS
20
21#ifndef WX_PRECOMP
22 #include "wx/dynarray.h"
23 #include "wx/utils.h"
24 #include "wx/intl.h"
25 #include "wx/choice.h"
26 #include "wx/combobox.h"
27 #include "wx/radiobox.h"
28 #include "wx/radiobut.h"
29 #include "wx/checkbox.h"
30 #include "wx/scrolbar.h"
31 #include "wx/gauge.h"
32 #include "wx/stattext.h"
33 #include "wx/textctrl.h"
34 #include "wx/button.h"
35 #include "wx/listbox.h"
36 #include "wx/slider.h"
37 #include "wx/checklst.h"
38#endif
39
40#include "wx/spinctrl.h"
41// #include "wx/datectrl.h" -- can't use it in this (core) file for now
42
43#if wxUSE_SPINBTN
44 #include "wx/spinbutt.h"
45#endif
46#if wxUSE_TOGGLEBTN
47 #include "wx/tglbtn.h"
48#endif
49#include "wx/filename.h"
50
51#include "wx/valgen.h"
52
53IMPLEMENT_CLASS(wxGenericValidator, wxValidator)
54
55wxGenericValidator::wxGenericValidator(bool *val)
56{
57 Initialize();
58 m_pBool = val;
59}
60
61wxGenericValidator::wxGenericValidator(int *val)
62{
63 Initialize();
64 m_pInt = val;
65}
66
67wxGenericValidator::wxGenericValidator(wxString *val)
68{
69 Initialize();
70 m_pString = val;
71}
72
73wxGenericValidator::wxGenericValidator(wxArrayInt *val)
74{
75 Initialize();
76 m_pArrayInt = val;
77}
78
79#if wxUSE_DATETIME
80
81wxGenericValidator::wxGenericValidator(wxDateTime *val)
82{
83 Initialize();
84 m_pDateTime = val;
85}
86
87#endif // wxUSE_DATETIME
88
89wxGenericValidator::wxGenericValidator(wxFileName *val)
90{
91 Initialize();
92 m_pFileName = val;
93}
94
95wxGenericValidator::wxGenericValidator(float *val)
96{
97 Initialize();
98 m_pFloat = val;
99}
100
101wxGenericValidator::wxGenericValidator(double *val)
102{
103 Initialize();
104 m_pDouble = val;
105}
106
107wxGenericValidator::wxGenericValidator(const wxGenericValidator& val)
108 : wxValidator()
109{
110 Copy(val);
111}
112
113bool wxGenericValidator::Copy(const wxGenericValidator& val)
114{
115 wxValidator::Copy(val);
116
117 m_pBool = val.m_pBool;
118 m_pInt = val.m_pInt;
119 m_pString = val.m_pString;
120 m_pArrayInt = val.m_pArrayInt;
121#if wxUSE_DATETIME
122 m_pDateTime = val.m_pDateTime;
123#endif // wxUSE_DATETIME
124 m_pFileName = val.m_pFileName;
125 m_pFloat = val.m_pFloat;
126 m_pDouble = val.m_pDouble;
127
128 return true;
129}
130
131// Called to transfer data to the window
132bool wxGenericValidator::TransferToWindow(void)
133{
134 if ( !m_validatorWindow )
135 return false;
136
137 // bool controls
138#if wxUSE_CHECKBOX
139 if (wxDynamicCast(m_validatorWindow, wxCheckBox))
140 {
141 wxCheckBox* pControl = (wxCheckBox*) m_validatorWindow;
142 if (m_pBool)
143 {
144 pControl->SetValue(*m_pBool);
145 return true;
146 }
147 } else
148#endif
149#if wxUSE_RADIOBTN
150 if (wxDynamicCast(m_validatorWindow, wxRadioButton))
151 {
152 wxRadioButton* pControl = (wxRadioButton*) m_validatorWindow;
153 if (m_pBool)
154 {
155 pControl->SetValue(*m_pBool) ;
156 return true;
157 }
158 } else
159#endif
160
161#if wxUSE_TOGGLEBTN
162 if (wxDynamicCast(m_validatorWindow, wxToggleButton))
163 {
164 wxToggleButton * pControl = (wxToggleButton *) m_validatorWindow;
165 if (m_pBool)
166 {
167 pControl->SetValue(*m_pBool);
168 return true;
169 }
170 } else
171#if (defined(__WXMAC__) || defined(__WXMSW__) || defined(__WXGTK20__)) && !defined(__WXUNIVERSAL__)
172 if (wxDynamicCast(m_validatorWindow, wxBitmapToggleButton))
173 {
174 wxBitmapToggleButton * pControl = (wxBitmapToggleButton *) m_validatorWindow;
175 if (m_pBool)
176 {
177 pControl->SetValue(*m_pBool);
178 return true;
179 }
180 } else
181#endif
182#endif
183
184 // int controls
185#if wxUSE_GAUGE
186 if (wxDynamicCast(m_validatorWindow, wxGauge))
187 {
188 wxGauge* pControl = (wxGauge*) m_validatorWindow;
189 if (m_pInt)
190 {
191 pControl->SetValue(*m_pInt);
192 return true;
193 }
194 } else
195#endif
196#if wxUSE_RADIOBOX
197 if (wxDynamicCast(m_validatorWindow, wxRadioBox))
198 {
199 wxRadioBox* pControl = (wxRadioBox*) m_validatorWindow;
200 if (m_pInt)
201 {
202 pControl->SetSelection(*m_pInt) ;
203 return true;
204 }
205 } else
206#endif
207#if wxUSE_SCROLLBAR
208 if (wxDynamicCast(m_validatorWindow, wxScrollBar))
209 {
210 wxScrollBar* pControl = (wxScrollBar*) m_validatorWindow;
211 if (m_pInt)
212 {
213 pControl->SetThumbPosition(*m_pInt) ;
214 return true;
215 }
216 } else
217#endif
218#if wxUSE_SPINCTRL && !defined(__WXMOTIF__)
219 if (wxDynamicCast(m_validatorWindow, wxSpinCtrl))
220 {
221 wxSpinCtrl* pControl = (wxSpinCtrl*) m_validatorWindow;
222 if (m_pInt)
223 {
224 pControl->SetValue(*m_pInt);
225 return true;
226 }
227 } else
228#endif
229#if wxUSE_SPINBTN
230 if (wxDynamicCast(m_validatorWindow, wxSpinButton))
231 {
232 wxSpinButton* pControl = (wxSpinButton*) m_validatorWindow;
233 if (m_pInt)
234 {
235 pControl->SetValue(*m_pInt) ;
236 return true;
237 }
238 } else
239#endif
240#if wxUSE_SLIDER
241 if (wxDynamicCast(m_validatorWindow, wxSlider))
242 {
243 wxSlider* pControl = (wxSlider*) m_validatorWindow;
244 if (m_pInt)
245 {
246 pControl->SetValue(*m_pInt) ;
247 return true;
248 }
249 } else
250#endif
251
252 // date time controls
253#if 0 // wxUSE_DATEPICKCTRL -- temporary fix for shared build linking
254 if (wxDynamicCast(m_validatorWindow, wxDatePickerCtrl))
255 {
256 wxDatePickerCtrl* pControl = (wxDatePickerCtrl*) m_validatorWindow;
257 if (m_pDateTime)
258 {
259 pControl->SetValue(*m_pDateTime) ;
260 return true;
261 }
262 } else
263#endif
264
265 // string controls
266#if wxUSE_BUTTON
267 if (wxDynamicCast(m_validatorWindow, wxButton))
268 {
269 wxButton* pControl = (wxButton*) m_validatorWindow;
270 if (m_pString)
271 {
272 pControl->SetLabel(*m_pString) ;
273 return true;
274 }
275 } else
276#endif
277#if wxUSE_COMBOBOX
278 if (wxDynamicCast(m_validatorWindow, wxComboBox))
279 {
280 wxComboBox* pControl = (wxComboBox*) m_validatorWindow;
281 if (m_pInt)
282 {
283 pControl->SetSelection(*m_pInt) ;
284 return true;
285 }
286 else if (m_pString)
287 {
288 if (pControl->FindString(* m_pString) != wxNOT_FOUND)
289 {
290 pControl->SetStringSelection(* m_pString);
291 }
292 if ((m_validatorWindow->GetWindowStyle() & wxCB_READONLY) == 0)
293 {
294 pControl->SetValue(* m_pString);
295 }
296 return true;
297 }
298 } else
299#endif
300#if wxUSE_CHOICE
301 if (wxDynamicCast(m_validatorWindow, wxChoice))
302 {
303 wxChoice* pControl = (wxChoice*) m_validatorWindow;
304 if (m_pInt)
305 {
306 pControl->SetSelection(*m_pInt) ;
307 return true;
308 }
309 else if (m_pString)
310 {
311 if (pControl->FindString(* m_pString) != wxNOT_FOUND)
312 {
313 pControl->SetStringSelection(* m_pString);
314 }
315 return true;
316 }
317 } else
318#endif
319#if wxUSE_STATTEXT
320 if (wxDynamicCast(m_validatorWindow, wxStaticText))
321 {
322 wxStaticText* pControl = (wxStaticText*) m_validatorWindow;
323 if (m_pString)
324 {
325 pControl->SetLabel(*m_pString) ;
326 return true;
327 }
328 } else
329#endif
330#if wxUSE_TEXTCTRL
331 if (wxDynamicCast(m_validatorWindow, wxTextCtrl))
332 {
333 wxTextCtrl* pControl = (wxTextCtrl*) m_validatorWindow;
334 if (m_pString)
335 {
336 pControl->SetValue(*m_pString) ;
337 return true;
338 }
339 else if (m_pInt)
340 {
341 wxString str;
342 str.Printf(wxT("%d"), *m_pInt);
343 pControl->SetValue(str);
344 return true;
345 }
346 else if (m_pFileName)
347 {
348 pControl->SetValue(m_pFileName->GetFullPath());
349 return true;
350 }
351 else if (m_pFloat)
352 {
353 pControl->SetValue(wxString::Format(wxT("%g"), *m_pFloat));
354 return true;
355 }
356 else if (m_pDouble)
357 {
358 pControl->SetValue(wxString::Format(wxT("%g"), *m_pDouble));
359 return true;
360 }
361 } else
362#endif
363
364 // array controls
365#if wxUSE_CHECKLISTBOX
366 // NOTE: wxCheckListBox is a wxListBox, so wxCheckListBox MUST come first:
367 if (wxDynamicCast(m_validatorWindow, wxCheckListBox))
368 {
369 wxCheckListBox* pControl = (wxCheckListBox*) m_validatorWindow;
370 if (m_pArrayInt)
371 {
372 // clear all selections
373 size_t i,
374 count = pControl->GetCount();
375 for ( i = 0 ; i < count; i++ )
376 pControl->Check(i, false);
377
378 // select each item in our array
379 count = m_pArrayInt->GetCount();
380 for ( i = 0 ; i < count; i++ )
381 pControl->Check(m_pArrayInt->Item(i));
382
383 return true;
384 }
385 else
386 return false;
387 } else
388#endif
389#if wxUSE_LISTBOX
390 if (wxDynamicCast(m_validatorWindow, wxListBox))
391 {
392 wxListBox* pControl = (wxListBox*) m_validatorWindow;
393 if (m_pArrayInt)
394 {
395 // clear all selections
396 size_t i,
397 count = pControl->GetCount();
398 for ( i = 0 ; i < count; i++ )
399 pControl->Deselect(i);
400
401 // select each item in our array
402 count = m_pArrayInt->GetCount();
403 for ( i = 0 ; i < count; i++ )
404 pControl->SetSelection(m_pArrayInt->Item(i));
405
406 return true;
407 }
408 } else
409#endif
410 { // to match the last 'else' above
411 }
412
413 // unrecognized control, or bad pointer
414 return false;
415}
416
417// Called to transfer data from the window
418bool wxGenericValidator::TransferFromWindow(void)
419{
420 if ( !m_validatorWindow )
421 return false;
422
423 // BOOL CONTROLS **************************************
424#if wxUSE_CHECKBOX
425 if (wxDynamicCast(m_validatorWindow, wxCheckBox))
426 {
427 wxCheckBox* pControl = (wxCheckBox*) m_validatorWindow;
428 if (m_pBool)
429 {
430 *m_pBool = pControl->GetValue() ;
431 return true;
432 }
433 } else
434#endif
435#if wxUSE_RADIOBTN
436 if (wxDynamicCast(m_validatorWindow, wxRadioButton))
437 {
438 wxRadioButton* pControl = (wxRadioButton*) m_validatorWindow;
439 if (m_pBool)
440 {
441 *m_pBool = pControl->GetValue() ;
442 return true;
443 }
444 } else
445#endif
446#if wxUSE_TOGGLEBTN
447 if (wxDynamicCast(m_validatorWindow, wxToggleButton))
448 {
449 wxToggleButton *pControl = (wxToggleButton *) m_validatorWindow;
450 if (m_pBool)
451 {
452 *m_pBool = pControl->GetValue() ;
453 return true;
454 }
455 } else
456#if (defined(__WXMAC__) || defined(__WXMSW__) || defined(__WXGTK20__)) && !defined(__WXUNIVERSAL__)
457 if (wxDynamicCast(m_validatorWindow, wxBitmapToggleButton))
458 {
459 wxBitmapToggleButton *pControl = (wxBitmapToggleButton *) m_validatorWindow;
460 if (m_pBool)
461 {
462 *m_pBool = pControl->GetValue() ;
463 return true;
464 }
465 } else
466#endif
467#endif
468
469 // INT CONTROLS ***************************************
470#if wxUSE_GAUGE
471 if (wxDynamicCast(m_validatorWindow, wxGauge))
472 {
473 wxGauge* pControl = (wxGauge*) m_validatorWindow;
474 if (m_pInt)
475 {
476 *m_pInt = pControl->GetValue() ;
477 return true;
478 }
479 } else
480#endif
481#if wxUSE_RADIOBOX
482 if (wxDynamicCast(m_validatorWindow, wxRadioBox))
483 {
484 wxRadioBox* pControl = (wxRadioBox*) m_validatorWindow;
485 if (m_pInt)
486 {
487 *m_pInt = pControl->GetSelection() ;
488 return true;
489 }
490 } else
491#endif
492#if wxUSE_SCROLLBAR
493 if (wxDynamicCast(m_validatorWindow, wxScrollBar))
494 {
495 wxScrollBar* pControl = (wxScrollBar*) m_validatorWindow;
496 if (m_pInt)
497 {
498 *m_pInt = pControl->GetThumbPosition() ;
499 return true;
500 }
501 } else
502#endif
503#if wxUSE_SPINCTRL && !defined(__WXMOTIF__)
504 if (wxDynamicCast(m_validatorWindow, wxSpinCtrl))
505 {
506 wxSpinCtrl* pControl = (wxSpinCtrl*) m_validatorWindow;
507 if (m_pInt)
508 {
509 *m_pInt=pControl->GetValue();
510 return true;
511 }
512 } else
513#endif
514#if wxUSE_SPINBTN
515 if (wxDynamicCast(m_validatorWindow, wxSpinButton))
516 {
517 wxSpinButton* pControl = (wxSpinButton*) m_validatorWindow;
518 if (m_pInt)
519 {
520 *m_pInt = pControl->GetValue() ;
521 return true;
522 }
523 } else
524#endif
525#if wxUSE_SLIDER
526 if (wxDynamicCast(m_validatorWindow, wxSlider))
527 {
528 wxSlider* pControl = (wxSlider*) m_validatorWindow;
529 if (m_pInt)
530 {
531 *m_pInt = pControl->GetValue() ;
532 return true;
533 }
534 } else
535#endif
536
537 // DATE TIME CONTROLS ************************************
538#if 0 // wxUSE_DATEPICKCTRL -- temporary fix for shared build linking
539 if (wxDynamicCast(m_validatorWindow, wxDatePickerCtrl))
540 {
541 wxDatePickerCtrl* pControl = (wxDatePickerCtrl*) m_validatorWindow;
542 if (m_pDateTime)
543 {
544 *m_pDateTime = pControl->GetValue() ;
545 return true;
546 }
547 } else
548#endif
549
550 // STRING CONTROLS ************************************
551#if wxUSE_BUTTON
552 if (wxDynamicCast(m_validatorWindow, wxButton))
553 {
554 wxButton* pControl = (wxButton*) m_validatorWindow;
555 if (m_pString)
556 {
557 *m_pString = pControl->GetLabel() ;
558 return true;
559 }
560 } else
561#endif
562#if wxUSE_COMBOBOX
563 if (wxDynamicCast(m_validatorWindow, wxComboBox))
564 {
565 wxComboBox* pControl = (wxComboBox*) m_validatorWindow;
566 if (m_pInt)
567 {
568 *m_pInt = pControl->GetSelection() ;
569 return true;
570 }
571 else if (m_pString)
572 {
573 if (m_validatorWindow->GetWindowStyle() & wxCB_READONLY)
574 *m_pString = pControl->GetStringSelection();
575 else
576 *m_pString = pControl->GetValue();
577 return true;
578 }
579 } else
580#endif
581#if wxUSE_CHOICE
582 if (wxDynamicCast(m_validatorWindow, wxChoice))
583 {
584 wxChoice* pControl = (wxChoice*) m_validatorWindow;
585 if (m_pInt)
586 {
587 *m_pInt = pControl->GetSelection() ;
588 return true;
589 }
590 else if (m_pString)
591 {
592 *m_pString = pControl->GetStringSelection();
593 return true;
594 }
595 } else
596#endif
597#if wxUSE_STATTEXT
598 if (wxDynamicCast(m_validatorWindow, wxStaticText))
599 {
600 wxStaticText* pControl = (wxStaticText*) m_validatorWindow;
601 if (m_pString)
602 {
603 *m_pString = pControl->GetLabel() ;
604 return true;
605 }
606 } else
607#endif
608#if wxUSE_TEXTCTRL
609 if (wxDynamicCast(m_validatorWindow, wxTextCtrl))
610 {
611 wxTextCtrl* pControl = (wxTextCtrl*) m_validatorWindow;
612 if (m_pString)
613 {
614 *m_pString = pControl->GetValue() ;
615 return true;
616 }
617 else if (m_pInt)
618 {
619 *m_pInt = wxAtoi(pControl->GetValue());
620 return true;
621 }
622 else if (m_pFileName)
623 {
624 m_pFileName->Assign(pControl->GetValue());
625 return true;
626 }
627 else if (m_pFloat)
628 {
629 *m_pFloat = (float)wxAtof(pControl->GetValue());
630 return true;
631 }
632 else if (m_pDouble)
633 {
634 *m_pDouble = wxAtof(pControl->GetValue());
635 return true;
636 }
637 } else
638#endif
639
640 // ARRAY CONTROLS *************************************
641#if wxUSE_CHECKLISTBOX
642 // NOTE: wxCheckListBox isa wxListBox, so wxCheckListBox MUST come first:
643 if (wxDynamicCast(m_validatorWindow, wxCheckListBox))
644 {
645 wxCheckListBox* pControl = (wxCheckListBox*) m_validatorWindow;
646 if (m_pArrayInt)
647 {
648 // clear our array
649 m_pArrayInt->Clear();
650
651 // add each selected item to our array
652 size_t i,
653 count = pControl->GetCount();
654 for ( i = 0; i < count; i++ )
655 {
656 if (pControl->IsChecked(i))
657 m_pArrayInt->Add(i);
658 }
659
660 return true;
661 }
662 else
663 return false;
664 } else
665#endif
666#if wxUSE_LISTBOX
667 if (wxDynamicCast(m_validatorWindow, wxListBox))
668 {
669 wxListBox* pControl = (wxListBox*) m_validatorWindow;
670 if (m_pArrayInt)
671 {
672 // clear our array
673 m_pArrayInt->Clear();
674
675 // add each selected item to our array
676 size_t i,
677 count = pControl->GetCount();
678 for ( i = 0; i < count; i++ )
679 {
680 if (pControl->IsSelected(i))
681 m_pArrayInt->Add(i);
682 }
683
684 return true;
685 }
686 } else
687#endif
688
689 // unrecognized control, or bad pointer
690 return false;
691
692 return false;
693}
694
695/*
696 Called by constructors to initialize ALL data members
697*/
698void wxGenericValidator::Initialize()
699{
700 m_pBool = NULL;
701 m_pInt = NULL;
702 m_pString = NULL;
703 m_pArrayInt = NULL;
704#if wxUSE_DATETIME
705 m_pDateTime = NULL;
706#endif // wxUSE_DATETIME
707 m_pFileName = NULL;
708 m_pFloat = NULL;
709 m_pDouble = NULL;
710}
711
712#endif // wxUSE_VALIDATORS