example: vaenc-dynamic-reconfigure: Support H265.

Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/2036>
This commit is contained in:
Víctor Manuel Jáquez Leal 2022-11-15 06:58:14 +01:00 committed by He Junyan
parent c365389930
commit 8f96453b0f

View file

@ -45,30 +45,6 @@ typedef struct
gint prev_height; gint prev_height;
} TestCallbackData; } TestCallbackData;
static gboolean
check_encoder_available (const gchar * encoder_name)
{
gboolean ret = TRUE;
GstElement *elem;
elem = gst_element_factory_make (encoder_name, NULL);
if (!elem) {
gst_printerrln ("%s is not available", encoder_name);
return FALSE;
}
if (gst_element_set_state (elem,
GST_STATE_PAUSED) != GST_STATE_CHANGE_SUCCESS) {
gst_printerrln ("cannot open device");
ret = FALSE;
}
gst_element_set_state (elem, GST_STATE_NULL);
gst_object_unref (elem);
return ret;
}
static gboolean static gboolean
bus_msg (GstBus * bus, GstMessage * msg, gpointer user_data) bus_msg (GstBus * bus, GstMessage * msg, gpointer user_data)
{ {
@ -450,22 +426,33 @@ gint
main (gint argc, gchar ** argv) main (gint argc, gchar ** argv)
{ {
GstElement *pipeline; GstElement *pipeline;
GstElement *src, *capsfilter, *enc, *dec, *parser, *sink; GstElement *src, *capsfilter, *convert, *enc, *dec, *parser, *vpp, *sink;
GstElement *queue0, *queue1;
GstStateChangeReturn sret; GstStateChangeReturn sret;
GError *error = NULL; GError *error = NULL;
GOptionContext *option_ctx; GOptionContext *option_ctx;
GstCaps *caps; GstCaps *caps;
GstPad *pad; GstPad *pad;
TestCallbackData data = { 0, }; TestCallbackData data = { 0, };
gchar *encoder_name = NULL; gchar *codec = NULL;
gulong deep_notify_id = 0; gulong deep_notify_id = 0;
guint idx;
/* *INDENT-OFF* */ /* *INDENT-OFF* */
GOptionEntry options[] = { const GOptionEntry options[] = {
{"encoder", 0, 0, G_OPTION_ARG_STRING, &encoder_name, {"codec", 'c', 0, G_OPTION_ARG_STRING, &codec,
"VA video encoder element to test, default: vah264enc"}, "Codec to test: [ *h264, h265 ]"},
{NULL} {NULL}
}; };
const struct {
const char *codec;
const char *encoder;
const char *parser;
const char *decoder;
} elements_map[] = {
{ "h264", "vah264enc", "h264parse", "vah264dec" },
{ "h265", "vah265enc", "h265parse", "vah265dec" },
};
/* *INDENT-ON* */ /* *INDENT-ON* */
#define MAKE_ELEMENT_AND_ADD(elem, name) G_STMT_START { \ #define MAKE_ELEMENT_AND_ADD(elem, name) G_STMT_START { \
@ -493,16 +480,19 @@ main (gint argc, gchar ** argv)
g_option_context_free (option_ctx); g_option_context_free (option_ctx);
gst_init (NULL, NULL); gst_init (NULL, NULL);
if (!encoder_name) if (!codec)
encoder_name = g_strdup ("vah264enc"); codec = g_strdup ("h264");
if (!check_encoder_available (encoder_name)) { for (idx = 0; idx < G_N_ELEMENTS (elements_map); idx++) {
gst_printerrln ("Cannot load %s plugin", encoder_name); if (g_strcmp0 (elements_map[idx].codec, codec) == 0)
exit (1); break;
} }
/* prepare the pipeline */ if (idx == G_N_ELEMENTS (elements_map)) {
loop = g_main_loop_new (NULL, FALSE); gst_printerrln ("Unsupported codec: %s", codec);
exit (1);
}
g_free (codec);
pipeline = gst_pipeline_new (NULL); pipeline = gst_pipeline_new (NULL);
@ -510,29 +500,30 @@ main (gint argc, gchar ** argv)
g_object_set (src, "pattern", 1, NULL); g_object_set (src, "pattern", 1, NULL);
MAKE_ELEMENT_AND_ADD (capsfilter, "capsfilter"); MAKE_ELEMENT_AND_ADD (capsfilter, "capsfilter");
MAKE_ELEMENT_AND_ADD (enc, encoder_name); MAKE_ELEMENT_AND_ADD (convert, "videoconvert");
MAKE_ELEMENT_AND_ADD (enc, elements_map[idx].encoder);
/* gst_util_set_object_arg (G_OBJECT (enc), "rate-control", rate_control); */ MAKE_ELEMENT_AND_ADD (queue0, "queue");
MAKE_ELEMENT_AND_ADD (parser, elements_map[idx].parser);
if (g_strcmp0 (encoder_name, "vah264enc") == 0) { MAKE_ELEMENT_AND_ADD (dec, elements_map[idx].decoder);
MAKE_ELEMENT_AND_ADD (parser, "h264parse"); MAKE_ELEMENT_AND_ADD (vpp, "vapostproc");
MAKE_ELEMENT_AND_ADD (dec, "vah264dec"); MAKE_ELEMENT_AND_ADD (queue1, "queue");
} else {
g_assert_not_reached ();
}
MAKE_ELEMENT_AND_ADD (sink, "autovideosink"); MAKE_ELEMENT_AND_ADD (sink, "autovideosink");
if (!gst_element_link_many (src, capsfilter, enc, parser, dec, sink, NULL)) { if (!gst_element_link_many (src, capsfilter, convert, enc, queue0,
parser, dec, vpp, queue1, sink, NULL)) {
gst_printerrln ("Failed to link element"); gst_printerrln ("Failed to link element");
exit (1); exit (1);
} }
caps = gst_caps_new_simple ("video/x-raw", "width", G_TYPE_INT, caps = gst_caps_new_simple ("video/x-raw", "width", G_TYPE_INT,
width, "height", G_TYPE_INT, height, NULL); width, "height", G_TYPE_INT, height,
"format", G_TYPE_STRING, "I420", NULL);
g_object_set (capsfilter, "caps", caps, NULL); g_object_set (capsfilter, "caps", caps, NULL);
gst_caps_unref (caps); gst_caps_unref (caps);
g_object_set (convert, "chroma-mode", 3, NULL);
g_object_set (convert, "dither", 0, NULL);
data.pipeline = pipeline; data.pipeline = pipeline;
data.capsfilter = capsfilter; data.capsfilter = capsfilter;
data.encoder = enc; data.encoder = enc;
@ -544,6 +535,8 @@ main (gint argc, gchar ** argv)
data.prev_width = width; data.prev_width = width;
data.prev_height = height; data.prev_height = height;
loop = g_main_loop_new (NULL, FALSE);
deep_notify_id = deep_notify_id =
gst_element_add_property_deep_notify_watch (pipeline, NULL, TRUE); gst_element_add_property_deep_notify_watch (pipeline, NULL, TRUE);
@ -552,7 +545,7 @@ main (gint argc, gchar ** argv)
/* run the pipeline */ /* run the pipeline */
sret = gst_element_set_state (pipeline, GST_STATE_PLAYING); sret = gst_element_set_state (pipeline, GST_STATE_PLAYING);
if (sret == GST_STATE_CHANGE_FAILURE) { if (sret == GST_STATE_CHANGE_FAILURE) {
gst_printerrln ("Pipeline doesn't want to playing\n"); gst_printerrln ("Pipeline doesn't want to playing");
} else { } else {
set_key_handler ((KeyInputCallback) keyboard_cb, &data); set_key_handler ((KeyInputCallback) keyboard_cb, &data);
g_main_loop_run (loop); g_main_loop_run (loop);
@ -567,7 +560,6 @@ main (gint argc, gchar ** argv)
gst_object_unref (pipeline); gst_object_unref (pipeline);
g_main_loop_unref (loop); g_main_loop_unref (loop);
g_free (encoder_name);
return 0; return 0;
} }