2 // "$Id: Fl_Spinner.H 8339 2011-01-30 12:50:19Z ianmacarthur $"
4 // Spinner widget for the Fast Light Tool Kit (FLTK).
6 // Copyright 1998-2010 by Bill Spitzak and others.
8 // This library is free software; you can redistribute it and/or
9 // modify it under the terms of the GNU Library General Public
10 // License as published by the Free Software Foundation; either
11 // version 2 of the License, or (at your option) any later version.
13 // This library is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 // Library General Public License for more details.
18 // You should have received a copy of the GNU Library General Public
19 // License along with this library; if not, write to the Free Software
20 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
23 // Please report all bugs and problems on the following page:
25 // http://www.fltk.org/str.php
29 Fl_Spinner widget . */
35 // Include necessary headers...
38 # include <FL/Enumerations.H>
39 # include <FL/Fl_Group.H>
40 # include <FL/Fl_Input.H>
41 # include <FL/Fl_Repeat_Button.H>
47 This widget is a combination of the input
48 widget and repeat buttons. The user can either type into the
49 input area or use the buttons to change the value.
51 class FL_EXPORT Fl_Spinner : public Fl_Group {
53 double value_; // Current value
54 double minimum_; // Minimum value
55 double maximum_; // Maximum value
56 double step_; // Amount to add/subtract for up/down
57 const char *format_; // Format string
59 Fl_Input input_; // Input field for the value
61 up_button_, // Up button
62 down_button_; // Down button
65 static void sb_cb(Fl_Widget *w, Fl_Spinner *sb) {
66 double v; // New value
68 if (w == &(sb->input_)) {
69 // Something changed in the input field...
70 v = atof(sb->input_.value());
72 if (v < sb->minimum_) {
73 sb->value_ = sb->minimum_;
75 } else if (v > sb->maximum_) {
76 sb->value_ = sb->maximum_;
78 } else sb->value_ = v;
79 } else if (w == &(sb->up_button_)) {
80 // Up button pressed...
81 v = sb->value_ + sb->step_;
83 if (v > sb->maximum_) sb->value_ = sb->minimum_;
87 } else if (w == &(sb->down_button_)) {
88 // Down button pressed...
89 v = sb->value_ - sb->step_;
91 if (v < sb->minimum_) sb->value_ = sb->maximum_;
100 char s[255]; // Value string
102 if (format_[0]=='%'&&format_[1]=='.'&&format_[2]=='*') { // precision argument
103 // this code block is a simplified version of
104 // Fl_Valuator::format() and works well (but looks ugly)
106 char temp[64], *sp = temp;
107 sprintf(temp, "%.12f", step_);
110 while (sp>temp && *sp=='0') sp--;
111 while (sp>temp && (*sp>='0' && *sp<='9')) { sp--; c++; }
112 sprintf(s, format_, c, value_);
114 sprintf(s, format_, value_);
122 Creates a new Fl_Spinner widget using the given position, size,
124 <P>Inherited destructor Destroys the widget and any value associated with it.
126 Fl_Spinner(int X, int Y, int W, int H, const char *L = 0)
127 : Fl_Group(X, Y, W, H, L),
128 input_(X, Y, W - H / 2 - 2, H),
129 up_button_(X + W - H / 2 - 2, Y, H / 2 + 2, H / 2, "@-42<"),
130 down_button_(X + W - H / 2 - 2, Y + H - H / 2,
131 H / 2 + 2, H / 2, "@-42>") {
140 align(FL_ALIGN_LEFT);
143 input_.type(FL_INT_INPUT);
144 input_.when(FL_WHEN_ENTER_KEY | FL_WHEN_RELEASE);
145 input_.callback((Fl_Callback *)sb_cb, this);
147 up_button_.callback((Fl_Callback *)sb_cb, this);
149 down_button_.callback((Fl_Callback *)sb_cb, this);
152 /** Sets or returns the format string for the value. */
153 const char *format() { return (format_); }
154 /** Sets or returns the format string for the value. */
155 void format(const char *f) { format_ = f; update(); }
157 int handle(int event) {
161 if (Fl::event_key() == FL_Up) {
162 up_button_.do_callback();
164 } else if (Fl::event_key() == FL_Down) {
165 down_button_.do_callback();
170 if (input_.take_focus()) return 1;
174 return Fl_Group::handle(event);
177 /** Speling mistakes retained for source compatibility \deprecated */
178 double maxinum() const { return (maximum_); }
179 /** Gets the maximum value of the widget. */
180 double maximum() const { return (maximum_); }
181 /** Sets the maximum value of the widget. */
182 void maximum(double m) { maximum_ = m; }
183 /** Speling mistakes retained for source compatibility \deprecated */
184 double mininum() const { return (minimum_); }
185 /** Gets the minimum value of the widget. */
186 double minimum() const { return (minimum_); }
187 /** Sets the minimum value of the widget. */
188 void minimum(double m) { minimum_ = m; }
189 /** Sets the minimum and maximum values for the widget. */
190 void range(double a, double b) { minimum_ = a; maximum_ = b; }
191 void resize(int X, int Y, int W, int H) {
192 Fl_Group::resize(X,Y,W,H);
194 input_.resize(X, Y, W - H / 2 - 2, H);
195 up_button_.resize(X + W - H / 2 - 2, Y, H / 2 + 2, H / 2);
196 down_button_.resize(X + W - H / 2 - 2, Y + H - H / 2,
200 Sets or returns the amount to change the value when the user clicks a button.
201 Before setting step to a non-integer value, the spinner
202 type() should be changed to floating point.
204 double step() const { return (step_); }
205 /** See double Fl_Spinner::step() const */
206 void step(double s) {
208 if (step_ != (int)step_) input_.type(FL_FLOAT_INPUT);
209 else input_.type(FL_INT_INPUT);
212 /** Gets the color of the text in the input field. */
213 Fl_Color textcolor() const {
214 return (input_.textcolor());
216 /** Sets the color of the text in the input field. */
217 void textcolor(Fl_Color c) {
220 /** Gets the font of the text in the input field. */
221 Fl_Font textfont() const {
222 return (input_.textfont());
224 /** Sets the font of the text in the input field. */
225 void textfont(Fl_Font f) {
228 /** Gets the size of the text in the input field. */
229 Fl_Fontsize textsize() const {
230 return (input_.textsize());
232 /** Sets the size of the text in the input field. */
233 void textsize(Fl_Fontsize s) {
236 /** Gets the numeric representation in the input field.
237 \see Fl_Spinner::type(uchar)
239 uchar type() const { return (input_.type()); }
240 /** Sets the numeric representation in the input field.
241 Valid values are FL_INT_INPUT and FL_FLOAT_INPUT.
242 Also changes the format() template.
243 Setting a new spinner type via a superclass pointer will not work.
244 \note type is not a virtual function.
247 if (v==FL_FLOAT_INPUT) {
254 /** Gets the current value of the widget. */
255 double value() const { return (value_); }
257 Sets the current value of the widget.
258 Before setting value to a non-integer value, the spinner
259 type() should be changed to floating point.
261 void value(double v) { value_ = v; update(); }
264 #endif // !Fl_Spinner_H
267 // End of "$Id: Fl_Spinner.H 8339 2011-01-30 12:50:19Z ianmacarthur $".