Opened 15 months ago

Last modified 12 months ago

#11582 new enhancement

Please add an option to make the new "elapsed" stat optional

Reported by: Anton1699 Owned by:
Priority: wish Component: ffmpeg
Version: unspecified Keywords:
Cc: MasterQuestionable Blocked By:
Blocking: Reproduced by developer: no
Analyzed by developer: no

Description

This commit added the elapsed time to the output of -stats. I would like to propose an option like -stats_print_elapsed_time <bool> (enabled by default) to disable this new behavior. I also don't think the elapsed time should be the first data point, it's not as important as the actual progress being made.

Attachments (1)

FFmpeg Progress Bar.gif (43.1 KB ) - added by forthrin 14 months ago.
FFmpeg Progress Bar

Download all attachments as: .zip

Change History (7)

comment:1 by MasterQuestionable, 14 months ago

Cc: MasterQuestionable added

͏    "-stats_elapsed_time" should suffice.
͏    Or probably custom stats entries support..?
͏    ("-statsf a,b", "-statsf -elapsed_time")
͏    .
͏    If someone really has the interest?

͏    Note: "-stats" is boolean expecting no option.

Last edited 14 months ago by MasterQuestionable (previous) (diff)

comment:2 by Seb, 14 months ago

I agree the line has become way too long, it overflows my cmd window and messes up.
Ideally, the progress line could be tuned, by removing stuff

-stats -stats-fields "-fps,-q,-elapsed,+bitrate"

by forthrin, 14 months ago

Attachment: FFmpeg Progress Bar.gif added

FFmpeg Progress Bar

comment:3 by forthrin, 14 months ago

Timely that this should come up now, as I wrote a progress bar just a few days ago.

Fundamental principles for a good progress bar:

  • Present the most relevant information for the user
  • Stay within Terminal width (ws_col) as to prevent flooding

A -stats-fields variable might be a good idea, albeit cumbersome having to specify for every use.

An alternative is to remove elements in order of importance as window shrinks (like UI toolbars).

The progress bar now boasts a rather hefty set of variables:

  • frame=1080
  • fps=0.0
  • q=-1.0
  • size=116KiB
  • time=00:00:17.96
  • bitrate=52.8kbits/s
  • (dup)
  • (drop)
  • speed=51x
  • elapsed=0:00:00.35

Personally, my only questions when converting files are:

  • How large will it be
  • How long will it take (and when done, how long did it *actually* take)
  • Name of current file being converted

Which formed the basis for the attached implementation.

Progress visualization could be separated into progress.c so people could get creative with different implementations.

in reply to:  3 comment:4 by Gyan, 14 months ago

Replying to forthrin:

A -stats-fields variable might be a good idea, albeit cumbersome having to specify for every use.

We can assign it a default value, as well as some presets.

comment:5 by forthrin, 14 months ago

@Gyan: Presets sound great! Example (disregarding backwards compatibility for now):

$ ffmpeg -bars
Presets:
  none: No progress bar
  peek: Estimated encoding time left, estimated target size and filename
  term: Most important values within 80 fixed characters (default)
  flex: Most important values within dynamic Terminal width
  full: Everything
Fields:
  frame: Frame number
  fps: Frames encoded per second (user time)
  etc.
  color: Show progress as background color
Variants:
  -bar -> key=value
  +bar -> value

$ ffmpeg +bar peek,color -i in.mp4 out.mp4
 4096M   64m  out.mp4

$ ffmpeg +bar frame,q -i in.mp4 out.mp4
1234 28.0

$ ffmpeg -bar frame,q -i in.mp4 out.mp4
frame=1234 q=28.0

Some questions:

  1. Do you think a selection of progress bars belong in a dedicated progress.c file, or best done via -progress /tmp/fifo and a script (eg. Ruby) running alongside FFmpeg?

Using a script eliminates icky string and Unicode handling in C, but begs the launching of the script and keeping the FIFO continuously readable/writable from respective sides.

  1. duration (recording time) is required for ETA and target size. How to get recording_time (recently moved from InputFile to Demuxer) from print_report() without hacking?

(Must obviously iterate all i/o files to find global maximum recording time.)

diff --git a/fftools/ffmpeg.c b/fftools/ffmpeg.c
index de607cac..3b1794fa 100644
--- a/fftools/ffmpeg.c
+++ b/fftools/ffmpeg.c
@@ -687,2 +687,4 @@ static void print_report(int is_last_report, int64_t timer_start, int64_t cur_ti
     av_bprintf(&buf, " elapsed=%"PRId64":%02d:%02d.%02d", hours, mins, secs, ms / 10);
+    av_bprintf(&buf_script, "duration=%lld\n", FFMIN(input_files[0]->ctx->duration, input_files[0]->recording_time));
+    av_bprintf(&buf_script, "url=%s\n", output_files[0]->url);
 
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 7868f3d8..a97fca05 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -506,3 +506,3 @@ typedef struct InputFile {
     int64_t          start_time;
-
+    int64_t          recording_time; // git.ffmpeg.org/gitweb/ffmpeg.git/commit/8f592
     /* streams that ffmpeg is aware of;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index cb4318c7..f8201fd2 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -1875,3 +1875,3 @@ int ifile_open(const OptionsContext *o, const char *filename, Scheduler *sch)
     f->start_time = start_time;
-    d->recording_time = recording_time;
+    f->recording_time = d->recording_time = recording_time; // HACK
     f->input_sync_ref = o->input_sync_ref;

Then:

    columns = current_width_of_terminal
    est_size = (duration / out_time_ms) * total_size / 1_000_000
    est_time = (duration - out_time_ms) / speed / 1_000_000
    progress = columns * est_time / duration

comment:6 by forthrin, 12 months ago

@Gyan: Ping

Note: See TracTickets for help on using tickets.