blind-square-gradient.c - blind - suckless command-line video editing utility
 (HTM) git clone git://git.suckless.org/blind
 (DIR) Log
 (DIR) Files
 (DIR) Refs
 (DIR) README
 (DIR) LICENSE
       ---
       blind-square-gradient.c (2330B)
       ---
            1 /* See LICENSE file for copyright and license details. */
            2 #ifndef TYPE
            3 #include "common.h"
            4 
            5 USAGE("-w width -h height")
            6 
            7 static size_t width = 0;
            8 static size_t height = 0;
            9 static int with_multiplier;
           10 
           11 #define FILE "blind-square-gradient.c"
           12 #include "define-functions.h"
           13 
           14 int
           15 main(int argc, char *argv[])
           16 {
           17         struct stream stream;
           18         void (*process)(struct stream *stream);
           19 
           20         ARGBEGIN {
           21         case 'w':
           22                 width = etozu_flag('w', UARGF(), 1, SIZE_MAX);
           23                 break;
           24         case 'h':
           25                 height = etozu_flag('h', UARGF(), 1, SIZE_MAX);
           26                 break;
           27         default:
           28                 usage();
           29         } ARGEND;
           30 
           31         if (!width || !height || argc)
           32                 usage();
           33 
           34         eopen_stream(&stream, NULL);
           35 
           36         SELECT_PROCESS_FUNCTION(&stream);
           37         CHECK_N_CHAN(&stream, 4, 4);
           38 
           39         if (stream.width > 3 || stream.height > 3 ||
           40             stream.width * stream.height < 2 ||
           41             stream.width * stream.height > 3)
           42                 eprintf("<stdin>: each frame must contain exactly 2 or 3 pixels\n");
           43 
           44         with_multiplier = stream.width * stream.height == 3;
           45 
           46         stream.width = width;
           47         stream.height = height;
           48         fprint_stream_head(stdout, &stream);
           49         efflush(stdout, "<stdout>");
           50         process(&stream);
           51         return 0;
           52 }
           53 
           54 #else
           55 
           56 static void
           57 PROCESS(struct stream *stream)
           58 {
           59         typedef TYPE pixel_t[4];
           60         pixel_t buf[BUFSIZ / sizeof(pixel_t)];
           61         TYPE *params, x1, y1, x2, y2, norm, rd = 1; 
           62         TYPE x, y, p, r, rx, ry;
           63         size_t ix, iy, ptr = 0;
           64         for (;;) {
           65                 while (stream->ptr < stream->frame_size) {
           66                         if (!eread_stream(stream, stream->frame_size - stream->ptr)) {
           67                                 ewriteall(STDOUT_FILENO, buf, ptr * sizeof(*buf), "<stdout>");
           68                                 return;
           69                         }
           70                 }
           71                 params = (TYPE *)stream->buf;
           72                 x1 = (params)[0];
           73                 y1 = (params)[1];
           74                 x2 = (params)[4];
           75                 y2 = (params)[5];
           76                 if (with_multiplier)
           77                         rd = (params)[9];
           78                 memmove(stream->buf, stream->buf + stream->frame_size,
           79                         stream->ptr -= stream->frame_size);
           80 
           81                 x2 -= x1;
           82                 y2 -= y1;
           83                 norm = sqrt(x2 * x2 + y2 * y2);
           84                 x2 /= norm;
           85                 y2 /= norm;
           86 
           87                 for (iy = 0; iy < height; iy++) {
           88                         y = (TYPE)iy - y1;
           89                         for (ix = 0; ix < width; ix++) {
           90                                 x = (TYPE)ix - x1;
           91                                 p = x * x2 + y * y2;
           92                                 rx = x - p * x2;
           93                                 ry = y - p * y2;
           94                                 r = sqrt(rx * rx + ry * ry) / rd;
           95                                 p = abs(p);
           96                                 x = MAX(p, r) / norm;
           97                                 buf[ptr][0] = buf[ptr][1] = buf[ptr][2] = buf[ptr][3] = x;
           98                                 if (++ptr == ELEMENTSOF(buf)) {
           99                                         ewriteall(STDOUT_FILENO, buf, sizeof(buf), "<stdout>");
          100                                         ptr = 0;
          101                                 }
          102                         }
          103                 }
          104         }
          105 }
          106 
          107 #endif