Signed-off-by: Paul B Mahol <one...@gmail.com> --- doc/filters.texi | 2 +- libavfilter/f_graphmonitor.c | 119 +++++++++++++++++++++++++++++++---- 2 files changed, 109 insertions(+), 12 deletions(-)
diff --git a/doc/filters.texi b/doc/filters.texi index cbb16f22b2..c1672cc7f7 100644 --- a/doc/filters.texi +++ b/doc/filters.texi @@ -11909,7 +11909,7 @@ Set video output size. Default is @var{hd720}. Set video opacity. Default is @var{0.9}. Allowed range is from @var{0} to @var{1}. @item mode, m -Set output mode, can be @var{fulll} or @var{compact}. +Set output mode, can be @var{full} or @var{compact} or @var{tiny}. In @var{compact} mode only filters with some queued frames have displayed stats. @item flags, f diff --git a/libavfilter/f_graphmonitor.c b/libavfilter/f_graphmonitor.c index 74779965d9..e440a82af7 100644 --- a/libavfilter/f_graphmonitor.c +++ b/libavfilter/f_graphmonitor.c @@ -72,10 +72,11 @@ static const AVOption graphmonitor_options[] = { { "s", "set monitor size", OFFSET(w), AV_OPT_TYPE_IMAGE_SIZE, {.str="hd720"}, 0, 0, VF }, { "opacity", "set video opacity", OFFSET(opacity), AV_OPT_TYPE_FLOAT, {.dbl=.9}, 0, 1, VF }, { "o", "set video opacity", OFFSET(opacity), AV_OPT_TYPE_FLOAT, {.dbl=.9}, 0, 1, VF }, - { "mode", "set mode", OFFSET(mode), AV_OPT_TYPE_INT, {.i64=0}, 0, 1, VF, "mode" }, - { "m", "set mode", OFFSET(mode), AV_OPT_TYPE_INT, {.i64=0}, 0, 1, VF, "mode" }, + { "mode", "set mode", OFFSET(mode), AV_OPT_TYPE_INT, {.i64=0}, 0, 2, VF, "mode" }, + { "m", "set mode", OFFSET(mode), AV_OPT_TYPE_INT, {.i64=0}, 0, 2, VF, "mode" }, { "full", NULL, 0, AV_OPT_TYPE_CONST, {.i64=0}, 0, 0, VF, "mode" }, { "compact", NULL, 0, AV_OPT_TYPE_CONST, {.i64=1}, 0, 0, VF, "mode" }, + { "tiny", NULL, 0, AV_OPT_TYPE_CONST, {.i64=2}, 0, 0, VF, "mode" }, { "flags", "set flags", OFFSET(flags), AV_OPT_TYPE_FLAGS, {.i64=MODE_QUEUE}, 0, INT_MAX, VF, "flags" }, { "f", "set flags", OFFSET(flags), AV_OPT_TYPE_FLAGS, {.i64=MODE_QUEUE}, 0, INT_MAX, VF, "flags" }, { "queue", NULL, 0, AV_OPT_TYPE_CONST, {.i64=MODE_QUEUE}, 0, 0, VF, "flags" }, @@ -246,19 +247,11 @@ static void draw_items(AVFilterContext *ctx, AVFrame *out, } } -static int create_frame(AVFilterContext *ctx, int64_t pts) +static void full_compact(AVFilterContext *ctx, AVFrame *out) { GraphMonitorContext *s = ctx->priv; - AVFilterLink *outlink = ctx->outputs[0]; - AVFrame *out; int xpos, ypos = 0; - out = ff_get_video_buffer(outlink, outlink->w, outlink->h); - if (!out) - return AVERROR(ENOMEM); - - clear_image(s, out, outlink); - for (int i = 0; i < ctx->graph->nb_filters; i++) { AVFilterContext *filter = ctx->graph->filters[i]; char buffer[1024] = { 0 }; @@ -307,6 +300,110 @@ static int create_frame(AVFilterContext *ctx, int64_t pts) } ypos += 5; } +} + +static void draw_box(AVFrame *out, int x, int y, int w, int h, uint32_t border, uint32_t fill) +{ + uint8_t *dst; + + if (x + w >= out->width || y + h >= out->height) + return; + + dst = out->data[0] + y * out->linesize[0] + x * 4; + + for (int i = 0; i < w; i++) { + AV_WL24(dst + i * 4, border); + } + + for (int i = 0; i < h; i++) { + AV_WL24(dst, border); + AV_WL24(dst + 4 * w, border); + dst += out->linesize[0]; + } + + dst = out->data[0] + (y + h - 1) * out->linesize[0] + x * 4; + + for (int i = 0; i < w; i++) { + AV_WL24(dst + i * 4, border); + } + + dst = out->data[0] + (y + 1) * out->linesize[0] + (x + 1) * 4; + + for (int j = 0; j < h - 2; j++) { + for (int i = 0; i < w - 1; i++) { + AV_WL24(dst + i * 4, fill); + } + dst += out->linesize[0]; + } +} + +#define aicolor 0x11CC44 +#define aocolor 0xCC1144 +#define vicolor 0x99FF00 +#define vocolor 0xFF9900 + +static void tiny(AVFilterContext *ctx, AVFrame *out) +{ + int xpos, ypos = 2; + + for (int i = 0; i < ctx->graph->nb_filters; i++) { + AVFilterContext *filter = ctx->graph->filters[i]; + + xpos = 2; + for (int j = 0; j < filter->nb_inputs; j++) { + AVFilterLink *l = filter->inputs[j]; + size_t frames = ff_inlink_queued_frames(l); + uint32_t icolor = l->type == AVMEDIA_TYPE_VIDEO ? vicolor : aicolor; + + draw_box(out, xpos, ypos, 8, 8, icolor, FFMIN(255, frames)); + xpos += 10; + + draw_box(out, xpos, ypos, 4, 8, icolor, (l->frame_count_in % 255) << 8); + draw_box(out, xpos+4, ypos, 4, 8, icolor, (l->frame_count_out % 255) << 16); + xpos += 12; + } + + xpos = 2; + ypos += 8 * (filter->nb_inputs > 0) + 2; + + for (int j = 0; j < filter->nb_outputs; j++) { + AVFilterLink *l = filter->outputs[j]; + size_t frames = ff_inlink_queued_frames(l); + uint32_t ocolor = l->type == AVMEDIA_TYPE_VIDEO ? vocolor : aocolor; + + draw_box(out, xpos, ypos, 8, 8, ocolor, FFMIN(255, frames)); + xpos += 10; + + draw_box(out, xpos, ypos, 4, 8, ocolor, (l->frame_count_in % 255) << 8); + draw_box(out, xpos+4, ypos, 4, 8, ocolor, (l->frame_count_out % 255) << 16); + xpos += 12; + } + + ypos += 8 * (filter->nb_outputs > 0) + 2; + } +} + +static int create_frame(AVFilterContext *ctx, int64_t pts) +{ + GraphMonitorContext *s = ctx->priv; + AVFilterLink *outlink = ctx->outputs[0]; + AVFrame *out; + + out = ff_get_video_buffer(outlink, outlink->w, outlink->h); + if (!out) + return AVERROR(ENOMEM); + + clear_image(s, out, outlink); + + switch (s->mode) { + case 0: + case 1: + full_compact(ctx, out); + break; + case 2: + tiny(ctx, out); + break; + } out->pts = pts; s->pts = pts + 1; -- 2.17.1 _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org https://ffmpeg.org/mailman/listinfo/ffmpeg-devel To unsubscribe, visit link above, or email ffmpeg-devel-requ...@ffmpeg.org with subject "unsubscribe".