colorpicker upgrades, titler fixes
authorGood Guy <[email protected]>
Sun, 5 Mar 2017 01:05:30 +0000 (18:05 -0700)
committerGood Guy <[email protected]>
Sun, 5 Mar 2017 01:05:30 +0000 (18:05 -0700)
18 files changed:
cinelerra-5.1/cinelerra/colorpicker.C
cinelerra-5.1/cinelerra/colorpicker.h
cinelerra-5.1/cinelerra/grabpick_dn.png [new file with mode: 0644]
cinelerra-5.1/cinelerra/grabpick_dn_png.h [new file with mode: 0644]
cinelerra-5.1/cinelerra/grabpick_hi.png [new file with mode: 0644]
cinelerra-5.1/cinelerra/grabpick_hi_png.h [new file with mode: 0644]
cinelerra-5.1/cinelerra/grabpick_up.png [new file with mode: 0644]
cinelerra-5.1/cinelerra/grabpick_up_png.h [new file with mode: 0644]
cinelerra-5.1/cinelerra/pluginclient.C
cinelerra-5.1/cinelerra/pluginclient.h
cinelerra-5.1/guicast/bcbutton.C
cinelerra-5.1/guicast/bctextbox.C
cinelerra-5.1/guicast/bctextbox.h
cinelerra-5.1/guicast/bcwindowbase.C
cinelerra-5.1/guicast/bcwindowbase.h
cinelerra-5.1/plugins/titler/titler.C
cinelerra-5.1/plugins/titler/titlerwindow.C
cinelerra-5.1/plugins/titler/titlerwindow.h

index b3befe77f387bdc50fa4dc0d8b7a570fb6af5c52..969e8c98ce6d870f643e32d1d5d0e4dacbd905fc 100644 (file)
  *
  */
 
+#include "bcbutton.h"
+#include "bccapture.h"
 #include "bcdisplayinfo.h"
 #include "colorpicker.h"
 #include "condition.h"
 #include "language.h"
 #include "mutex.h"
-#include "mwindow.inc"
+#include "mwindow.h"
 #include "cicolors.h"
 #include "vframe.h"
 
 #include <string.h>
 #include <unistd.h>
 
+#define PALETTE_DATA "palette.dat"
 
 ColorThread::ColorThread(int do_alpha, const char *title)
  : BC_DialogThread()
@@ -72,9 +75,7 @@ BC_Window* ColorThread::new_gui()
        BC_DisplayInfo display_info;
        int x = display_info.get_abs_cursor_x() + 25;
        int y = display_info.get_abs_cursor_y() - 100;
-       int w = 540, h = 290;
-       if( do_alpha )
-               h += 40 + PalletteAPH::calculate_h();
+       int w = 540, h = 330;
        if( do_okcancel )
                h += bmax(BC_OKButton::calculate_h(),BC_CancelButton::calculate_h());
        int root_w = display_info.get_root_w(), root_h = display_info.get_root_h();
@@ -123,6 +124,8 @@ ColorWindow::ColorWindow(ColorThread *thread, int x, int y, int w, int h, const
        rgb_r = 0;  rgb_g = 0;  rgb_b = 0;
        yuv_y = 0;  yuv_u = 0;  yuv_v = 0;
        aph_a = 0;
+
+       button_grabbed = 0;
 }
 ColorWindow::~ColorWindow()
 {
@@ -130,6 +133,9 @@ ColorWindow::~ColorWindow()
        delete rgb_r;  delete rgb_g;  delete rgb_b;
        delete yuv_y;  delete yuv_u;  delete yuv_v;
        delete aph_a;
+
+       update_history(rgb888());
+       save_history();
 }
 
 void ColorWindow::create_objects()
@@ -149,6 +155,16 @@ void ColorWindow::create_objects()
        output->create_objects();
        y += output->get_h() + 20;
 
+       load_history();  int x1 = x;
+       add_tool(hex_btn = new PaletteHexButton(this, x1, y));
+       char hex[BCSTRLEN];  sprintf(hex,"%06x",thread->output);
+       x1 += hex_btn->get_w() + 5;
+       add_tool(hex_box = new PaletteHex(this, x1, y, hex));
+       x1 += hex_box->get_w() + 15;
+       add_tool(grab_btn = new PaletteGrabButton(this, x1, y));
+       y += hex_box->get_h() + 15;
+       add_tool(history = new PaletteHistory(this, 10, y));
+
        x += 240;
        add_tool(new BC_Title(x, y =y0, _("H:"), SMALLFONT));
        add_tool(new BC_Title(x, y+=25, _("S:"), SMALLFONT));
@@ -175,17 +191,27 @@ void ColorWindow::create_objects()
                add_tool(alpha = new PaletteAlpha(this, x, y+=40));
 
        x += hue->get_w() + 10;
-       hsv_h = new PalletteHSV(this, x,y= y0, hsv.h, 0, 360);  hsv_h->create_objects();
-       hsv_s = new PalletteHSV(this, x,y+=25, hsv.s, 0, 1);    hsv_s->create_objects();
-       hsv_v = new PalletteHSV(this, x,y+=25, hsv.v, 0, 1);    hsv_v->create_objects();
-       rgb_r = new PalletteRGB(this, x,y+=40, rgb.r, 0, 1);    rgb_r->create_objects();
-       rgb_g = new PalletteRGB(this, x,y+=25, rgb.g, 0, 1);    rgb_g->create_objects();
-       rgb_b = new PalletteRGB(this, x,y+=25, rgb.b, 0, 1);    rgb_b->create_objects();
-       yuv_y = new PalletteYUV(this, x,y+=40, yuv.y, 0, 1);    yuv_y->create_objects();
-       yuv_u = new PalletteYUV(this, x,y+=25, yuv.u, 0, 1);    yuv_u->create_objects();
-       yuv_v = new PalletteYUV(this, x,y+=25, yuv.v, 0, 1);    yuv_v->create_objects();
+       hsv_h = new PaletteHSV(this, x,y= y0, hsv.h, 0, 360);
+       hsv_h->create_objects();  hsv_h->set_tooltip(_("Hue"));
+       hsv_s = new PaletteHSV(this, x,y+=25, hsv.s, 0, 1);
+       hsv_s->create_objects();  hsv_s->set_tooltip(_("Saturation"));
+       hsv_v = new PaletteHSV(this, x,y+=25, hsv.v, 0, 1);
+       hsv_v->create_objects();  hsv_v->set_tooltip(_("Value"));
+       rgb_r = new PaletteRGB(this, x,y+=40, rgb.r, 0, 1);
+       rgb_r->create_objects();  rgb_r->set_tooltip(_("Red"));
+       rgb_g = new PaletteRGB(this, x,y+=25, rgb.g, 0, 1);
+       rgb_g->create_objects();  rgb_g->set_tooltip(_("Green"));
+       rgb_b = new PaletteRGB(this, x,y+=25, rgb.b, 0, 1);
+       rgb_b->create_objects();  rgb_b->set_tooltip(_("Blue"));
+       yuv_y = new PaletteYUV(this, x,y+=40, yuv.y, 0, 1);
+       yuv_y->create_objects();  yuv_y->set_tooltip(_("Luminance"));
+       yuv_u = new PaletteYUV(this, x,y+=25, yuv.u, 0, 1);
+       yuv_u->create_objects();  yuv_u->set_tooltip(_("Compliment Red"));
+       yuv_v = new PaletteYUV(this, x,y+=25, yuv.v, 0, 1);
+       yuv_v->create_objects();  yuv_v->set_tooltip(_("Compliment Blue"));
        if( thread->do_alpha ) {
-               aph_a = new PalletteAPH(this, x,y+=40, aph, 0, 1); aph_a->create_objects();
+               aph_a = new PaletteAPH(this, x,y+=40, aph, 0, 1);
+               aph_a->create_objects();  aph_a->set_tooltip(_("Alpha"));
        }
        if( thread->do_okcancel ) {
                add_tool(new BC_OKButton(this));
@@ -193,6 +219,7 @@ void ColorWindow::create_objects()
        }
 
        update_display();
