#include <stdlib.h>
#include <assert.h>
-#include "glsl_manager.h"
+#include "filter_glsl_manager.h"
#include <movit/init.h>
#include <movit/padding_effect.h>
+#include "optional_effect.h"
static float alignment_parse( char* align )
{
return ret;
}
-static struct mlt_geometry_item_s get_geometry( mlt_profile profile, mlt_filter filter, mlt_frame frame )
-{
- mlt_properties properties = MLT_FRAME_PROPERTIES( frame );
- mlt_properties filter_props = MLT_FILTER_PROPERTIES( filter );
- struct mlt_geometry_item_s item;
- mlt_geometry geometry = (mlt_geometry) mlt_properties_get_data( filter_props, "geometry", NULL );
- char *string = mlt_properties_get( properties, "resize.geometry" );
- int length = mlt_filter_get_length2( filter, frame );
-
- if ( !geometry ) {
- geometry = mlt_geometry_init();
- mlt_properties_set_data( filter_props, "geometry", geometry, 0,
- (mlt_destructor) mlt_geometry_close, NULL );
- mlt_geometry_parse( geometry, string, length, profile->width, profile->height );
- } else {
- mlt_geometry_refresh( geometry, string, length, profile->width, profile->height );
- }
-
- mlt_geometry_fetch( geometry, &item, mlt_filter_get_position( filter, frame ) );
-
- if ( !mlt_properties_get_int( properties, "resize.fill" ) ) {
- int x = mlt_properties_get_int( properties, "meta.media.width" );
- item.w = item.w > x ? x : item.w;
- x = mlt_properties_get_int( properties, "meta.media.height" );
- item.h = item.h > x ? x : item.h;
- }
-
- return item;
-}
-
static int get_image( mlt_frame frame, uint8_t **image, mlt_image_format *format, int *width, int *height, int writable )
{
int error = 0;
int owidth = *width;
int oheight = *height;
- // Use a geometry to compute position and size
- struct mlt_geometry_item_s geometry_item;
- geometry_item.x = geometry_item.y = 0.0f;
- geometry_item.distort = 0;
- if ( mlt_properties_get( properties, "resize.geometry" ) ) {
- geometry_item = get_geometry( profile, filter, frame );
- owidth = lrintf( geometry_item.w );
- oheight = lrintf( geometry_item.h );
+ // Use a mlt_rect to compute position and size
+ mlt_rect rect;
+ rect.x = rect.y = 0.0;
+ if ( mlt_properties_get( properties, "resize.rect" ) ) {
+ mlt_position position = mlt_filter_get_position( filter, frame );
+ mlt_position length = mlt_filter_get_length2( filter, frame );
+ rect = mlt_properties_anim_get_rect( properties, "resize.rect", position, length );
+ if ( strchr( mlt_properties_get( properties, "resize.rect" ), '%' ) ) {
+ rect.x *= profile->width;
+ rect.w *= profile->width;
+ rect.y *= profile->height;
+ rect.h *= profile->height;
+ }
+ if ( !mlt_properties_get_int( properties, "resize.fill" ) ) {
+ int x = mlt_properties_get_int( properties, "meta.media.width" );
+ rect.w = rect.w > x ? x : rect.w;
+ x = mlt_properties_get_int( properties, "meta.media.height" );
+ rect.h = rect.h > x ? x : rect.h;
+ }
+ owidth = lrintf( rect.w );
+ oheight = lrintf( rect.h );
}
// Check for the special case - no aspect ratio means no problem :-)
if ( *format == mlt_image_none || ( rescale && !strcmp( rescale, "none" ) ) )
return mlt_frame_get_image( frame, image, format, width, height, writable );
- if ( mlt_properties_get_int( properties, "distort" ) == 0 &&
- geometry_item.distort == 0 )
+ if ( mlt_properties_get_int( properties, "distort" ) == 0 )
{
// Normalise the input and out display aspect
int normalised_width = profile->width;
// Offset the position according to alignment
float w = float( *width - owidth );
float h = float( *height - oheight );
- if ( mlt_properties_get( properties, "resize.geometry" ) ) {
- // default left if geometry supplied
- geometry_item.x += w * alignment_parse( mlt_properties_get( properties, "resize.halign" ) ) / 2.0f;
- geometry_item.y += h * alignment_parse( mlt_properties_get( properties, "resize.valign" ) ) / 2.0f;
+ if ( mlt_properties_get( properties, "resize.rect" ) ) {
+ // default left if rect supplied
+ rect.x += w * alignment_parse( mlt_properties_get( properties, "resize.halign" ) ) / 2.0f;
+ rect.y += h * alignment_parse( mlt_properties_get( properties, "resize.valign" ) ) / 2.0f;
} else {
- // default center if no geometry
- geometry_item.x = w * 0.5f;
- geometry_item.y = h * 0.5f;
+ // default center if no rect
+ rect.x = w * 0.5f;
+ rect.y = h * 0.5f;
}
if ( !error ) {
+ mlt_properties filter_properties = MLT_FILTER_PROPERTIES( filter );
GlslManager::get_instance()->lock_service( frame );
- Effect* effect = GlslManager::get_effect( filter, frame );
- if ( effect ) {
- bool ok = effect->set_int( "width", *width );
- ok |= effect->set_int( "height", *height );
- ok |= effect->set_float( "left", geometry_item.x );
- ok |= effect->set_float( "top", geometry_item.y );
- assert(ok);
- }
+ mlt_properties_set_int( filter_properties, "movit.parms.int.width", *width );
+ mlt_properties_set_int( filter_properties, "movit.parms.int.height", *height );
+ mlt_properties_set_double( filter_properties, "movit.parms.float.left", rect.x );
+ mlt_properties_set_double( filter_properties, "movit.parms.float.top", rect.y );
+
+ bool disable = ( *width == owidth && *height == oheight );
+ mlt_properties_set_int( filter_properties, "movit.parms.int.disable", disable );
+
GlslManager::get_instance()->unlock_service( frame );
+
+ GlslManager::set_effect_input( MLT_FILTER_SERVICE( filter ), frame, (mlt_service) *image );
+ GlslManager::set_effect( MLT_FILTER_SERVICE( filter ), frame, new OptionalEffect<PaddingEffect> );
+ *image = (uint8_t *) MLT_FILTER_SERVICE( filter );
+ return error;
}
return error;
static mlt_frame process( mlt_filter filter, mlt_frame frame )
{
- if ( !GlslManager::get_effect( filter, frame ) )
- GlslManager::add_effect( filter, frame, new PaddingEffect );
mlt_frame_push_service( frame, filter );
mlt_frame_push_get_image( frame, get_image );
return frame;