3a2e6cf2ea38877c4c71afedf5b38a613e41c8fc
[goodguy/cinelerra.git] / cinelerra-5.1 / plugins / histogram / histogramwindow.C
1
2 /*
3  * CINELERRA
4  * Copyright (C) 1997-2011 Adam Williams <broadcast at earthling dot net>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  *
20  */
21
22 #include "bcdisplayinfo.h"
23 #include "bcsignals.h"
24 #include "cursors.h"
25 #include "histogram.h"
26 #include "histogramconfig.h"
27 #include "histogramwindow.h"
28 #include "keys.h"
29 #include "language.h"
30 #include "theme.h"
31
32 #include <unistd.h>
33
34
35
36
37 HistogramWindow::HistogramWindow(HistogramMain *plugin)
38  : PluginClientWindow(plugin,
39         plugin->w,
40         plugin->h,
41         xS(440),
42         yS(500),
43         1)
44 {
45         this->plugin = plugin;
46         active_value = 0;
47 }
48
49 HistogramWindow::~HistogramWindow()
50 {
51 }
52
53
54 void HistogramWindow::create_objects()
55 {
56         int margin = plugin->get_theme()->widget_border;
57         int x = margin, y = margin, x1 = margin;
58
59         add_subwindow(mode_v = new HistogramMode(plugin,
60                 x,
61                 y,
62                 HISTOGRAM_VALUE,
63                 _("Value")));
64         x += mode_v->get_w() + margin;
65         add_subwindow(mode_r = new HistogramMode(plugin,
66                 x,
67                 y,
68                 HISTOGRAM_RED,
69                 _("Red")));
70         x += mode_r->get_w() + margin;
71         add_subwindow(mode_g = new HistogramMode(plugin,
72                 x,
73                 y,
74                 HISTOGRAM_GREEN,
75                 _("Green")));
76         x += mode_g->get_w() + margin;
77         add_subwindow(mode_b = new HistogramMode(plugin,
78                 x,
79                 y,
80                 HISTOGRAM_BLUE,
81                 _("Blue")));
82
83
84         x = get_w() - margin - plugin->get_theme()->get_image_set("histogram_rgb_toggle")[0]->get_w();
85         add_subwindow(parade_on = new HistogramParade(plugin,
86                 this,
87                 x,
88                 y,
89                 1));
90         x -= parade_on->get_w() + margin;
91         add_subwindow(parade_off = new HistogramParade(plugin,
92                 this,
93                 x,
94                 y,
95                 0));
96
97
98         x = x1;
99         y += parade_on->get_h() + margin;
100         add_subwindow(canvas_title1 = new BC_Title(margin,
101                 y,
102                 "-10%"));
103         add_subwindow(canvas_title2 = new BC_Title(get_w() - get_text_width(MEDIUMFONT, "110%") - margin,
104                 y,
105                 "110%"));
106
107         y += canvas_title2->get_h() + margin;
108         x = x1;
109         canvas_h = get_h() - y - yS(210);
110
111
112         add_subwindow(low_input_carrot = new HistogramCarrot(plugin,
113                 this,
114                 x,
115                 y + canvas_h));
116
117         x = low_input_carrot->get_w() / 2 + x;
118         canvas_w = get_w() - x - x;
119
120         title1_x = x;
121         title2_x = x + (int)(canvas_w * -HIST_MIN_INPUT / FLOAT_RANGE);
122         title3_x = x + (int)(canvas_w * (1.0 - HIST_MIN_INPUT) / FLOAT_RANGE);
123         title4_x = x + (int)(canvas_w);
124
125
126
127
128
129         add_subwindow(canvas = new HistogramCanvas(plugin,
130                 this,
131                 x,
132                 y,
133                 canvas_w,
134                 canvas_h));
135
136 // Canvas border
137         draw_3d_border(x - 2,
138                 y - 2,
139                 canvas_w + 4,
140                 canvas_h + 4,
141                 get_bg_color(),
142                 BLACK,
143                 MDGREY,
144                 get_bg_color());
145
146 // Calculate output curve with no value function
147         plugin->tabulate_curve(plugin->mode, 0);
148
149         y += canvas->get_h();
150         x = margin;
151
152         add_subwindow(gamma_carrot = new HistogramCarrot(plugin,
153                 this,
154                 canvas->get_x() +
155                         canvas->get_w() / 2 -
156                         low_input_carrot->get_w() / 2 ,
157                 y));
158
159         add_subwindow(high_input_carrot = new HistogramCarrot(plugin,
160                 this,
161                 canvas->get_x() +
162                         canvas->get_w() -
163                         low_input_carrot->get_w() / 2,
164                 y));
165         y += low_input_carrot->get_h() + margin;
166
167
168 //      add_subwindow(title = new BC_Title(x, y, _("Input:")));
169 //      x += title->get_w() + margin;
170         low_input = new HistogramText(plugin, this, x, y);
171         low_input->create_objects();
172
173         x = get_w() / 2 - low_input->get_w() / 2;
174         gamma = new HistogramText(plugin, this, x, y, 0.01, 100.);
175         gamma->create_objects();
176
177         x = get_w() - low_input->get_w() - margin;
178         high_input = new HistogramText(plugin, this, x, y);
179         high_input->create_objects();
180
181         y += high_input->get_h() + margin;
182         x = x1;
183
184         add_subwindow(output = new HistogramSlider(plugin, this,
185                 canvas->get_x(), y, canvas->get_w(), yS(20), 0));
186         output->update();
187
188 // Output border
189         draw_3d_border(output->get_x() - 2, output->get_y() - 2,
190                 output->get_w() + 4, output->get_h() + 4,
191                 get_bg_color(), BLACK, MDGREY, get_bg_color());
192         y += output->get_h();
193
194         add_subwindow(low_output_carrot = new HistogramCarrot(plugin,
195                 this, margin, y));
196
197         add_subwindow(high_output_carrot = new HistogramCarrot(plugin,
198                 this, canvas->get_x() + canvas->get_w() -
199                         low_output_carrot->get_w() / 2, y));
200         y += high_output_carrot->get_h() + margin;
201
202 //      add_subwindow(title = new BC_Title(x, y, _("Output:")));
203 //      x += title->get_w() + margin;
204         low_output = new HistogramText(plugin, this, x, y);
205         low_output->create_objects();
206         high_output = new HistogramText(plugin, this,
207                 get_w() - low_output->get_w() - margin, y);
208         high_output->create_objects();
209
210         x = x1;
211         y += high_output->get_h() + margin;
212
213         add_subwindow(bar = new BC_Bar(x, y, get_w() - margin * 2));
214         y += bar->get_h() + margin;
215
216         add_subwindow(automatic = new HistogramAuto(plugin, x, y));
217
218         //int y1 = y;
219         x = xS(200);
220         add_subwindow(threshold_title = new BC_Title(x, y, _("Threshold:")));
221         x += threshold_title->get_w() + margin;
222         threshold = new HistogramText(plugin, this, x, y);
223         threshold->create_objects();
224
225         x = get_w() / 2;
226         add_subwindow(reset = new HistogramReset(plugin,
227                 x, y + threshold->get_h() + margin));
228
229         x = x1;
230         y += automatic->get_h() + margin;
231         add_subwindow(plot = new HistogramPlot(plugin, x, y));
232
233         y += plot->get_h() + yS(5);
234         add_subwindow(split = new HistogramSplit(plugin, x, y));
235
236         update(1, 1, 1, 1);
237
238         flash(0);
239         show_window();
240 }
241
242
243
244 int HistogramWindow::resize_event(int w, int h)
245 {
246         int xdiff = w - get_w();
247         int ydiff = h - get_h();
248
249         parade_on->reposition_window(parade_on->get_x() + xdiff,
250                 parade_on->get_y());
251         parade_off->reposition_window(parade_off->get_x() + xdiff,
252                 parade_on->get_y());
253         canvas_title2->reposition_window(canvas_title2->get_x() + xdiff,
254                 canvas_title2->get_y());
255
256 // Canvas follows window size
257         canvas_w = canvas_w + xdiff;
258         canvas_h = canvas_h + ydiff;
259         canvas->reposition_window(canvas->get_x(),
260                 canvas->get_y(),
261                 canvas_w,
262                 canvas_h);
263
264 // Canvas border
265         draw_3d_border(canvas->get_x() - 2,
266                 canvas->get_y() - 2,
267                 canvas_w + 4,
268                 canvas_h + 4,
269                 get_bg_color(),
270                 BLACK,
271                 MDGREY,
272                 get_bg_color());
273
274         low_input_carrot->reposition_window(low_input_carrot->get_x(),
275                 low_input_carrot->get_y() + ydiff);
276         gamma_carrot->reposition_window(gamma_carrot->get_x(),
277                 gamma_carrot->get_y() + ydiff);
278         high_input_carrot->reposition_window(high_input_carrot->get_x(),
279                 high_input_carrot->get_y() + ydiff);
280
281         low_input->reposition_window(low_input->get_x(),
282                 low_input->get_y() + ydiff);
283         gamma->reposition_window(w / 2 - gamma->get_w() / 2,
284                 gamma->get_y() + ydiff);
285         high_input->reposition_window(high_input->get_x() + xdiff,
286                 low_input->get_y() + ydiff);
287
288         output->reposition_window(output->get_x(),
289                 output->get_y() + ydiff,
290                 output->get_w() + xdiff,
291                 output->get_h());
292         output->update();
293
294 // Output border
295         draw_3d_border(output->get_x() - 2,
296                 output->get_y() - 2,
297                 output->get_w() + 4,
298                 output->get_h() + 4,
299                 get_bg_color(),
300                 BLACK,
301                 MDGREY,
302                 get_bg_color());
303
304         low_output_carrot->reposition_window(low_output_carrot->get_x(),
305                 low_output_carrot->get_y() + ydiff);
306         high_output_carrot->reposition_window(high_output_carrot->get_x(),
307                 high_output_carrot->get_y() + ydiff);
308
309         low_output->reposition_window(low_output->get_x(),
310                 low_output->get_y() + ydiff);
311         high_output->reposition_window(high_output->get_x() + xdiff,
312                 high_output->get_y() + ydiff);
313
314         bar->reposition_window(bar->get_x(),
315                 bar->get_y() + ydiff,
316                 bar->get_w() + xdiff);
317
318         automatic->reposition_window(automatic->get_x(),
319                 automatic->get_y() + ydiff);
320         threshold_title->reposition_window(threshold_title->get_x(),
321                 threshold_title->get_y() + ydiff);
322         threshold->reposition_window(threshold->get_x(),
323                 threshold->get_y() + ydiff);
324         reset->reposition_window(reset->get_x(),
325                 reset->get_y() + ydiff);
326
327         plot->reposition_window(plot->get_x(),
328                 plot->get_y() + ydiff);
329         split->reposition_window(split->get_x(),
330                 split->get_y() + ydiff);
331
332         update(1, 1, 1, 1);
333
334         plugin->w = w;
335         plugin->h = h;
336         flash();
337         return 1;
338 }
339
340
341
342 int HistogramWindow::keypress_event()
343 {
344         int result = 0;
345
346         if(active_value)
347         {
348                 float sign = 1;
349                 for(int i = 0; i < HISTOGRAM_MODES; i++)
350                 {
351                         if(active_value == &plugin->config.gamma[i])
352                                 sign = -1;
353                 }
354
355                 if(get_keypress() == RIGHT || get_keypress() == UP)
356                 {
357                         *active_value += sign * PRECISION;
358                         plugin->config.boundaries();
359                         update(1, 1, 1, 0);
360                         plugin->send_configure_change();
361                         return 1;
362                 }
363                 else
364                 if(get_keypress() == LEFT || get_keypress() == DOWN)
365                 {
366                         *active_value -= sign * PRECISION;
367                         plugin->config.boundaries();
368                         update(1, 1, 1, 0);
369                         plugin->send_configure_change();
370                         return 1;
371                 }
372         }
373
374         return result;
375 }
376
377 void HistogramWindow::update(int do_canvases,
378         int do_carrots,
379         int do_text,
380         int do_toggles)
381 {
382         if(do_toggles)
383         {
384                 automatic->update(plugin->config.automatic);
385                 mode_v->update(plugin->mode == HISTOGRAM_VALUE ? 1 : 0);
386                 mode_r->update(plugin->mode == HISTOGRAM_RED ? 1 : 0);
387                 mode_g->update(plugin->mode == HISTOGRAM_GREEN ? 1 : 0);
388                 mode_b->update(plugin->mode == HISTOGRAM_BLUE ? 1 : 0);
389                 plot->update(plugin->config.plot);
390                 split->update(plugin->config.split);
391                 parade_on->update(plugin->parade ? 1 : 0);
392                 parade_off->update(plugin->parade ? 0 : 1);
393                 output->update();
394         }
395
396         if(do_canvases)
397         {
398                 update_canvas();
399         }
400
401         if(do_carrots)
402         {
403                 low_input_carrot->update();
404                 high_input_carrot->update();
405                 gamma_carrot->update();
406                 low_output_carrot->update();
407                 high_output_carrot->update();
408         }
409
410         if(do_text)
411         {
412                 low_input->update();
413                 gamma->update();
414                 high_input->update();
415                 low_output->update();
416                 high_output->update();
417                 threshold->update();
418         }
419
420
421 }
422
423
424 void HistogramWindow::draw_canvas_mode(int mode, int color, int y, int h)
425 {
426         int *accum = plugin->accum[mode];
427         int accum_per_canvas_i = HISTOGRAM_SLOTS / canvas_w + 1;
428         float accum_per_canvas_f = (float)HISTOGRAM_SLOTS / canvas_w;
429         int normalize = 0;
430         int max = 0;
431
432
433 // Draw histogram
434         for(int i = 0; i < HISTOGRAM_SLOTS; i++)
435         {
436                 if(accum && accum[i] > normalize) normalize = accum[i];
437         }
438
439
440         if(normalize)
441         {
442                 for(int i = 0; i < canvas_w; i++)
443                 {
444                         int accum_start = (int)(accum_per_canvas_f * i);
445                         int accum_end = accum_start + accum_per_canvas_i;
446                         max = 0;
447                         for(int j = accum_start; j < accum_end; j++)
448                         {
449                                 max = MAX(accum[j], max);
450                         }
451
452 //                      max = max * h / normalize;
453                         max = (int)(log(max) / log(normalize) * h);
454
455                         canvas->set_color(BLACK);
456                         canvas->draw_line(i, y, i, y + h - max);
457                         canvas->set_color(color);
458                         canvas->draw_line(i, y + h - max, i, y + h);
459                 }
460         }
461         else
462         {
463                 canvas->set_color(BLACK);
464                 canvas->draw_box(0, y, canvas_w, h);
465         }
466
467 // Draw overlays
468         canvas->set_color(WHITE);
469         canvas->set_line_width(2);
470         int y1 = 0;
471
472 // Draw output line
473         for(int i = 0; i < canvas_w; i++)
474         {
475                 float input = (float)i /
476                                 canvas_w *
477                                 FLOAT_RANGE +
478                                 HIST_MIN_INPUT;
479                 float output = plugin->calculate_level(input,
480                         mode,
481                         0);
482
483                 int y2 = h - (int)(output * h);
484                 if(i > 0)
485                 {
486                         canvas->draw_line(i - 1, y + y1, i, y + y2);
487                 }
488                 y1 = y2;
489         }
490
491         canvas->set_line_width(1);
492
493 }
494
495
496 void HistogramWindow::update_canvas()
497 {
498         if(plugin->parade)
499         {
500                 draw_canvas_mode(HISTOGRAM_RED, RED, 0, canvas_h / 3);
501                 draw_canvas_mode(HISTOGRAM_GREEN, GREEN, canvas_h / 3, canvas_h / 3);
502                 draw_canvas_mode(HISTOGRAM_BLUE, BLUE, canvas_h * 2 / 3, canvas_h - canvas_h * 2 / 3);
503         }
504         else
505         {
506                 draw_canvas_mode(plugin->mode, MEGREY, 0, canvas_h);
507         }
508
509
510 // Draw 0 and 100% lines.
511         canvas->set_color(RED);
512         int x = (int)(canvas_w * -HIST_MIN_INPUT / FLOAT_RANGE);
513         canvas->draw_line(x,
514                 0,
515                 x,
516                 canvas_h);
517         x = (int)(canvas_w * (1.0 - HIST_MIN_INPUT) / FLOAT_RANGE);
518         canvas->draw_line(x,
519                 0,
520                 x,
521                 canvas_h);
522         canvas->flash();
523 }
524
525
526
527
528 HistogramParade::HistogramParade(HistogramMain *plugin,
529         HistogramWindow *gui,
530         int x,
531         int y,
532         int value)
533  : BC_Toggle(x,
534         y,
535         value ? plugin->get_theme()->get_image_set("histogram_rgb_toggle") :
536                 plugin->get_theme()->get_image_set("histogram_toggle"),
537         0)
538 {
539         this->plugin = plugin;
540         this->gui = gui;
541         this->value = value;
542         if(value)
543                 set_tooltip(_("RGB Parade on"));
544         else
545                 set_tooltip(_("RGB Parade off"));
546 }
547
548 int HistogramParade::handle_event()
549 {
550         update(1);
551         plugin->parade = value;
552         gui->update(1,
553                 0,
554                 0,
555                 1);
556         return 1;
557 }
558
559
560
561
562
563
564
565 HistogramCanvas::HistogramCanvas(HistogramMain *plugin,
566         HistogramWindow *gui,
567         int x,
568         int y,
569         int w,
570         int h)
571  : BC_SubWindow(x,
572         y,
573         w,
574         h,
575         BLACK)
576 {
577         this->plugin = plugin;
578         this->gui = gui;
579 }
580
581 int HistogramCanvas::button_press_event()
582 {
583         int result = 0;
584         if(is_event_win() && cursor_inside())
585         {
586                 if(!plugin->dragging_point &&
587                         (!plugin->config.automatic || plugin->mode == HISTOGRAM_VALUE))
588                 {
589                         gui->deactivate();
590                 }
591         }
592         return result;
593 }
594
595 int HistogramCanvas::cursor_motion_event()
596 {
597         if(is_event_win() && cursor_inside())
598         {
599         }
600         return 0;
601 }
602
603 int HistogramCanvas::button_release_event()
604 {
605         return 0;
606 }
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621 HistogramReset::HistogramReset(HistogramMain *plugin,
622         int x,
623         int y)
624  : BC_GenericButton(x, y, _("Reset"))
625 {
626         this->plugin = plugin;
627 }
628 int HistogramReset::handle_event()
629 {
630         plugin->config.reset(0);
631         ((HistogramWindow*)plugin->thread->window)->update(1, 1, 1, 1);
632         plugin->send_configure_change();
633         return 1;
634 }
635
636
637
638
639
640
641
642 HistogramCarrot::HistogramCarrot(HistogramMain *plugin,
643         HistogramWindow *gui,
644         int x,
645         int y)
646  : BC_Toggle(x,
647         y,
648         plugin->get_theme()->get_image_set("histogram_carrot"),
649         0)
650 {
651         this->plugin = plugin;
652         this->gui = gui;
653         drag_operation = 0;
654 }
655
656 HistogramCarrot::~HistogramCarrot()
657 {
658 }
659
660 float* HistogramCarrot::get_value()
661 {
662         if(this == gui->low_input_carrot)
663         {
664                 return &plugin->config.low_input[plugin->mode];
665         }
666         else
667         if(this == gui->high_input_carrot)
668         {
669                 return &plugin->config.high_input[plugin->mode];
670         }
671         else
672         if(this == gui->gamma_carrot)
673         {
674                 return &plugin->config.gamma[plugin->mode];
675         }
676         else
677         if(this == gui->low_output_carrot)
678         {
679                 return &plugin->config.low_output[plugin->mode];
680         }
681         else
682         if(this == gui->high_output_carrot)
683         {
684                 return &plugin->config.high_output[plugin->mode];
685         }
686         return 0;
687 }
688
689 void HistogramCarrot::update()
690 {
691         int new_x = 0;
692         float *value = get_value();
693
694         if(this != gui->gamma_carrot)
695         {
696                 new_x = (int)(gui->canvas->get_x() +
697                         (*value - HIST_MIN_INPUT) *
698                         gui->canvas->get_w() /
699                         (HIST_MAX_INPUT - HIST_MIN_INPUT) -
700                         get_w() / 2);
701         }
702         else
703         {
704                 float min = plugin->config.low_input[plugin->mode];
705                 float max = plugin->config.high_input[plugin->mode];
706                 float delta = (max - min) / 2.0;
707                 float mid = min + delta;
708                 float tmp = log10(1.0 / *value);
709                 tmp = mid + delta * tmp;
710
711 //printf("HistogramCarrot::update %d %f %f\n", __LINE__, *value, tmp);
712
713                         new_x = gui->canvas->get_x() -
714                                 get_w() / 2 +
715                                 (int)(gui->canvas->get_w() *
716                                 (tmp - HIST_MIN_INPUT) /
717                                 (HIST_MAX_INPUT - HIST_MIN_INPUT));
718         }
719
720         reposition_window(new_x, get_y());
721 }
722
723 int HistogramCarrot::button_press_event()
724 {
725         if(is_event_win() && get_buttonpress() == 1)
726         {
727                 //int w = get_w();
728                 gui->deactivate();
729                 set_status(BC_Toggle::TOGGLE_DOWN);
730
731                 BC_Toggle::update(0);
732                 gui->active_value = get_value();
733 // Disable the other toggles
734                 if(this != gui->low_input_carrot) gui->low_input_carrot->BC_Toggle::update(0);
735                 if(this != gui->high_input_carrot) gui->high_input_carrot->BC_Toggle::update(0);
736                 if(this != gui->gamma_carrot) gui->gamma_carrot->BC_Toggle::update(0);
737                 if(this != gui->low_output_carrot) gui->low_output_carrot->BC_Toggle::update(0);
738                 if(this != gui->high_output_carrot) gui->high_output_carrot->BC_Toggle::update(0);
739                 starting_x = get_x();
740                 offset_x = gui->get_relative_cursor_x();
741                 offset_y = gui->get_relative_cursor_y();
742 //printf("HistogramCarrot::button_press_event %d %d %d\n", __LINE__, starting_x, offset_x);
743                 drag_operation = 1;
744                 draw_face(1, 1);
745                 return 1;
746         }
747         return 0;
748 }
749
750 int HistogramCarrot::button_release_event()
751 {
752         int result = BC_Toggle::button_release_event();
753         handle_event();
754         drag_operation = 0;
755         return result;
756 }
757
758 int HistogramCarrot::cursor_motion_event()
759 {
760         int cursor_x = gui->get_relative_cursor_x();
761
762         if(drag_operation)
763         {
764 //printf("HistogramCarrot::cursor_motion_event %d %d\n", __LINE__, cursor_x);
765                 int new_x = starting_x + cursor_x - offset_x;
766
767 // Clamp x
768 // Get level from x
769                 float *value = get_value();
770                 if(this == gui->gamma_carrot)
771                 {
772                         float min = gui->low_input_carrot->get_x();
773                         float max = gui->high_input_carrot->get_x();
774                         float delta = (max - min) / 2.0;
775                         if(delta >= 0.5)
776                         {
777                                 float mid = min + delta;
778                                 float tmp = (float)(new_x - mid) /
779                                         delta;
780                                 tmp = 1.0 / pow(10, tmp);
781                                 CLAMP(tmp, MIN_GAMMA, MAX_GAMMA);
782                                 *value = tmp;
783 //printf("HistogramCarrot::update %d %f\n", __LINE__, tmp);
784                         }
785                 }
786                 else
787                 {
788                         int min_x = gui->canvas->get_x() - get_w() / 2;
789                         int max_x = gui->canvas->get_x() + gui->canvas->get_w() - get_w() / 2;
790                         CLAMP(new_x, min_x, max_x);
791                         *value = HIST_MIN_INPUT +
792                                 (HIST_MAX_INPUT - HIST_MIN_INPUT) *
793                                 (new_x - min_x) /
794                                 (max_x - min_x);
795                 }
796
797                 reposition_window(new_x, get_y());
798                 flush();
799
800                 gui->update(1,
801                         (this == gui->low_input_carrot || this == gui->high_input_carrot),
802                         1,
803                         0);
804                 plugin->send_configure_change();
805
806                 return 1;
807         }
808         return 0;
809 }
810
811
812
813
814
815
816
817
818 HistogramSlider::HistogramSlider(HistogramMain *plugin,
819         HistogramWindow *gui,
820         int x,
821         int y,
822         int w,
823         int h,
824         int is_input)
825  : BC_SubWindow(x, y, w, h)
826 {
827         this->plugin = plugin;
828         this->gui = gui;
829         this->is_input = is_input;
830         operation = NONE;
831 }
832
833 int HistogramSlider::input_to_pixel(float input)
834 {
835         return (int)((input - HIST_MIN_INPUT) / FLOAT_RANGE * get_w());
836 }
837
838 void HistogramSlider::update()
839 {
840         int w = get_w();
841         int h = get_h();
842         //int half_h = get_h() / 2;
843         //int quarter_h = get_h() / 4;
844         int mode = plugin->mode;
845         int r = 0xff;
846         int g = 0xff;
847         int b = 0xff;
848
849         clear_box(0, 0, w, h);
850
851         switch(mode)
852         {
853                 case HISTOGRAM_RED:
854                         g = b = 0x00;
855                         break;
856                 case HISTOGRAM_GREEN:
857                         r = b = 0x00;
858                         break;
859                 case HISTOGRAM_BLUE:
860                         r = g = 0x00;
861                         break;
862         }
863
864         for(int i = 0; i < w; i++)
865         {
866                 int color = (int)(i * 0xff / w);
867                 set_color(((r * color / 0xff) << 16) |
868                         ((g * color / 0xff) << 8) |
869                         (b * color / 0xff));
870
871                 draw_line(i, 0, i, h);
872         }
873
874
875         flash();
876 }
877
878
879
880
881
882
883
884
885
886 HistogramAuto::HistogramAuto(HistogramMain *plugin,
887         int x,
888         int y)
889  : BC_CheckBox(x, y, plugin->config.automatic, _("Automatic"))
890 {
891         this->plugin = plugin;
892 }
893
894 int HistogramAuto::handle_event()
895 {
896         plugin->config.automatic = get_value();
897         plugin->send_configure_change();
898         return 1;
899 }
900
901
902
903
904 HistogramPlot::HistogramPlot(HistogramMain *plugin,
905         int x,
906         int y)
907  : BC_CheckBox(x, y, plugin->config.plot, _("Plot histogram"))
908 {
909         this->plugin = plugin;
910 }
911
912 int HistogramPlot::handle_event()
913 {
914         plugin->config.plot = get_value();
915         plugin->send_configure_change();
916         return 1;
917 }
918
919
920
921
922 HistogramSplit::HistogramSplit(HistogramMain *plugin,
923         int x,
924         int y)
925  : BC_CheckBox(x, y, plugin->config.split, _("Split output"))
926 {
927         this->plugin = plugin;
928 }
929
930 int HistogramSplit::handle_event()
931 {
932         plugin->config.split = get_value();
933         plugin->send_configure_change();
934         return 1;
935 }
936
937
938
939 HistogramMode::HistogramMode(HistogramMain *plugin,
940         int x,
941         int y,
942         int value,
943         char *text)
944  : BC_Radial(x, y, plugin->mode == value, text)
945 {
946         this->plugin = plugin;
947         this->value = value;
948 }
949 int HistogramMode::handle_event()
950 {
951         HistogramWindow *gui = (HistogramWindow*)plugin->thread->window;
952         plugin->mode = value;
953         plugin->current_point= -1;
954         gui->active_value = 0;
955         gui->low_input_carrot->BC_Toggle::update(0);
956         gui->gamma_carrot->BC_Toggle::update(0);
957         gui->high_input_carrot->BC_Toggle::update(0);
958         gui->low_output_carrot->BC_Toggle::update(0);
959         gui->high_output_carrot->BC_Toggle::update(0);
960         gui->update(1, 1, 1, 1);
961 //      plugin->send_configure_change();
962         return 1;
963 }
964
965
966
967
968
969
970
971
972
973
974 HistogramText::HistogramText(HistogramMain *plugin,
975         HistogramWindow *gui, int x, int y, float hist_min, float hist_max)
976  : BC_TumbleTextBox(gui, 0.0, hist_min, hist_max, x, y, xS(70))
977 {
978         this->plugin = plugin;
979         this->gui = gui;
980         set_precision(DIGITS);
981         set_increment(PRECISION);
982 }
983
984 float* HistogramText::get_value()
985 {
986         if(this == gui->low_input)
987         {
988                 return &plugin->config.low_input[plugin->mode];
989         }
990         else
991         if(this == gui->high_input)
992         {
993                 return &plugin->config.high_input[plugin->mode];
994         }
995         else
996         if(this == gui->gamma)
997         {
998                 return &plugin->config.gamma[plugin->mode];
999         }
1000         else
1001         if(this == gui->low_output)
1002         {
1003                 return &plugin->config.low_output[plugin->mode];
1004         }
1005         else
1006         if(this == gui->high_output)
1007         {
1008                 return &plugin->config.high_output[plugin->mode];
1009         }
1010         else
1011         if(this == gui->threshold)
1012         {
1013                 return &plugin->config.threshold;
1014         }
1015
1016         return 0;
1017 }
1018
1019 int HistogramText::handle_event()
1020 {
1021         float *output = get_value();
1022         if(output)
1023         {
1024                 *output = atof(get_text());
1025         }
1026
1027         gui->update(1, 1, 0, 0);
1028         plugin->send_configure_change();
1029         return 1;
1030 }
1031
1032 void HistogramText::update()
1033 {
1034         float *output = get_value();
1035         if(output)
1036         {
1037                 BC_TumbleTextBox::update(*output);
1038         }
1039 }
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054