[Cogl] [PATCH 09/13] cogl-gst: video-sink: add gl upload support

Lionel Landwerlin llandwerlin at gmail.com
Mon Dec 9 03:17:56 PST 2013


---
 cogl-gst/cogl-gst-video-sink.c | 77 +++++++++++++++++++++++++++++++++++++++---
 1 file changed, 73 insertions(+), 4 deletions(-)

diff --git a/cogl-gst/cogl-gst-video-sink.c b/cogl-gst/cogl-gst-video-sink.c
index fd6c18d..07fb475 100644
--- a/cogl-gst/cogl-gst-video-sink.c
+++ b/cogl-gst/cogl-gst-video-sink.c
@@ -73,7 +73,8 @@
   (G_PARAM_READABLE | G_PARAM_WRITABLE | COGL_GST_PARAM_STATIC)
 
 static const char cogl_gst_video_sink_caps_str[] =
-  GST_VIDEO_CAPS_MAKE_WITH_FEATURES("memory:SystemMemory", BASE_SINK_CAPS);
+  GST_VIDEO_CAPS_MAKE_WITH_FEATURES("memory:SystemMemory", BASE_SINK_CAPS)
+  ";" GST_VIDEO_CAPS_MAKE_WITH_FEATURES(GST_CAPS_FEATURE_META_GST_VIDEO_GL_TEXTURE_UPLOAD_META, "RGBA");
 
 static GstStaticPadTemplate sinktemplate_all =
   GST_STATIC_PAD_TEMPLATE ("sink",
@@ -157,6 +158,8 @@ typedef struct _CoglGstRenderer
                           CoglPipeline *pipeline);
   CoglBool (*upload) (CoglGstVideoSink *sink,
                       GstBuffer *buffer);
+  CoglBool (*upload_gl) (CoglGstVideoSink *sink,
+                         GstBuffer *buffer);
   void (*shutdown) (CoglGstVideoSink *sink);
 } CoglGstRenderer;
 
@@ -434,6 +437,12 @@ clear_frame_textures (CoglGstVideoSink *sink)
 
 /**/
 
+static CoglBool
+cogl_gst_dummy_upload_gl (CoglGstVideoSink *sink, GstBuffer *buffer)
+{
+  return FALSE;
+}
+
 static void
 cogl_gst_dummy_shutdown (CoglGstVideoSink *sink)
 {
@@ -586,6 +595,7 @@ static CoglGstRenderer rgb24_renderer =
   { COGL_PIPELINE_FILTER_LINEAR_MIPMAP_LINEAR, COGL_PIPELINE_FILTER_LINEAR, },
   cogl_gst_rgb_setup_pipeline,
   cogl_gst_rgb24_upload,
+  cogl_gst_dummy_upload_gl,
   cogl_gst_dummy_shutdown,
 };
 
@@ -626,16 +636,63 @@ map_fail:
   }
 }
 
