1 // Copyright (c) 2013, Thomas Goyne <plorkyeran@aegisub.org>
2 //
3 // Permission to use, copy, modify, and distribute this software for any
4 // purpose with or without fee is hereby granted, provided that the above
5 // copyright notice and this permission notice appear in all copies.
6 //
7 // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
8 // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
9 // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
10 // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
11 // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
12 // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
13 // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
14 //
15 // Aegisub Project http://www.aegisub.org/
16 
17 #include <libaegisub/exception.h>
18 
19 #include <string>
20 #include <wx/combobox.h>
21 #include <wx/radiobox.h>
22 #include <wx/validate.h>
23 
24 class IntValidator final : public wxValidator {
25 	int value;
26 	bool allow_negative;
27 
28 	bool CheckCharacter(int chr, bool is_first) const;
29 	void OnChar(wxKeyEvent& event);
30 
Validate(wxWindow *)31 	bool Validate(wxWindow *) override { return true; }
Clone()32 	wxObject* Clone() const override { return new IntValidator(*this); }
33 	bool TransferToWindow() override;
TransferFromWindow()34 	bool TransferFromWindow() override { return true; }
35 
36 	IntValidator(IntValidator const& rgt);
37 
38 public:
39 	explicit IntValidator(int val=0, bool allow_negative=false);
40 };
41 
42 class DoubleValidator final : public wxValidator {
43 	double *value;
44 	double min;
45 	double max;
46 	wxChar decimal_sep;
47 
Validate(wxWindow * parent)48 	bool Validate(wxWindow* parent) override { return true; }
49 	bool CheckCharacter(int chr, bool is_first, bool *got_decimal) const;
50 	void OnChar(wxKeyEvent& event);
51 
52 	DoubleValidator(DoubleValidator const& rgt);
53 
Clone()54 	wxObject* Clone() const override { return new DoubleValidator(*this); }
55 	bool TransferToWindow() override;
56 	bool TransferFromWindow() override;
57 
58 public:
59 	explicit DoubleValidator(double *val, bool allow_negative=false);
60 	explicit DoubleValidator(double *val, double min, double max);
61 };
62 
63 class DoubleSpinValidator final : public wxValidator {
64 	double *value;
Clone()65 	wxValidator *Clone() const override { return new DoubleSpinValidator(value); }
Validate(wxWindow *)66 	bool Validate(wxWindow*) override { return true; }
67 	bool TransferToWindow() override;
68 	bool TransferFromWindow() override;
69 
70 public:
DoubleSpinValidator(double * value)71 	DoubleSpinValidator(double *value) : value(value) { }
72 };
73 
74 template<typename T>
75 class EnumBinder final : public wxValidator {
76 	T *value;
77 
Clone()78 	wxObject *Clone() const override { return new EnumBinder<T>(value); }
Validate(wxWindow *)79 	bool Validate(wxWindow *) override { return true; }
80 
TransferFromWindow()81 	bool TransferFromWindow() override {
82 		if (auto rb = dynamic_cast<wxRadioBox*>(GetWindow()))
83 			*value = static_cast<T>(rb->GetSelection());
84 		else if (auto rb = dynamic_cast<wxComboBox*>(GetWindow()))
85 			*value = static_cast<T>(rb->GetSelection());
86 		else
87 			throw agi::InternalError("Control type not supported by EnumBinder");
88 		return true;
89 	}
90 
TransferToWindow()91 	bool TransferToWindow() override {
92 		if (auto rb = dynamic_cast<wxRadioBox*>(GetWindow()))
93 			rb->SetSelection(static_cast<int>(*value));
94 		else if (auto cb = dynamic_cast<wxComboBox*>(GetWindow()))
95 			cb->SetSelection(static_cast<int>(*value));
96 		else
97 			throw agi::InternalError("Control type not supported by EnumBinder");
98 		return true;
99 	}
100 
101 public:
EnumBinder(T * value)102 	explicit EnumBinder(T *value) : value(value) { }
EnumBinder(EnumBinder const & rhs)103 	EnumBinder(EnumBinder const& rhs) : wxValidator(rhs), value(rhs.value) { }
104 };
105 
106 template<typename T>
MakeEnumBinder(T * value)107 EnumBinder<T> MakeEnumBinder(T *value) {
108 	return EnumBinder<T>(value);
109 }
110 
111 class StringBinder final : public wxValidator {
112 	std::string *value;
113 
Clone()114 	wxObject* Clone() const override { return new StringBinder(value); }
Validate(wxWindow *)115 	bool Validate(wxWindow*) override { return true;}
116 	bool TransferToWindow() override;
117 	bool TransferFromWindow() override;
118 
119 public:
StringBinder(std::string * value)120 	explicit StringBinder(std::string *value) : value(value) { }
121 };
122