boxblur tweak for w=1:h=0, speedup canvas bline draw for floatautos+audio waveform...
authorGood Guy <[email protected]>
Wed, 8 Apr 2020 00:37:17 +0000 (18:37 -0600)
committerGood Guy <[email protected]>
Wed, 8 Apr 2020 00:37:17 +0000 (18:37 -0600)
cinelerra-5.1/cinelerra/boxblur.C
cinelerra-5.1/cinelerra/indexfile.C
cinelerra-5.1/cinelerra/resourcepixmap.C
cinelerra-5.1/cinelerra/trackcanvas.C
cinelerra-5.1/cinelerra/trackcanvas.h
cinelerra-5.1/guicast/bcwindowbase.C

index d0c00c0904a13c5fa8f62dbdbc4d7d9a2d03db2a..31f017d8fb4d086e7db47616189e7f2c796479fd 100644 (file)
@@ -6,6 +6,7 @@ void blurt(dst_t *dst, int dst_step, src_t *src, int src_step,
                int len, int radius, float s)
 {
        int n = len/2-1;
+       if( n <= 0 ) return;
        if( radius > n ) radius = n;
        const int length = radius*2 + 1;
        const int inv = s * ((1<<16) + length/2)/length;
index 87b8853a28344ad1059a25b59be72910f08e2ac9..e73a87100a8fa56cd769ffc28807e3c2eeec60c0 100644 (file)
@@ -790,7 +790,7 @@ SET_TRACE
 // A different algorithm has to be used if it's 1 sample per pixel and the
 // index is used.  Now the min and max values are equal so we join the max samples.
                if(mwindow->edl->local_session->zoom_sample == 1) {
-                       canvas->draw_line(x2 - 1, !rect_audio ? prev_y1 : center_pixel, x2, y1, pixmap);
+                       canvas->draw_bline(x2 - 1, !rect_audio ? prev_y1 : center_pixel, x2, y1, pixmap);
                }
                else {
 // Extend line height if it doesn't connect to previous line
@@ -801,7 +801,7 @@ SET_TRACE
                        else {
                                first_frame = 0;
                        }
-                       canvas->draw_line(x2, y1, x2, !rect_audio ? y2 : center_pixel, pixmap);
+                       canvas->draw_bline(x2, y1, x2, !rect_audio ? y2 : center_pixel, pixmap);
                }
                prev_y1 = next_y1;
                prev_y2 = next_y2;
index b0bc49b7ffbf5020ce8764ac5024ff1ddccbe763..1201f044073d01511c461fb56b0d0f6ec172042d 100644 (file)
@@ -523,9 +523,9 @@ void ResourcePixmap::draw_audio_source(TrackCanvas *canvas, Edit *edit, int x, i
                                y2 = CLIP(y1, 0, y_max);
 //printf("ResourcePixmap::draw_audio_source %d %d %d\n", __LINE__, y1, y2);
                                if( !rect_audio )
-                                       canvas->draw_line(x1, y0, x2, y2, this);
+                                       canvas->draw_bline(x1, y0, x2, y2, this);
                                else
-                                       canvas->draw_line(x2, center_pixel, x2, y2, this);
+                                       canvas->draw_bline(x2, center_pixel, x2, y2, this);
                        }
                }
 
index a4faec2b9de802c3f6e168b833bebe443740bea2..96726f68222334a5a9af0f6766b404a1469ffdc3 100644 (file)
@@ -2781,6 +2781,24 @@ int TrackCanvas::test_floatauto(FloatAuto *current, int x, int y, int in_x,
        return result;
 }
 
+static int is_linear(FloatAuto *prev, FloatAuto *next)
+{
+       if( !prev || !next ) return 1;
+       if( prev->curve_mode == FloatAuto::LINEAR ) return 1;
+       int64_t ipos, opos;
+       if( !(ipos = prev->get_control_in_position()) &&
+           !(opos = prev->get_control_out_position()) ) return 1;
+       if( !ipos || !opos ) return 0;
+       float ival = prev->get_control_in_value();
+       float oval = prev->get_control_out_value();
+       float cval = prev->get_value(), nval = next->get_value();
+       if( !ival && !oval && EQUIV(cval, nval) ) return 1;
+       float ig = ival / ipos, og = oval / opos;
+       int64_t cpos = prev->position, npos = next->position;
+       float g = (nval - cval) / (npos - cpos);
+       if( EQUIV(ig, g) && EQUIV(og, g) ) return 1;
+       return 0;
+}
 
 // Get the float value & y for position x on the canvas
 #define X_TO_FLOATLINE(x) \
