[FFmpeg-cvslog] lavfi/curves: add plot option

Clément Bœsch git at videolan.org
Sun Jul 24 13:20:44 EEST 2016


ffmpeg | branch: master | Clément Bœsch <u at pkh.me> | Fri Jul 22 01:17:44 2016 +0200| [4a8f5f1fd83dfa92e02901e543d79124c4e551dc] | committer: Clément Bœsch

lavfi/curves: add plot option

> http://git.videolan.org/gitweb.cgi/ffmpeg.git/?a=commit;h=4a8f5f1fd83dfa92e02901e543d79124c4e551dc
---

 doc/filters.texi        |   10 ++++++++
 libavfilter/vf_curves.c |   64 +++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 74 insertions(+)

diff --git a/doc/filters.texi b/doc/filters.texi
index 03da9b0..5a64853 100644
--- a/doc/filters.texi
+++ b/doc/filters.texi
@@ -5750,6 +5750,8 @@ options. In this case, the unset component(s) will fallback on this
 @option{all} setting.
 @item psfile
 Specify a Photoshop curves file (@code{.acv}) to import the settings from.
+ at item plot
+Save Gnuplot script of the curves in specified file.
 @end table
 
 To avoid some filtergraph syntax conflicts, each key points list need to be
@@ -5796,6 +5798,14 @@ Use a Photoshop preset and redefine the points of the green component:
 @example
 curves=psfile='MyCurvesPresets/purple.acv':green='0/0 0.45/0.53 1/1'
 @end example
+
+ at item
+Check out the curves of the @code{cross_process} profile using @command{ffmpeg}
+and @command{gnuplot}:
+ at example
+ffmpeg -f lavfi -i color -vf curves=cross_process:plot=/tmp/curves.plt -frames:v 1 -f null -
+gnuplot -p /tmp/curves.plt
+ at end example
 @end itemize
 
 @section datascope
diff --git a/libavfilter/vf_curves.c b/libavfilter/vf_curves.c
index 7128fbe..84df448 100644
--- a/libavfilter/vf_curves.c
+++ b/libavfilter/vf_curves.c
@@ -67,6 +67,7 @@ typedef struct {
     char *psfile;
     uint8_t rgba_map[4];
     int step;
+    char *plot_filename;
 } CurvesContext;
 
 typedef struct ThreadData {
@@ -98,6 +99,7 @@ static const AVOption curves_options[] = {
     { "b",     "set blue points coordinates",  OFFSET(comp_points_str[2]), AV_OPT_TYPE_STRING, {.str=NULL}, .flags = FLAGS },
     { "all",   "set points coordinates for all components", OFFSET(comp_points_str_all), AV_OPT_TYPE_STRING, {.str=NULL}, .flags = FLAGS },
     { "psfile", "set Photoshop curves file name", OFFSET(psfile), AV_OPT_TYPE_STRING, {.str=NULL}, .flags = FLAGS },
+    { "plot", "save Gnuplot script of the curves in specified file", OFFSET(plot_filename), AV_OPT_TYPE_STRING, {.str=NULL}, .flags = FLAGS },
     { NULL }
 };
 
@@ -377,6 +379,65 @@ end:
     return ret;
 }
 
+static int dump_curves(const char *fname, uint8_t graph[NB_COMP + 1][256],
+                       struct keypoint *comp_points[NB_COMP + 1])
+{
+    int i;
+    AVBPrint buf;
+    static const char * const colors[] = { "red", "green", "blue", "#404040", };
+    FILE *f = av_fopen_utf8(fname, "w");
+
+    av_assert0(FF_ARRAY_ELEMS(colors) == NB_COMP + 1);
+
+    if (!f) {
+        int ret = AVERROR(errno);
+        av_log(NULL, AV_LOG_ERROR, "Cannot open file '%s' for writing: %s\n",
+               fname, av_err2str(ret));
+        return ret;
+    }
+
+    av_bprint_init(&buf, 0, AV_BPRINT_SIZE_UNLIMITED);
+
+    av_bprintf(&buf, "set xtics 0.1\n");
+    av_bprintf(&buf, "set ytics 0.1\n");
+    av_bprintf(&buf, "set size square\n");
+    av_bprintf(&buf, "set grid\n");
+
+    for (i = 0; i < FF_ARRAY_ELEMS(colors); i++) {
+        av_bprintf(&buf, "%s'-' using 1:2 with lines lc '%s' title ''",
+                   i ? ", " : "plot ", colors[i]);
+        if (comp_points[i])
+            av_bprintf(&buf, ", '-' using 1:2 with points pointtype 3 lc '%s' title ''",
+                    colors[i]);
+    }
+    av_bprintf(&buf, "\n");
+
+    for (i = 0; i < FF_ARRAY_ELEMS(colors); i++) {
+        int x;
+
+        /* plot generated values */
+        for (x = 0; x < 256; x++)
+            av_bprintf(&buf, "%f %f\n", x/255., graph[i][x]/255.);
+        av_bprintf(&buf, "e\n");
+
+        /* plot user knots */
+        if (comp_points[i]) {
+            const struct keypoint *point = comp_points[i];
+
+            while (point) {
+                av_bprintf(&buf, "%f %f\n", point->x, point->y);
+                point = point->next;
+            }
+            av_bprintf(&buf, "e\n");
+        }
+    }
+
+    fwrite(buf.str, 1, buf.len, f);
+    fclose(f);
+    av_bprint_finalize(&buf, NULL);
+    return 0;
+}
+
 static av_cold int init(AVFilterContext *ctx)
 {
     int i, j, ret;
@@ -448,6 +509,9 @@ static av_cold int init(AVFilterContext *ctx)
         }
     }
 
+    if (curves->plot_filename)
+        dump_curves(curves->plot_filename, curves->graph, comp_points);
+
     for (i = 0; i < NB_COMP + 1; i++) {
         struct keypoint *point = comp_points[i];
         while (point) {



More information about the ffmpeg-cvslog mailing list