+       update_history();
        show_window(1);
        unlock_window();
 }
@@ -265,18 +292,49 @@ void ColorWindow::update_display()
        yuv_y->update(yuv.y);
        yuv_u->update(yuv.u);
        yuv_v->update(yuv.v);
+       hex_box->update();
+
        if( thread->do_alpha )
                aph_a->update(aph);
 }
 
 int ColorWindow::handle_event()
 {
-       int r = 255*rgb.r + 0.5, g = 255*rgb.g + 0.5, b = 255*rgb.b + 0.5;
-       int result = (r << 16) | (g << 8) | (b << 0);
-       thread->handle_new_color(result, (int)(255*aph + 0.5));
+       thread->handle_new_color(rgb888(), (int)(255*aph + 0.5));
        return 1;
 }
 
+int ColorWindow::button_press_event()
+{
+       if( button_grabbed ) {
+               grab_cursor();
+       }
+       return 0;
+}
+int ColorWindow::button_release_event()
+{
+       if( button_grabbed ) {
+               grab_btn->disable();
+               grab_btn->enable();
+               ungrab_buttons();
+               ungrab_cursor();
+               button_grabbed = 0;
+               int cx, cy;
+               get_abs_cursor_xy(cx, cy);
+//printf("grabbed button %d,%d\n",cx,cy);
+               BC_Capture capture_bitmap(1, 1, 0);
+               VFrame vframe(1,1,BC_RGB888);
+               capture_bitmap.capture_frame(&vframe, cx,cy);
+               unsigned char *data = vframe.get_data();
+               rgb.r = data[0]/255.;  rgb.g = data[1]/255.;  rgb.b = data[2]/255.;
+               update_rgb();
+               update_display();
+               update_history();
+               return handle_event();
+       }
+       return 0;
+}
+
 
 PaletteWheel::PaletteWheel(ColorWindow *window, int x, int y)
  : BC_SubWindow(x, y, 170, 170)
