r125: This commit was manufactured by cvs2svn to create tag 'r1_1_7-last'.
[cinelerra_cv/mob.git] / hvirtual / guicast / bcpot.C
blob0fdd1bb9182790eac4c14cce9dab13d56362de42
1 #include "bcpot.h"
2 #include "bcresources.h"
3 #include "colors.h"
4 #include "keys.h"
5 #include "units.h"
6 #include "vframe.h"
8 #include <ctype.h>
9 #include <math.h>
10 #include <string.h>
11 #define MIN_ANGLE 225
12 #define MAX_ANGLE -45
14 BC_Pot::BC_Pot(int x, int y, VFrame **data)
15  : BC_SubWindow(x, y, -1, -1, -1)
17         this->data = data;
18         for(int i = 0; i < POT_STATES; i++)
19                 images[i] = 0;
22 BC_Pot::~BC_Pot()
26 int BC_Pot::initialize()
28         if(!data)
29         {
30                 data = get_resources()->pot_images;
31         }
33         status = POT_UP;
34         set_data(data);
35         w = data[0]->get_w();
36         h = data[0]->get_h();
37         BC_SubWindow::initialize();
38         draw();
39         return 0;
42 int BC_Pot::reposition_window(int x, int y)
44         BC_WindowBase::reposition_window(x, y);
45         draw();
46         return 0;
49 int BC_Pot::set_data(VFrame **data)
51         for(int i = 0; i < POT_STATES; i++)
52                 if(images[i]) delete images[i];
54         for(int i = 0; i < POT_STATES; i++)
55                 images[i] = new BC_Pixmap(parent_window, data[i], PIXMAP_ALPHA);
56         return 0;
60 int BC_Pot::draw()
62         int x1, y1, x2, y2;
63         draw_top_background(parent_window, 0, 0, get_w(), get_h());
64         draw_pixmap(images[status]);
65         set_color(BLACK);
67         angle_to_coords(x1, y1, x2, y2, percentage_to_angle(get_percentage()));
68         draw_line(x1, y1, x2, y2);
70         flash();
71         return 0;
74 float BC_Pot::percentage_to_angle(float percentage)
76         return percentage * (MAX_ANGLE - MIN_ANGLE) + MIN_ANGLE;
79 float BC_Pot::angle_to_percentage(float angle)
81         return (angle - MIN_ANGLE) / (MAX_ANGLE - MIN_ANGLE);
85 int BC_Pot::angle_to_coords(int &x1, int &y1, int &x2, int &y2, float angle)
87         x1 = get_resources()->pot_x1;
88         y1 = get_resources()->pot_y1;
89         if(status == POT_DN)
90         {
91                 x1 += 2;
92                 y1 += 2;
93         }
95         while(angle < 0) angle += 360;
97         x2 = (int)(cos(angle / 360 * (2 * M_PI)) * get_resources()->pot_r + x1);
98         y2 = (int)(-sin(angle / 360 * (2 * M_PI)) * get_resources()->pot_r + y1);
99         return 0;
102 float BC_Pot::coords_to_angle(int x2, int y2)
104         int x1, y1, x, y;
105         float angle;
107         x1 = get_resources()->pot_x1;
108         y1 = get_resources()->pot_y1;
109         if(status == POT_DN)
110         {
111                 x1 += 2;
112                 y1 += 2;
113         }
115         x = x2 - x1;
116         y = y2 - y1;
118         if(x > 0 && y <= 0)
119         {
120                 angle = atan((float)-y / x) / (2 * M_PI) * 360;
121         }
122         else
123         if(x < 0 && y <= 0)
124         {
125                 angle = 180 - atan((float)-y / -x) / (2 * M_PI) * 360;
126         }
127         else
128         if(x < 0 && y > 0)
129         {
130                 angle = 180 - atan((float)-y / -x) / (2 * M_PI) * 360;
131         }
132         else
133         if(x > 0 && y > 0)
134         {
135                 angle = 360 + atan((float)-y / x) / (2 * M_PI) * 360;
136         }
137         else
138         if(x == 0 && y < 0)
139         {
140                 angle = 90;
141         }
142         else
143         if(x == 0 && y > 0)
144         {
145                 angle = 270;
146         }
147         else
148         if(x == 0 && y == 0)
149         {
150                 angle = 0;
151         }
153         return angle;
159 void BC_Pot::show_value_tooltip()
161         set_tooltip(get_caption());
162         show_tooltip(50);
163         keypress_tooltip_timer = 2000;
166 int BC_Pot::repeat_event(int64_t duration)
168         if(duration == top_level->get_resources()->tooltip_delay)
169         {
170                 if(tooltip_on)
171                 {
172                         if(keypress_tooltip_timer > 0)
173                         {
174                                 keypress_tooltip_timer -= get_resources()->tooltip_delay;
175                         }
176                         else
177                         if(status != POT_HIGH && status != POT_DN)
178                         {
179                                 hide_tooltip();
180                         }
181                 }
182                 else
183                 if(status == POT_HIGH)
184                 {
185                         if(!tooltip_text[0] || isdigit(tooltip_text[0]))
186                         {
187                                 set_tooltip(get_caption());
188                                 show_tooltip(50);
189                         }
190                         else
191                                 show_tooltip();
192                         tooltip_done = 1;
193                         return 1;
194                 }
195         }
196         return 0;
199 int BC_Pot::keypress_event()
201         int result = 0;
202         switch(get_keypress())
203         {
204                 case UP:
205                         increase_value();
206                         result = 1;
207                         break;
208                 case DOWN:
209                         decrease_value();
210                         result = 1;
211                         break;
212                 case LEFT:
213                         decrease_value();
214                         result = 1;
215                         break;
216                 case RIGHT:
217                         increase_value();
218                         result = 1;
219                         break;
220         }
222         if(result)
223         {
224                 show_value_tooltip();
225                 draw();
226                 handle_event();
227         }
228         return result;
231 int BC_Pot::cursor_enter_event()
233         if(top_level->event_win == win)
234         {
235 // Set caption if no tooltip
236                 tooltip_done = 0;
237                 if(!top_level->button_down && status == POT_UP)
238                 {
239                         status = POT_HIGH;
240                 }
241                 draw();
242         }
243         return 0;
246 int BC_Pot::cursor_leave_event()
248         if(status == POT_HIGH)
249         {
250                 status = POT_UP;
251                 draw();
252                 hide_tooltip();
253         }
254         return 0;
257 int BC_Pot::button_press_event()
259         if(!tooltip_on) top_level->hide_tooltip();
260         if(top_level->event_win == win)
261         {
262                 if(status == POT_HIGH || status == POT_UP)
263                 {
264                         if(get_buttonpress() == 4)
265                         {
266                                 increase_value();
267                                 show_value_tooltip();
268                                 draw();
269                                 handle_event();
270                         }
271                         else
272                         if(get_buttonpress() == 5)
273                         {
274                                 decrease_value();
275                                 show_value_tooltip();
276                                 draw();
277                                 handle_event();
278                         }
279                         else
280                         {
281                                 status = POT_DN;
282                                 start_cursor_angle = coords_to_angle(get_cursor_x(), get_cursor_y());
283                                 start_needle_angle = percentage_to_angle(get_percentage());
284                                 angle_offset = start_cursor_angle - start_needle_angle;
285                                 prev_angle = start_cursor_angle;
286                                 angle_correction = 0;
287                                 draw();
288                                 top_level->deactivate();
289                                 top_level->active_subwindow = this;
290                                 show_value_tooltip();
291                         }
292                         return 1;
293                 }
294         }
295         return 0;
298 int BC_Pot::button_release_event()
300         if(top_level->event_win == win)
301         {
302                 if(status == POT_DN)
303                 {
304                         if(cursor_inside())
305                                 status = POT_HIGH;
306                         else
307                         {
308                                 status = POT_UP;
309                                 top_level->hide_tooltip();
310                         }
311                 }
312                 draw();
313         }
314         return 0;
317 int BC_Pot::cursor_motion_event()
319         if(top_level->button_down && 
320                 top_level->event_win == win && 
321                 status == POT_DN)
322         {
323                 float angle = coords_to_angle(get_cursor_x(), get_cursor_y());
325                 if(prev_angle >= 0 && prev_angle < 90 &&
326                         angle >= 270 && angle < 360)
327                 {
328                         angle_correction -= 360;
329                 }
330                 else
331                 if(prev_angle >= 270 && prev_angle < 360 &&
332                         angle >= 0 && angle < 90)
333                 {
334                         angle_correction += 360;
335                 }
336                 
337                 prev_angle = angle;
339                 if(percentage_to_value(angle_to_percentage(angle + angle_correction - angle_offset)))
340                 {
341                         set_tooltip(get_caption());
342                         draw();
343                         handle_event();
344                 }
345                 return 1;
346         }
347         return 0;
360 BC_FPot::BC_FPot(int x, 
361         int y, 
362         float value, 
363         float minvalue, 
364         float maxvalue, 
365         VFrame **data)
366  : BC_Pot(x, y, data)
368         this->value = value;
369         this->minvalue = minvalue;
370         this->maxvalue = maxvalue;
371         precision = 0.1;
374 BC_FPot::~BC_FPot()
378 int BC_FPot::increase_value()
380         value += precision;
381         if(value > maxvalue) value = maxvalue;
382         return 0;
385 int BC_FPot::decrease_value()
387         value -= precision;
388         if(value < minvalue) value = minvalue;
389         return 0;
392 void BC_FPot::set_precision(float value)
394         this->precision = value;
397 char*  BC_FPot::get_caption()
399         sprintf(caption, "%.2f", value);
400         return caption;
403 float BC_FPot::get_percentage()
405         return (value - minvalue) / (maxvalue - minvalue);
408 int BC_FPot::percentage_to_value(float percentage)
410         float old_value = value;
411         value = percentage * (maxvalue - minvalue) + minvalue;
412         value = Units::quantize(value, precision);
413         if(value < minvalue) value = minvalue;
414         if(value > maxvalue) value = maxvalue;
415         if(value != old_value) return 1;
416         return 0;
419 float BC_FPot::get_value()
421         return value;
424 void BC_FPot::update(float value)
426         if(value != this->value)
427         {
428                 this->value = value;
429                 draw();
430         }
440 BC_IPot::BC_IPot(int x, 
441         int y, 
442         int64_t value, 
443         int64_t minvalue, 
444         int64_t maxvalue, 
445         VFrame **data)
446  : BC_Pot(x, y, data)
448         this->value = value;
449         this->minvalue = minvalue;
450         this->maxvalue = maxvalue;
453 BC_IPot::~BC_IPot()
457 int BC_IPot::increase_value()
459         value++;
460         if(value > maxvalue) value = maxvalue;
461         return 0;
464 int BC_IPot::decrease_value()
466         value--;
467         if(value < minvalue) value = minvalue;
468         return 0;
471 char*  BC_IPot::get_caption()
473         sprintf(caption, "%ld", value);
474         return caption;
477 float BC_IPot::get_percentage()
479         return ((float)value - minvalue) / (maxvalue - minvalue);
482 int BC_IPot::percentage_to_value(float percentage)
484         int64_t old_value = value;
485         value = (int64_t)(percentage * (maxvalue - minvalue) + minvalue);
486         if(value < minvalue) value = minvalue;
487         if(value > maxvalue) value = maxvalue;
488         if(value != old_value) return 1;
489         return 0;
492 int64_t BC_IPot::get_value()
494         return value;
497 void BC_IPot::update(int64_t value)
499         if(this->value != value)
500         {
501                 this->value = value;
502                 draw();
503         }
512 BC_QPot::BC_QPot(int x, 
513         int y, 
514         int64_t value, 
515         VFrame **data)
516  : BC_Pot(x, y, data)
518         this->value = Freq::fromfreq(value);
519         this->minvalue = 0;
520         this->maxvalue = TOTALFREQS;
523 BC_QPot::~BC_QPot()
527 int BC_QPot::increase_value()
529         value++;
530         if(value > maxvalue) value = maxvalue;
531         return 0;
534 int BC_QPot::decrease_value()
536         value--;
537         if(value < minvalue) value = minvalue;
538         return 0;
541 char*  BC_QPot::get_caption()
543         sprintf(caption, "%ld", Freq::tofreq(value));
544         return caption;
547 float BC_QPot::get_percentage()
549         return ((float)value - minvalue) / (maxvalue - minvalue);
552 int BC_QPot::percentage_to_value(float percentage)
554         int64_t old_value = value;
555         value = (int64_t)(percentage * (maxvalue - minvalue) + minvalue);
556         if(value < minvalue) value = minvalue;
557         if(value > maxvalue) value = maxvalue;
558         if(value != old_value) return 1;
559         return 0;
562 int64_t BC_QPot::get_value()
564         return Freq::tofreq(value);
567 void BC_QPot::update(int64_t value)
569         if(this->value != value)
570         {
571                 this->value = Freq::fromfreq(value);
572                 draw();
573         }
583 BC_PercentagePot::BC_PercentagePot(int x, 
584         int y, 
585         float value, 
586         float minvalue, 
587         float maxvalue, 
588         VFrame **data)
589  : BC_Pot(x, y, data)
591         this->value = value;
592         this->minvalue = minvalue;
593         this->maxvalue = maxvalue;
596 BC_PercentagePot::~BC_PercentagePot()
600 int BC_PercentagePot::increase_value()
602         value++;
603         if(value > maxvalue) value = maxvalue;
604         return 0;
607 int BC_PercentagePot::decrease_value()
609         value--;
610         if(value < minvalue) value = minvalue;
611         return 0;
614 char*  BC_PercentagePot::get_caption()
616         sprintf(caption, "%d%%", (int)(get_percentage() * 100 + 0.5));
617         return caption;
620 float BC_PercentagePot::get_percentage()
622         return (value - minvalue) / (maxvalue - minvalue);
625 int BC_PercentagePot::percentage_to_value(float percentage)
627         float old_value = value;
628         value = percentage * (maxvalue - minvalue) + minvalue;
629         if(value < minvalue) value = minvalue;
630         if(value > maxvalue) value = maxvalue;
631         if(value != old_value) return 1;
632         return 0;
635 float BC_PercentagePot::get_value()
637         return value;
640 void BC_PercentagePot::update(float value)
642         if(this->value != value)
643         {
644                 this->value = value;
645                 draw();
646         }