luma key use alpha channel in mode 3 to blend, fix chroma key (use different algorithm), added alpha:select by chroma key, added alpha blend

This commit is contained in:
niels
2015-11-06 23:29:24 +01:00
parent 565d333f35
commit 05e45a8caa
11 changed files with 437 additions and 319 deletions

View File

@@ -96,6 +96,7 @@ libvje_la_SOURCES = vj-effect.c vj-effman.c effects/common.c \
effects/contourextract.c effects/maskstop.c effects/photoplay.c effects/videoplay.c effects/rgbchannel.c \
effects/videowall.c effects/flare.c effects/radioactive.c effects/baltantv.c effects/constantblend.c effects/picinpic.c effects/bgsubtract.c effects/cali.c effects/median.c effects/average-blend.c effects/perspective.c \
effects/toalpha.c effects/mixtoalpha.c effects/alpha2img.c effects/alphafill.c effects/alphaflatten.c \
effects/magicalphaoverlays.c effects/travelmatte.c effects/feathermask.c effects/alphaselect.c
effects/magicalphaoverlays.c effects/travelmatte.c effects/feathermask.c effects/alphaselect.c \
effects/alphaselect2.c effects/alphablend.c

View File

@@ -0,0 +1,59 @@
/*
* Linux VeeJay
*
* Copyright(C)2015 Niels Elburg <nelburg@gmail.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License , or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307 , USA.
*/
#include <config.h>
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <libvjmem/vjmem.h>
#include "alphablend.h"
#include "common.h"
vj_effect *alphablend_init(int w, int h)
{
vj_effect *ve = (vj_effect *) vj_calloc(sizeof(vj_effect));
ve->num_params = 0;
ve->description = "Alpha: Blend";
ve->sub_format = 1;
ve->extra_frame = 1;
ve->parallel = 1;
ve->has_user = 0;
return ve;
}
static inline int blend_plane( uint8_t *dst, uint8_t *A, uint8_t *B, uint8_t *aA, int size )
{
unsigned int i;
for( i = 0; i < size; i ++ )
{
unsigned int op0 = aA[i];
unsigned int op1 = 0xff - op0;
dst[i] = (op1 * A[i] + op0 * B[i] ) >> 8;
}
return 0;
}
void alphablend_apply( VJFrame *frame, VJFrame *frame2, int width,int height)
{
int uv_len = (frame->ssm ? frame->len : frame->uv_len );
blend_plane( frame->data[0], frame->data[0], frame2->data[0], frame2->data[3], frame->len );
blend_plane( frame->data[1], frame->data[1], frame2->data[1], frame2->data[3], uv_len );
blend_plane( frame->data[2], frame->data[2], frame2->data[2], frame2->data[3], uv_len );
}

View File

@@ -0,0 +1,30 @@
/*
* Linux VeeJay
*
* Copyright(C)2015 Niels Elburg <nwelburg@gmail.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License , or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307 , USA.
*/
#ifndef ALPHABLEND_H
#define ALPHABLEND_H
#include <libvje/vje.h>
#include <sys/types.h>
#include <stdint.h>
vj_effect *alphablend_init(int w, int h);
void alphablend_apply( VJFrame *frame, VJFrame *frame2, int width,int height);
#endif

View File

