]> git.sesse.net Git - mlt/blobdiff - src/modules/gtk2/filter_rescale.c
Merge branch 'master' of dennedy.org:git/mltframework.org/mlt
[mlt] / src / modules / gtk2 / filter_rescale.c
index 774c0d682f515c6ac9b073cf5df2387a41c085d1..e7b574cadd51e0f51cad6b82a3e56bfd532f3d6e 100644 (file)
@@ -18,9 +18,9 @@
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  */
 
-#include "filter_rescale.h"
 #include "pixops.h"
 
+#include <framework/mlt_filter.h>
 #include <framework/mlt_frame.h>
 #include <framework/mlt_factory.h>
 
@@ -29,7 +29,7 @@
 #include <stdlib.h>
 #include <gdk-pixbuf/gdk-pixbuf.h>
 
-static int filter_scale( mlt_frame this, uint8_t **image, mlt_image_format iformat, mlt_image_format oformat, int iwidth, int iheight, int owidth, int oheight )
+static int filter_scale( mlt_frame this, uint8_t **image, mlt_image_format *format, int iwidth, int iheight, int owidth, int oheight )
 {
        // Get the properties
        mlt_properties properties = MLT_FRAME_PROPERTIES( this );
@@ -44,14 +44,19 @@ static int filter_scale( mlt_frame this, uint8_t **image, mlt_image_format iform
                interp = PIXOPS_INTERP_NEAREST;
        else if ( strcmp( interps, "tiles" ) == 0 )
                interp = PIXOPS_INTERP_TILES;
-       else if ( strcmp( interps, "hyper" ) == 0 )
+       else if ( strcmp( interps, "hyper" ) == 0 || strcmp( interps, "bicubic" ) == 0 )
                interp = PIXOPS_INTERP_HYPER;
 
+       int bpp;
+       int size = mlt_image_format_size( *format, owidth, oheight, &bpp );
+
        // Carry out the rescaling
-       if ( iformat == mlt_image_yuv422 && oformat == mlt_image_yuv422 )
+       switch ( *format )
+       {
+       case mlt_image_yuv422:
        {
                // Create the output image
-               uint8_t *output = mlt_pool_alloc( owidth * ( oheight + 1 ) * 2 );
+               uint8_t *output = mlt_pool_alloc( size );
 
                // Calculate strides
                int istride = iwidth * 2;
@@ -60,73 +65,58 @@ static int filter_scale( mlt_frame this, uint8_t **image, mlt_image_format iform
                yuv422_scale_simple( output, owidth, oheight, ostride, *image, iwidth, iheight, istride, interp );
                
                // Now update the frame
-               mlt_properties_set_data( properties, "image", output, owidth * ( oheight + 1 ) * 2, ( mlt_destructor )mlt_pool_release, NULL );
-               mlt_properties_set_int( properties, "width", owidth );
-               mlt_properties_set_int( properties, "height", oheight );
+               mlt_frame_set_image( this, output, size, mlt_pool_release );
 
                // Return the output
                *image = output;
+               break;
        }
-       else if ( iformat == mlt_image_rgb24 || iformat == mlt_image_rgb24a )
+       case mlt_image_rgb24:
+       case mlt_image_rgb24a:
+       case mlt_image_opengl:
        {
-               int bpp = (iformat == mlt_image_rgb24a ? 4 : 3 );
-                       
-               // Create the yuv image
-               uint8_t *output = mlt_pool_alloc( owidth * ( oheight + 1 ) * 2 );
+               // Create the output image
+               uint8_t *output = mlt_pool_alloc( size );
 
                if ( strcmp( interps, "none" ) && ( iwidth != owidth || iheight != oheight ) )
                {
                        GdkPixbuf *pixbuf = gdk_pixbuf_new_from_data( *image, GDK_COLORSPACE_RGB,
-                               ( iformat == mlt_image_rgb24a ), 8, iwidth, iheight,
+                               ( *format == mlt_image_rgb24a || *format == mlt_image_opengl ), 8, iwidth, iheight,
                                iwidth * bpp, NULL, NULL );
-
                        GdkPixbuf *scaled = gdk_pixbuf_scale_simple( pixbuf, owidth, oheight, interp );
                        g_object_unref( pixbuf );
-                       
-                       // Extract YUV422 and alpha
-                       if ( bpp == 4 )
-                       {
-                               // Allocate the alpha mask
-                               uint8_t *alpha = mlt_pool_alloc( owidth * ( oheight + 1 ) );
-
-                               // Convert the image and extract alpha
-                               mlt_convert_rgb24a_to_yuv422( gdk_pixbuf_get_pixels( scaled ), owidth, oheight, gdk_pixbuf_get_rowstride( scaled ), output, alpha );
 
-                               mlt_properties_set_data( properties, "alpha", alpha, owidth * ( oheight + 1 ), ( mlt_destructor )mlt_pool_release, NULL );
-                       }
-                       else
+                       int src_stride = gdk_pixbuf_get_rowstride( scaled );
+                       int dst_stride = owidth * bpp;
+                       if ( src_stride != dst_stride )
                        {
-                               // No alpha to extract
-                               mlt_convert_rgb24_to_yuv422( gdk_pixbuf_get_pixels( scaled ), owidth, oheight, gdk_pixbuf_get_rowstride( scaled ), output );
-                       }
-                       g_object_unref( scaled );
-               }
-               else
-               {
-                       // Extract YUV422 and alpha
-                       if ( bpp == 4 )
-                       {
-                               // Allocate the alpha mask
-                               uint8_t *alpha = mlt_pool_alloc( owidth * ( oheight + 1 ) );
-
-                               // Convert the image and extract alpha
-                               mlt_convert_rgb24a_to_yuv422( *image, owidth, oheight, owidth * 4, output, alpha );
-
-                               mlt_properties_set_data( properties, "alpha", alpha, owidth * ( oheight + 1 ), ( mlt_destructor )mlt_pool_release, NULL );
+                               int y = oheight;
+                               uint8_t *src = gdk_pixbuf_get_pixels( scaled );
+                               uint8_t *dst = output;
+                               while ( y-- )
+                               {
+                                       memcpy( dst, src, dst_stride );
+                                       dst += dst_stride;
+                                       src += src_stride;
+                               }
                        }
                        else
                        {
-                               // No alpha to extract
-                               mlt_convert_rgb24_to_yuv422( *image, owidth, oheight, owidth * 3, output );
+                               memcpy( output, gdk_pixbuf_get_pixels( scaled ), owidth * oheight * bpp );
                        }
-               }
 
-               // Now update the frame
-               mlt_properties_set_data( properties, "image", output, owidth * ( oheight + 1 ) * 2, ( mlt_destructor )mlt_pool_release, NULL );
-               mlt_properties_set_int( properties, "width", owidth );
-               mlt_properties_set_int( properties, "height", oheight );
+                       g_object_unref( scaled );
 
-               *image = output;
+                       // Now update the frame
+                       mlt_frame_set_image( this, output, size, mlt_pool_release );
+       
+                       // Return the output
+                       *image = output;
+               }
+               break;
+       }
+       default:
+               break;
        }
 
        return 0;
@@ -135,10 +125,10 @@ static int filter_scale( mlt_frame this, uint8_t **image, mlt_image_format iform
 /** Constructor for the filter.
 */
 
-mlt_filter filter_rescale_init( char *arg )
+mlt_filter filter_rescale_init( mlt_profile profile, char *arg )
 {
        // Create a new scaler
-       mlt_filter this = mlt_factory_filter( "rescale", arg );
+       mlt_filter this = mlt_factory_filter( profile, "rescale", arg );
 
        // If successful, then initialise it
        if ( this != NULL )