From ea35adc55f68ba3a48c2e3fc0d75dcb9cb3fd8d4 Mon Sep 17 00:00:00 2001 From: He Junyan Date: Fri, 13 Oct 2023 21:34:19 +0800 Subject: [PATCH] gl: upload: Implement the fixate_caps virtual function We now prefer the 2D target than other targets when fixating src caps. Part-of: --- girs/GstGL-1.0.gir | 26 +++++++ .../ext/gl/gstgluploadelement.c | 13 +++- .../gst-libs/gst/gl/gstglupload.c | 71 +++++++++++++++++++ .../gst-libs/gst/gl/gstglupload.h | 6 ++ 4 files changed, 115 insertions(+), 1 deletion(-) diff --git a/girs/GstGL-1.0.gir b/girs/GstGL-1.0.gir index 1ff5ac638a..2626db4479 100644 --- a/girs/GstGL-1.0.gir +++ b/girs/GstGL-1.0.gir @@ -7385,6 +7385,32 @@ A #GstGLUpload can be created with gst_gl_upload_new() + + Fixate the @othercaps based on the information of the @caps. + + + the fixated caps + + + + + a #GstGLUpload + + + + the pad #GstPadDirection + + + + a #GstCaps as the reference + + + + a #GstCaps to fixate + + + + diff --git a/subprojects/gst-plugins-base/ext/gl/gstgluploadelement.c b/subprojects/gst-plugins-base/ext/gl/gstgluploadelement.c index 2a28ed724f..215ee31848 100644 --- a/subprojects/gst-plugins-base/ext/gl/gstgluploadelement.c +++ b/subprojects/gst-plugins-base/ext/gl/gstgluploadelement.c @@ -58,11 +58,12 @@ gst_gl_upload_element_prepare_output_buffer (GstBaseTransform * bt, static GstFlowReturn gst_gl_upload_element_transform (GstBaseTransform * bt, GstBuffer * buffer, GstBuffer * outbuf); static gboolean gst_gl_upload_element_stop (GstBaseTransform * bt); +static GstCaps *gst_gl_upload_element_fixate_caps (GstBaseTransform * bt, + GstPadDirection direction, GstCaps * caps, GstCaps * othercaps); static GstStateChangeReturn gst_gl_upload_element_change_state (GstElement * element, GstStateChange transition); - static GstStaticPadTemplate gst_gl_upload_element_src_pad_template = GST_STATIC_PAD_TEMPLATE ("src", GST_PAD_SRC, @@ -110,6 +111,7 @@ gst_gl_upload_element_class_init (GstGLUploadElementClass * klass) bt_class->prepare_output_buffer = gst_gl_upload_element_prepare_output_buffer; bt_class->transform = gst_gl_upload_element_transform; bt_class->stop = gst_gl_upload_element_stop; + bt_class->fixate_caps = gst_gl_upload_element_fixate_caps; element_class->change_state = gst_gl_upload_element_change_state; @@ -331,6 +333,15 @@ gst_gl_upload_element_transform (GstBaseTransform * bt, GstBuffer * buffer, return GST_FLOW_OK; } +static GstCaps * +gst_gl_upload_element_fixate_caps (GstBaseTransform * bt, + GstPadDirection direction, GstCaps * caps, GstCaps * othercaps) +{ + GstGLUploadElement *upload = GST_GL_UPLOAD_ELEMENT (bt); + + return gst_gl_upload_fixate_caps (upload->upload, direction, caps, othercaps); +} + static GstStateChangeReturn gst_gl_upload_element_change_state (GstElement * element, GstStateChange transition) diff --git a/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.c b/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.c index db1f891594..225d1176e7 100644 --- a/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.c +++ b/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.c @@ -3526,3 +3526,74 @@ restart: #undef NEXT_METHOD } + +/** + * gst_gl_upload_fixate_caps: + * @upload: a #GstGLUpload + * @direction: the pad #GstPadDirection + * @caps: a #GstCaps as the reference + * @othercaps: (transfer full): a #GstCaps to fixate + * + * Fixate the @othercaps based on the information of the @caps. + * + * Returns: (transfer full): the fixated caps + * + * Since: 1.24 + */ +GstCaps * +gst_gl_upload_fixate_caps (GstGLUpload * upload, GstPadDirection direction, + GstCaps * caps, GstCaps * othercaps) +{ + guint n, i; + GstGLTextureTarget target; + GstCaps *ret_caps = NULL; + + GST_DEBUG_OBJECT (upload, "Fixate caps %" GST_PTR_FORMAT ", using caps %" + GST_PTR_FORMAT ", direction is %s.", othercaps, caps, + direction == GST_PAD_SRC ? "src" : "sink"); + + if (direction == GST_PAD_SRC) { + ret_caps = gst_caps_fixate (othercaps); + goto out; + } + + if (gst_caps_is_fixed (othercaps)) { + ret_caps = othercaps; + goto out; + } + + /* Prefer target 2D->rectangle->oes */ + for (target = GST_GL_TEXTURE_TARGET_2D; + target <= GST_GL_TEXTURE_TARGET_EXTERNAL_OES; target++) { + n = gst_caps_get_size (othercaps); + for (i = 0; i < n; i++) { + GstStructure *s; + + s = gst_caps_get_structure (othercaps, i); + if (_structure_check_target (s, 1 << target)) + break; + } + + /* If the target is found, fixate the other fields */ + if (i < n) { + ret_caps = gst_caps_new_empty (); + gst_caps_append_structure_full (ret_caps, + gst_structure_copy (gst_caps_get_structure (othercaps, i)), + gst_caps_features_copy (gst_caps_get_features (othercaps, i))); + + ret_caps = gst_caps_fixate (ret_caps); + gst_caps_set_simple (ret_caps, "texture-target", G_TYPE_STRING, + gst_gl_texture_target_to_string (target), NULL); + + gst_caps_unref (othercaps); + + goto out; + } + } + + ret_caps = gst_caps_fixate (othercaps); + +out: + GST_DEBUG_OBJECT (upload, "Fixate return %" GST_PTR_FORMAT, ret_caps); + return ret_caps; +} diff --git a/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.h b/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.h index 5911584222..20040c174d 100644 --- a/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.h +++ b/subprojects/gst-plugins-base/gst-libs/gst/gl/gstglupload.h @@ -119,6 +119,12 @@ GstGLUploadReturn gst_gl_upload_perform_with_buffer (GstGLUpload * upload, GstBuffer * buffer, GstBuffer ** outbuf_ptr); +GST_GL_API +GstCaps * gst_gl_upload_fixate_caps (GstGLUpload * upload, + GstPadDirection direction, + GstCaps * caps, + GstCaps * othercaps); + G_END_DECLS #endif /* __GST_GL_UPLOAD_H__ */