@@ -2813,45 +2831,45 @@ void TrackCanvas::draw_floatline(int center_pixel,
        int x1, int y1, int x2, int y2,
        int color, int autogrouptype)
 {
+       int ytop = center_pixel - yscale / 2;
+       int ybot = center_pixel + yscale / 2 - 1;
+       y1 += center_pixel;  y2 += center_pixel;
+       if( (y1 < ytop && y1 >= ybot) && (y2 < ytop || y2 >= ybot) ) return;
+// check for line draw
+       if( is_linear(previous, next) ) {
+               draw_line(x1, y1, x2, y2);
+               return;
+       }
+
 // Solve bezier equation for either every pixel or a certain large number of
 // points.
 
 // Not using slope intercept
        x1 = MAX(0, x1);
-       int prev_y = y1 + center_pixel;
-
+       draw_pixel(x1, y1);
+       int prev_y = y1;
 
 // Call by reference fails for some reason here
        FloatAuto *previous1 = previous, *next1 = next;
        float automation_min = mwindow->edl->local_session->automation_mins[autogrouptype];
        float automation_max = mwindow->edl->local_session->automation_maxs[autogrouptype];
        float automation_range = automation_max - automation_min;
-
-       for(int x = x1; x < x2; x++)
-       {
+       for( int x=x1; x<x2; ++x ) {
 // Interpolate value between frames
                X_TO_FLOATLINE(x)
 
-               if(/* x > x1 && */
-                       y >= center_pixel - yscale / 2 &&
-                       y < center_pixel + yscale / 2 - 1)
-               {
-// printf("TrackCanvas::draw_floatline y=%d min=%d max=%d\n",
-// y,
-// (int)(center_pixel - yscale / 2),
-// (int)(center_pixel + yscale / 2 - 1));
-
-//printf("draw_line(%d,%d,  %d,%d)\n", x - 1, prev_y  , x, y);
-                       draw_line(x - 1, prev_y  , x, y   );
+               if( /* x > x1 && */ y >= ytop && y < ybot ) {
+                       int x1 = x-1, y1 = prev_y, x2 = x, y2 = y;
+                       if( abs(y2-y1) < 2 )
+                               draw_pixel(x2, y2);
+                       else
+                               draw_bline(x1, y1, x2, y2);
                }
                prev_y = y;
        }
 }
 
 
-
-
-
 int TrackCanvas::test_floatline(int center_pixel,
                FloatAutos *autos,
                double unit_start,
@@ -3698,6 +3716,43 @@ int TrackCanvas::draw_hairline(Auto *auto_keyframe, int color, int show)
        return 0;
 }
 
+void TrackCanvas::draw_bline(int x1, int y1, int x2, int y2, BC_Pixmap *pixmap)
+{
+// Short lines are all overhead to hw or sw setup, use bresenhams
+       if( y1 > y2 ) {
+               int tx = x1;  x1 = x2;  x2 = tx;
+               int ty = y1;  y1 = y2;  y2 = ty;
+       }
+
+       int x = x1, y = y1;
+       int dx = x2-x1, dy = y2-y1;
+       int dx2 = 2*dx, dy2 = 2*dy;
+       if( dx < 0 ) dx = -dx;
+       int r = dx > dy ? dx : dy, n = r;
+       int dir = 0;
+       if( dx2 < 0 ) dir += 1;
+       if( dy >= dx ) {
+               if( dx2 >= 0 ) do {     /* +Y, +X */
+                       draw_pixel(x, y++, pixmap);
+                       if( (r -= dx2) < 0 ) { r += dy2;  ++x; }
+               } while( --n >= 0 );
+               else do {               /* +Y, -X */
+                       draw_pixel(x, y++, pixmap);
+                       if( (r += dx2) < 0 ) { r += dy2;  --x; }
+               } while( --n >= 0 );
+       }
+       else {
+               if( dx2 >= 0 ) do {     /* +X, +Y */
+                       draw_pixel(x++, y, pixmap);
+                       if( (r -= dy2) < 0 ) { r += dx2;  ++y; }
+               } while( --n >= 0 );
+               else do {               /* -X, +Y */
+                       draw_pixel(x--, y, pixmap);
+                       if( (r -= dy2) < 0 ) { r -= dx2;  ++y; }
+               } while( --n >= 0 );
+       }
+}
+
 void TrackCanvas::draw_overlays()
 {
        int new_cursor, update_cursor, rerender;
index 4b9c4eba22736a68f8c5be3f8fd9013260ea6f44..490b67b151419ecca3607097cf103c4bd29d6928 100644 (file)
@@ -71,6 +71,7 @@ public:
        void draw_highlighting();
        void draw_keyframe_reticle();
        int draw_hairline(Auto *auto_keyframe, int color, int show);
+       void draw_bline(int x1, int y1, int x2, int y2, BC_Pixmap *pixmap=0);
 
 // User can either call draw or draw_overlays to copy a fresh
 // canvas and just draw the overlays over it
index e64b2eb04b15fbed85aa667d67aaec122acb650c..a2cccd2cf4da8abac6f37276c0af1ce4516aeabf 100644 (file)
@@ -4357,6 +4357,10 @@ void BC_WindowBase::init_resources(float scale)
                int wx, wy, ww, wh;
                int cins = info.xinerama_big_screen();
                if( !info.xinerama_geometry(cins, wx, wy, ww, wh) ) {
+                       int sh = ww * 9 / 16;
+                       int sw = wh * 16 / 9;
+                       if( sw < ww ) ww = sw;
+                       if( sh < wh ) wh = sh;
                        if( (x_scale = ww/1920.) < 1 ) x_scale = 1;
                        if( (y_scale = wh/1080.) < 1 ) y_scale = 1;
                }