commit 34d326d46d31332fa2182793475672617933a939
parent 88752940275b41cf4b8c978f226ff7d55a5f6575
Author: Mattias Andrée <maandree@kth.se>
Date: Wed, 5 Jul 2017 19:29:13 +0200
Add blind-dual-key
Signed-off-by: Mattias Andrée <maandree@kth.se>
Diffstat:
5 files changed, 143 insertions(+), 0 deletions(-)
diff --git a/Makefile b/Makefile
@@ -20,6 +20,7 @@ BIN =\
blind-dissolve\
blind-dot-product\
blind-double-sine-wave\
+ blind-dual-key\
blind-extend\
blind-extract-alpha\
blind-find-rectangle\
diff --git a/README b/README
@@ -60,6 +60,9 @@ UTILITIES
blind-double-sine-wave(1)
Apply double-sine-wave repetition to gradient
+ blind-dual-key(1)
+ Apply transparency to a video based on two videos and two key
+
blind-extend(1)
Add margins to a video
diff --git a/man/blind-dual-key.1 b/man/blind-dual-key.1
@@ -0,0 +1,55 @@
+.TH BLIND-DUAL-KEY 1 blind
+.SH NAME
+blind-dual-key - Apply transparency to a video based on two videos and two key
+.SH SYNOPSIS
+.B blind-dual-key
+.I X
+.I Y
+.I Z
+.I dual-X
+.I dual-Y
+.I dual-Z
+.I dual-video
+.SH DESCRIPTION
+.B blind-dual-key
+reads a video from stdin and a video
+.IR dual-video .
+These two videos should be idential, except
+with two different background colours. The
+background colour used in the video from
+stdin should be specified in the arguments
+.IR X ,
+.IR Y ,
+and
+.IR Z ,
+using the CIE XYZ colour model. The
+background colour used in the video from
+.I dual-video
+should be specified in the arguments
+.IR dual-X ,
+.IR dual-Y ,
+and
+.IR dual-Z ,
+using the CIE XYZ colour model. Using this information,
+.B blind-dual-key
+reconstruct the alpha channel of the video
+and prints the video with its alpha channel to
+stdout.
+.SH NOTES
+.B blind-dual-key
+may be changed in the future to use some other colour model,
+therefore, it is recommended to also use
+.BR blind-colour-ciexyz (1)
+if you are specifying the colour in CIE XYZ.
+.P
+When making a video whose transparancy is recovered with
+.BR blind-dual-key ,
+select to opposite background colours, for
+example black and white or green and magenta.
+.SH SEE ALSO
+.BR blind (7),
+.BR blind-colour-ciexyz (1),
+.BR blind-colour-srgb (1)
+.SH AUTHORS
+Mattias Andrée
+.RI < maandree@kth.se >
diff --git a/man/blind.7 b/man/blind.7
@@ -76,6 +76,9 @@ Calculate the dot product of colours in a video
.BR blind-double-sine-wave (1)
Apply double-sine-wave repetition to gradient
.TP
+.BR blind-dual-key(1)
+Apply transparency to a video based on two videos and two key
+.TP
.BR blind-extend (1)
Add margins to a video
.TP
diff --git a/src/blind-dual-key.c b/src/blind-dual-key.c
@@ -0,0 +1,81 @@
+/* See LICENSE file for copyright and license details. */
+#include "common.h"
+
+USAGE("[-m] X Y Z dual-X dual-Y dual-Z dual-stream")
+
+static double X1, Y1, Z1, X2, Y2, Z2;
+
+#define PROCESS(TYPE)\
+ do {\
+ size_t i;\
+ TYPE x1k = (TYPE)X1, y1k = (TYPE)Y1, z1k = (TYPE)Z1;\
+ TYPE x2k = (TYPE)X2, y2k = (TYPE)Y2, z2k = (TYPE)Z2;\
+ TYPE x1, y1, z1, a1, x2, y2, z2, a2;\
+ TYPE alpha, xalpha, yalpha, zalpha;\
+ for (i = 0; i < n; i += stream->pixel_size) {\
+ x1 = ((TYPE *)(stream->buf + i))[0];\
+ y1 = ((TYPE *)(stream->buf + i))[1];\
+ z1 = ((TYPE *)(stream->buf + i))[2];\
+ a1 = ((TYPE *)(stream->buf + i))[3];\
+ x2 = ((TYPE *)(dual->buf + i))[0];\
+ y2 = ((TYPE *)(dual->buf + i))[1];\
+ z2 = ((TYPE *)(dual->buf + i))[2];\
+ a2 = ((TYPE *)(dual->buf + i))[3];\
+ if (x1 == x2 && y1 == y2 && z1 == z2) {\
+ if (a1 != a2)\
+ ((TYPE *)(stream->buf + i))[3] = (a1 + a2) / 2;\
+ continue;\
+ }\
+ xalpha = x1 == x2 ? (TYPE)0 : (x2 - x1 + x1k - x2k) / (x1k - x2k);\
+ yalpha = y1 == y2 ? (TYPE)0 : (y2 - y1 + y1k - y2k) / (y1k - y2k);\
+ zalpha = z1 == z2 ? (TYPE)0 : (z2 - z1 + z1k - z2k) / (z1k - z2k);\
+ alpha = xalpha > yalpha ? xalpha : yalpha;\
+ alpha = alpha > zalpha ? alpha : zalpha;\
+ if (!alpha) {\
+ ((TYPE *)(stream->buf + i))[0] = (TYPE)0;\
+ ((TYPE *)(stream->buf + i))[1] = (TYPE)0;\
+ ((TYPE *)(stream->buf + i))[2] = (TYPE)0;\
+ ((TYPE *)(stream->buf + i))[3] = (TYPE)0;\
+ } else {\
+ ((TYPE *)(stream->buf + i))[0] = ((x1 - x1k + x2 - x2k) / alpha + x1k + x2k) / 2;\
+ ((TYPE *)(stream->buf + i))[1] = ((y1 - y1k + y2 - y2k) / alpha + y1k + y2k) / 2;\
+ ((TYPE *)(stream->buf + i))[2] = ((z1 - z1k + z2 - z2k) / alpha + z1k + z2k) / 2;\
+ ((TYPE *)(stream->buf + i))[3] = (a1 + a2) / 2 * alpha;\
+ }\
+ }\
+ } while (0)
+
+static void process_lf(struct stream *stream, struct stream *dual, size_t n) {PROCESS(double);}
+static void process_f (struct stream *stream, struct stream *dual, size_t n) {PROCESS(float);}
+
+int
+main(int argc, char *argv[])
+{
+ struct stream stream, dual;
+ void (*process)(struct stream *stream, struct stream *dual, size_t n);
+
+ UNOFLAGS(argc != 7);
+
+ X1 = etolf_arg("the X value", argv[0]);
+ Y1 = etolf_arg("the Y value", argv[1]);
+ Z1 = etolf_arg("the Z value", argv[2]);
+
+ X2 = etolf_arg("the dual-X value", argv[3]);
+ Y2 = etolf_arg("the dual-Y value", argv[4]);
+ Z2 = etolf_arg("the dual-Z value", argv[5]);
+
+ eopen_stream(&stream, NULL);
+ eopen_stream(&dual, argv[6]);
+
+ if (!strcmp(stream.pixfmt, "xyza"))
+ process = process_lf;
+ else if (!strcmp(stream.pixfmt, "xyza f"))
+ process = process_f;
+ else
+ eprintf("pixel format %s is not supported, try xyza\n", stream.pixfmt);
+
+ fprint_stream_head(stdout, &stream);
+ efflush(stdout, "<stdout>");
+ process_two_streams(&stream, &dual, STDOUT_FILENO, "<stdout>", process);
+ return 0;
+}