Message ID | 20191214225931.28368-1-alexandre.schmidt@gmail.com |
---|---|
State | New |
Headers | show |
On Sat, 14 Dec 2019, Alexandre Heitor Schmidt wrote: > avfilter/drawtext: Added two special metadata tags which can, be used by > 'drawtext' filter and others to have access to source file path, and its > basename. > > The new field AVPacket->source_file will contain a path to its corresponding > filename everytime the packet corresponds to a single file. This behavior is > common for image2 filter. When this field is filled, frames passed to filters > will contain two special metadata tags called source_path (the entire path to > the file) and source_basename (only the file name). These metatags can be > used by filters like drawtext to be able to plot the entire path or the > basename of it respectively to the frame being processed. > > doc/filters: The documentation for drawtext was also updated and an usage > example was added. > > Fixes #2874. This seems like something that be done less intrusively by setting an AV_PKT_DATA_STRINGS_METADATA packet side data for each packet. That is automatically transformed to frame metadata which can be referenced by the drawtext filter. Regards, Marton > > Signed-off-by: Alexandre Heitor Schmidt <alexandre.schmidt@gmail.com> > --- > doc/filters.texi | 13 +++++++++++++ > fftools/ffmpeg.c | 12 ++++++++++++ > libavcodec/avcodec.h | 8 ++++++++ > libavcodec/avpacket.c | 1 + > libavformat/img2dec.c | 9 +++++++++ > 5 files changed, 43 insertions(+) > > diff --git a/doc/filters.texi b/doc/filters.texi > index 93f54a2e1e..d984efb73b 100644 > --- a/doc/filters.texi > +++ b/doc/filters.texi > @@ -9726,6 +9726,12 @@ printed by running @code{ffprobe -show_frames}. > String metadata generated in filters leading to > the drawtext filter are also available. > > +There are two special metadata fields (@var{source_path} and @var{source_basename}) > +which can be used when input format has a file corresponding to each frame, such > +as @var{image2}. @var{source_path} will output the entire path to the filename > +which generated the frame in question, while @var{source_basename} outputs the > +equivalent to @code{basename(source_path)}. > + > @item n, frame_num > The frame number, starting from 0. > > @@ -9872,6 +9878,13 @@ drawtext=fontfile=FreeSans.ttf:text=DOG:fontsize=24:x=10:y=20+24-max_glyph_a, > drawtext=fontfile=FreeSans.ttf:text=cow:fontsize=24:x=80:y=20+24-max_glyph_a > @end example > > +@item > +Plot special @var{source_basename} metadata, extracted from each input frame, or > +the string "NA" if the metadata is not defined. > +@example > +drawtext="fontsize=20:fontcolor=white:fontfile=FreeSans.ttf:text='%{metadata\:source_basename\:NA}':x=10:y=10" > +@end example > + > @end itemize > > For more information about libfreetype, check: > diff --git a/fftools/ffmpeg.c b/fftools/ffmpeg.c > index 27f68933f8..9285f86a81 100644 > --- a/fftools/ffmpeg.c > +++ b/fftools/ffmpeg.c > @@ -2375,6 +2375,18 @@ static int decode_video(InputStream *ist, AVPacket *pkt, int *got_output, int64_ > if (ret < 0) > *decode_failed = 1; > > + /** > + * Set filename as a frame metadata, if it's not empty. This will allow filters > + * like drawtext to use this information for cases like image2, where each frame > + * corresponds to a file. > + */ > + if (pkt) { > + if ( pkt->source_filename != NULL ) { > + av_dict_set(&decoded_frame->metadata, "source_path", pkt->source_filename, 0); > + av_dict_set(&decoded_frame->metadata, "source_basename", av_basename(pkt->source_filename), 0); > + } > + } > + > // The following line may be required in some cases where there is no parser > // or the parser does not has_b_frames correctly > if (ist->st->codecpar->video_delay < ist->dec_ctx->has_b_frames) { > diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h > index 119b32dc1f..4e285f4dd8 100644 > --- a/libavcodec/avcodec.h > +++ b/libavcodec/avcodec.h > @@ -1511,6 +1511,14 @@ typedef struct AVPacket { > attribute_deprecated > int64_t convergence_duration; > #endif > + > + /** > + * In cases where the packet corresponds to the contents of one single > + * file, like when image2 is used, this is set to the source filename, > + * so it can be used by filters like drawtext, to plot the source > + * filename on the frame. > + */ > + char *source_filename; > } AVPacket; > #define AV_PKT_FLAG_KEY 0x0001 ///< The packet contains a keyframe > #define AV_PKT_FLAG_CORRUPT 0x0002 ///< The packet content is corrupted > diff --git a/libavcodec/avpacket.c b/libavcodec/avpacket.c > index 858f827a0a..c357e2fbac 100644 > --- a/libavcodec/avpacket.c > +++ b/libavcodec/avpacket.c > @@ -46,6 +46,7 @@ FF_ENABLE_DEPRECATION_WARNINGS > pkt->buf = NULL; > pkt->side_data = NULL; > pkt->side_data_elems = 0; > + pkt->source_filename = NULL; > } > > AVPacket *av_packet_alloc(void) > diff --git a/libavformat/img2dec.c b/libavformat/img2dec.c > index f8b4a655a5..02119d89fc 100644 > --- a/libavformat/img2dec.c > +++ b/libavformat/img2dec.c > @@ -485,6 +485,15 @@ int ff_img_read_packet(AVFormatContext *s1, AVPacket *pkt) > > if (s->is_pipe) > pkt->pos = avio_tell(f[0]); > + else { > + // Set the filename which corresponds to this packet. > + pkt->source_filename = av_malloc(strlen(filename)); > + if (!pkt->source_filename) { > + av_log(NULL, AV_LOG_FATAL, "Failed to allocate source_filename\n"); > + return AVERROR(ENOMEM); > + } > + pkt->source_filename = av_asprintf("%s", filename); > + } > > pkt->size = 0; > for (i = 0; i < 3; i++) { > -- > 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-request@ffmpeg.org with subject "unsubscribe".
On 14/12/2019 23:15, Marton Balint wrote: > On Sat, 14 Dec 2019, Alexandre Heitor Schmidt wrote: >> avfilter/drawtext: Added two special metadata tags which can, be used by >> 'drawtext' filter and others to have access to source file path, and its >> basename. >> >> The new field AVPacket->source_file will contain a path to its >> corresponding >> filename everytime the packet corresponds to a single file. This >> behavior is >> common for image2 filter. When this field is filled, frames passed to >> filters >> will contain two special metadata tags called source_path (the entire >> path to >> the file) and source_basename (only the file name). These metatags >> can be >> used by filters like drawtext to be able to plot the entire path or the >> basename of it respectively to the frame being processed. >> >> doc/filters: The documentation for drawtext was also updated and an >> usage >> example was added. >> >> Fixes #2874. > > This seems like something that be done less intrusively by setting an > AV_PKT_DATA_STRINGS_METADATA packet side data for each packet. That is > automatically transformed to frame metadata which can be referenced by > the drawtext filter. > > Regards, > Marton That's great, Marton! Thanks for the tip! I'll research on how to use AV_PKT_DATA_STRINGS_METADATA properly and re-submit the patch. By the way, how should I proceed with the patch at https://patchwork.ffmpeg.org/patch/16798/? I think it should be deleted until I have it implemented the way you suggested, right? Thanks again! Best wishes, Alex. > >> >> Signed-off-by: Alexandre Heitor Schmidt <alexandre.schmidt@gmail.com> >> --- >> doc/filters.texi | 13 +++++++++++++ >> fftools/ffmpeg.c | 12 ++++++++++++ >> libavcodec/avcodec.h | 8 ++++++++ >> libavcodec/avpacket.c | 1 + >> libavformat/img2dec.c | 9 +++++++++ >> 5 files changed, 43 insertions(+) >> >> diff --git a/doc/filters.texi b/doc/filters.texi >> index 93f54a2e1e..d984efb73b 100644 >> --- a/doc/filters.texi >> +++ b/doc/filters.texi >> @@ -9726,6 +9726,12 @@ printed by running @code{ffprobe -show_frames}. >> String metadata generated in filters leading to >> the drawtext filter are also available. >> >> +There are two special metadata fields (@var{source_path} and >> @var{source_basename}) >> +which can be used when input format has a file corresponding to each >> frame, such >> +as @var{image2}. @var{source_path} will output the entire path to >> the filename >> +which generated the frame in question, while @var{source_basename} >> outputs the >> +equivalent to @code{basename(source_path)}. >> + >> @item n, frame_num >> The frame number, starting from 0. >> >> @@ -9872,6 +9878,13 @@ >> drawtext=fontfile=FreeSans.ttf:text=DOG:fontsize=24:x=10:y=20+24-max_glyph_a, >> drawtext=fontfile=FreeSans.ttf:text=cow:fontsize=24:x=80:y=20+24-max_glyph_a >> >> @end example >> >> +@item >> +Plot special @var{source_basename} metadata, extracted from each >> input frame, or >> +the string "NA" if the metadata is not defined. >> +@example >> +drawtext="fontsize=20:fontcolor=white:fontfile=FreeSans.ttf:text='%{metadata\:source_basename\:NA}':x=10:y=10" >> >> +@end example >> + >> @end itemize >> >> For more information about libfreetype, check: >> diff --git a/fftools/ffmpeg.c b/fftools/ffmpeg.c >> index 27f68933f8..9285f86a81 100644 >> --- a/fftools/ffmpeg.c >> +++ b/fftools/ffmpeg.c >> @@ -2375,6 +2375,18 @@ static int decode_video(InputStream *ist, >> AVPacket *pkt, int *got_output, int64_ >> if (ret < 0) >> *decode_failed = 1; >> >> + /** >> + * Set filename as a frame metadata, if it's not empty. This >> will allow filters >> + * like drawtext to use this information for cases like image2, >> where each frame >> + * corresponds to a file. >> + */ >> + if (pkt) { >> + if ( pkt->source_filename != NULL ) { >> + av_dict_set(&decoded_frame->metadata, "source_path", >> pkt->source_filename, 0); >> + av_dict_set(&decoded_frame->metadata, "source_basename", >> av_basename(pkt->source_filename), 0); >> + } >> + } >> + >> // The following line may be required in some cases where there >> is no parser >> // or the parser does not has_b_frames correctly >> if (ist->st->codecpar->video_delay < ist->dec_ctx->has_b_frames) { >> diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h >> index 119b32dc1f..4e285f4dd8 100644 >> --- a/libavcodec/avcodec.h >> +++ b/libavcodec/avcodec.h >> @@ -1511,6 +1511,14 @@ typedef struct AVPacket { >> attribute_deprecated >> int64_t convergence_duration; >> #endif >> + >> + /** >> + * In cases where the packet corresponds to the contents of one >> single >> + * file, like when image2 is used, this is set to the source >> filename, >> + * so it can be used by filters like drawtext, to plot the source >> + * filename on the frame. >> + */ >> + char *source_filename; >> } AVPacket; >> #define AV_PKT_FLAG_KEY 0x0001 ///< The packet contains a keyframe >> #define AV_PKT_FLAG_CORRUPT 0x0002 ///< The packet content is corrupted >> diff --git a/libavcodec/avpacket.c b/libavcodec/avpacket.c >> index 858f827a0a..c357e2fbac 100644 >> --- a/libavcodec/avpacket.c >> +++ b/libavcodec/avpacket.c >> @@ -46,6 +46,7 @@ FF_ENABLE_DEPRECATION_WARNINGS >> pkt->buf = NULL; >> pkt->side_data = NULL; >> pkt->side_data_elems = 0; >> + pkt->source_filename = NULL; >> } >> >> AVPacket *av_packet_alloc(void) >> diff --git a/libavformat/img2dec.c b/libavformat/img2dec.c >> index f8b4a655a5..02119d89fc 100644 >> --- a/libavformat/img2dec.c >> +++ b/libavformat/img2dec.c >> @@ -485,6 +485,15 @@ int ff_img_read_packet(AVFormatContext *s1, >> AVPacket *pkt) >> >> if (s->is_pipe) >> pkt->pos = avio_tell(f[0]); >> + else { >> + // Set the filename which corresponds to this packet. >> + pkt->source_filename = av_malloc(strlen(filename)); >> + if (!pkt->source_filename) { >> + av_log(NULL, AV_LOG_FATAL, "Failed to allocate >> source_filename\n"); >> + return AVERROR(ENOMEM); >> + } >> + pkt->source_filename = av_asprintf("%s", filename); >> + } >> >> pkt->size = 0; >> for (i = 0; i < 3; i++) { >> -- >> 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-request@ffmpeg.org with subject "unsubscribe". > _______________________________________________ > ffmpeg-devel mailing list > ffmpeg-devel@ffmpeg.org > https://ffmpeg.org/mailman/listinfo/ffmpeg-devel > > To unsubscribe, visit link above, or email > ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
On Sat, Dec 14, 2019 at 10:59:31PM +0000, Alexandre Heitor Schmidt wrote: > avfilter/drawtext: Added two special metadata tags which can, be used by > 'drawtext' filter and others to have access to source file path, and its > basename. > > The new field AVPacket->source_file will contain a path to its corresponding > filename everytime the packet corresponds to a single file. This behavior is > common for image2 filter. When this field is filled, frames passed to filters > will contain two special metadata tags called source_path (the entire path to > the file) and source_basename (only the file name). These metatags can be > used by filters like drawtext to be able to plot the entire path or the > basename of it respectively to the frame being processed. > > doc/filters: The documentation for drawtext was also updated and an usage > example was added. > > Fixes #2874. > > Signed-off-by: Alexandre Heitor Schmidt <alexandre.schmidt@gmail.com> > --- > doc/filters.texi | 13 +++++++++++++ > fftools/ffmpeg.c | 12 ++++++++++++ > libavcodec/avcodec.h | 8 ++++++++ > libavcodec/avpacket.c | 1 + > libavformat/img2dec.c | 9 +++++++++ > 5 files changed, 43 insertions(+) doc/filters.texi:9885: misplaced { doc/filters.texi:9885: misplaced } make: *** [doc/ffprobe-all.html] Error 1 make: *** Waiting for unfinished jobs.... doc/filters.texi:9885: misplaced { doc/filters.texi:9885: misplaced } make: *** [doc/ffplay-all.html] Error 1 doc/filters.texi:9885: misplaced { doc/filters.texi:9885: misplaced } make: *** [doc/ffmpeg-all.html] Error 1 doc/filters.texi:9885: misplaced { doc/filters.texi:9885: misplaced } make: *** [doc/ffmpeg-filters.html] Error 1 [...]
On 15/12/2019 15:04, Michael Niedermayer wrote: > On Sat, Dec 14, 2019 at 10:59:31PM +0000, Alexandre Heitor Schmidt wrote: >> avfilter/drawtext: Added two special metadata tags which can, be used by >> 'drawtext' filter and others to have access to source file path, and its >> basename. >> >> The new field AVPacket->source_file will contain a path to its corresponding >> filename everytime the packet corresponds to a single file. This behavior is >> common for image2 filter. When this field is filled, frames passed to filters >> will contain two special metadata tags called source_path (the entire path to >> the file) and source_basename (only the file name). These metatags can be >> used by filters like drawtext to be able to plot the entire path or the >> basename of it respectively to the frame being processed. >> >> doc/filters: The documentation for drawtext was also updated and an usage >> example was added. >> >> Fixes #2874. >> >> Signed-off-by: Alexandre Heitor Schmidt <alexandre.schmidt@gmail.com> >> --- >> doc/filters.texi | 13 +++++++++++++ >> fftools/ffmpeg.c | 12 ++++++++++++ >> libavcodec/avcodec.h | 8 ++++++++ >> libavcodec/avpacket.c | 1 + >> libavformat/img2dec.c | 9 +++++++++ >> 5 files changed, 43 insertions(+) > > doc/filters.texi:9885: misplaced { > doc/filters.texi:9885: misplaced } > make: *** [doc/ffprobe-all.html] Error 1 > make: *** Waiting for unfinished jobs.... > doc/filters.texi:9885: misplaced { > doc/filters.texi:9885: misplaced } > make: *** [doc/ffplay-all.html] Error 1 > doc/filters.texi:9885: misplaced { > doc/filters.texi:9885: misplaced } > make: *** [doc/ffmpeg-all.html] Error 1 > doc/filters.texi:9885: misplaced { > doc/filters.texi:9885: misplaced } > make: *** [doc/ffmpeg-filters.html] Error 1 > > [...] I saw the problem... git messed up the @item and @example tags in docs. :S I'll find out why and re-submit the patch. I have to redo it anyway to use AV_PKT_DATA_STRINGS_METADATA, as suggested by Marton Balint. Alex.
diff --git a/doc/filters.texi b/doc/filters.texi index 93f54a2e1e..d984efb73b 100644 --- a/doc/filters.texi +++ b/doc/filters.texi @@ -9726,6 +9726,12 @@ printed by running @code{ffprobe -show_frames}. String metadata generated in filters leading to the drawtext filter are also available. +There are two special metadata fields (@var{source_path} and @var{source_basename}) +which can be used when input format has a file corresponding to each frame, such +as @var{image2}. @var{source_path} will output the entire path to the filename +which generated the frame in question, while @var{source_basename} outputs the +equivalent to @code{basename(source_path)}. + @item n, frame_num The frame number, starting from 0. @@ -9872,6 +9878,13 @@ drawtext=fontfile=FreeSans.ttf:text=DOG:fontsize=24:x=10:y=20+24-max_glyph_a, drawtext=fontfile=FreeSans.ttf:text=cow:fontsize=24:x=80:y=20+24-max_glyph_a @end example +@item +Plot special @var{source_basename} metadata, extracted from each input frame, or +the string "NA" if the metadata is not defined. +@example +drawtext="fontsize=20:fontcolor=white:fontfile=FreeSans.ttf:text='%{metadata\:source_basename\:NA}':x=10:y=10" +@end example + @end itemize For more information about libfreetype, check: diff --git a/fftools/ffmpeg.c b/fftools/ffmpeg.c index 27f68933f8..9285f86a81 100644 --- a/fftools/ffmpeg.c +++ b/fftools/ffmpeg.c @@ -2375,6 +2375,18 @@ static int decode_video(InputStream *ist, AVPacket *pkt, int *got_output, int64_ if (ret < 0) *decode_failed = 1; + /** + * Set filename as a frame metadata, if it's not empty. This will allow filters + * like drawtext to use this information for cases like image2, where each frame + * corresponds to a file. + */ + if (pkt) { + if ( pkt->source_filename != NULL ) { + av_dict_set(&decoded_frame->metadata, "source_path", pkt->source_filename, 0); + av_dict_set(&decoded_frame->metadata, "source_basename", av_basename(pkt->source_filename), 0); + } + } + // The following line may be required in some cases where there is no parser // or the parser does not has_b_frames correctly if (ist->st->codecpar->video_delay < ist->dec_ctx->has_b_frames) { diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h index 119b32dc1f..4e285f4dd8 100644 --- a/libavcodec/avcodec.h +++ b/libavcodec/avcodec.h @@ -1511,6 +1511,14 @@ typedef struct AVPacket { attribute_deprecated int64_t convergence_duration; #endif + + /** + * In cases where the packet corresponds to the contents of one single + * file, like when image2 is used, this is set to the source filename, + * so it can be used by filters like drawtext, to plot the source + * filename on the frame. + */ + char *source_filename; } AVPacket; #define AV_PKT_FLAG_KEY 0x0001 ///< The packet contains a keyframe #define AV_PKT_FLAG_CORRUPT 0x0002 ///< The packet content is corrupted diff --git a/libavcodec/avpacket.c b/libavcodec/avpacket.c index 858f827a0a..c357e2fbac 100644 --- a/libavcodec/avpacket.c +++ b/libavcodec/avpacket.c @@ -46,6 +46,7 @@ FF_ENABLE_DEPRECATION_WARNINGS pkt->buf = NULL; pkt->side_data = NULL; pkt->side_data_elems = 0; + pkt->source_filename = NULL; } AVPacket *av_packet_alloc(void) diff --git a/libavformat/img2dec.c b/libavformat/img2dec.c index f8b4a655a5..02119d89fc 100644 --- a/libavformat/img2dec.c +++ b/libavformat/img2dec.c @@ -485,6 +485,15 @@ int ff_img_read_packet(AVFormatContext *s1, AVPacket *pkt) if (s->is_pipe) pkt->pos = avio_tell(f[0]); + else { + // Set the filename which corresponds to this packet. + pkt->source_filename = av_malloc(strlen(filename)); + if (!pkt->source_filename) { + av_log(NULL, AV_LOG_FATAL, "Failed to allocate source_filename\n"); + return AVERROR(ENOMEM); + } + pkt->source_filename = av_asprintf("%s", filename); + } pkt->size = 0; for (i = 0; i < 3; i++) {
avfilter/drawtext: Added two special metadata tags which can, be used by 'drawtext' filter and others to have access to source file path, and its basename. The new field AVPacket->source_file will contain a path to its corresponding filename everytime the packet corresponds to a single file. This behavior is common for image2 filter. When this field is filled, frames passed to filters will contain two special metadata tags called source_path (the entire path to the file) and source_basename (only the file name). These metatags can be used by filters like drawtext to be able to plot the entire path or the basename of it respectively to the frame being processed. doc/filters: The documentation for drawtext was also updated and an usage example was added. Fixes #2874. Signed-off-by: Alexandre Heitor Schmidt <alexandre.schmidt@gmail.com> --- doc/filters.texi | 13 +++++++++++++ fftools/ffmpeg.c | 12 ++++++++++++ libavcodec/avcodec.h | 8 ++++++++ libavcodec/avpacket.c | 1 + libavformat/img2dec.c | 9 +++++++++ 5 files changed, 43 insertions(+)