Have now added documentation and cleaned up some unused variables with
the new patch. Also on a second thought the option names
"show_pixel_format_descriptions" or "show_pixel_formats" seem less
confusing to me than "show_pixel_descriptions" so I did choose the
shorter "show_pixel_formats".
What I would like to add in a follow-up patch is a way to output the
flags. I see different options:
a) Output a character per flag (R=RGB, A=ALPHA, B=BITSTREAM, ...) but
this needs extra documentation and might be confusing due to collisions
(P=PALETTE or P=PLANAR? B=BIG-ENDIAN or B=BITSTREAM?)
Example: flag="RAP"
b) Output a list of flag names separated by comma or space. This would
fit mostly with JSON (comma) or XML (space) output format style, I guess.
Example 1: flag="rgb,alpha,palette"
Example 2: flag="rgb alpha palette"
c) Output each flag as a boolean value. This increases amount of output
but fits better to output formats like CSV or INI.
Example: is_rgb="1" has_alpha="1" is_bitstream="0" has_palette="1"
What do you think?
Tobias
>From 5938c171472469e91bb2b7445100ab6509929ba7 Mon Sep 17 00:00:00 2001
From: Tobias Rapp <t.r...@noa-audio.com>
Date: Thu, 11 Sep 2014 09:16:52 +0200
Subject: [PATCH] ffprobe: add -show_pixel_formats option
Adds option -show_pixel_formats to ffprobe which lists all
available pixel formats with some details.
---
doc/ffprobe.texi | 6 +++++
doc/ffprobe.xsd | 15 +++++++++++
ffprobe.c | 78 ++++++++++++++++++++++++++++++++++++++++++++++++++++++--
3 files changed, 97 insertions(+), 2 deletions(-)
diff --git a/doc/ffprobe.texi b/doc/ffprobe.texi
index 0a39ed4..5c90470 100644
--- a/doc/ffprobe.texi
+++ b/doc/ffprobe.texi
@@ -321,6 +321,12 @@ Show information related to program and library versions.
This is the
equivalent of setting both @option{-show_program_version} and
@option{-show_library_versions} options.
+@item -show_pixel_formats
+Show information about all pixel formats supported by FFmpeg.
+
+Pixel format information for each format is printed within a section
+with name "PIXEL_FORMAT".
+
@item -bitexact
Force bitexact output, useful to produce output which is not dependent
on the specific build.
diff --git a/doc/ffprobe.xsd b/doc/ffprobe.xsd
index 5dfbb47..33c4f20 100644
--- a/doc/ffprobe.xsd
+++ b/doc/ffprobe.xsd
@@ -10,6 +10,7 @@
<xsd:sequence>
<xsd:element name="program_version"
type="ffprobe:programVersionType" minOccurs="0" maxOccurs="1" />
<xsd:element name="library_versions"
type="ffprobe:libraryVersionsType" minOccurs="0" maxOccurs="1" />
+ <xsd:element name="pixel_formats"
type="ffprobe:pixelFormatsType" minOccurs="0" maxOccurs="1" />
<xsd:element name="packets" type="ffprobe:packetsType"
minOccurs="0" maxOccurs="1" />
<xsd:element name="frames" type="ffprobe:framesType"
minOccurs="0" maxOccurs="1" />
<xsd:element name="programs" type="ffprobe:programsType"
minOccurs="0" maxOccurs="1" />
@@ -277,4 +278,18 @@
<xsd:element name="library_version"
type="ffprobe:libraryVersionType" minOccurs="0" maxOccurs="unbounded"/>
</xsd:sequence>
</xsd:complexType>
+
+ <xsd:complexType name="pixelFormatType">
+ <xsd:attribute name="name" type="xsd:string"
use="required"/>
+ <xsd:attribute name="nb_components" type="xsd:int"
use="required"/>
+ <xsd:attribute name="bits_per_pixel" type="xsd:int"/>
+ <xsd:attribute name="bits_per_component" type="xsd:int"/>
+ <xsd:attribute name="chroma_sub_sampling" type="xsd:string"/>
+ </xsd:complexType>
+
+ <xsd:complexType name="pixelFormatsType">
+ <xsd:sequence>
+ <xsd:element name="pixel_format" type="ffprobe:pixelFormatType"
minOccurs="0" maxOccurs="unbounded"/>
+ </xsd:sequence>
+ </xsd:complexType>
</xsd:schema>
diff --git a/ffprobe.c b/ffprobe.c
index 9bb0f0f..621df04 100644
--- a/ffprobe.c
+++ b/ffprobe.c
@@ -66,6 +66,7 @@ static int do_show_stream_disposition = 0;
static int do_show_data = 0;
static int do_show_program_version = 0;
static int do_show_library_versions = 0;
+static int do_show_pixel_formats = 0;
static int do_show_chapter_tags = 0;
static int do_show_format_tags = 0;
@@ -132,6 +133,8 @@ typedef enum {
SECTION_ID_PACKET,
SECTION_ID_PACKETS,
SECTION_ID_PACKETS_AND_FRAMES,
+ SECTION_ID_PIXEL_FORMAT,
+ SECTION_ID_PIXEL_FORMATS,
SECTION_ID_PROGRAM_STREAM_DISPOSITION,
SECTION_ID_PROGRAM_STREAM_TAGS,
SECTION_ID_PROGRAM,
@@ -165,6 +168,8 @@ static struct section sections[] = {
[SECTION_ID_PACKETS] = { SECTION_ID_PACKETS, "packets",
SECTION_FLAG_IS_ARRAY, { SECTION_ID_PACKET, -1} },
[SECTION_ID_PACKETS_AND_FRAMES] = { SECTION_ID_PACKETS_AND_FRAMES,
"packets_and_frames", SECTION_FLAG_IS_ARRAY, { SECTION_ID_PACKET, -1} },
[SECTION_ID_PACKET] = { SECTION_ID_PACKET, "packet", 0, { -1 }
},
+ [SECTION_ID_PIXEL_FORMATS] = { SECTION_ID_PIXEL_FORMATS,
"pixel_formats", SECTION_FLAG_IS_ARRAY, { SECTION_ID_PIXEL_FORMAT, -1 } },
+ [SECTION_ID_PIXEL_FORMAT] = { SECTION_ID_PIXEL_FORMAT,
"pixel_format", 0, { -1 } },
[SECTION_ID_PROGRAM_STREAM_DISPOSITION] = {
SECTION_ID_PROGRAM_STREAM_DISPOSITION, "disposition", 0, { -1 }, .unique_name =
"program_stream_disposition" },
[SECTION_ID_PROGRAM_STREAM_TAGS] = {
SECTION_ID_PROGRAM_STREAM_TAGS, "tags", SECTION_FLAG_HAS_VARIABLE_FIELDS, { -1
}, .element_name = "tag", .unique_name = "program_stream_tags" },
[SECTION_ID_PROGRAM] = { SECTION_ID_PROGRAM, "program",
0, { SECTION_ID_PROGRAM_TAGS, SECTION_ID_PROGRAM_STREAMS, -1 } },
@@ -175,7 +180,8 @@ static struct section sections[] = {
[SECTION_ID_PROGRAMS] = { SECTION_ID_PROGRAMS,
"programs", SECTION_FLAG_IS_ARRAY, { SECTION_ID_PROGRAM, -1 } },
[SECTION_ID_ROOT] = { SECTION_ID_ROOT, "root",
SECTION_FLAG_IS_WRAPPER,
{ SECTION_ID_CHAPTERS,
SECTION_ID_FORMAT, SECTION_ID_FRAMES, SECTION_ID_PROGRAMS, SECTION_ID_STREAMS,
- SECTION_ID_PACKETS,
SECTION_ID_ERROR, SECTION_ID_PROGRAM_VERSION, SECTION_ID_LIBRARY_VERSIONS, -1}
},
+ SECTION_ID_PACKETS,
SECTION_ID_ERROR, SECTION_ID_PROGRAM_VERSION, SECTION_ID_LIBRARY_VERSIONS,
+ SECTION_ID_PIXEL_FORMATS, -1} },
[SECTION_ID_STREAMS] = { SECTION_ID_STREAMS, "streams",
SECTION_FLAG_IS_ARRAY, { SECTION_ID_STREAM, -1 } },
[SECTION_ID_STREAM] = { SECTION_ID_STREAM, "stream", 0, {
SECTION_ID_STREAM_DISPOSITION, SECTION_ID_STREAM_TAGS, -1 } },
[SECTION_ID_STREAM_DISPOSITION] = { SECTION_ID_STREAM_DISPOSITION,
"disposition", 0, { -1 }, .unique_name = "stream_disposition" },
@@ -2557,6 +2563,69 @@ static void ffprobe_show_library_versions(WriterContext
*w)
writer_print_section_footer(w);
}
+static int get_bits_per_component(const AVPixFmtDescriptor *pixdesc)
+{
+ int c, bits, first_bits = 0;
+
+ for (c = 0; c < pixdesc->nb_components; c++) {
+ bits = pixdesc->comp[c].depth_minus1 + 1;
+ if (c == 0)
+ first_bits = bits;
+ else if (bits != first_bits)
+ return 0;
+ }
+
+ return first_bits;
+}
+
+static const char *get_chroma_sub_sample_string(const AVPixFmtDescriptor
*pixdesc)
+{
+ if (!pixdesc)
+ return NULL;
+ if ((pixdesc->flags & AV_PIX_FMT_FLAG_RGB) || pixdesc->nb_components < 3)
+ return NULL;
+
+ if ((pixdesc->log2_chroma_w == 0) && (pixdesc->log2_chroma_h == 0))
+ return "4:4:4";
+ else if ((pixdesc->log2_chroma_w == 0) && (pixdesc->log2_chroma_h == 1))
+ return "4:4:0";
+ else if ((pixdesc->log2_chroma_w == 1) && (pixdesc->log2_chroma_h == 0))
+ return "4:2:2";
+ else if ((pixdesc->log2_chroma_w == 1) && (pixdesc->log2_chroma_h == 1))
+ return "4:2:0";
+ else if ((pixdesc->log2_chroma_w == 2) && (pixdesc->log2_chroma_h == 0))
+ return "4:1:1";
+ else if ((pixdesc->log2_chroma_w == 2) && (pixdesc->log2_chroma_h == 2))
+ return "4:1:0";
+ else
+ return "unknown";
+}
+
+static void ffprobe_show_pixel_formats(WriterContext *w)
+{
+ const AVPixFmtDescriptor *pixdesc = NULL;
+ const char *s;
+ int n;
+
+ writer_print_section_header(w, SECTION_ID_PIXEL_FORMATS);
+ while (pixdesc = av_pix_fmt_desc_next(pixdesc)) {
+ writer_print_section_header(w, SECTION_ID_PIXEL_FORMAT);
+ print_str("name", pixdesc->name);
+ print_int("nb_components", pixdesc->nb_components);
+ n = av_get_bits_per_pixel(pixdesc);
+ if (n) print_int ("bits_per_pixel", n);
+ else print_str_opt("bits_per_pixel", "N/A");
+ n = get_bits_per_component(pixdesc);
+ if (n) print_int ("bits_per_component", n);
+ else print_str_opt("bits_per_component", "N/A");
+ s = get_chroma_sub_sample_string(pixdesc);
+ if (s) print_str ("chroma_sub_sampling", s);
+ else print_str_opt("chroma_sub_sampling", "unknown");
+ writer_print_section_footer(w);
+ }
+ writer_print_section_footer(w);
+}
+
static int opt_format(void *optctx, const char *opt, const char *arg)
{
iformat = av_find_input_format(arg);
@@ -2890,6 +2959,7 @@ DEFINE_OPT_SHOW_SECTION(format, FORMAT);
DEFINE_OPT_SHOW_SECTION(frames, FRAMES);
DEFINE_OPT_SHOW_SECTION(library_versions, LIBRARY_VERSIONS);
DEFINE_OPT_SHOW_SECTION(packets, PACKETS);
+DEFINE_OPT_SHOW_SECTION(pixel_formats, PIXEL_FORMATS);
DEFINE_OPT_SHOW_SECTION(program_version, PROGRAM_VERSION);
DEFINE_OPT_SHOW_SECTION(streams, STREAMS);
DEFINE_OPT_SHOW_SECTION(programs, PROGRAMS);
@@ -2928,6 +2998,7 @@ static const OptionDef real_options[] = {
{ "show_program_version", 0, {(void*)&opt_show_program_version}, "show
ffprobe version" },
{ "show_library_versions", 0, {(void*)&opt_show_library_versions}, "show
library versions" },
{ "show_versions", 0, {(void*)&opt_show_versions}, "show program
and library versions" },
+ { "show_pixel_formats", 0, {(void*)&opt_show_pixel_formats}, "show pixel
format descriptions" },
{ "show_private_data", OPT_BOOL, {(void*)&show_private_data}, "show
private data" },
{ "private", OPT_BOOL, {(void*)&show_private_data}, "same as
show_private_data" },
{ "bitexact", OPT_BOOL, {&do_bitexact}, "force bitexact output" },
@@ -2984,6 +3055,7 @@ int main(int argc, char **argv)
SET_DO_SHOW(FRAMES, frames);
SET_DO_SHOW(LIBRARY_VERSIONS, library_versions);
SET_DO_SHOW(PACKETS, packets);
+ SET_DO_SHOW(PIXEL_FORMATS, pixel_formats);
SET_DO_SHOW(PROGRAM_VERSION, program_version);
SET_DO_SHOW(PROGRAMS, programs);
SET_DO_SHOW(STREAMS, streams);
@@ -3048,10 +3120,12 @@ int main(int argc, char **argv)
ffprobe_show_program_version(wctx);
if (do_show_library_versions)
ffprobe_show_library_versions(wctx);
+ if (do_show_pixel_formats)
+ ffprobe_show_pixel_formats(wctx);
if (!input_filename &&
((do_show_format || do_show_programs || do_show_streams ||
do_show_chapters || do_show_packets || do_show_error) ||
- (!do_show_program_version && !do_show_library_versions))) {
+ (!do_show_program_version && !do_show_library_versions &&
!do_show_pixel_formats))) {
show_usage();
av_log(NULL, AV_LOG_ERROR, "You have to specify one input
file.\n");
av_log(NULL, AV_LOG_ERROR, "Use -h to get full help or, even
better, run 'man %s'.\n", program_name);
--
1.9.1
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel