Introduction
Introduction Statistics Contact Development Disclaimer Help
Add blind-invert-matrix - blind - suckless command-line video editing utility
git clone git://git.suckless.org/blind
Log
Files
Refs
README
LICENSE
---
commit 4621e6f35cda10654d2bbfb4df579ec89fb7f99d
parent fc3bad11b3628c3b77df97327f1cdaf19d96aa9e
Author: Mattias Andrée <[email protected]>
Date: Fri, 14 Jul 2017 19:25:21 +0200
Add blind-invert-matrix
Signed-off-by: Mattias Andrée <[email protected]>
Diffstat:
M Makefile | 1 +
M README | 3 +++
A man/blind-invert-matrix.1 | 35 +++++++++++++++++++++++++++++…
M man/blind-multiply-matrices.1 | 1 +
M man/blind.7 | 3 +++
A src/blind-invert-matrix.c | 132 +++++++++++++++++++++++++++++…
6 files changed, 175 insertions(+), 0 deletions(-)
---
diff --git a/Makefile b/Makefile
@@ -39,6 +39,7 @@ BIN =\
blind-hexagon-tessellation\
blind-interleave\
blind-invert-luma\
+ blind-invert-matrix\
blind-linear-gradient\
blind-make-kernel\
blind-matrix-orthoproject\
diff --git a/README b/README
@@ -111,6 +111,9 @@ UTILITIES
blind-invert-luma(1)
Invert the luminosity of a video
+ blind-invert-matrix(1)
+ Invert matrix-video
+
blind-linear-gradient(1)
Generate a video with a linear gradient
diff --git a/man/blind-invert-matrix.1 b/man/blind-invert-matrix.1
@@ -0,0 +1,35 @@
+.TH BLIND-INVERT-MATRIX 1 blind
+.SH NAME
+blind-invert-matrix - Invert matrix-vidoes
+.SH SYNOPSIS
+.B blind-invert-matrix
+[-e]
+.SH DESCRIPTION
+.B blind-invert-matrix
+reads a video representing a matrix from
+stdin, inverts it, and prints the results
+to stdout.
+.P
+The matrix must be at least as wide as it
+is tall. If the matrix is wider than it is
+tall, it is treated as an augmented matrix,
+and the unaugmented square matrix is
+eliminated to the identity matrix and the
+resuling augment is printed.
+.SH OPTIONS
+.TP
+.B -e
+Apply optimisation that assumes all channels
+are identical.
+.SH SEE ALSO
+.BR blind (7),
+.BR blind-multiply-matrices (1),
+.BR blind-transpose (1),
+.BR blind-flip (1),
+.BR blind-flop (1),
+.BR blind-rotate-90 (1),
+.BR blind-rotate-180 (1),
+.BR blind-rotate-270 (1)
+.SH AUTHORS
+Mattias Andrée
+.RI < [email protected] >
diff --git a/man/blind-multiply-matrices.1 b/man/blind-multiply-matrices.1
@@ -38,6 +38,7 @@ in reverse order.
.BR blind-matrix-shear (1),
.BR blind-matrix-translate (1),
.BR blind-matrix-transpose (1),
+.BR blind-invert-matrix (1),
.BR blind-transpose (1),
.BR blind-flip (1),
.BR blind-flop (1),
diff --git a/man/blind.7 b/man/blind.7
@@ -127,6 +127,9 @@ Framewise interleave videos
.BR blind-invert-luma (1)
Invert the luminosity of a video
.TP
+.BR blind-invert-matrix (1)
+Invert matrix-video
+.TP
.BR blind-linear-gradient (1)
Generate a video with a linear gradient
.TP
diff --git a/src/blind-invert-matrix.c b/src/blind-invert-matrix.c
@@ -0,0 +1,132 @@
+/* See LICENSE file for copyright and license details. */
+#include "common.h"
+
+USAGE("")
+
+static int equal = 0;
+
+#define SUB_ROWS()\
+ do {\
+ p2 = matrix + r2 * cn;\
+ t = p2[r1][0];\
+ for (c = 0; c < cn; c++)\
+ p1[c][0] -= p2[c][0] * t;\
+ } while (0)
+
+#define PROCESS(TYPE)\
+ do {\
+ typedef TYPE pixel_t[4];\
+ size_t rn = stream->height, r1, r2, c;\
+ size_t cn = stream->width > rn ? stream->width : 2 * rn;\
+ pixel_t *matrix = buf, *p1, *p2 = NULL;\
+ TYPE t;\
+ \
+ for (r1 = 0; r1 < rn; r1++) {\
+ p1 = matrix + r1 * cn;\
+ if (!p1[r1][0]) {\
+ for (r2 = r1 + 1; r2 < rn; r2++) {\
+ p2 = matrix + r2 * cn;\
+ if (p2[r1][0])\
+ break;\
+ }\
+ if (r2 == rn)\
+ eprintf("matrix is not invertable\n");\
+ for (c = 0; c < cn; c++)\
+ t = p1[c][0], p1[c][0] = p2[c][0], p2[…
+ }\
+ t = p1[r1][0];\
+ for (c = 0; c < cn; c++)\
+ p1[c][0] /= t;\
+ for (r2 = r1 + 1; r2 < rn; r2++)\
+ SUB_ROWS();\
+ }\
+ \
+ for (r1 = rn; r1--;) {\
+ p1 = matrix + r1 * cn;\
+ for (r2 = r1; r2--;)\
+ SUB_ROWS();\
+ }\
+ } while (0)
+
+static void process_lf(struct stream *stream, void *buf) { PROCESS(double); }
+static void process_f (struct stream *stream, void *buf) { PROCESS(float); }
+
+int
+main(int argc, char *argv[])
+{
+ struct stream stream;
+ size_t width, x, y, row_size, chan_size;
+ char *buf, *one = alloca(4 * sizeof(double)), *p;
+ void (*process)(struct stream *stream, void *buf);
+
+ ARGBEGIN {
+ case 'e':
+ equal = 1;
+ break;
+ default:
+ usage();
+ } ARGEND;
+
+ if (argc)
+ usage();
+
+ eopen_stream(&stream, NULL);
+ echeck_dimensions(&stream, WIDTH | HEIGHT, NULL);
+ width = stream.width;
+ if (stream.width < stream.height)
+ eprintf("<stdin>: the video must be at least as wide as it is …
+ else if (stream.width > stream.height)
+ stream.width -= stream.height;
+ fprint_stream_head(stdout, &stream);
+ stream.width = width;
+ efflush(stdout, "<stdout>");
+
+ if (!strcmp(stream.pixfmt, "xyza")) {
+ *(double *)one = 1;
+ process = process_lf;
+ } else if (!strcmp(stream.pixfmt, "xyza f")) {
+ *(float *)one = 1;
+ process = process_f;
+ } else {
+ eprintf("pixel format %s is not supported, try xyza\n", stream…
+ }
+
+ chan_size = stream.pixel_size / 4;
+ memcpy(one + 1 * chan_size, one, chan_size);
+ memcpy(one + 2 * chan_size, one, chan_size);
+ memcpy(one + 3 * chan_size, one, chan_size);
+
+ width = stream.width > stream.height ? stream.width : 2 * stream.heigh…
+ buf = emalloc2(width, stream.col_size);
+ row_size = width * stream.pixel_size;
+
+ while (eread_frame(&stream, buf)) {
+ if (stream.width == stream.height) {
+ for (y = stream.height; y--;) {
+ memmove(buf + y * row_size, buf + y * stream.r…
+ memset(buf + y * row_size + stream.row_size, 0…
+ memcpy(buf + y * row_size + y * stream.pixel_s…
+ }
+ }
+ if (equal) {
+ process(&stream, buf + 1 * chan_size);
+ for (y = 0; y < stream.height; y++) {
+ for (x = 0; x < stream.width; x++) {
+ p = buf + y * row_size + x * stream.pi…
+ memcpy(p + chan_size, p, chan_size);
+ memcpy(p + 2 * chan_size, p, 2 * chan_…
+ }
+ }
+ } else {
+ process(&stream, buf + 0 * chan_size);
+ process(&stream, buf + 1 * chan_size);
+ process(&stream, buf + 2 * chan_size);
+ process(&stream, buf + 3 * chan_size);
+ }
+ for (y = 0; y < stream.height; y++)
+ ewriteall(STDOUT_FILENO, buf + y * row_size + stream.r…
+ }
+
+ free(buf);
+ return 0;
+}
You are viewing proxied material from suckless.org. The copyright of proxied material belongs to its original authors. Any comments or complaints in relation to proxied material should be directed to the original authors of the content concerned. Please see the disclaimer for more details.