+static CoglBool
+cogl_gst_rgb32_upload_gl (CoglGstVideoSink *sink,
+                          GstBuffer *buffer)
+{
+  CoglGstVideoSinkPrivate *priv = sink->priv;
+  GstVideoGLTextureUploadMeta *upload_meta;
+  guint gl_handle[MAX_LAYERS];
+
+  clear_frame_textures (sink);
+
+  upload_meta = gst_buffer_get_video_gl_texture_upload_meta (buffer);
+  if (!upload_meta) {
+    GST_WARNING ("Buffer does not support GLTextureUploadMeta API");
+    return FALSE;
+  }
+
+  if (upload_meta->n_textures != priv->renderer->n_layers ||
+      upload_meta->texture_type[0] != GST_VIDEO_GL_TEXTURE_TYPE_RGBA) {
+    GST_WARNING ("cogl-gst-video-sink only supports gl upload in a single RGBA texture");
+    return FALSE;
+  }
+
+  priv->frame[0] = COGL_TEXTURE (cogl_texture_2d_new_with_size (priv->ctx,
+                                                                priv->info.width,
+                                                                priv->info.height,
+                                                                COGL_PIXEL_FORMAT_RGBA_8888));
+
+  if (!cogl_texture_allocate (priv->frame[0], NULL)) {
+    GST_WARNING ("Couldn't allocate cogl texture");
+    return FALSE;
+  }
+
+  if (!cogl_texture_get_gl_texture (priv->frame[0], &gl_handle[0], NULL)) {
+    GST_WARNING ("Couldn't get gl texture");
+    return FALSE;
+  }
+
+  if (!gst_video_gl_texture_upload_meta_upload (upload_meta, gl_handle)) {
+    GST_WARNING ("GL texture upload failed");
+    return FALSE;
+  }
+
+  return TRUE;
+}
+
 static CoglGstRenderer rgb32_renderer =
 {
   "RGB 32",
   COGL_GST_RGB32,
   0,
-  GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE_WITH_FEATURES("memory:SystemMemory", "{ RGBA, BGRA }")),
+  GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE_WITH_FEATURES("memory:SystemMemory", "{ RGBA, BGRA }")
+                   ";" GST_VIDEO_CAPS_MAKE_WITH_FEATURES(GST_CAPS_FEATURE_META_GST_VIDEO_GL_TEXTURE_UPLOAD_META, "RGBA")),
   1, /* n_layers */
   { COGL_PIPELINE_FILTER_LINEAR_MIPMAP_LINEAR, COGL_PIPELINE_FILTER_LINEAR, },
   cogl_gst_rgb_setup_pipeline,
   cogl_gst_rgb32_upload,
+  cogl_gst_rgb32_upload_gl,
   cogl_gst_dummy_shutdown,
 };
 
@@ -796,6 +853,7 @@ static CoglGstRenderer yv12_glsl_renderer =
   },
   cogl_gst_yv12_glsl_setup_pipeline,
   cogl_gst_yv12_upload,
+  cogl_gst_dummy_upload_gl,
   cogl_gst_dummy_shutdown,
 };
 
@@ -813,6 +871,7 @@ static CoglGstRenderer i420_glsl_renderer =
   },
   cogl_gst_yv12_glsl_setup_pipeline,
   cogl_gst_i420_upload,
+  cogl_gst_dummy_upload_gl,
   cogl_gst_dummy_shutdown,
 };
 
@@ -899,6 +958,7 @@ static CoglGstRenderer ayuv_glsl_renderer =
   },
   cogl_gst_ayuv_glsl_setup_pipeline,
   cogl_gst_ayuv_upload,
+  cogl_gst_dummy_upload_gl,
   cogl_gst_dummy_shutdown,
 };
 
@@ -1004,6 +1064,7 @@ static CoglGstRenderer nv12_glsl_renderer =
   },
   cogl_gst_nv12_glsl_setup_pipeline,
   cogl_gst_nv12_upload,
+  cogl_gst_dummy_upload_gl,
   cogl_gst_dummy_shutdown,
 };
 
@@ -1279,8 +1340,14 @@ cogl_gst_source_dispatch (GSource *source,
 
   if (buffer)
     {
-      if (!priv->renderer->upload (gst_source->sink, buffer))
-        goto fail_upload;
+      if (gst_buffer_get_video_gl_texture_upload_meta (buffer) != NULL) {
+        if (!priv->renderer->upload_gl (gst_source->sink, buffer)) {
+          goto fail_upload;
+        }
+      } else {
+        if (!priv->renderer->upload (gst_source->sink, buffer))
+          goto fail_upload;
+      }
 
       gst_buffer_unref (buffer);
     }
@@ -1505,6 +1572,8 @@ cogl_gst_video_sink_propose_allocation (GstBaseSink *base_sink, GstQuery *query)
 
   gst_query_add_allocation_meta (query,
                                  GST_VIDEO_META_API_TYPE, NULL);
+  gst_query_add_allocation_meta (query,
+                                 GST_VIDEO_GL_TEXTURE_UPLOAD_META_API_TYPE, NULL);
 
   return TRUE;
 }
-- 
1.8.5



More information about the Cogl mailing list