@@ -0,0 +1,167 @@
/*
* Linux VeeJay
*
* Copyright(C)2015 Niels Elburg <nelburg@gmail.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License , or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307 , USA.
*/
/*
* originally from http://gc-films.com/chromakey.html
*/
#include <stdint.h>
#include <stdio.h>
#include <libvjmem/vjmem.h>
#include "rgbkey.h"
#include <math.h>
#include "common.h"
vj_effect *alphaselect2_init(int w, int h)
{
vj_effect *ve;
ve = (vj_effect *) vj_calloc(sizeof(vj_effect));
ve->num_params = 7;
ve->defaults = (int *) vj_calloc(sizeof(int) * ve->num_params); /* default values */
ve->limits[0] = (int *) vj_calloc(sizeof(int) * ve->num_params); /* min */
ve->limits[1] = (int *) vj_calloc(sizeof(int) * ve->num_params); /* max */
ve->defaults[0] = 15; /* tolerance near */
ve->defaults[1] = 0; /* r */
ve->defaults[2] = 255; /* g */
ve->defaults[3] = 0; /* b */
ve->defaults[4] = 15; /* tolerance far */
ve->defaults[5] = 1; /* show alpha */
ve->defaults[6] = 0; /* use existing alpha */
ve->limits[0][0] = 1;
ve->limits[1][0] = 255;
ve->limits[0][1] = 0;
ve->limits[1][1] = 255;
ve->limits[0][2] = 0;
ve->limits[1][2] = 255;
ve->limits[0][3] = 0;
ve->limits[1][3] = 255;
ve->limits[0][4] = 0;
ve->limits[1][4] = 255;
ve->limits[0][5] = 0;
ve->limits[1][5] = 1;
ve->limits[0][6] = 0;
ve->limits[1][6] = 1;
ve->has_user = 0;
ve->parallel = 1;
ve->description = "Alpha: Select by chroma key";
ve->extra_frame = 0;
ve->sub_format = 1;
ve->rgb_conv = 1;
ve->param_description = vje_build_param_list(ve->num_params,"Tolerance Near","Red","Green","Blue", "Tolerance Far", "Show Mask", "Use Alpha-IN");
return ve;
}
static inline double color_distance( uint8_t Cb, uint8_t Cr, int Cbk, int Crk, int dA, int dB )
{
double tmp = 0.0;
fast_sqrt( tmp, (Cbk - Cb) * (Cbk-Cb) + (Crk - Cr) * (Crk - Cr) );
if( tmp < dA ) { /* near color key == bg */
return 0.0;
}
if( tmp < dB ) { /* middle region */
return (tmp - dA)/(dB - dA); /* distance to key color */
}
return 1.0; /* far from color key == fg */
}
void alphaselect2_apply( VJFrame *frame, int width,
int height, int tola, int r, int g,
int b, int tolb, int show, int alpha)
{
unsigned int pos;
uint8_t *Y = frame->data[0];
uint8_t *Cb = frame->data[1];
uint8_t *Cr = frame->data[2];
uint8_t *A = frame->data[3];
int cb,cr,iy,iu,iv;
_rgb2yuv(r,g,b,iy,iu,iv);
if( show ) {
if( alpha ) {
for (pos = (width * height); pos != 0; pos--) {
if(A[pos] == 0)
continue;
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
A[pos] = (uint8_t) (d * 255.0);
if( A[pos] < 255 ) {
Y[pos] = Y[pos] * d;
Cb[pos] = 128;
Cr[pos] = 128;
}
else if( A[pos] == 0) {
Cb[pos] = 128;
Cr[pos] = 128;
Y[pos] = pixel_Y_lo_;
}
}
}
else
{
for (pos = (width * height); pos != 0; pos--) {
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
A[pos] = (uint8_t) (d * 255.0);
if( A[pos] < 255 ) {
Y[pos] = Y[pos] * d;
Cb[pos] = 128;
Cr[pos] = 128;
}
else if (A[pos] == 0) {
Cb[pos] = 128;
Cr[pos] = 128;
Y[pos] = pixel_Y_lo_;
}
/* A[pos] = (uint8_t) (d * 255.0);
Y[pos] = (d * 255);
Cb[pos] = 128;
Cr[pos] = 128; */
}
}
}
else {
if( alpha ) {
for (pos = (width * height); pos != 0; pos--) {
if( A[pos] == 0 )
continue;
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
A[pos] = (uint8_t) (d * 255.0);
}
}
else {
for (pos = (width * height); pos != 0; pos--) {
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
A[pos] = (uint8_t) (d * 255.0);
}
}
}
}

View File