@@ -584,10 +642,7 @@ int PaletteOutput::handle_event()
 
 int PaletteOutput::draw()
 {
-       int r = 255*window->rgb.r + 0.5f;
-       int g = 255*window->rgb.g + 0.5f;
-       int b = 255*window->rgb.b + 0.5f;
-       set_color((r << 16) | (g << 8) | (b << 0));
+       set_color(window->rgb888());
        draw_box(2, 2, get_w() - 4, get_h() - 4);
        draw_3d_border(0, 0, get_w(), get_h(), 1);
        return 0;
@@ -777,7 +832,7 @@ void ColorWindow::update_rgb(float r, float g, float b)
 {
        { float y, u, v;
        YUV::rgb_to_yuv_f(r, g, b, y, u, v);
-       u += 0.5f;  v += 0.5f;
+       u += 0.5;  v += 0.5;
        bclamp(y, 0, 1);    yuv.y = y;
        bclamp(u, 0, 1);    yuv.u = u;
        bclamp(v, 0, 1);    yuv.v = v; }
@@ -790,7 +845,7 @@ void ColorWindow::update_rgb(float r, float g, float b)
 
 void ColorWindow::update_yuv(float y, float u, float v)
 {
-       u -= 0.5f;  v -= 0.5f;
+       u -= 0.5;  v -= 0.5;
        { float r, g, b;
        YUV::yuv_to_rgb_f(r, g, b, y, u, v);
        bclamp(r, 0, 1);   rgb.r = r;
@@ -812,13 +867,77 @@ void ColorWindow::update_hsv(float h, float s, float v)
        bclamp(b, 0, 1);   rgb.b = b;
        float y, u, v;
        YUV::rgb_to_yuv_f(r, g, b, y, u, v);
-       u += 0.5f;  v += 0.5f;
+       u += 0.5;  v += 0.5;
        bclamp(y, 0, 1);   yuv.y = y;
        bclamp(u, 0, 1);   yuv.u = u;
        bclamp(v, 0, 1);   yuv.v = v; }
 }
 
-PalletteNum::PalletteNum(ColorWindow *window, int x, int y,
+void ColorWindow::load_history()
+{
+       char history_path[BCTEXTLEN];
+       MWindow::create_defaults_path(history_path,PALETTE_DATA);
+       FILE *fp = fopen(history_path,"r");
+       int i=0;
+       if( fp ) {
+               while( i < PALLETTE_HISTORY_SIZE ) {
+                       char line[BCSTRLEN];
+                       if( !fgets(line,sizeof(line)-1,fp) ) break;
+                       line[sizeof(line)-1] = 0;
+                       if( sscanf(line, "%x",&palette_history[i]) != 1 ) break;
+                       ++i;
+               }
+               fclose(fp);
+       }
+       int r = 0, g = 0, b = 0;
+       float v0 = 0, v1 = 1;
+       while( i < PALLETTE_HISTORY_SIZE ) {
+               int grey_code = i ^ (i>>1);
+               r = 255 * ((grey_code&4) ? v0 : v1);
+               g = 255 * ((grey_code&2) ? v0 : v1);
+               b = 255 * ((grey_code&1) ? v0 : v1);
+               int color = (r<<16) | (g<<8) | (b<<0);
+               palette_history[i++] = color;
+               if( i & 7 ) continue;
+               v0 = 0.5f * (v0+.5f);
+               v1 = 0.5f * (v1+.5f);
+       }
+}
+void ColorWindow::save_history()
+{
+       char history_path[BCTEXTLEN];
+       MWindow::create_defaults_path(history_path,PALETTE_DATA);
+       FILE *fp = fopen(history_path,"w");
+       if( fp ) {
+               for( int i=0; i<PALLETTE_HISTORY_SIZE; ++i ) {
+                       fprintf(fp, "%06x\n", palette_history[i]);
+               }
+               fclose(fp);
+       }
+}
+void ColorWindow::update_history(int color)
+{
+       int out = palette_history[0];
+       palette_history[0] = color;
+       for( int i=1; out != color && i<PALLETTE_HISTORY_SIZE; ++i ) {
+               int in = out;
+               out = palette_history[i];
+               palette_history[i] = in;
+       }
+}
+void ColorWindow::update_history()
+{
+       update_history(rgb888());
+       history->update(0);
+}
+int ColorWindow::rgb888()
+{
+       int r = 255*rgb.r + 0.5, g = 255*rgb.g + 0.5, b = 255*rgb.b + 0.5;
+       bclamp(r, 0, 255);  bclamp(g, 0, 255);  bclamp(b, 0, 255);
+       return (r<<16) | (g<<8) | (b<<0);
+}
+
+PaletteNum::PaletteNum(ColorWindow *window, int x, int y,
        float &output, float min, float max)
  : BC_TumbleTextBox(window, output, min, max, x, y, 64)
 {
@@ -828,12 +947,12 @@ PalletteNum::PalletteNum(ColorWindow *window, int x, int y,
        set_precision(2);
 }
 
-PalletteNum::~PalletteNum()
+PaletteNum::~PaletteNum()
 {
 }
 
 
-int PalletteHSV::handle_event()
+int PaletteHSV::handle_event()
 {
        update_output();
        window->update_hsv();
@@ -842,7 +961,7 @@ int PalletteHSV::handle_event()
        return 1;
 }
 
-int PalletteRGB::handle_event()
+int PaletteRGB::handle_event()
 {
        update_output();
        window->update_rgb();
@@ -851,7 +970,7 @@ int PalletteRGB::handle_event()
        return 1;
 }
 
-int PalletteYUV::handle_event()
+int PaletteYUV::handle_event()
 {
        update_output();
        window->update_yuv();
@@ -860,7 +979,7 @@ int PalletteYUV::handle_event()
        return 1;
 }
 
-int PalletteAPH::handle_event()
+int PaletteAPH::handle_event()
 {
        update_output();
        window->update_display();
@@ -868,3 +987,157 @@ int PalletteAPH::handle_event()
        return 1;
 }
 
+PaletteHexButton::PaletteHexButton(ColorWindow *window, int x, int y)
+ : BC_GenericButton(x, y, 50, "#")
+{
+       this->window = window;
+       set_tooltip(_("hex rgb color"));
+}
+PaletteHexButton::~PaletteHexButton()
+{
+}
+int PaletteHexButton::handle_event()
+{
+       const char *hex = window->hex_box->get_text();
+       int color;
+       if( sscanf(hex,"%x",&color) == 1 ) {
+               float r = ((color>>16) & 0xff) / 255.;
+               float g = ((color>>8)  & 0xff) / 255.;
+               float b = ((color>>0)  & 0xff) / 255.;
+               window->rgb.r = r;  window->rgb.g = g;  window->rgb.b = b;
+               window->update_rgb();
+               window->update_display();
+               window->update_history();
+               window->handle_event();
+       }
+       return 1;
+}
+
+PaletteHex::PaletteHex(ColorWindow *window, int x, int y, const char *hex)
+ : BC_TextBox(x, y, 100, 1, hex)
+{
+       this->window = window;
+}
+PaletteHex::~PaletteHex()
+{
+}
+void PaletteHex::update()
+{
+       char hex[BCSTRLEN];  sprintf(hex,"%06x",window->rgb888());
+       BC_TextBox::update(hex);
+}
+
+int PaletteHex::handle_event()
+{
+       return 1;
+}
+
+#include "grabpick_up_png.h"
+#include "grabpick_hi_png.h"
+#include "grabpick_dn_png.h"
+
+PaletteGrabButton::PaletteGrabButton(ColorWindow *window, int x, int y)
+ : BC_Button(x, y, vframes)
+{
+       this->window = window;
+       vframes[0] = new VFramePng(grabpick_up_png);
+       vframes[1] = new VFramePng(grabpick_hi_png);
+       vframes[2] = new VFramePng(grabpick_dn_png);
+       set_tooltip(_("grab from anywhere picker"));
+}
+PaletteGrabButton::~PaletteGrabButton()
+{
+        for( int i=0; i<3; ++i )
+                delete vframes[i];
+}
+int PaletteGrabButton::handle_event()
+{
+       if( window->grab_buttons() ) {
+               window->button_grabbed = 1;
+               button_press_event(); // redraw face HI
+       }
+       return 1;
+}
+
+PaletteHistory::PaletteHistory(ColorWindow *window, int x, int y)
+ : BC_SubWindow(x,y, 200, 24)
+{
+       this->window = window;
+       button_down = 0;
+       set_tooltip(_("color history"));
+}
+PaletteHistory::~PaletteHistory()
+{
+}
+void PaletteHistory::update(int flush)
+{
+       int x1 = 0, x2 = 0;
+       for( int i=0; i<PALLETTE_HISTORY_SIZE; x1=x2 ) {
+               int rgb = window->palette_history[i];
+               x2 = (++i * get_w())/PALLETTE_HISTORY_SIZE;
+               draw_3d_box(x1,0,x2-x1,get_h(),WHITE,BLACK,rgb,LTBLUE,DKBLUE);
+       }
+       flash(flush);
+}
+
+int PaletteHistory::button_press_event()
+{
+       if( button_down || !is_event_win() ) return 0;
+       button_down =  1;
+       cursor_motion_event();
+       return 1;
+}
+int PaletteHistory::button_release_event()
+{
+       if( !button_down || !is_event_win() ) return 0;
+       cursor_motion_event();
+       if( button_down > 0 ) {
+               window->handle_event();
+               window->update_display();
+               window->update_history();
+       }
+       button_down =  0;
+       return 1;
+}
+int PaletteHistory::cursor_motion_event()
+{
+       if( !button_down || !is_event_win() ) return 0;
+       hide_tooltip();
+       int pick = (PALLETTE_HISTORY_SIZE * get_cursor_x()) / get_w();
+       bclamp(pick, 0, PALLETTE_HISTORY_SIZE-1);
+       int color = window->palette_history[pick];
+       float r = ((color>>16) & 0xff) / 255.;
+       float g = ((color>>8)  & 0xff) / 255.;
+       float b = ((color>>0)  & 0xff) / 255.;
+       if( window->rgb.r != r || window->rgb.g != g || window->rgb.b != b ) {
+               window->rgb.r = r;  window->rgb.g = g;  window->rgb.b = b;
+               window->update_rgb();
+               window->update_display();
+       }
+       return 1;
+}
+
+int PaletteHistory::cursor_enter_event()
+{
+       set_tooltip_done(0);
+       return 0;
+}
+int PaletteHistory::cursor_leave_event()
+{
+       hide_tooltip();
+       set_tooltip_done(0);
+       return 0;
+}
+int PaletteHistory::repeat_event(int64_t duration)
+{
+       int result = 0;
+
+       if( duration == get_resources()->tooltip_delay &&
+           get_tooltip() && *get_tooltip() && cursor_above() ) {
+               show_tooltip();
+               set_tooltip_done(1);
+               result = 1;
+       }
+       return result;
+}
+
index 383bd87703aed1008683e8ea161568120ab63f77..a63069324050b12ecac6d3b6f6488f2edb86a09f 100644 (file)
 #ifndef COLORPICKER_H
 #define COLORPICKER_H
 
+#include "bcbutton.h"
 #include "bcdialog.h"
+#include "bctextbox.h"
+#include "bcsubwindow.h"
 #include "clip.h"
 #include "condition.inc"
 #include "guicast.h"
@@ -30,6 +33,8 @@
 #include "thread.h"
 #include "vframe.inc"
 
+#define PALLETTE_HISTORY_SIZE 16
+
 class ColorWindow;
 class PaletteWheel;
 class PaletteWheelValue;
@@ -44,10 +49,14 @@ class PaletteLum;
 class PaletteCr;
 class PaletteCb;
 class PaletteAlpha;
-class PalletteHSV;
-class PalletteRGB;
-class PalletteYUV;
-class PalletteAPH;
+class PaletteHSV;
+class PaletteRGB;
+class PaletteYUV;
+class PaletteAPH;
+class PaletteHexButton;
+class PaletteHex;
+class PaletteGrabButton;
+class PaletteHistory;
 
 class ColorThread : public BC_DialogThread
 {
@@ -79,6 +88,8 @@ public:
        void update_hsv();
        void update_yuv();
        int handle_event();
+       int button_press_event();
+       int button_release_event();
 
        struct { float r, g, b; } rgb;
        struct { float y, u, v; } yuv;
@@ -87,9 +98,9 @@ public:
        void update_rgb(float r, float g, float b);
        void update_hsv(float h, float s, float v);
        void update_yuv(float y, float u, float v);
+       int rgb888();
 
        ColorThread *thread;
-
        PaletteWheel *wheel;
        PaletteWheelValue *wheel_value;
        PaletteOutput *output;
@@ -104,12 +115,24 @@ public:
        PaletteCb  *c_b;
        PaletteAlpha *alpha;
 
-       PalletteHSV *hsv_h, *hsv_s, *hsv_v;
-       PalletteRGB *rgb_r, *rgb_g, *rgb_b;
-       PalletteYUV *yuv_y, *yuv_u, *yuv_v;
-       PalletteAPH *aph_a;
+       PaletteHSV *hsv_h, *hsv_s, *hsv_v;
+       PaletteRGB *rgb_r, *rgb_g, *rgb_b;
+       PaletteYUV *yuv_y, *yuv_u, *yuv_v;
+       PaletteAPH *aph_a;
+
+       PaletteHexButton *hex_btn;
+       PaletteHex *hex_box;
+       PaletteGrabButton *grab_btn;
+       PaletteHistory *history;
 
        VFrame *value_bitmap;
+       int button_grabbed;
+
+       int palette_history[PALLETTE_HISTORY_SIZE];
+       void load_history();
+       void save_history();
+       void update_history(int color);
+       void update_history();
 };
 
 
@@ -249,53 +272,100 @@ public:
        ColorWindow *window;
 };
 
-class PalletteNum : public BC_TumbleTextBox
+class PaletteNum : public BC_TumbleTextBox
 {
 public:
        ColorWindow *window;
        float *output;
 
-       PalletteNum(ColorWindow *window, int x, int y,
+       PaletteNum(ColorWindow *window, int x, int y,
                        float &output, float min, float max);
-       ~PalletteNum();
+       ~PaletteNum();
        void update_output() { *output = atof(get_text()); }
        static int calculate_h() { return BC_Tumbler::calculate_h(); }
 };
 
-class PalletteRGB : public PalletteNum
+class PaletteRGB : public PaletteNum
 {
 public:
-       PalletteRGB(ColorWindow *window, int x, int y,
+       PaletteRGB(ColorWindow *window, int x, int y,
                        float &output, float min, float max)
-        : PalletteNum(window, x, y, output, min, max) {}
+        : PaletteNum(window, x, y, output, min, max) {}
        int handle_event();
 };
 
-class PalletteYUV : public PalletteNum
+class PaletteYUV : public PaletteNum
 {
 public:
-       PalletteYUV(ColorWindow *window, int x, int y,
+       PaletteYUV(ColorWindow *window, int x, int y,
                        float &output, float min, float max)
-        : PalletteNum(window, x, y, output, min, max) {}
+        : PaletteNum(window, x, y, output, min, max) {}
        int handle_event();
 };
 
-class PalletteHSV : public PalletteNum
+class PaletteHSV : public PaletteNum
 {
 public:
-       PalletteHSV(ColorWindow *window, int x, int y,
+       PaletteHSV(ColorWindow *window, int x, int y,
                        float &output, float min, float max)
-        : PalletteNum(window, x, y, output, min, max) {}
+        : PaletteNum(window, x, y, output, min, max) {}
        int handle_event();
 };
 
-class PalletteAPH : public PalletteNum
+class PaletteAPH : public PaletteNum
 {
 public:
-       PalletteAPH(ColorWindow *window, int x, int y,
+       PaletteAPH(ColorWindow *window, int x, int y,
                        float &output, float min, float max)
-        : PalletteNum(window, x, y, output, min, max) {}
+        : PaletteNum(window, x, y, output, min, max) {}
+       int handle_event();
+};
+
+class PaletteHexButton : public BC_GenericButton
+{
+public:
+       PaletteHexButton(ColorWindow *window, int x, int y);
+       ~PaletteHexButton();
        int handle_event();
+       ColorWindow *window;
+};
+
+class PaletteHex : public BC_TextBox
+{
+public:
+       PaletteHex(ColorWindow *window, int x, int y, const char *hex);
+       ~PaletteHex();
+       int handle_event();
+       void update();
+       ColorWindow *window;
+};
+
+class PaletteGrabButton : public BC_Button
+{
+public:
+       PaletteGrabButton(ColorWindow *window, int x, int y);
+       ~PaletteGrabButton();
+       int handle_event();
+
+       ColorWindow *window;
+       VFrame *vframes[3];
+};
+
+class PaletteHistory : public BC_SubWindow
+{
+public:
+       PaletteHistory(ColorWindow *window, int x, int y);
+       ~PaletteHistory();
+       void update(int flush=1);
+       int button_press_event();
+       int button_release_event();
+       int cursor_motion_event();
+       int cursor_enter_event();
+       int cursor_leave_event();
+       int repeat_event(int64_t duration);
+
+       ColorWindow *window;
+       int button_down;
 };
 
 #endif
diff --git a/cinelerra-5.1/cinelerra/grabpick_dn.png b/cinelerra-5.1/cinelerra/grabpick_dn.png
new file mode 100644 (file)
index 0000000..86e09a9
Binary files /dev/null and b/cinelerra-5.1/cinelerra/grabpick_dn.png differ
diff --git a/cinelerra-5.1/cinelerra/grabpick_dn_png.h b/cinelerra-5.1/cinelerra/grabpick_dn_png.h
new file mode 100644 (file)
index 0000000..e38e905
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef GRABPICK_DN_PNG_H
+#define GRABPICK_DN_PNG_H
+
+static unsigned char grabpick_dn_png[] = 
+{
+       0x00, 0x00, 0x01, 0x27, 
+       0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52, 
+       0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x08, 0x06, 0x00, 0x00, 0x00, 0xe0, 0x77, 0x3d, 
+       0xf8, 0x00, 0x00, 0x00, 0x06, 0x62, 0x4b, 0x47, 0x44, 0x00, 0xff, 0x00, 0x00, 0x00, 0x00, 0x33, 
+       0x27, 0x7c, 0xf3, 0x00, 0x00, 0x00, 0x09, 0x70, 0x48, 0x59, 0x73, 0x00, 0x00, 0x0b, 0x13, 0x00, 
+       0x00, 0x0b, 0x13, 0x01, 0x00, 0x9a, 0x9c, 0x18, 0x00, 0x00, 0x00, 0x07, 0x74, 0x49, 0x4d, 0x45, 
+       0x07, 0xe1, 0x03, 0x04, 0x00, 0x3b, 0x14, 0xff, 0x66, 0xb4, 0x45, 0x00, 0x00, 0x00, 0x21, 0x69, 
+       0x54, 0x58, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x43, 
+       0x72, 0x65, 0x61, 0x74, 0x65, 0x64, 0x20, 0x77, 0x69, 0x74, 0x68, 0x20, 0x54, 0x68, 0x65, 0x20, 
+       0x47, 0x49, 0x4d, 0x50, 0x6d, 0xb0, 0x97, 0x00, 0x00, 0x00, 0x00, 0x87, 0x49, 0x44, 0x41, 0x54, 
+       0x48, 0xc7, 0xd5, 0x95, 0x51, 0x0e, 0x80, 0x30, 0x08, 0x43, 0xcb, 0xb2, 0xfb, 0x5f, 0x19, 0xbf, 
+       0x96, 0x4c, 0xa2, 0xa1, 0x80, 0x98, 0x8c, 0xaf, 0x99, 0x2d, 0xaf, 0x2b, 0x45, 0x15, 0x05, 0x14, 
+       0x8d, 0x35, 0xd0, 0x5c, 0x87, 0x08, 0xa8, 0x36, 0x0a, 0x2c, 0xf8, 0x8b, 0xc8, 0x28, 0xdd, 0xd4, 
+       0x7b, 0x4e, 0x39, 0x50, 0x0d, 0xed, 0xc7, 0x04, 0x44, 0x7c, 0x91, 0x75, 0xa6, 0x9c, 0xc1, 0x93, 
+       0x88, 0x81, 0x03, 0xc0, 0x4c, 0x41, 0x45, 0xee, 0xeb, 0x4f, 0xc6, 0xd4, 0x02, 0x99, 0x76, 0xa5, 
+       0x33, 0xb0, 0xe0, 0xf2, 0x7b, 0x60, 0x67, 0x7d, 0x77, 0xe3, 0x38, 0x11, 0xea, 0x63, 0x47, 0x06, 
+       0x9a, 0x73, 0x50, 0x80, 0xc7, 0xa7, 0x28, 0x00, 0xe6, 0x1c, 0xec, 0xb7, 0x4f, 0xc0, 0xf9, 0x90, 
+       0x93, 0x70, 0x3e, 0xe4, 0x42, 0xcd, 0xae, 0xd6, 0x70, 0x2d, 0x2a, 0xc2, 0x7f, 0x69, 0xd1, 0xf9, 
+       0x3f, 0xfd, 0x0b, 0xd5, 0xf7, 0x38, 0x1d, 0xc9, 0x8c, 0x5f, 0x3f, 0x00, 0x00, 0x00, 0x00, 0x49, 
+       0x45, 0x4e, 0x44, 0xae, 0x42, 0x60, 0x82
+};
+
+#endif
diff --git a/cinelerra-5.1/cinelerra/grabpick_hi.png b/cinelerra-5.1/cinelerra/grabpick_hi.png
new file mode 100644 (file)
index 0000000..5a0eb06
Binary files /dev/null and b/cinelerra-5.1/cinelerra/grabpick_hi.png differ
diff --git a/cinelerra-5.1/cinelerra/grabpick_hi_png.h b/cinelerra-5.1/cinelerra/grabpick_hi_png.h
new file mode 100644 (file)
index 0000000..a3535a0
--- /dev/null
@@ -0,0 +1,30 @@
+#ifndef GRABPICK_HI_PNG_H
+#define GRABPICK_HI_PNG_H
+
+static unsigned char grabpick_hi_png[] = 
+{
+       0x00, 0x00, 0x01, 0x46, 
+       0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52, 
+       0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x08, 0x06, 0x00, 0x00, 0x00, 0xe0, 0x77, 0x3d, 
+       0xf8, 0x00, 0x00, 0x00, 0x06, 0x62, 0x4b, 0x47, 0x44, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0xa0, 
+       0xbd, 0xa7, 0x93, 0x00, 0x00, 0x00, 0x09, 0x70, 0x48, 0x59, 0x73, 0x00, 0x00, 0x0b, 0x13, 0x00, 
+       0x00, 0x0b, 0x13, 0x01, 0x00, 0x9a, 0x9c, 0x18, 0x00, 0x00, 0x00, 0x07, 0x74, 0x49, 0x4d, 0x45, 
+       0x07, 0xe1, 0x03, 0x04, 0x01, 0x01, 0x17, 0x42, 0x04, 0x51, 0xb1, 0x00, 0x00, 0x00, 0x21, 0x69, 
+       0x54, 0x58, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x43, 
+       0x72, 0x65, 0x61, 0x74, 0x65, 0x64, 0x20, 0x77, 0x69, 0x74, 0x68, 0x20, 0x54, 0x68, 0x65, 0x20, 
+       0x47, 0x49, 0x4d, 0x50, 0x6d, 0xb0, 0x97, 0x00, 0x00, 0x00, 0x00, 0xa6, 0x49, 0x44, 0x41, 0x54, 
+       0x48, 0xc7, 0xd5, 0x95, 0x41, 0x0e, 0x80, 0x20, 0x0c, 0x04, 0x17, 0xc2, 0x19, 0xaf, 0xfa, 0x4a, 
+       0x7d, 0x8a, 0xbf, 0xd4, 0xab, 0x7e, 0x00, 0x4f, 0x45, 0x34, 0x20, 0x52, 0xa8, 0x89, 0xbd, 0x18, 
+       0xa3, 0x99, 0x6d, 0x77, 0xc5, 0xaa, 0x71, 0xb1, 0x0e, 0x82, 0xa5, 0x21, 0x5c, 0xff, 0x10, 0x98, 
+       0xfb, 0x4d, 0x4e, 0x80, 0xe0, 0x29, 0x11, 0x5d, 0xd3, 0x69, 0xee, 0x9e, 0x35, 0xc1, 0x93, 0x1d, 
+       0xb1, 0xe7, 0x45, 0x02, 0xd3, 0xda, 0x65, 0x45, 0xe8, 0x9d, 0xea, 0x0c, 0x62, 0x22, 0x77, 0x38, 
+       0x00, 0x18, 0x16, 0x54, 0x29, 0xc0, 0xb9, 0x24, 0x94, 0x35, 0xc1, 0x05, 0x1e, 0x5c, 0x73, 0x99, 
+       0x94, 0x59, 0x44, 0x70, 0xc0, 0x4f, 0xd0, 0xe4, 0x1c, 0x78, 0x00, 0x41, 0x03, 0x7b, 0x72, 0xc1, 
+       0x9b, 0xe2, 0x74, 0x23, 0xde, 0x3f, 0xe5, 0xa0, 0x5b, 0x7d, 0x2d, 0xa9, 0x32, 0x9c, 0x73, 0xd0, 
+       0xec, 0x67, 0x17, 0x76, 0xcf, 0x81, 0xbf, 0x0e, 0x99, 0x0b, 0x07, 0x00, 0x25, 0xbd, 0xd1, 0xa2, 
+       0x19, 0xcc, 0xc3, 0x7e, 0x76, 0xbf, 0x58, 0xb9, 0x85, 0x53, 0x0b, 0xff, 0xc4, 0xa2, 0xff, 0x2f, 
+       0xfd, 0x03, 0xf8, 0x5c, 0x43, 0x58, 0x06, 0x5d, 0x27, 0xc5, 0x00, 0x00, 0x00, 0x00, 0x49, 0x45, 
+       0x4e, 0x44, 0xae, 0x42, 0x60, 0x82
+};
+
+#endif
diff --git a/cinelerra-5.1/cinelerra/grabpick_up.png b/cinelerra-5.1/cinelerra/grabpick_up.png
new file mode 100644 (file)
index 0000000..7acd339
Binary files /dev/null and b/cinelerra-5.1/cinelerra/grabpick_up.png differ
diff --git a/cinelerra-5.1/cinelerra/grabpick_up_png.h b/cinelerra-5.1/cinelerra/grabpick_up_png.h
new file mode 100644 (file)
index 0000000..4040a7a
--- /dev/null
@@ -0,0 +1,29 @@
+#ifndef GRABPICK_UP_PNG_H
+#define GRABPICK_UP_PNG_H
+
+static unsigned char grabpick_up_png[] = 
+{
+       0x00, 0x00, 0x01, 0x35, 
+       0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52, 
+       0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x08, 0x06, 0x00, 0x00, 0x00, 0xe0, 0x77, 0x3d, 
+       0xf8, 0x00, 0x00, 0x00, 0x06, 0x62, 0x4b, 0x47, 0x44, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0xa0, 
+       0xbd, 0xa7, 0x93, 0x00, 0x00, 0x00, 0x09, 0x70, 0x48, 0x59, 0x73, 0x00, 0x00, 0x0b, 0x13, 0x00, 
+       0x00, 0x0b, 0x13, 0x01, 0x00, 0x9a, 0x9c, 0x18, 0x00, 0x00, 0x00, 0x07, 0x74, 0x49, 0x4d, 0x45, 
+       0x07, 0xe1, 0x03, 0x04, 0x01, 0x00, 0x18, 0xcb, 0xa0, 0x7d, 0x61, 0x00, 0x00, 0x00, 0x21, 0x69, 
+       0x54, 0x58, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x43, 
+       0x72, 0x65, 0x61, 0x74, 0x65, 0x64, 0x20, 0x77, 0x69, 0x74, 0x68, 0x20, 0x54, 0x68, 0x65, 0x20, 
+       0x47, 0x49, 0x4d, 0x50, 0x6d, 0xb0, 0x97, 0x00, 0x00, 0x00, 0x00, 0x95, 0x49, 0x44, 0x41, 0x54, 
+       0x48, 0xc7, 0x63, 0xcc, 0x7f, 0xce, 0xf7, 0x9f, 0x81, 0x86, 0x80, 0x89, 0x81, 0xc6, 0x60, 0x68, 
+       0x58, 0x30, 0x41, 0xe2, 0x23, 0xed, 0x2c, 0x80, 0x19, 0x8e, 0xcb, 0x12, 0x26, 0x4a, 0x5c, 0x4a, 
+       0x88, 0x4f, 0x96, 0x0f, 0xf0, 0x05, 0x07, 0x36, 0x79, 0x92, 0x2c, 0x28, 0x78, 0xc1, 0x4f, 0xd0, 
+       0x12, 0x98, 0x1a, 0x8a, 0xe3, 0x00, 0x9b, 0x25, 0xe8, 0x86, 0x33, 0x30, 0x30, 0x30, 0xb0, 0x90, 
+       0x63, 0x68, 0xc1, 0x0b, 0x7e, 0x14, 0x36, 0x55, 0x92, 0x29, 0xba, 0x81, 0xc4, 0x04, 0x17, 0xd9, 
+       0x71, 0x80, 0x6e, 0x30, 0xc5, 0xf9, 0x00, 0x3d, 0xad, 0x23, 0xfb, 0x86, 0x90, 0x4f, 0x18, 0x89, 
+       0x29, 0xec, 0x88, 0x8d, 0x50, 0xb2, 0x7c, 0x40, 0x89, 0xe1, 0x24, 0xa7, 0x22, 0x52, 0x0c, 0x26, 
+       0xca, 0x07, 0xc8, 0xae, 0x27, 0xc7, 0x70, 0xa2, 0x23, 0x99, 0x5c, 0xc3, 0x89, 0x8e, 0x64, 0x4a, 
+       0x00, 0x0b, 0xad, 0x82, 0x86, 0xa8, 0x20, 0xa2, 0xd4, 0x70, 0xba, 0x04, 0xd1, 0xd0, 0xaf, 0xf4, 
+       0x01, 0xf0, 0x79, 0x47, 0xee, 0xc7, 0xb6, 0x2f, 0x49, 0x00, 0x00, 0x00, 0x00, 0x49, 0x45, 0x4e, 
+       0x44, 0xae, 0x42, 0x60, 0x82
+};
+
+#endif
index 6af3a3139a00c8fa67617869c84c553407c8a626..bc6ca8eb9e191841b4ecb4952e1edf96fb3370d8 100644 (file)
@@ -75,7 +75,7 @@ void PluginClientThread::run()
        if(client->window_x < 0) client->window_x = info.get_abs_cursor_x();
        if(client->window_y < 0) client->window_y = info.get_abs_cursor_y();
        if(!window)
-               window = client->new_window();
+               window = (PluginClientWindow*)client->new_window();
 
        if(window) {
                window->lock_window("PluginClientThread::run");
@@ -91,6 +91,7 @@ void PluginClientThread::run()
 //printf("PluginClientThread::run %p %d\n", this, __LINE__);
                window->hide_window(1);
                window->unlock_window();
+               window->done_event(result);
 // Can't save defaults in the destructor because it's not called immediately
 // after closing.
                /* if(client->defaults) */ client->save_defaults_xml();
index 260a0edad2e8c1bb55bf5704a39df75a9707a91f..51a4ecc13ce97f4d063716bc6955c57401c22aef 100644 (file)
@@ -160,6 +160,7 @@ public:
 
        virtual int translation_event();
        virtual int close_event();
+       virtual void done_event(int result) {}
 
        PluginClient *client;
 };
@@ -178,7 +179,7 @@ public:
 
        BC_WindowBase* get_window();
        PluginClient* get_client();
-       BC_WindowBase *window;
+       PluginClientWindow *window;
        PluginClient *client;
 
 private:
index ab5292791bd51f730e4c2f62e599b3054329c8f6..90a4681db0ddd6d28750315449cdafeb3dc7cce8 100644 (file)
@@ -111,6 +111,7 @@ void BC_Button::enable()
 void BC_Button::disable()
 {
        enabled = 0;
+       status = BUTTON_UP;
        draw_face();
 }
 
index 5d40ecb995b7f00231ca2cdb902524ec8182be11..78c51e00c6b16a60ba39e1a3605082348a9d3cc2 100644 (file)
@@ -2788,3 +2788,9 @@ void BC_TumbleTextBox::set_boundaries(float min, float max)
 {
        tumbler->set_boundaries(min, max);
 }
+
+void BC_TumbleTextBox::set_tooltip(const char *text)
+{
+       textbox->set_tooltip(text);
+}
+
index a4d94e68958a32814b7c9300712e1ebdf0e9ef14..c8e2a71a4d747b29647608d70f2c7d5694012bf2 100644 (file)
@@ -410,6 +410,7 @@ public:
        void set_precision(int precision);
        void set_increment(float value);
        void set_log_floatincrement(int value);
+       void set_tooltip(const char *text);
 
        friend class BC_TumbleTextBoxText;
        friend class BC_TumbleTextBoxTumble;
index d7761f9501202a9b8aba39630e7a70e62c26e2c2..823d81aa609b18099724ca341cd2d24d2e876dfd 100644 (file)
@@ -118,7 +118,6 @@ BC_WindowBase::~BC_WindowBase()
                top_level->dequeue_events(win);
 #endif
 // drop active window refs to this
-               if(top_level->active_grab == this) top_level->active_grab = 0;
                if(top_level->active_menubar == this) top_level->active_menubar = 0;
                if(top_level->active_popup_menu == this) top_level->active_popup_menu = 0;
                if(top_level->active_subwindow == this) top_level->active_subwindow = 0;
@@ -130,6 +129,7 @@ BC_WindowBase::~BC_WindowBase()
                parent_window->subwindows->remove(this);
        }
 
+       if(grab_active) grab_active->active_grab = 0;
        if(icon_window) delete icon_window;
        if(window_type == POPUP_WINDOW)
                parent_window->remove_popup(this);
@@ -291,6 +291,7 @@ int BC_WindowBase::initialize()
        last_motion_win = 0;
        key_pressed = 0;
        active_grab = 0;
+       grab_active = 0;
        active_menubar = 0;
        active_popup_menu = 0;
        active_subwindow = 0;
@@ -1870,6 +1871,10 @@ int BC_WindowBase::set_tooltip(const char *text)
        }
        return 0;
 }
+void BC_WindowBase::set_tooltip_done(int v)
+{
+       tooltip_done = v;
+}
 
 // signal the event handler to repeat
 int BC_WindowBase::set_repeat(int64_t duration)
@@ -2027,7 +2032,7 @@ void BC_WindowBase::init_cursors()
        hourglass_cursor = XCreateFontCursor(display, XC_watch);
 
 
-       char cursor_data[] = { 0,0,0,0, 0,0,0,0 };
+       static char cursor_data[] = { 0,0,0,0, 0,0,0,0 };
        Colormap colormap = DefaultColormap(display, screen);
        Pixmap pixmap_bottom = XCreateBitmapFromData(display,
                rootwin, cursor_data, 8, 8);
@@ -2037,6 +2042,49 @@ void BC_WindowBase::init_cursors()
                pixmap_bottom, pixmap_bottom, &black, &black, 0, 0);
 //     XDefineCursor(display, win, transparent_cursor);
        XFreePixmap(display, pixmap_bottom);
+
+       int iw = 23, iw1 = iw-1, iw2 = iw/2;
+       int ih = 23, ih1 = ih-1, ih2 = ih/2;
+       VFrame grab(iw,ih,BC_RGB888);
+       grab.clear_frame();
+       grab.set_pixel_color(RED);   // fg
+       grab.draw_smooth(iw2,0,   iw1,0,   iw1,ih2);
+       grab.draw_smooth(iw1,ih2, iw1,ih1, iw2,ih1);
+       grab.draw_smooth(iw2,ih1, 0,ih1,   0,ih2);
+       grab.draw_smooth(0,ih2,   0,0,     iw2,0);
+       grab.set_pixel_color(WHITE); // bg
+       grab.draw_line(0,ih2,     iw2-2,ih2);
+       grab.draw_line(iw2+2,ih2, iw1,ih2);
+       grab.draw_line(iw2,0,     iw2,ih2-2);
+       grab.draw_line(iw2,ih2+2, iw2,ih1);
+
+       int bpl = (iw+7)/8, isz = bpl * ih;
+       char img[isz];  memset(img, 0, isz);
+       char msk[isz];  memset(msk, 0, isz);
+       unsigned char **rows = grab.get_rows();
+       for( int iy=0; iy<ih; ++iy ) {
+               char *op = img + iy*bpl;
+               char *mp = msk + iy*bpl;
+               unsigned char *ip = rows[iy];
+               for( int ix=0; ix<iw; ++ix,ip+=3 ) {
+                       if( ip[0] ) mp[ix>>3] |= (1<<(ix&7));
+                       if( !ip[1] ) op[ix>>3] |= (1<<(ix&7));
+               }
+       }
+       unsigned long white_pix = WhitePixel(display, screen);
+       unsigned long black_pix = BlackPixel(display, screen);
+       Pixmap img_xpm = XCreatePixmapFromBitmapData(display, rootwin,
+               img, iw,ih, white_pix,black_pix, 1);
+       Pixmap msk_xpm = XCreatePixmapFromBitmapData(display, rootwin,
+               msk, iw,ih, white_pix,black_pix, 1);
+
+       XColor fc, bc;
+       fc.flags = bc.flags = DoRed | DoGreen | DoBlue;
+       fc.red = 0xffff; fc.green = fc.blue = 0;  // fg
+       bc.red = bc.green = bc.blue = 0x0000;     // bg
+       grabbed_cursor = XCreatePixmapCursor(display, img_xpm,msk_xpm, &fc,&bc, iw2,ih2);
+       XFreePixmap(display, img_xpm);
+       XFreePixmap(display, msk_xpm);
 }
 
 int BC_WindowBase::evaluate_color_model(int client_byte_order, int server_byte_order, int depth)
@@ -3314,14 +3362,41 @@ int BC_WindowBase::grab(BC_WindowBase *window)
 {
        if( window->active_grab && this != window->active_grab ) return 0;
        window->active_grab = this;
+       this->grab_active = window;
        return 1;
 }
 int BC_WindowBase::ungrab(BC_WindowBase *window)
 {
        if( window->active_grab && this != window->active_grab ) return 0;
        window->active_grab = 0;
+       this->grab_active = 0;
        return 1;
 }
+int BC_WindowBase::grab_buttons()
+{
+       XSync(top_level->display, False);
+       if( XGrabButton(top_level->display, AnyButton, AnyModifier,
+                       top_level->rootwin, True, ButtonPressMask | ButtonReleaseMask,
+                       GrabModeAsync, GrabModeSync, None, grabbed_cursor) == GrabSuccess ) {
+               set_active_subwindow(this);
+               return 0;
+       }
+       return 1;
+}
+void BC_WindowBase::ungrab_buttons()
+{
+       XUngrabButton(top_level->display, AnyButton, AnyModifier, top_level->rootwin);
+       set_active_subwindow(0);
+       unhide_cursor();
+}
+void BC_WindowBase::grab_cursor()
+{
+       XDefineCursor(top_level->display, top_level->rootwin, grabbed_cursor);
+}
+void BC_WindowBase::ungrab_cursor()
+{
+       XUndefineCursor(top_level->display, top_level->rootwin);
+}
 
 int BC_WindowBase::get_w()
 {
index cd4ba72905945122329dcc07d585253e4af1cd6b..767427dc2a7a63c45d6eaeec75b0092f083d3071 100644 (file)
@@ -93,6 +93,7 @@
 #endif
 #include <X11/extensions/Xinerama.h>
 #ifdef HAVE_GL
+#define GL_GLEXT_PROTOTYPES
 #include <GL/glx.h>
 #endif
 
@@ -460,6 +461,11 @@ public:
 // Reroute toplevel events
        int grab(BC_WindowBase *window);
        int ungrab(BC_WindowBase *window);
+// Grab button events
+       int grab_buttons();
+       void ungrab_buttons();
+       void grab_cursor();
+       void ungrab_cursor();
 // Get a bitmap to draw on the window with
        BC_Bitmap* new_bitmap(int w, int h, int color_model = -1);
 // Draw a bitmap on the window
@@ -508,6 +514,7 @@ public:
        int unset_repeat(int64_t duration);
        const char *get_tooltip();
        int set_tooltip(const char *text);
+       void set_tooltip_done(int v);
        int show_tooltip(int w = -1, int h = -1);
        int hide_tooltip();
        int set_icon(VFrame *data);
@@ -637,7 +644,7 @@ private:
 // Type of window defined above
        int window_type;
 // keypress/pointer active grab
-       BC_WindowBase* active_grab;
+       BC_WindowBase *active_grab, *grab_active;
 // Pointer to the active menubar in the window.
        BC_MenuBar* active_menubar;
 // pointer to the active popup menu in the window
@@ -827,6 +834,7 @@ private:
        Cursor downright_resize_cursor;
        Cursor hourglass_cursor;
        Cursor transparent_cursor;
+       Cursor grabbed_cursor;
 
        int xvideo_port_id;
        ArrayList<BC_ResizeCall*> resize_history;
index a90731dd963d03654005b1bbd415f064258c83c4..b7d8e7275ac374018140353560d102eca867db5b 100644 (file)
@@ -46,6 +46,7 @@
 #include "language.h"
 #include "mwindow.inc"
 #include "overlayframe.h"
+#include "plugin.h"
 #include "renderengine.h"
 #include "titler.h"
 #include "titlerwindow.h"
@@ -81,38 +82,36 @@ REGISTER_PLUGIN(TitleMain)
 
 TitleConfig::TitleConfig()
 {
+       strcpy(font, "fixed");
+       strcpy(encoding, DEFAULT_ENCODING);
        style = 0;
+       size = 24;
        color = BLACK;
        alpha = 0xff;
+       outline_size = 0.;
+       outline_color = WHITE;
        outline_alpha = 0xff;
-       size = 24;
+       color_stroke = 0xff0000;
+       stroke_width = 1.0;
        motion_strategy = NO_MOTION;
-       loop = 0;
        line_pitch = 0;
+       loop = 0;
        hjustification = JUSTIFY_CENTER;
        vjustification = JUSTIFY_MID;
-       fade_in = 0.0;
-       fade_out = 0.0;
+       fade_in = 0.0;  fade_out = 0.0;
+       pixels_per_second = 100.0;
+       wtext[0] = 0;  wlen = 0;
        title_x = title_y = 0.0;
        title_w = title_h = 0;
-       dropshadow = 2;
-       strcpy(font, "fixed");
-       strcpy(encoding, DEFAULT_ENCODING);
-       timecode_format = DEFAULT_TIMECODEFORMAT;
-       pixels_per_second = 1.0;
-       timecode = 0;
-       stroke_width = 1.0;
-       wtext[0] = 0;  wlen = 0;
-       color_stroke = 0xff0000;
-       outline_color = WHITE;
-       background = 0;
-       strcpy(background_path, "");
-
-       outline_size = 0;
        window_w = 800;
        window_h = 460;
        next_keyframe_position = 0;
        prev_keyframe_position = 0;
+       timecode = 0;
+       dropshadow = 2;
+       background = 0;
+       strcpy(background_path, "");
+       timecode_format = DEFAULT_TIMECODEFORMAT;
        drag = 0;
        loop_playback = 0;
 }
@@ -124,102 +123,118 @@ TitleConfig::~TitleConfig()
 int TitleConfig::equivalent(TitleConfig &that)
 {
        return !strcasecmp(font, that.font) &&
+               !strcasecmp(encoding, that.encoding) &&
                style == that.style &&
                size == that.size &&
                color == that.color &&
-               color_stroke == that.color_stroke &&
-               stroke_width == that.stroke_width &&
-               outline_color == that.outline_color &&
                alpha == that.alpha &&
+               outline_size == that.outline_size &&
+               outline_color == that.outline_color &&
                outline_alpha == that.outline_alpha &&
-               EQUIV(pixels_per_second, that.pixels_per_second) &&
-               motion_strategy == that.motion_strategy &&
-               loop == that.loop &&
+               color_stroke == that.color_stroke &&
+               stroke_width == that.stroke_width &&
+// dont require redraw for these
+//             motion_strategy == that.motion_strategy &&
                line_pitch == that.line_pitch &&
+//             loop == that.loop &&
                hjustification == that.hjustification &&
                vjustification == that.vjustification &&
-               fade_in == that.fade_in && fade_out == that.fade_out &&
-               title_x == that.title_x && title_y == that.title_y &&
+//             fade_in == that.fade_in && fade_out == that.fade_out &&
+//             EQUIV(pixels_per_second, that.pixels_per_second) &&
+               wlen == that.wlen &&
+               !memcmp(wtext, that.wtext, wlen * sizeof(wchar_t)) &&
+//             title_x == that.title_x && title_y == that.title_y &&
                title_w == that.title_w && title_h == that.title_h &&
-               dropshadow == that.dropshadow &&
+//             window_w == that.window_w && window_h == that.window_h &&
                timecode == that.timecode &&
+               dropshadow == that.dropshadow &&
+               background == that.background &&
+               !strcmp(background_path, that.background_path) &&
                timecode_format == that.timecode_format &&
-               outline_size == that.outline_size &&
-               !strcasecmp(encoding, that.encoding) &&
-               wlen == that.wlen &&
-               !memcmp(wtext, that.wtext, wlen * sizeof(wchar_t));
+//             drag == that.drag &&
+               loop_playback == that.loop_playback;
 }
 
 void TitleConfig::copy_from(TitleConfig &that)
 {
        strcpy(font, that.font);
+       strcpy(encoding, that.encoding);
        style = that.style;
        size = that.size;
        color = that.color;
-       color_stroke = that.color_stroke;
-       stroke_width = that.stroke_width;
-       outline_color = that.outline_color;
        alpha = that.alpha;
+       outline_size = that.outline_size;
+       outline_color = that.outline_color;
        outline_alpha = that.outline_alpha;
-       pixels_per_second = that.pixels_per_second;
+       color_stroke = that.color_stroke;
+       stroke_width = that.stroke_width;
        motion_strategy = that.motion_strategy;
-       loop = that.loop;
        line_pitch = that.line_pitch;
+       loop = that.loop;
        hjustification = that.hjustification;
        vjustification = that.vjustification;
        fade_in = that.fade_in;
        fade_out = that.fade_out;
-       title_x = that.title_x;
-       title_y = that.title_y;
-       title_w = that.title_w;
-       title_h = that.title_h;
-       dropshadow = that.dropshadow;
+       pixels_per_second = that.pixels_per_second;
+       wlen = that.wlen;
+       memcpy(wtext, that.wtext, that.wlen * sizeof(wchar_t));
+       title_x = that.title_x;  title_y = that.title_y;
+       title_w = that.title_w;  title_h = that.title_h;
+       window_w = that.window_w;  window_h = that.window_h;
        timecode = that.timecode;
+       dropshadow = that.dropshadow;
+       background = that.background;
+       strcpy(background_path, that.background_path);
        timecode_format = that.timecode_format;
-       outline_size = that.outline_size;
-       strcpy(encoding, that.encoding);
-       memcpy(wtext, that.wtext, that.wlen * sizeof(wchar_t));
-       wlen = that.wlen;
-       window_w = that.window_w;
-       window_h = that.window_h;
+       drag = that.drag;
+       loop_playback = that.loop_playback;
 }
 
 void TitleConfig::interpolate(TitleConfig &prev, TitleConfig &next,
        int64_t prev_frame, int64_t next_frame, int64_t current_frame)
 {
+       double next_scale = (double)(current_frame - prev_frame) / (next_frame - prev_frame);
+       double prev_scale = (double)(next_frame - current_frame) / (next_frame - prev_frame);
        strcpy(font, prev.font);
        strcpy(encoding, prev.encoding);
        style = prev.style;
        size = prev.size;
        color = prev.color;
-       color_stroke = prev.color_stroke;
-       stroke_width = prev.stroke_width;
-       outline_color = prev.outline_color;
        alpha = prev.alpha;
+       outline_size = prev.outline_size;
+       outline_color = prev.outline_color;
        outline_alpha = prev.outline_alpha;
+       color_stroke = prev.color_stroke;
+       stroke_width = prev.stroke_width;
        motion_strategy = prev.motion_strategy;
-       loop = prev.loop;
        line_pitch = prev.line_pitch;
+       loop = prev.loop;
        hjustification = prev.hjustification;
        vjustification = prev.vjustification;
        fade_in = prev.fade_in;
        fade_out = prev.fade_out;
-       outline_size = prev.outline_size;
        pixels_per_second = prev.pixels_per_second;
-       memcpy(wtext, prev.wtext, prev.wlen * sizeof(wchar_t));
        wlen = prev.wlen;
+       memcpy(wtext, prev.wtext, prev.wlen * sizeof(wchar_t));
        wtext[wlen] = 0;
-
-       double next_scale = (double)(current_frame - prev_frame) / (next_frame - prev_frame);
-       double prev_scale = (double)(next_frame - current_frame) / (next_frame - prev_frame);
-       this->title_x = prev.title_x * prev_scale + next.title_x * next_scale;
-       this->title_y = prev.title_y * prev_scale + next.title_y * next_scale;
-//     this->title_x = prev.title_x;
-//     this->title_y = prev.title_y;
+       this->title_x = prev.title_x == next.title_x ? prev.title_x :
+               prev.title_x * prev_scale + next.title_x * next_scale;
+       this->title_y = prev.title_y == next.title_y ? prev.title_y :
+               prev.title_y * prev_scale + next.title_y * next_scale;
+       this->title_w = prev.title_w == next.title_w ? prev.title_w :
+               prev.title_w * prev_scale + next.title_w * next_scale;
+       this->title_h = prev.title_h == next.title_h ? prev.title_h :
+               prev.title_h * prev_scale + next.title_h * next_scale;
+       window_w = prev.window_w;
+       window_h = prev.window_h;
        timecode = prev.timecode;
+       this->dropshadow = prev.dropshadow == next.dropshadow ? prev.dropshadow :
+               prev.dropshadow * prev_scale + next.dropshadow * next_scale;
+       background = prev.background;
+       strcpy(background_path, prev.background_path);
        timecode_format = prev.timecode_format;
-       this->dropshadow = prev.dropshadow * prev_scale + next.dropshadow * next_scale;
-//     this->dropshadow = prev.dropshadow;
+       drag = prev.drag;
+       loop_playback = prev.loop_playback;
 }
 
 void TitleConfig::to_wtext(const char *from_enc, const char *text, int tlen)
@@ -2055,7 +2070,7 @@ int TitleMain::get_visible_text()
        case RIGHT_TO_LEFT:
        case LEFT_TO_RIGHT: {
                float magnitude = config.pixels_per_second *
-                       (get_source_position() - config.prev_keyframe_position) /
+                       (get_source_position() - get_source_start()) /
                        PluginVClient::project_frame_rate;
                if( config.loop ) {
                        int loop_size = text_w + title_w;
@@ -2270,21 +2285,21 @@ int TitleMain::draw_underline(VFrame *mask, int alpha)
 
 void TitleMain::draw_overlay()
 {
-
 //printf("TitleMain::draw_overlay 1\n");
         fade = 1;
         if( !EQUIV(config.fade_in, 0) ) {
-               int fade_len = lroundf(config.fade_in * PluginVClient::project_frame_rate);
-               int fade_position = get_source_position() - config.prev_keyframe_position;
+               int64_t plugin_start = server->plugin->startproject;
+               int64_t fade_len = lroundf(config.fade_in * PluginVClient::project_frame_rate);
+               int64_t fade_position = get_source_position() - plugin_start;
 
                if( fade_position >= 0 && fade_position < fade_len ) {
                        fade = (float)fade_position / fade_len;
                }
        }
         if( !EQUIV(config.fade_out, 0) ) {
-               int fade_len = lroundf(config.fade_out * PluginVClient::project_frame_rate);
-               int fade_position = config.next_keyframe_position - get_source_position();
-
+               int64_t plugin_end = server->plugin->startproject + server->plugin->length;
+               int64_t fade_len = lroundf(config.fade_out * PluginVClient::project_frame_rate);
+               int64_t fade_position = plugin_end - get_source_position();
 
                if( fade_position >= 0 && fade_position < fade_len ) {
                        fade = (float)fade_position / fade_len;
index a97974aaee5530ab97ee9ee84c4d86656a91ee26..721bc6a10c0da64fbffaf070cd8fbcc37b0a16a5 100644 (file)
@@ -114,9 +114,13 @@ TitleWindow::TitleWindow(TitleMain *client)
        loop_playback = 0;
 }
 
-TitleWindow::~TitleWindow()
+void TitleWindow::done_event(int result)
 {
        ungrab(client->server->mwindow->cwindow->gui);
+}
+
+TitleWindow::~TitleWindow()
+{
        delete color_popup;
        delete png_popup;
        for( int i=0; i<fonts.size(); ++i )
index 0461cee4a010920a60a8a6f02fc683eded226a72..5af1c7aad67ff8626f8021671d00b49572e371f8 100644 (file)
@@ -96,6 +96,7 @@ public:
        void next_font();
        void check_style(const char *font_name);
        int insert_ibeam(const char *txt, int adv);
+       void done_event(int result);
 
        TitleMain *client;