Skip to content
Merged

Cropofx #1257

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion src/framework/metaschema.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -184,4 +184,6 @@ mapping:
"normalized_coordinates": # For types that represent coordinates, whether values are normalized to 0..1
type: bool
default: no

"normalized_default": # Whether the default value is normalized to 0..1
type: bool
default: no
32 changes: 22 additions & 10 deletions src/modules/openfx/filter_openfx.c
Original file line number Diff line number Diff line change
Expand Up @@ -223,19 +223,31 @@ static void update_plugin_params(mlt_properties properties,
if (!mlt_properties_exists(properties, param_name))
continue;
char *type = mlt_properties_get(param, "type");
char *widget = mlt_properties_get(param, "widget");
if (!type)
continue;
if (widget && (strcmp(widget, "point") == 0 || strcmp(widget, "size") == 0)
&& strcmp(type, "float") == 0) {
if (strcmp(type, "rect") == 0) {
mlt_rect value = mlt_properties_anim_get_rect(properties, param_name, position, length);
mltofx_param_set_value(image_effect_params, param_name, mltofx_prop_double2d, value);
} else if (widget && (strcmp(widget, "point") == 0 || strcmp(widget, "size") == 0)
&& strcmp(type, "integer") == 0) {
mlt_rect value = mlt_properties_anim_get_rect(properties, param_name, position, length);
int x = (int) value.x;
int y = (int) value.y;
mltofx_param_set_value(image_effect_params, param_name, mltofx_prop_int2d, x, y);
// Look up the native OFX param type to select the correct setter
mlt_properties ofx_param = mlt_properties_get_properties(image_effect_params,
param_name);
const char *ofx_type = ofx_param ? mlt_properties_get(ofx_param, "t") : NULL;
if (ofx_type && strcmp(ofx_type, kOfxParamTypeInteger2D) == 0)
mltofx_param_set_value(image_effect_params,
param_name,
mltofx_prop_int2d,
(int) value.x,
(int) value.y);
else if (ofx_type && strcmp(ofx_type, kOfxParamTypeDouble3D) == 0)
mltofx_param_set_value(image_effect_params, param_name, mltofx_prop_double3d, value);
else if (ofx_type && strcmp(ofx_type, kOfxParamTypeInteger3D) == 0)
mltofx_param_set_value(image_effect_params,
param_name,
mltofx_prop_int3d,
(int) value.x,
(int) value.y,
(int) value.w);
else
mltofx_param_set_value(image_effect_params, param_name, mltofx_prop_double2d, value);
} else if (strcmp(type, "float") == 0) {
double value = mlt_properties_anim_get_double(properties, param_name, position, length);
mltofx_param_set_value(image_effect_params, param_name, mltofx_prop_double, value);
Expand Down
196 changes: 161 additions & 35 deletions src/modules/openfx/mlt_openfx.c
Original file line number Diff line number Diff line change
Expand Up @@ -731,6 +731,8 @@ static OfxStatus paramDefine(OfxParamSetHandle paramSet,
mlt_properties param_props = mlt_properties_new();
mlt_properties_set_properties(pt, "p", param_props);
mlt_properties_close(param_props);
// Back-reference to the paramSet so paramGetValueImpl can navigate to image_effect.
mlt_properties_set_data(pt, "_ps", params, 0, NULL, NULL);
mlt_properties_set_properties(params, name, pt);
mlt_properties_close(pt);

Expand Down Expand Up @@ -1039,6 +1041,53 @@ static OfxStatus paramGetValueImpl(OfxParamHandle paramHandle, va_list ap)
if (status != kOfxStatOK) {
*X = 0.0;
*Y = 0.0;
} else {
// If the default was declared in normalised coordinates, convert to canonical.
// kOfxParamPropDefaultCoordinateSystem may be set on the effect descriptor
// (via getPropertySet) rather than on the individual param descriptor.
mlt_properties paramset = mlt_properties_get_data(param, "_ps", NULL);
mlt_properties plugin_props = paramset
? mlt_properties_get_properties(paramset,
"plugin_props")
: NULL;
mlt_properties ie = plugin_props
? (mlt_properties) mlt_properties_get_data(plugin_props,
"_ie",
NULL)
: NULL;
char *coord_sys = kOfxParamCoordinatesCanonical;
OfxStatus cs_on_param = propGetString((OfxPropertySetHandle) param_props,
kOfxParamPropDefaultCoordinateSystem,
0,
&coord_sys);
if (cs_on_param != kOfxStatOK) {
coord_sys = kOfxParamCoordinatesCanonical;
if (ie) {
mlt_properties effect_props = mlt_properties_get_properties(ie, "props");
if (effect_props)
propGetString((OfxPropertySetHandle) effect_props,
kOfxParamPropDefaultCoordinateSystem,
0,
&coord_sys);
}
}
if (strcmp(coord_sys, kOfxParamCoordinatesNormalised) == 0) {
if (ie) {
double ext_w = 0.0, ext_h = 0.0;
propGetDouble((OfxPropertySetHandle) ie,
kOfxImageEffectPropProjectExtent,
0,
&ext_w);
propGetDouble((OfxPropertySetHandle) ie,
kOfxImageEffectPropProjectExtent,
1,
&ext_h);
if (ext_w > 0.0)
*X *= ext_w;
if (ext_h > 0.0)
*Y *= ext_h;
}
}
}
}
} else if (strcmp(param_type, kOfxParamTypeInteger2D) == 0) {
Expand Down Expand Up @@ -2912,6 +2961,9 @@ void *mltofx_fetch_params(OfxPlugin *plugin, mlt_properties params, mlt_properti
mlt_properties_set_properties(image_effect, "params", iparams);
mlt_properties_set_properties(iparams, "plugin_props", props);
mlt_properties_set_properties(image_effect, "mltofx_params", params);
// Back-reference to image_effect stored on plugin_props so paramGetValueImpl
// can access project extent without disturbing the param iteration loop.
mlt_properties_set_data(props, "_ie", image_effect, 0, NULL, NULL);

propSetString((OfxPropertySetHandle) props,
kOfxImageEffectPropContext,
Expand Down Expand Up @@ -3067,32 +3119,42 @@ void *mltofx_fetch_params(OfxPlugin *plugin, mlt_properties params, mlt_properti
|| strcmp(param_type, kOfxParamTypeRGB) == 0) {
mlt_properties_set(p, "type", "color");
mlt_properties_set(p, "widget", "color");
} else if (strcmp(param_type, kOfxParamTypeDouble2D)
== 0) { // can be rendered as 2 double number input fields
mlt_properties_set(p, "type", "float");
} else if (strcmp(param_type, kOfxParamTypeDouble2D) == 0) {
mlt_properties_set(p, "type", "rect");

char *type = kOfxParamDoubleTypeXY;
char *coordinate_system = kOfxParamCoordinatesCanonical;
propGetString((OfxPropertySetHandle) ppp, kOfxParamPropDoubleType, 0, &type);
propGetString((OfxPropertySetHandle) ppp,
kOfxParamPropDefaultCoordinateSystem,
0,
&coordinate_system);

if (strcmp(type, kOfxParamDoubleTypeXYAbsolute) == 0) {
mlt_properties_set(p, "widget", "point");
mlt_properties_set(p, "normalized_coordinates", "no");
} else if (strcmp(type, kOfxParamDoubleTypeXY) == 0) {
mlt_properties_set(p, "widget", "size");
mlt_properties_set(p, "normalized_coordinates", "no");
}

if (strcmp(coordinate_system, kOfxParamCoordinatesCanonical) == 0) {
mlt_properties_set(p, "normalized_coordinates", "no");
} else if (strcmp(coordinate_system, kOfxParamCoordinatesNormalised) == 0) {
mlt_properties_set(p, "normalized_coordinates", "yes");
char *default_coords = "";
OfxStatus status = propGetString((OfxPropertySetHandle) ppp,
kOfxParamPropDefaultCoordinateSystem,
0,
&default_coords);
if (status == kOfxStatOK) {
if (!strcmp(default_coords, kOfxParamCoordinatesCanonical)) {
mlt_properties_set(p, "normalized_default", "no");
} else if (!strcmp(default_coords, kOfxParamCoordinatesNormalised)) {
mlt_properties_set(p, "normalized_default", "yes");
}
} else if (plugin && plugin->pluginIdentifier
&& !strcmp("net.sf.openfx.CropPlugin", plugin->pluginIdentifier)) {
// Workaround for the crop plugin which does not report
// default coordinates, but uses normalized.
mlt_properties_set(p, "normalized_default", "yes");
}
} else if (strcmp(param_type, kOfxParamTypeInteger2D) == 0) {
// can be rendered as 2 integer number input fields
mlt_properties_set(p, "type", "integer");
mlt_properties_set(p, "type", "rect");
} else if (strcmp(param_type, kOfxParamTypeDouble3D) == 0) {
mlt_properties_set(p, "type", "rect");
} else if (strcmp(param_type, kOfxParamTypeInteger3D) == 0) {
mlt_properties_set(p, "type", "rect");
}

int layout_hint = 0;
Expand Down Expand Up @@ -3155,26 +3217,54 @@ void *mltofx_fetch_params(OfxPlugin *plugin, mlt_properties params, mlt_properti
propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &default_value);
mlt_properties_set_double(p, "default", default_value);
} else if (strcmp(param_type, kOfxParamTypeDouble2D) == 0) {
double default_value1 = 0.0, default_value2 = 0.0;

propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &default_value1);
propGetDouble((OfxPropertySetHandle) ppp, p_name, 1, &default_value2);

// for some reason with DBL_MIN DBL_MAX it segfault
if (!isnormal(default_value1) || default_value1 <= FLT_MIN
|| default_value1 >= FLT_MAX)
default_value1 = 0.0;
if (!isnormal(default_value2) || default_value2 <= FLT_MIN
|| default_value2 >= FLT_MAX)
default_value2 = 0.0;

char default_value[90] = "";
snprintf(default_value,
sizeof(default_value),
"%.4f %.4f",
default_value1,
default_value2);
mlt_properties_set(p, "default", default_value);
double x = 0.0, y = 0.0;

propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &x);
propGetDouble((OfxPropertySetHandle) ppp, p_name, 1, &y);

// Validate and sanitize values
if (!isnormal(x) || x <= FLT_MIN || x >= FLT_MAX)
x = 0.0;
if (!isnormal(y) || y <= FLT_MIN || y >= FLT_MAX)
y = 0.0;

char rect_str[100];
snprintf(rect_str, sizeof(rect_str), "%g %g", x, y);
mlt_properties_set(p, "default", rect_str);

} else if (strcmp(param_type, kOfxParamTypeInteger2D) == 0) {
int ix = 0, iy = 0;
propGetInt((OfxPropertySetHandle) ppp, p_name, 0, &ix);
propGetInt((OfxPropertySetHandle) ppp, p_name, 1, &iy);
char rect_str[100];
snprintf(rect_str, sizeof(rect_str), "%d %d", ix, iy);
mlt_properties_set(p, "default", rect_str);

} else if (strcmp(param_type, kOfxParamTypeDouble3D) == 0) {
double x3 = 0.0, y3 = 0.0, z3 = 0.0;
propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &x3);
propGetDouble((OfxPropertySetHandle) ppp, p_name, 1, &y3);
propGetDouble((OfxPropertySetHandle) ppp, p_name, 2, &z3);
if (!isnormal(x3) || x3 <= FLT_MIN || x3 >= FLT_MAX)
x3 = 0.0;
if (!isnormal(y3) || y3 <= FLT_MIN || y3 >= FLT_MAX)
y3 = 0.0;
if (!isnormal(z3) || z3 <= FLT_MIN || z3 >= FLT_MAX)
z3 = 0.0;
// rect.w holds the third dimension
char rect_str[100];
snprintf(rect_str, sizeof(rect_str), "%g %g %g", x3, y3, z3);
mlt_properties_set(p, "default", rect_str);

} else if (strcmp(param_type, kOfxParamTypeInteger3D) == 0) {
int ix = 0, iy = 0, iz = 0;
propGetInt((OfxPropertySetHandle) ppp, p_name, 0, &ix);
propGetInt((OfxPropertySetHandle) ppp, p_name, 1, &iy);
propGetInt((OfxPropertySetHandle) ppp, p_name, 2, &iz);
// rect.w holds the third dimension
char rect_str[100];
snprintf(rect_str, sizeof(rect_str), "%d %d %d", ix, iy, iz);
mlt_properties_set(p, "default", rect_str);

} else if (strcmp(param_type, kOfxParamTypeString) == 0) {
char *default_value = "";
Expand Down Expand Up @@ -3251,6 +3341,16 @@ void *mltofx_fetch_params(OfxPlugin *plugin, mlt_properties params, mlt_properti
double minimum_value = 0.0;
propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &minimum_value);
mlt_properties_set_double(p, "minimum", minimum_value);
} else if (strcmp(param_type, kOfxParamTypeDouble2D) == 0) {
min_set = 1;
double minimum_value = 0.0;
propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &minimum_value);
mlt_properties_set_double(p, "minimum", minimum_value);
} else if (strcmp(param_type, kOfxParamTypeInteger2D) == 0) {
min_set = 1;
int minimum_value = 0;
propGetInt((OfxPropertySetHandle) ppp, p_name, 0, &minimum_value);
mlt_properties_set_int(p, "minimum", minimum_value);
} else if (strcmp(param_type, kOfxParamTypeString) == 0) {
char *minimum_value = "";
propGetString((OfxPropertySetHandle) ppp, p_name, 0, &minimum_value);
Expand All @@ -3269,6 +3369,16 @@ void *mltofx_fetch_params(OfxPlugin *plugin, mlt_properties params, mlt_properti
double maximum_value = 0.0;
propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &maximum_value);
mlt_properties_set_double(p, "maximum", maximum_value);
} else if (strcmp(param_type, kOfxParamTypeDouble2D) == 0) {
max_set = 1;
double maximum_value = 0.0;
propGetDouble((OfxPropertySetHandle) ppp, p_name, 0, &maximum_value);
mlt_properties_set_double(p, "maximum", maximum_value);
} else if (strcmp(param_type, kOfxParamTypeInteger2D) == 0) {
max_set = 1;
int maximum_value = 0;
propGetInt((OfxPropertySetHandle) ppp, p_name, 0, &maximum_value);
mlt_properties_set_int(p, "maximum", maximum_value);
} else if (strcmp(param_type, kOfxParamTypeString) == 0) {
char *maximum_value = "";
propGetString((OfxPropertySetHandle) ppp, p_name, 0, &maximum_value);
Expand Down Expand Up @@ -3353,6 +3463,22 @@ void mltofx_param_set_value(mlt_properties params, char *key, mltofx_property_ty
propSetInt((OfxPropertySetHandle) param_props, "MltOfxParamValue", 1, y);
} break;

case mltofx_prop_double3d: {
mlt_rect value = va_arg(ap, mlt_rect);
propSetDouble((OfxPropertySetHandle) param_props, "MltOfxParamValue", 0, value.x);
propSetDouble((OfxPropertySetHandle) param_props, "MltOfxParamValue", 1, value.y);
propSetDouble((OfxPropertySetHandle) param_props, "MltOfxParamValue", 2, value.w);
} break;

case mltofx_prop_int3d: {
int x = va_arg(ap, int);
int y = va_arg(ap, int);
int z = va_arg(ap, int);
propSetInt((OfxPropertySetHandle) param_props, "MltOfxParamValue", 0, x);
propSetInt((OfxPropertySetHandle) param_props, "MltOfxParamValue", 1, y);
propSetInt((OfxPropertySetHandle) param_props, "MltOfxParamValue", 2, z);
} break;

default:
break;
}
Expand Down
2 changes: 2 additions & 0 deletions src/modules/openfx/mlt_openfx.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ typedef enum {
mltofx_prop_color = 32,
mltofx_prop_double2d = 64,
mltofx_prop_int2d = 128,
mltofx_prop_double3d = 256,
mltofx_prop_int3d = 512,
} mltofx_property_type;

typedef enum {
Expand Down
Loading