@@ -74,18 +74,15 @@ void lumakey_simple_alpha(uint8_t *yuv1[4], uint8_t *yuv2[4], int width,
a1 = yuv1[0][x + y];
a2 = yuv2[0][x + y];
/*
if ( a1 >= threshold && a1 <= threshold2) {
Y = (op0 * a1 + op1 * a2 )/255;
Cb = (op0 * yuv1[1][x+y] + op1 * yuv2[1][x+y])/255;
Cr =(op0 * yuv1[2][x+y] + op1 * yuv2[2][x+y])/255;
}
*/
if (a1 >= threshold && a1 <= threshold2) {
Y = ((op0 * a1) + (op1 * a2)) >> 8;
Cb = ((op0 * yuv1[1][x + y]) + (op1 * yuv2[1][x + y])) >> 8;
Cr = ((op0 * yuv1[2][x + y]) + (op1 * yuv2[2][x + y])) >> 8;
if (a1 >= threshold && a1 <= threshold2) {
alpha = ((op0 * yuv1[3][x+y]) + (op1 * yuv2[3][x+y]) )>> 8;
unsigned int aA = 255 - alpha;
unsigned int aB = alpha;
Y = ((aA * a1) + (aB * a2)) >> 8;
Cb = ((aA * yuv1[1][x + y]) + (aB * yuv2[1][x + y])) >> 8;
Cr = ((aA * yuv1[2][x + y]) + (aB * yuv2[2][x + y])) >> 8;
yuv1[0][x + y] = Y; // < 16 ? 16 : Y > 235 ? 235 : Y;
yuv1[1][x + y] = Cb; // < 16 ? 16 : Cb > 240 ? 240 : Cb;
yuv1[2][x + y] = Cr; // < 16 ? 16 : Cr > 240 ? 240 : Cr;

View File

@@ -1,7 +1,7 @@
/*
* Linux VeeJay
*
* Copyright(C)2004 Niels Elburg <elburg@hio.hen.nl>
* Copyright(C)2004 Niels Elburg <nwelburg@gmail.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -25,41 +25,28 @@
#include <math.h>
#include "common.h"
/*
This effect is based on this small project:
http://www.cs.utah.edu/~michael/chroma/
The algorithm decides which pixels belong to resp. foreground
or background. Other effects that make use of this same algorithm are
Complex Invert, Complex Negation, Complex Saturation, Smooth RGB Key
Isolate by Color , Complex Threshold and Blend by Color Key,
*/
/*
(march,2005) fixed flaw (signed vs. unsigned) in algorithm
use selectable rgb -> yuv formula,
* originally from http://gc-films.com/chromakey.html
*/
vj_effect *rgbkey_init(int w,int h)
{
vj_effect *ve;
ve = (vj_effect *) vj_calloc(sizeof(vj_effect));
ve->num_params = 6;
ve->num_params = 7;
ve->defaults = (int *) vj_calloc(sizeof(int) * ve->num_params); /* default values */
ve->limits[0] = (int *) vj_calloc(sizeof(int) * ve->num_params); /* min */
ve->limits[1] = (int *) vj_calloc(sizeof(int) * ve->num_params); /* max */
ve->defaults[0] = 4500; /* angle , 45 degrees*/
ve->defaults[0] = 15; /* tolerance near */
ve->defaults[1] = 0; /* r */
ve->defaults[2] = 0; /* g */
ve->defaults[3] = 255; /* b */
ve->defaults[4] = 1; /* type */
ve->defaults[5] = 1200; /* noise */
ve->defaults[2] = 255; /* g */
ve->defaults[3] = 0; /* b */
ve->defaults[4] = 1; /* tolerance far */
ve->defaults[5] = 1; /* show selection */
ve->defaults[6] = 0; /* use alpha */
ve->limits[0][0] = 1;
ve->limits[1][0] = 9000;
ve->limits[1][0] = 255;
ve->limits[0][1] = 0;
ve->limits[1][1] = 255;
@@ -71,12 +58,15 @@ vj_effect *rgbkey_init(int w,int h)
ve->limits[1][3] = 255;
ve->limits[0][4] = 0;
ve->limits[1][4] = 1; /* total noise suppression off */
ve->limits[1][4] = 255;
ve->limits[0][5] = 0;
ve->limits[1][5] = 5500;
ve->limits[1][5] = 1;
ve->param_description = vje_build_param_list(ve->num_params, "Angle", "Red", "Green", "Blue", "Mode", "Noise suppression");
ve->limits[0][6] = 0;
ve->limits[1][6] = 4; /* logical alpha operator */
ve->param_description = vje_build_param_list(ve->num_params, "Tolerance Near", "Red", "Green", "Blue", "Tolerance Far", "Show FG", "Alpa operator");
ve->has_user = 0;
ve->description = "Chroma Key (RGB)";
ve->extra_frame = 1;
@@ -85,250 +75,137 @@ vj_effect *rgbkey_init(int w,int h)
ve->parallel = 1;
return ve;
}
/*
void rgbkey_scan_fg(uint8_t * src2[3], int *r, int *g, int *b)
static inline double color_distance( uint8_t Cb, uint8_t Cr, int Cbk, int Crk, int dA, int dB )
{
*r = (int) (+(1.0 * Y2[0]) + (0 * Cb2[0]) +
(1.402 * Cr2[0]));
*g = (int) (+(1.0 * Y2[0]) - (0.344136 * Cb2[0]) +
(-0.714136 * Cr2[0]));
*b = (int) (+(1.0 * Y2[0]) + (1.772 * Cb2[0]) +
(0 * Cr2[0]));
}
*/
void rgbkey_apply1(VJFrame *frame, VJFrame *frame2, int width,
int height, int i_angle, int r, int g,
int b, int i_noise)
{
uint8_t *fg_y, *fg_cb, *fg_cr;
uint8_t *bg_y, *bg_cb, *bg_cr;
int accept_angle_tg, accept_angle_ctg, one_over_kc;
int kfgy_scale, kg;
uint8_t cb, cr;
int kbg, x1, y1;
float kg1, tmp, aa = 255.0f, bb = 255.0f, _y = 0;
float angle = (float) i_angle / 100.0f;
float noise_level = (i_noise / 100.0f);
unsigned int pos;
uint8_t val, tmp1;
uint8_t *Y = frame->data[0];
uint8_t *Cb= frame->data[1];
uint8_t *Cr= frame->data[2];
uint8_t *Y2 = frame2->data[0];
uint8_t *Cb2= frame2->data[1];
uint8_t *Cr2= frame2->data[2];
uint8_t iy,iu,iv;
_rgb2yuv( r,g,b, iy,iu,iv );
_y = (float) iy;
aa = (float) iu;
bb = (float) iv;
tmp = sqrt(((aa * aa) + (bb * bb)));
cb = 0xff * (aa / tmp);
cr = 0xff * (bb / tmp);
kg1 = tmp;
/* obtain coordinate system for cb / cr */
accept_angle_tg = (int)( 15.0f * tanf(M_PI * angle / 180.0f));
accept_angle_ctg= (int)( 15.0f / tanf(M_PI * angle / 180.0f));
tmp = 1 / kg1;
one_over_kc = 0xff * 2 * tmp - 0xff;
kfgy_scale = 0xf * (float) (_y) / kg1;
kg = kg1;
/* intialize pointers */
fg_y = Y;
fg_cb = Cb;
fg_cr = Cr;
/* 2005: swap these !! */
bg_y = Y2;
bg_cb = Cb2;
bg_cr = Cr2;
for (pos = (width * height); pos != 0; pos--) {
short xx, yy;
/* convert foreground to xz coordinates where x direction is
defined by key color */
xx = (((fg_cb[pos]) * cb) + ((fg_cr[pos]) * cr)) >> 7;
yy = (((fg_cr[pos]) * cb) - ((fg_cb[pos]) * cr)) >> 7;
/* accept angle should not be > 90 degrees
reasonable results between 10 and 80 degrees.
*/
val = (xx * accept_angle_tg) >> 4;
if (abs(yy) < val) {
/* compute fg, suppress fg in xz according to kfg
*/
val = (yy * accept_angle_ctg) >> 4;
x1 = abs(val);
y1 = yy;
tmp1 = xx - x1;
kbg = (tmp1 * one_over_kc) >> 1;
if (kbg < 0)
kbg = 0;
if (kbg > 255)
kbg = 255;
val = (tmp1 * kfgy_scale) >> 4;
if( val > 255 )
val = 255;
val = fg_y[pos] - val;
Y[pos] = val;
// convert suppressed fg back to cbcr
Cb[pos] = ((x1 * cb) - (y1 * cr)) >> 7;
Cr[pos] = ((x1 * cr) - (y1 * cb)) >> 7;
// deal with noise
val = (yy * yy) + (kg * kg);
if (val < (noise_level * noise_level)) {
kbg = 255;
Y[pos] = bg_y[pos];
Cb[pos] = bg_cb[pos];
Cr[pos] = bg_cr[pos];
}
else {
Y[pos] = (Y[pos] + (kbg * bg_y[pos])) >> 8;
Cb[pos] = (Cb[pos] + (kbg * bg_cb[pos])) >> 8;
Cr[pos] = (Cr[pos] + (kbg * bg_cr[pos])) >> 8;
}
}
}
double tmp = 0.0;
fast_sqrt( tmp, (Cbk - Cb) * (Cbk-Cb) + (Crk - Cr) * (Crk - Cr) );
if( tmp < dA ) { /* near color key == bg */
return 0.0;
}
if( tmp < dB ) { /* middle region */
return (tmp - dA)/(dB - dA); /* distance to key color */
}
return 1.0; /* far from color key == fg */
}
void rgbkey_apply2(VJFrame *frame, VJFrame *frame2, int width,
int height, int i_angle,int r, int g,
int b, int i_noise)
{
uint8_t *fg_y, *fg_cb, *fg_cr;
uint8_t *bg_y, *bg_cb, *bg_cr;
int accept_angle_tg, accept_angle_ctg, one_over_kc;
int kfgy_scale, kg;
uint8_t cb, cr;
int kbg, x1, y1;
float kg1, tmp, aa = 255.0, bb = 255.0, _y = 0;
float angle = (float) i_angle / 100.0f;
float noise_level = (i_noise / 100.0f);
unsigned int pos;
uint8_t val, tmp1;
uint8_t *Y = frame->data[0];
uint8_t *Cb= frame->data[1];
uint8_t *Cr= frame->data[2];
uint8_t *Y2 = frame2->data[0];
void rgbkey_apply(VJFrame *frame, VJFrame *frame2, int width,int height, int tola, int r, int g,int b, int tolb, int show, int alpha)
{
unsigned int pos;
uint8_t *Y = frame->data[0];
uint8_t *Cb = frame->data[1];
uint8_t *Cr = frame->data[2];
uint8_t *Y2 = frame2->data[0];
uint8_t *Cb2= frame2->data[1];
uint8_t *Cr2= frame2->data[2];
uint8_t iy,iu,iv;
uint8_t *B = frame2->data[3];
uint8_t *A = frame->data[3];
int cb,cr,iy,iu,iv;
_rgb2yuv(r,g,b,iy,iu,iv);
_rgb2yuv( r,g,b, iy,iu,iv );
_y = (float) iy;
aa = (float) iu;
bb = (float) iv;
tmp = sqrt(((aa * aa) + (bb * bb)));
cb = 255 * (aa / tmp);
cr = 255 * (bb / tmp);
kg1 = tmp;
/* obtain coordinate system for cb / cr */
accept_angle_tg = (int)( 15.0f * tanf(M_PI * angle / 180.0f));
accept_angle_ctg= (int)( 15.0f / tanf(M_PI * angle / 180.0f));
tmp = 1 / kg1;
one_over_kc = 0xff * 2 * tmp - 0xff;
kfgy_scale = 0xf * (float) (_y) / kg1;
kg = kg1;
/* intialize pointers */
fg_y = Y;
fg_cb = Cb;
fg_cr = Cr;
bg_y = Y2;
bg_cb = Cb2;
bg_cr = Cr2;
int len = frame->len;
for (pos = 0; pos < len; pos++) {
short xx, yy;
/* convert foreground to xz coordinates where x direction is
defined by key color */
xx = (((fg_cb[pos]) * cb) + ((fg_cr[pos]) * cr)) >> 7;
yy = (((fg_cr[pos]) * cb) - ((fg_cb[pos]) * cr)) >> 7;
/* accept angle should not be > 90 degrees
reasonable results between 10 and 80 degrees.
*/
val = (xx * accept_angle_tg) >> 4;
if (abs(yy) < val) {
/* compute fg, suppress fg in xz according to kfg */
val = (yy * accept_angle_ctg) >> 4;
x1 = abs(val);
y1 = yy;
tmp1 = xx - x1;
kbg = (tmp1 * one_over_kc) >> 1;
if (kbg < 0)
kbg = 0;
if (kbg > 255)
kbg = 255;
val = (tmp1 * kfgy_scale) >> 4;
val = fg_y[pos] - val;
Y[pos] = val;
/* convert suppressed fg back to cbcr */
Cb[pos] = ((x1 * cb) - (y1 * cr)) >> 7;
Cr[pos] = ((x1 * cr) - (y1 * cb)) >> 7;
/* deal with noise */
val = (yy * yy) + (kg * kg);
if (val < (noise_level * noise_level)) {
Y[pos] = 0; Cb[pos] = 128; Cr[pos] = 128;
//kbg = 0xff;
} else {
Y[pos] = (Y[pos] + (kbg * bg_y[pos])) >> 8;
Cb[pos] = (Cb[pos] + (kbg * bg_cb[pos])) >> 8;
Cr[pos] = (Cr[pos] + (kbg * bg_cr[pos])) >> 8;
if( alpha == 0 ) {
for (pos = (width * height); pos != 0; pos--) {
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
uint8_t op1 = (d * 255);
if( op1 == 0 ) {
Y[pos] = Y2[pos];
Cb[pos] = Cb2[pos];
Cr[pos] = Cr2[pos];
}
else {
uint8_t op0 = op1;
op1 = 255 - op1;
Y[pos] = ( (op0 * Y[pos]) + (op1 * Y2[pos])) >> 8;;
Cb[pos] = ( (op0 * Cb[pos]) + (op1 * Cb2[pos]))>> 8;
Cr[pos] = ( (op0 * Cr[pos]) + (op1 * Cr2[pos]))>>8;
}
}
}
else {
switch(alpha) {
case 1:
for (pos = (width * height); pos != 0; pos--) {
if( A[pos] == 0 )
continue;
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
uint8_t op1 = (d * 255);
if( op1 == 0 ) {
Y[pos] = Y2[pos];
Cb[pos] = Cb2[pos];
Cr[pos] = Cr2[pos];
}
else {
uint8_t op0 = op1;
op1 = 255 - op1;
Y[pos] = ( (op0 * Y[pos]) + (op1 * Y2[pos])) >> 8;;
Cb[pos] = ( (op0 * Cb[pos]) + (op1 * Cb2[pos]))>> 8;
Cr[pos] = ( (op0 * Cr[pos]) + (op1 * Cr2[pos]))>>8;
}
}
break;
case 2:
for (pos = (width * height); pos != 0; pos--) {
if( A[pos] == 0 && B[pos] == 0)
continue;
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
uint8_t op1 = (d * 255);
if( op1 == 0 ) {
Y[pos] = Y2[pos];
Cb[pos] = Cb2[pos];
Cr[pos] = Cr2[pos];
}
else {
uint8_t op0 = op1;
op1 = 255 - op1;
Y[pos] = ( (op0 * Y[pos]) + (op1 * Y2[pos])) >> 8;;
Cb[pos] = ( (op0 * Cb[pos]) + (op1 * Cb2[pos]))>> 8;
Cr[pos] = ( (op0 * Cr[pos]) + (op1 * Cr2[pos]))>>8;
}
}
break;
case 3:
for (pos = (width * height); pos != 0; pos--) {
if( A[pos] == 0 || B[pos] == 0)
continue;
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
uint8_t op1 = (d * 255);
if( op1 == 0 ) {
Y[pos] = Y2[pos];
Cb[pos] = Cb2[pos];
Cr[pos] = Cr2[pos];
}
else {
uint8_t op0 = op1;
op1 = 255 - op1;
Y[pos] = ( (op0 * Y[pos]) + (op1 * Y2[pos])) >> 8;;
Cb[pos] = ( (op0 * Cb[pos]) + (op1 * Cb2[pos]))>> 8;
Cr[pos] = ( (op0 * Cr[pos]) + (op1 * Cr2[pos]))>>8;
}
}
break;
case 4:
for (pos = (width * height); pos != 0; pos--) {
if( B[pos] == 0 )
continue;
double d = color_distance( Cb[pos],Cr[pos],iu,iv,tola,tolb );
uint8_t op1 = (d * 255);
if( op1 == 0 ) {
Y[pos] = Y2[pos];
Cb[pos] = Cb2[pos];
Cr[pos] = Cr2[pos];
}
else {
uint8_t op0 = op1;
op1 = 255 - op1;
Y[pos] = ( (op0 * Y[pos]) + (op1 * Y2[pos])) >> 8;;
Cb[pos] = ( (op0 * Cb[pos]) + (op1 * Cb2[pos]))>> 8;
Cr[pos] = ( (op0 * Cr[pos]) + (op1 * Cr2[pos]))>>8;
}
}
break;
}
}
}
}
/* this is the same as rgbkey_apply1, but here we have total noise suppression
*/
void rgbkey_apply(VJFrame *frame, VJFrame *frame2, int width,
int height, int i_angle, int red, int green,
int blue, int type, int i_noise)
{
switch (type) {
case 0:
rgbkey_apply1(frame, frame2, width, height, i_angle, red,
green, blue, i_noise);
break;
case 1:
rgbkey_apply2(frame, frame2, width, height, i_angle, red,
green, blue, i_noise);
break;
}
}
void rgbkey_free(){}

View File

@@ -25,8 +25,5 @@
#include <libvje/vje.h>
vj_effect *rgbkey_init();
void rgbkey_scan_fg(uint8_t * src2[3], int *r, int *g, int *b);
void rgbkey_apply(VJFrame *frame, VJFrame *frame2, int width,
int height, int i_angle, int i_noise,
int red, int green, int blue, int type );
void rgbkey_free();
void rgbkey_apply(VJFrame *frame, VJFrame *frame2, int width,int height, int tola, int r, int g,int b, int tolb, int show, int alpha);
#endif

View File

@@ -123,7 +123,7 @@ enum {
VJ_VIDEO_EFFECT_MIXTOALPHA = 248,
VJ_VIDEO_EFFECT_MAGICALPHA = 249,
VJ_VIDEO_EFFECT_TRAVELMATTE = 250,
VJ_VIDEO_EFFECT_ALPHABLEND = 251,
};
enum {
@@ -226,6 +226,7 @@ enum {
VJ_IMAGE_EFFECT_ALPHAFLATTEN = 196,
VJ_IMAGE_EFFECT_ALPHAFEATHERMASK = 197,
VJ_IMAGE_EFFECT_ALPHASELECT = 198,
VJ_IMAGE_EFFECT_ALPHASELECT2 = 199,
VJ_IMAGE_EFFECT_DUMMY=100,
};
@@ -233,7 +234,7 @@ enum {
#define VJ_IMAGE_EFFECT_MAX 199
#define VJ_VIDEO_EFFECT_MIN 200
#define VJ_VIDEO_EFFECT_MAX 251
#define VJ_VIDEO_EFFECT_MAX 252
#define VJ_VIDEO_COUNT (VJ_VIDEO_EFFECT_MAX - VJ_VIDEO_EFFECT_MIN)
@@ -378,7 +379,7 @@ extern void coloradjust_apply( VJFrame *frame, int width, int height,
extern void rgbkey_apply( VJFrame *frame, VJFrame *frame2, int width,
int height, int i_angle, int i_noise,
int r, int g, int b, int sup);
int r, int g, int b, int sup, int alpha);
extern void gamma_apply( VJFrame *frame,
int width, int height, int val);
@@ -647,4 +648,6 @@ extern void overlayalphamagic_apply(VJFrame *frame, VJFrame *frame2, int width,i
extern void travelmatte_apply( VJFrame *frame, VJFrame *frame2, int width,int height, int mode);
extern void feathermask_apply( VJFrame *frame, int width, int height );
extern void alphaselect_apply( VJFrame *frame, int width,int height, int i_angle, int r, int g,int b, int swap);
void alphaselect2_apply( VJFrame *frame, int width,int height, int tola, int r, int g,int b, int tolb, int show, int alpha);
void alphablend_apply( VJFrame *frame, VJFrame *frame2, int width,int height);
#endif

View File

@@ -177,6 +177,9 @@
#include "effects/magicalphaoverlays.h"
#include "effects/travelmatte.h"
#include "effects/feathermask.h"
#include "effects/alphaselect.h"
#include "effects/alphaselect2.h"
#include "effects/alphablend.h"
#include <libplugger/plugload.h>
#include <veejay/vims.h>
@@ -580,7 +583,8 @@ void vj_effect_initialize(int width, int height, int full_range)
vj_effects[48] = mixtoalpha_init(width,height);
vj_effects[49] = overlayalphamagic_init(width,height);
vj_effects[50] = travelmatte_init(width,height);
vj_effects[51] = dummy_init(width,height);
vj_effects[51] = alphablend_init(width,height);
vj_effects[52] = dummy_init(width,height);
vj_effects[i + 1] = mirrors2_init(width,height);
vj_effects[i + 2] = mirrors_init(width,height);
vj_effects[i + 3] = widthmirror_init(width,height);
@@ -679,6 +683,7 @@ void vj_effect_initialize(int width, int height, int full_range)
vj_effects[i + 96 ] = alphaflatten_init(width,height);
vj_effects[i + 97 ] = feathermask_init(width,height);
vj_effects[i + 98 ] = alphaselect_init(width,height);
vj_effects[i + 99 ] = alphaselect2_init(width,height);
max_width = width;
max_height = height;
@@ -784,7 +789,7 @@ int vj_effect_real_to_sequence(int effect_id)
}
else
{
if (effect_id > VJ_IMAGE_EFFECT_MIN && effect_id < VJ_IMAGE_EFFECT_MAX) {
if (effect_id > VJ_IMAGE_EFFECT_MIN && effect_id <= VJ_IMAGE_EFFECT_MAX) {
effect_id -= VJ_IMAGE_EFFECT_MIN;
effect_id += VJ_VIDEO_COUNT;
return effect_id;
@@ -1038,26 +1043,6 @@ int vj_effect_has_cb(int effect_id)
return 0;
}
int vj_effect_get_min_i()
{
return VJ_IMAGE_EFFECT_MIN;
}
int vj_effect_get_max_i()
{
return VJ_IMAGE_EFFECT_MAX;
}
int vj_effect_get_min_v()
{
return VJ_VIDEO_EFFECT_MIN;
}
int vj_effect_get_max_v()
{
return VJ_VIDEO_EFFECT_MAX;
}
int vj_effect_has_rgbkey(int effect_id)
{
int entry;
@@ -1074,7 +1059,7 @@ int vj_effect_is_valid(int effect_id)
{
if( effect_id >= VJ_EXT_EFFECT && effect_id < VJ_EXT_EFFECT + n_ext_plugs_)
return 1;
if( effect_id > VJ_IMAGE_EFFECT_MIN && effect_id < VJ_IMAGE_EFFECT_MAX )
if( effect_id > VJ_IMAGE_EFFECT_MIN && effect_id <= VJ_IMAGE_EFFECT_MAX )
return 1;
if( effect_id > VJ_VIDEO_EFFECT_MIN && effect_id < VJ_VIDEO_EFFECT_MAX )
return 1;

View File

@@ -430,6 +430,9 @@ void vj_effman_apply_image_effect(
case VJ_IMAGE_EFFECT_ALPHASELECT:
alphaselect_apply(frames[0],frames[0]->width,frames[0]->height,arg[0],arg[1],arg[2],arg[3],arg[4]);
break;
case VJ_IMAGE_EFFECT_ALPHASELECT2:
alphaselect2_apply(frames[0],frames[0]->width,frames[0]->height,arg[0],arg[1],arg[2],arg[3],arg[4],arg[5],arg[6]);
break;
}
}
@@ -502,7 +505,7 @@ void vj_effman_apply_video_effect( VJFrame **frames, vjp_kf *todo_info,int *arg,
break;
case VJ_VIDEO_EFFECT_RGBKEY:
rgbkey_apply(frames[0], frames[1], frames[0]->width, frames[0]->height,
arg[0], arg[1], arg[2], arg[3], arg[4], arg[5]);
arg[0], arg[1], arg[2], arg[3], arg[4], arg[5],arg[6]);
break;
case VJ_VIDEO_EFFECT_KEYSELECT:
keyselect_apply(frames[0],frames[1],frames[0]->width,frames[0]->height,
@@ -661,6 +664,9 @@ void vj_effman_apply_video_effect( VJFrame **frames, vjp_kf *todo_info,int *arg,
case VJ_VIDEO_EFFECT_TRAVELMATTE:
travelmatte_apply(frames[0],frames[1],frames[0]->width,frames[0]->height,arg[0]);
break;
case VJ_VIDEO_EFFECT_ALPHABLEND:
alphablend_apply(frames[0],frames[1],frames[0]->width,frames[0]->height);
break;
}
}

View File

@@ -22,7 +22,7 @@
#define FX_LIMIT 1024
#define MAX_EFFECTS 150
#define MAX_EFFECTS 152
#define PARAM_WIDTH (1<<0x2)
#define PARAM_HEIGHT (1<<0x3)
#define PARAM_FADER (1<<0x1)
@@ -46,7 +46,7 @@ typedef struct VJFrame_t
int shift_v;
int shift_h;
int format;
int width;
int width;
int height;
int ssm;
int stride[4];
@@ -102,8 +102,8 @@ typedef struct vj_effect_instance_t {
float *farr;
} vj_fx_instance;
extern int get_pixel_range_min_Y();
extern int get_pixel_range_min_UV();
extern int get_pixel_range_min_Y();
extern int get_pixel_range_min_UV();
extern void vj_effect_initialize(int width, int height, int range);
extern void vj_effect_shutdown();
extern int vj_effect_max_effects();
@@ -126,16 +126,12 @@ extern int vj_effect_get_summary_len(int entry);
extern void *vj_effect_activate(int e, int *retcode);
extern int vj_effect_deactivate(int e, void *ptr);
extern int vj_effect_initialized(int e, void *ptr);
extern int vj_effect_get_min_i();
extern int vj_effect_get_max_i();
extern int vj_effect_get_min_v();
extern int vj_effect_get_max_v();
extern int vj_effect_get_by_name(char *name);
extern int vj_effect_apply( VJFrame **frames, VJFrameInfo *frameinfo, vjp_kf *kf, int selector, int *arguments, void *ptr);
extern int vj_effect_prepare( VJFrame *frame, int selector);
extern void vj_effect_dump(void);
extern int rgb_parameter_conversion_type_;
extern int vj_effect_is_plugin( int fx_id );
extern int vj_effect_apply( VJFrame **frames, VJFrameInfo *frameinfo, vjp_kf *kf, int selector, int *arguments, void *ptr);
extern int vj_effect_prepare( VJFrame *frame, int selector);
extern void vj_effect_dump(void);
extern int rgb_parameter_conversion_type_;
extern int vj_effect_is_plugin( int fx_id );
extern void *vj_effect_get_data( int seq_id );
extern int vj_effect_is_parallel(int effect_id);
#endif