mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-09-09 05:38:58 +00:00
[081/906] start to add a glfilter
git-svn-id: svn://svn.wobow.com/GStreamer_playground/gst-plugins-gl@493 93df14bb-0f41-7a43-8087-d3e2a2f0e464
This commit is contained in:
parent
05f98c7346
commit
31be382a90
10 changed files with 795 additions and 59 deletions
|
@ -95,7 +95,7 @@ gst_gl_buffer_new_from_video_format (GstGLDisplay* display,
|
|||
{
|
||||
GstGLBuffer *buffer;
|
||||
|
||||
g_return_val_if_fail (video_format != GST_VIDEO_FORMAT_UNKNOWN, NULL);
|
||||
//g_return_val_if_fail (video_format != GST_VIDEO_FORMAT_UNKNOWN, NULL);
|
||||
g_return_val_if_fail (display != NULL, NULL);
|
||||
g_return_val_if_fail (width > 0, NULL);
|
||||
g_return_val_if_fail (height > 0, NULL);
|
||||
|
@ -109,9 +109,10 @@ gst_gl_buffer_new_from_video_format (GstGLDisplay* display,
|
|||
GST_BUFFER_SIZE (buffer) = gst_gl_buffer_format_get_size (video_format, context_width, context_height);
|
||||
|
||||
//blocking call, init texture
|
||||
gst_gl_display_textureRequested (buffer->display, buffer->video_format,
|
||||
buffer->width, buffer->height,
|
||||
&buffer->texture, &buffer->texture_u, &buffer->texture_v) ;
|
||||
if (video_format != GST_VIDEO_FORMAT_UNKNOWN)
|
||||
gst_gl_display_textureRequested (buffer->display, buffer->video_format,
|
||||
buffer->width, buffer->height,
|
||||
&buffer->texture, &buffer->texture_u, &buffer->texture_v) ;
|
||||
|
||||
return buffer;
|
||||
}
|
||||
|
|
|
@ -28,6 +28,7 @@
|
|||
static void gst_gl_display_finalize (GObject * object);
|
||||
static gpointer gst_gl_display_glutThreadFunc (GstGLDisplay* display);
|
||||
static void gst_gl_display_glutCreateWindow (GstGLDisplay* display);
|
||||
static void gst_gl_display_glutGenerateFBO (GstGLDisplay *display);
|
||||
static void gst_gl_display_glutDestroyWindow (GstGLDisplay* display);
|
||||
static void gst_gl_display_glutSetVisibleWindow (GstGLDisplay* display);
|
||||
static void gst_gl_display_glutPrepareTexture (GstGLDisplay* display);
|
||||
|
@ -93,6 +94,7 @@ gst_gl_display_init (GstGLDisplay *display, GstGLDisplayClass *klass)
|
|||
display->cond_fill = g_cond_new ();
|
||||
display->cond_clear = g_cond_new ();
|
||||
display->cond_video = g_cond_new ();
|
||||
display->cond_generateFBO = g_cond_new ();
|
||||
display->cond_create = g_cond_new ();
|
||||
display->cond_destroy = g_cond_new ();
|
||||
|
||||
|
@ -106,6 +108,12 @@ gst_gl_display_init (GstGLDisplay *display, GstGLDisplayClass *klass)
|
|||
display->graphicDepthBuffer = 0;
|
||||
display->graphicTexture = 0;
|
||||
|
||||
display->requestedFBO = 0;
|
||||
display->requestedDepthBuffer = 0;
|
||||
display->requestedTextureFBO = 0;
|
||||
display->requestedTextureFBOWidth = 0;
|
||||
display->requestedTextureFBOHeight = 0;
|
||||
|
||||
display->requestedTexture = 0;
|
||||
display->requestedTexture_u = 0;
|
||||
display->requestedTexture_v = 0;
|
||||
|
@ -326,6 +334,10 @@ gst_gl_display_finalize (GObject *object)
|
|||
g_cond_free (display->cond_video);
|
||||
display->cond_video = NULL;
|
||||
}
|
||||
if (display->cond_generateFBO) {
|
||||
g_cond_free (display->cond_generateFBO);
|
||||
display->cond_generateFBO = NULL;
|
||||
}
|
||||
if (display->cond_create) {
|
||||
g_cond_free (display->cond_create);
|
||||
display->cond_create = NULL;
|
||||
|
@ -343,7 +355,7 @@ gst_gl_display_finalize (GObject *object)
|
|||
if (g_hash_table_size (gst_gl_display_map) == 0)
|
||||
{
|
||||
g_thread_join (gst_gl_display_glutThread);
|
||||
GST_DEBUG ("Glut thread joined");
|
||||
g_print ("Glut thread joined\n");
|
||||
gst_gl_display_glutThread = NULL;
|
||||
g_async_queue_unref (gst_gl_display_messageQueue);
|
||||
g_hash_table_unref (gst_gl_display_map);
|
||||
|
@ -370,9 +382,9 @@ gst_gl_display_glutThreadFunc (GstGLDisplay *display)
|
|||
gst_gl_display_glutCreateWindow (display);
|
||||
gst_gl_display_unlock (display);
|
||||
|
||||
GST_DEBUG ("Glut mainLoop start");
|
||||
g_print ("Glut mainLoop start\n");
|
||||
glutMainLoop ();
|
||||
GST_DEBUG ("Glut mainLoop exited");
|
||||
g_print ("Glut mainLoop exited\n");
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
@ -397,7 +409,7 @@ gst_gl_display_glutCreateWindow (GstGLDisplay *display)
|
|||
display->title = g_string_append (display->title, buffer);
|
||||
glutWinId = glutCreateWindow (display->title->str, display->winId);
|
||||
|
||||
GST_DEBUG ("Context %d created\n", glutWinId);
|
||||
g_print ("Context %d created\n", glutWinId);
|
||||
|
||||
if (display->visible)
|
||||
glutShowWindow ();
|
||||
|
@ -646,6 +658,53 @@ gst_gl_display_glutCreateWindow (GstGLDisplay *display)
|
|||
}
|
||||
|
||||
|
||||
/* Called by the idle funtion */
|
||||
static void
|
||||
gst_gl_display_glutGenerateFBO (GstGLDisplay *display)
|
||||
{
|
||||
|
||||
glutSetWindow (display->glutWinId);
|
||||
|
||||
//-- generate frame buffer object
|
||||
|
||||
//setup FBO
|
||||
glGenFramebuffersEXT (1, &display->requestedFBO);
|
||||
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->requestedFBO);
|
||||
|
||||
//setup the render buffer for depth
|
||||
glGenRenderbuffersEXT(1, &display->requestedDepthBuffer);
|
||||
glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, display->requestedDepthBuffer);
|
||||
glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT,
|
||||
display->requestedTextureFBOWidth, display->requestedTextureFBOHeight);
|
||||
|
||||
//setup a texture to render to
|
||||
glGenTextures (1, &display->requestedTextureFBO);
|
||||
glBindTexture(GL_TEXTURE_RECTANGLE_ARB, display->requestedTextureFBO);
|
||||
glTexImage2D(GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA8,
|
||||
display->requestedTextureFBOWidth, display->requestedTextureFBOHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
|
||||
//attach the texture to the FBO to renderer to
|
||||
glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
|
||||
GL_TEXTURE_RECTANGLE_ARB, display->requestedTextureFBO, 0);
|
||||
|
||||
//attach the depth render buffer to the FBO
|
||||
glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT,
|
||||
GL_RENDERBUFFER_EXT, display->requestedDepthBuffer);
|
||||
|
||||
g_assert (glCheckFramebufferStatusEXT (GL_FRAMEBUFFER_EXT) ==
|
||||
GL_FRAMEBUFFER_COMPLETE_EXT);
|
||||
|
||||
//unbind the FBO
|
||||
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
|
||||
|
||||
g_cond_signal (display->cond_video);
|
||||
}
|
||||
|
||||
|
||||
/* Called by the idle function */
|
||||
static void
|
||||
gst_gl_display_glutDestroyWindow (GstGLDisplay *display)
|
||||
|
@ -695,7 +754,7 @@ gst_gl_display_glutDestroyWindow (GstGLDisplay *display)
|
|||
}
|
||||
|
||||
g_hash_table_remove (gst_gl_display_map, GINT_TO_POINTER (display->glutWinId));
|
||||
GST_DEBUG ("glut window destroyed: %d", display->glutWinId);
|
||||
g_print ("glut window destroyed: %d\n", display->glutWinId);
|
||||
|
||||
//if the map is empty, leaveMainloop and join the thread
|
||||
if (g_hash_table_size (gst_gl_display_map) == 0)
|
||||
|
@ -806,7 +865,7 @@ gst_gl_display_glut_idle (void)
|
|||
gst_gl_display_glutDispatchAction (msg);
|
||||
}
|
||||
}
|
||||
else GST_DEBUG ("timeout reached in idle func");
|
||||
else g_print ("timeout reached in idle func\n");
|
||||
}
|
||||
|
||||
|
||||
|
@ -841,6 +900,9 @@ gst_gl_display_glutDispatchAction (GstGLDisplayMsg* msg)
|
|||
case GST_GL_DISPLAY_ACTION_REDISPLAY:
|
||||
gst_gl_display_glutPostRedisplay (msg->display);
|
||||
break;
|
||||
case GST_GL_DISPLAY_ACTION_GENFBO:
|
||||
gst_gl_display_glutGenerateFBO (msg->display);
|
||||
break;
|
||||
default:
|
||||
g_assert_not_reached ();
|
||||
}
|
||||
|
@ -867,6 +929,7 @@ gst_gl_display_checkMsgValidity (GstGLDisplayMsg *msg)
|
|||
case GST_GL_DISPLAY_ACTION_CLEAR:
|
||||
case GST_GL_DISPLAY_ACTION_VIDEO:
|
||||
case GST_GL_DISPLAY_ACTION_REDISPLAY:
|
||||
case GST_GL_DISPLAY_ACTION_GENFBO:
|
||||
//msg is out of date if the associated display is not in the map
|
||||
if (!g_hash_table_lookup (gst_gl_display_map, GINT_TO_POINTER (msg->glutWinId)))
|
||||
valid = FALSE;
|
||||
|
@ -1010,7 +1073,7 @@ gst_gl_display_textureRequested (GstGLDisplay * display, GstVideoFormat video_fo
|
|||
|
||||
/* Called by gst_gl elements */
|
||||
void
|
||||
gst_gl_display_textureChanged (GstGLDisplay * display, GstVideoFormat video_format,
|
||||
gst_gl_display_textureChanged (GstGLDisplay* display, GstVideoFormat video_format,
|
||||
GLuint texture, GLuint texture_u, GLuint texture_v,
|
||||
gint width, gint height, gpointer data)
|
||||
{
|
||||
|
@ -1030,7 +1093,7 @@ gst_gl_display_textureChanged (GstGLDisplay * display, GstVideoFormat video_form
|
|||
|
||||
/* Called by gstglbuffer */
|
||||
void
|
||||
gst_gl_display_clearTexture (GstGLDisplay * display, guint texture,
|
||||
gst_gl_display_clearTexture (GstGLDisplay* display, guint texture,
|
||||
guint texture_u, guint texture_v)
|
||||
{
|
||||
gst_gl_display_lock (display);
|
||||
|
@ -1074,6 +1137,23 @@ gst_gl_display_postRedisplay (GstGLDisplay* display)
|
|||
}
|
||||
|
||||
|
||||
/* Called by gst_gl elements */
|
||||
void
|
||||
gst_gl_display_requestFBO (GstGLDisplay* display, gint width, gint height,
|
||||
guint* fbo, guint* depthbuffer, guint* texture)
|
||||
{
|
||||
gst_gl_display_lock (display);
|
||||
display->requestedTextureFBOWidth = width;
|
||||
display->requestedTextureFBOHeight = height;
|
||||
gst_gl_display_postMessage (GST_GL_DISPLAY_ACTION_GENFBO, display);
|
||||
g_cond_wait (display->cond_generateFBO, display->mutex);
|
||||
*fbo = display->requestedFBO;
|
||||
*depthbuffer = display->requestedDepthBuffer;
|
||||
*texture = display->requestedTextureFBO;
|
||||
gst_gl_display_unlock (display);
|
||||
}
|
||||
|
||||
|
||||
/* Called by gst_gl elements */
|
||||
void
|
||||
gst_gl_display_set_windowId (GstGLDisplay* display, gulong winId)
|
||||
|
@ -1088,7 +1168,7 @@ gst_gl_display_set_windowId (GstGLDisplay* display, gulong winId)
|
|||
if (g_hash_table_size (gst_gl_display_map) == 0)
|
||||
{
|
||||
g_thread_join (gst_gl_display_glutThread);
|
||||
GST_DEBUG ("Glut thread joined when setting winId");
|
||||
g_print ("Glut thread joined when setting winId\n");
|
||||
gst_gl_display_glutThread = NULL;
|
||||
g_async_queue_unref (gst_gl_display_messageQueue);
|
||||
g_hash_table_unref (gst_gl_display_map);
|
||||
|
|
|
@ -50,7 +50,8 @@ typedef enum {
|
|||
GST_GL_DISPLAY_ACTION_CHANGE,
|
||||
GST_GL_DISPLAY_ACTION_CLEAR,
|
||||
GST_GL_DISPLAY_ACTION_VIDEO,
|
||||
GST_GL_DISPLAY_ACTION_REDISPLAY
|
||||
GST_GL_DISPLAY_ACTION_REDISPLAY,
|
||||
GST_GL_DISPLAY_ACTION_GENFBO
|
||||
|
||||
} GstGLDisplayAction;
|
||||
|
||||
|
@ -78,20 +79,21 @@ typedef gboolean (* CDCB) ( GLuint, GLuint, GLuint);
|
|||
struct _GstGLDisplay {
|
||||
GObject object;
|
||||
|
||||
GMutex *mutex;
|
||||
GMutex* mutex;
|
||||
|
||||
GQueue* texturePool;
|
||||
|
||||
GCond *cond_make;
|
||||
GCond *cond_fill;
|
||||
GCond *cond_clear;
|
||||
GCond *cond_video;
|
||||
GCond* cond_make;
|
||||
GCond* cond_fill;
|
||||
GCond* cond_clear;
|
||||
GCond* cond_video;
|
||||
GCond* cond_generateFBO;
|
||||
|
||||
GCond *cond_create;
|
||||
GCond *cond_destroy;
|
||||
GCond* cond_create;
|
||||
GCond* cond_destroy;
|
||||
gint glutWinId;
|
||||
gulong winId;
|
||||
GString *title;
|
||||
GString* title;
|
||||
gint win_xpos;
|
||||
gint win_ypos;
|
||||
gint glcontext_width;
|
||||
|
@ -111,6 +113,13 @@ struct _GstGLDisplay {
|
|||
GLuint graphicDepthBuffer;
|
||||
GLuint graphicTexture;
|
||||
|
||||
//filter frame buffer object (GL -> GL)
|
||||
GLuint requestedFBO;
|
||||
GLuint requestedDepthBuffer;
|
||||
GLuint requestedTextureFBO;
|
||||
GLuint requestedTextureFBOWidth;
|
||||
GLuint requestedTextureFBOHeight;
|
||||
|
||||
GLuint requestedTexture;
|
||||
GLuint requestedTexture_u;
|
||||
GLuint requestedTexture_v;
|
||||
|
@ -211,6 +220,8 @@ void gst_gl_display_clearTexture (GstGLDisplay* display, guint texture,
|
|||
void gst_gl_display_videoChanged (GstGLDisplay* display, GstVideoFormat video_format,
|
||||
gpointer data);
|
||||
gboolean gst_gl_display_postRedisplay (GstGLDisplay* display);
|
||||
void gst_gl_display_requestFBO (GstGLDisplay* display, gint width, gint height,
|
||||
guint* fbo, guint* depthbuffer, guint* texture);
|
||||
void gst_gl_display_set_windowId (GstGLDisplay* display, gulong winId);
|
||||
|
||||
#endif
|
||||
|
|
329
gst/gl/gstglfilter.c
Normal file
329
gst/gl/gstglfilter.c
Normal file
|
@ -0,0 +1,329 @@
|
|||
/*
|
||||
* GStreamer
|
||||
* Copyright (C) 2008 Julien Isorce <julien.isorce@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include "gstglfilter.h"
|
||||
|
||||
#define GST_CAT_DEFAULT gst_gl_filter_debug
|
||||
GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT);
|
||||
|
||||
|
||||
static GstStaticPadTemplate gst_gl_filter_src_pad_template =
|
||||
GST_STATIC_PAD_TEMPLATE ("src",
|
||||
GST_PAD_SRC,
|
||||
GST_PAD_ALWAYS,
|
||||
GST_STATIC_CAPS (GST_GL_VIDEO_CAPS)
|
||||
);
|
||||
|
||||
static GstStaticPadTemplate gst_gl_filter_sink_pad_template =
|
||||
GST_STATIC_PAD_TEMPLATE ("sink",
|
||||
GST_PAD_SINK,
|
||||
GST_PAD_ALWAYS,
|
||||
GST_STATIC_CAPS (GST_GL_VIDEO_CAPS)
|
||||
);
|
||||
|
||||
#define DEBUG_INIT(bla) \
|
||||
GST_DEBUG_CATEGORY_INIT (gst_gl_filter_debug, "glfilter", 0, "glfilter element");
|
||||
|
||||
GST_BOILERPLATE_FULL (GstGLFilter, gst_gl_filter, GstBaseTransform,
|
||||
GST_TYPE_BASE_TRANSFORM, DEBUG_INIT);
|
||||
|
||||
static void gst_gl_filter_set_property (GObject * object, guint prop_id,
|
||||
const GValue * value, GParamSpec * pspec);
|
||||
static void gst_gl_filter_get_property (GObject * object, guint prop_id,
|
||||
GValue * value, GParamSpec * pspec);
|
||||
|
||||
static void gst_gl_filter_reset (GstGLFilter * filter);
|
||||
static gboolean gst_gl_filter_start (GstBaseTransform * bt);
|
||||
static gboolean gst_gl_filter_stop (GstBaseTransform * bt);
|
||||
static gboolean gst_gl_filter_get_unit_size (GstBaseTransform * trans,
|
||||
GstCaps * caps, guint * size);
|
||||
static GstFlowReturn gst_gl_filter_transform (GstBaseTransform * bt,
|
||||
GstBuffer * inbuf, GstBuffer * outbuf);
|
||||
static GstFlowReturn gst_gl_filter_prepare_output_buffer (GstBaseTransform *
|
||||
trans, GstBuffer * input, gint size, GstCaps * caps, GstBuffer ** buf);
|
||||
static gboolean gst_gl_filter_set_caps (GstBaseTransform * bt, GstCaps * incaps,
|
||||
GstCaps * outcaps);
|
||||
static gboolean gst_gl_filter_do_transform (GstGLFilter * filter,
|
||||
GstGLBuffer * inbuf, GstGLBuffer * outbuf);
|
||||
|
||||
|
||||
static void
|
||||
gst_gl_filter_base_init (gpointer klass)
|
||||
{
|
||||
GstElementClass *element_class = GST_ELEMENT_CLASS (klass);
|
||||
|
||||
gst_element_class_add_pad_template (element_class,
|
||||
gst_static_pad_template_get (&gst_gl_filter_src_pad_template));
|
||||
gst_element_class_add_pad_template (element_class,
|
||||
gst_static_pad_template_get (&gst_gl_filter_sink_pad_template));
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_class_init (GstGLFilterClass * klass)
|
||||
{
|
||||
GObjectClass *gobject_class;
|
||||
|
||||
gobject_class = (GObjectClass *) klass;
|
||||
gobject_class->set_property = gst_gl_filter_set_property;
|
||||
gobject_class->get_property = gst_gl_filter_get_property;
|
||||
|
||||
GST_BASE_TRANSFORM_CLASS (klass)->transform = gst_gl_filter_transform;
|
||||
GST_BASE_TRANSFORM_CLASS (klass)->start = gst_gl_filter_start;
|
||||
GST_BASE_TRANSFORM_CLASS (klass)->stop = gst_gl_filter_stop;
|
||||
GST_BASE_TRANSFORM_CLASS (klass)->set_caps = gst_gl_filter_set_caps;
|
||||
GST_BASE_TRANSFORM_CLASS (klass)->get_unit_size = gst_gl_filter_get_unit_size;
|
||||
GST_BASE_TRANSFORM_CLASS (klass)->prepare_output_buffer =
|
||||
gst_gl_filter_prepare_output_buffer;
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_init (GstGLFilter * filter, GstGLFilterClass * klass)
|
||||
{
|
||||
//gst_element_create_all_pads (GST_ELEMENT (filter));
|
||||
|
||||
filter->sinkpad = gst_element_get_static_pad (GST_ELEMENT (filter), "sink");
|
||||
filter->srcpad = gst_element_get_static_pad (GST_ELEMENT (filter), "src");
|
||||
|
||||
/*gst_gl_display_requestFBO
|
||||
|
||||
filter->fbo = */
|
||||
|
||||
gst_gl_filter_reset (filter);
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_set_property (GObject * object, guint prop_id,
|
||||
const GValue * value, GParamSpec * pspec)
|
||||
{
|
||||
//GstGLFilter *filter = GST_GL_FILTER (object);
|
||||
|
||||
switch (prop_id) {
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_get_property (GObject * object, guint prop_id,
|
||||
GValue * value, GParamSpec * pspec)
|
||||
{
|
||||
//GstGLFilter *filter = GST_GL_FILTER (object);
|
||||
|
||||
switch (prop_id) {
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_reset (GstGLFilter* filter)
|
||||
{
|
||||
if (filter->display)
|
||||
{
|
||||
g_object_unref (filter->display);
|
||||
filter->display = NULL;
|
||||
}
|
||||
filter->video_format = GST_VIDEO_FORMAT_UNKNOWN;
|
||||
filter->width = 0;
|
||||
filter->height = 0;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_gl_filter_start (GstBaseTransform* bt)
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_gl_filter_stop (GstBaseTransform* bt)
|
||||
{
|
||||
GstGLFilter *filter = GST_GL_FILTER (bt);
|
||||
|
||||
gst_gl_filter_reset (filter);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_gl_filter_get_unit_size (GstBaseTransform* trans, GstCaps* caps,
|
||||
guint* size)
|
||||
{
|
||||
gboolean ret;
|
||||
GstVideoFormat video_format;
|
||||
gint width;
|
||||
gint height;
|
||||
|
||||
ret = gst_gl_buffer_format_parse_caps (caps, &video_format, &width, &height);
|
||||
if (ret)
|
||||
*size = gst_gl_buffer_format_get_size (video_format, width, height);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static GstFlowReturn
|
||||
gst_gl_filter_prepare_output_buffer (GstBaseTransform* trans,
|
||||
GstBuffer* inbuf, gint size, GstCaps* caps, GstBuffer** buf)
|
||||
{
|
||||
GstGLFilter* filter;
|
||||
GstGLBuffer* gl_inbuf = GST_GL_BUFFER (inbuf);
|
||||
GstGLBuffer* gl_outbuf;
|
||||
|
||||
filter = GST_GL_FILTER (trans);
|
||||
|
||||
if (filter->display == NULL)
|
||||
filter->display = g_object_ref (gl_inbuf->display);
|
||||
|
||||
gl_outbuf = gst_gl_buffer_new_from_video_format (filter->display,
|
||||
filter->video_format,
|
||||
filter->width, filter->height,
|
||||
filter->width, filter->height);
|
||||
|
||||
*buf = GST_BUFFER (gl_outbuf);
|
||||
gst_buffer_set_caps (*buf, caps);
|
||||
|
||||
g_print ("gstglfilter: gst_gl_filter_prepare_output_buffer\n");
|
||||
|
||||
return GST_FLOW_OK;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_gl_filter_set_caps (GstBaseTransform * bt, GstCaps * incaps,
|
||||
GstCaps * outcaps)
|
||||
{
|
||||
GstGLFilter *filter;
|
||||
gboolean ret;
|
||||
|
||||
filter = GST_GL_FILTER (bt);
|
||||
|
||||
ret = gst_gl_buffer_format_parse_caps (incaps, &filter->video_format,
|
||||
&filter->width, &filter->height);
|
||||
|
||||
if (!ret)
|
||||
{
|
||||
GST_DEBUG ("bad caps");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
GST_ERROR ("set_caps %d %d", filter->width, filter->height);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static GstFlowReturn
|
||||
gst_gl_filter_transform (GstBaseTransform * bt, GstBuffer * inbuf,
|
||||
GstBuffer * outbuf)
|
||||
{
|
||||
GstGLFilter* filter;
|
||||
GstGLBuffer* gl_inbuf = GST_GL_BUFFER (inbuf);
|
||||
GstGLBuffer* gl_outbuf = GST_GL_BUFFER (outbuf);
|
||||
|
||||
filter = GST_GL_FILTER (bt);
|
||||
|
||||
g_print ("gstglfilter: gst_gl_filter_transform\n");
|
||||
|
||||
gst_gl_filter_do_transform (filter, gl_inbuf, gl_outbuf);
|
||||
|
||||
return GST_FLOW_OK;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_gl_filter_do_transform (GstGLFilter * filter,
|
||||
GstGLBuffer * inbuf, GstGLBuffer * outbuf)
|
||||
{
|
||||
GstGLDisplay* display = inbuf->display;
|
||||
GstGLFilterClass* filter_class = GST_GL_FILTER_GET_CLASS (filter);
|
||||
|
||||
outbuf->texture = inbuf->texture;
|
||||
|
||||
/*unsigned int fbo;
|
||||
|
||||
gst_gl_display_lock (display);
|
||||
|
||||
glGenFramebuffersEXT (1, &fbo);
|
||||
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, fbo);
|
||||
|
||||
glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT,
|
||||
GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_RECTANGLE_ARB, outbuf->texture, 0);
|
||||
|
||||
glDrawBuffer (GL_COLOR_ATTACHMENT0_EXT);
|
||||
glReadBuffer (GL_COLOR_ATTACHMENT0_EXT);
|
||||
|
||||
g_assert (glCheckFramebufferStatusEXT (GL_FRAMEBUFFER_EXT) ==
|
||||
GL_FRAMEBUFFER_COMPLETE_EXT);
|
||||
|
||||
glViewport (0, 0, outbuf->width, outbuf->height);
|
||||
|
||||
glClearColor (0.3, 0.3, 0.3, 1.0);
|
||||
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
|
||||
glMatrixMode (GL_PROJECTION);
|
||||
glLoadIdentity ();
|
||||
|
||||
glMatrixMode (GL_MODELVIEW);
|
||||
glLoadIdentity ();
|
||||
|
||||
glDisable (GL_CULL_FACE);
|
||||
glEnableClientState (GL_TEXTURE_COORD_ARRAY);
|
||||
|
||||
glColor4f (1, 1, 1, 1);
|
||||
|
||||
glEnable (GL_TEXTURE_RECTANGLE_ARB);
|
||||
glActiveTexture (GL_TEXTURE0);
|
||||
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, inbuf->texture);*/
|
||||
|
||||
filter_class->filter (filter, inbuf, outbuf);
|
||||
/*
|
||||
#if 0
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S, GL_CLAMP);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T, GL_CLAMP);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
|
||||
|
||||
glColor4f (1, 0, 1, 1);
|
||||
glBegin (GL_QUADS);
|
||||
|
||||
glNormal3f (0, 0, -1);
|
||||
|
||||
glTexCoord2f (inbuf->width, 0);
|
||||
glVertex3f (0.9, -0.9, 0);
|
||||
glTexCoord2f (0, 0);
|
||||
glVertex3f (-1.0, -1.0, 0);
|
||||
glTexCoord2f (0, inbuf->height);
|
||||
glVertex3f (-1.0, 1.0, 0);
|
||||
glTexCoord2f (inbuf->width, inbuf->height);
|
||||
glVertex3f (1.0, 1.0, 0);
|
||||
glEnd ();
|
||||
#endif
|
||||
|
||||
glFlush ();
|
||||
|
||||
glDeleteFramebuffersEXT (1, &fbo);
|
||||
|
||||
gst_gl_display_unlock (display);*/
|
||||
|
||||
return TRUE;
|
||||
}
|
64
gst/gl/gstglfilter.h
Normal file
64
gst/gl/gstglfilter.h
Normal file
|
@ -0,0 +1,64 @@
|
|||
/*
|
||||
* GStreamer
|
||||
* Copyright (C) 2008 Julien Isorce <julien.isorce@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#ifndef _GST_GL_FILTER_H_
|
||||
#define _GST_GL_FILTER_H_
|
||||
|
||||
#include <gst/gst.h>
|
||||
#include <gst/base/gstbasetransform.h>
|
||||
#include <gst/video/video.h>
|
||||
|
||||
#include "gstglbuffer.h"
|
||||
|
||||
#define GST_TYPE_GL_FILTER (gst_gl_filter_get_type())
|
||||
#define GST_GL_FILTER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_GL_FILTER,GstGLFilter))
|
||||
#define GST_IS_GL_FILTER(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_GL_FILTER))
|
||||
#define GST_GL_FILTER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass) ,GST_TYPE_GL_FILTER,GstGLFilterClass))
|
||||
#define GST_IS_GL_FILTER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass) ,GST_TYPE_GL_FILTER))
|
||||
#define GST_GL_FILTER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj) ,GST_TYPE_GL_FILTER,GstGLFilterClass))
|
||||
typedef struct _GstGLFilter GstGLFilter;
|
||||
typedef struct _GstGLFilterClass GstGLFilterClass;
|
||||
|
||||
typedef gboolean (*GstGLFilterProcessFunc) (GstGLFilter *filter,
|
||||
GstGLBuffer *inbuf, GstGLBuffer *outbuf);
|
||||
|
||||
struct _GstGLFilter
|
||||
{
|
||||
GstBaseTransform base_transform;
|
||||
|
||||
GstPad *srcpad;
|
||||
GstPad *sinkpad;
|
||||
|
||||
GstGLDisplay *display;
|
||||
GstVideoFormat video_format;
|
||||
int width;
|
||||
int height;
|
||||
};
|
||||
|
||||
struct _GstGLFilterClass
|
||||
{
|
||||
GstBaseTransformClass base_transform_class;
|
||||
GstGLFilterProcessFunc filter;
|
||||
};
|
||||
|
||||
GType gst_gl_filter_get_type(void);
|
||||
|
||||
#endif
|
||||
|
187
gst/gl/gstglfiltercube.c
Normal file
187
gst/gl/gstglfiltercube.c
Normal file
|
@ -0,0 +1,187 @@
|
|||
/*
|
||||
* GStreamer
|
||||
* Copyright (C) 2008 Julien Isorce <julien.isorce@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include "gstglfiltercube.h"
|
||||
|
||||
#define GST_CAT_DEFAULT gst_gl_filter_cube_debug
|
||||
GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT);
|
||||
|
||||
static const GstElementDetails element_details =
|
||||
GST_ELEMENT_DETAILS ("OpenGL cube filter",
|
||||
"Filter/Effect",
|
||||
"Put input texture on the cube faces",
|
||||
"Julien Isorce <julien.isorce@gmail.com>");
|
||||
|
||||
enum
|
||||
{
|
||||
PROP_0
|
||||
};
|
||||
|
||||
#define DEBUG_INIT(bla) \
|
||||
GST_DEBUG_CATEGORY_INIT (gst_gl_filter_cube_debug, "glfiltercube", 0, "glfiltercube element");
|
||||
|
||||
GST_BOILERPLATE_FULL (GstGLFilterCube, gst_gl_filter_cube, GstGLFilter,
|
||||
GST_TYPE_GL_FILTER, DEBUG_INIT);
|
||||
|
||||
static void gst_gl_filter_cube_set_property (GObject * object, guint prop_id,
|
||||
const GValue * value, GParamSpec * pspec);
|
||||
static void gst_gl_filter_cube_get_property (GObject * object, guint prop_id,
|
||||
GValue * value, GParamSpec * pspec);
|
||||
|
||||
static gboolean gst_gl_filter_cube_filter (GstGLFilter * filter,
|
||||
GstGLBuffer * inbuf, GstGLBuffer * outbuf);
|
||||
|
||||
|
||||
static void
|
||||
gst_gl_filter_cube_base_init (gpointer klass)
|
||||
{
|
||||
GstElementClass *element_class = GST_ELEMENT_CLASS (klass);
|
||||
|
||||
gst_element_class_set_details (element_class, &element_details);
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_cube_class_init (GstGLFilterCubeClass * klass)
|
||||
{
|
||||
GObjectClass *gobject_class;
|
||||
|
||||
gobject_class = (GObjectClass *) klass;
|
||||
gobject_class->set_property = gst_gl_filter_cube_set_property;
|
||||
gobject_class->get_property = gst_gl_filter_cube_get_property;
|
||||
|
||||
GST_GL_FILTER_CLASS (klass)->filter = gst_gl_filter_cube_filter;
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_cube_init (GstGLFilterCube * filter,
|
||||
GstGLFilterCubeClass * klass)
|
||||
{
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_cube_set_property (GObject * object, guint prop_id,
|
||||
const GValue * value, GParamSpec * pspec)
|
||||
{
|
||||
//GstGLFilterCube *filter = GST_GL_FILTER_CUBE (object);
|
||||
|
||||
switch (prop_id) {
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gst_gl_filter_cube_get_property (GObject * object, guint prop_id,
|
||||
GValue * value, GParamSpec * pspec)
|
||||
{
|
||||
//GstGLFilterCube *filter = GST_GL_FILTER_CUBE (object);
|
||||
|
||||
switch (prop_id) {
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_gl_filter_cube_filter (GstGLFilter * filter, GstGLBuffer * inbuf,
|
||||
GstGLBuffer * outbuf)
|
||||
{
|
||||
GstGLFilterCube* cube = GST_GL_FILTER_CUBE(filter);
|
||||
|
||||
g_print ("gstglfiltercube: gst_gl_filter_cube_filter\n");
|
||||
/*int i, j;
|
||||
double *vertex_x, *vertex_y;
|
||||
|
||||
glDisable (GL_CULL_FACE);
|
||||
glEnableClientState (GL_TEXTURE_COORD_ARRAY);
|
||||
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S, GL_CLAMP);
|
||||
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T, GL_CLAMP);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
|
||||
|
||||
glColor4f (1, 0, 1, 1);
|
||||
|
||||
|
||||
|
||||
glMatrixMode (GL_COLOR);
|
||||
glLoadMatrixd (matrix);
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_RED_BIAS, (1 - GAIN) / 2);
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_GREEN_BIAS, (1 - GAIN) / 2);
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_BLUE_BIAS, (1 - GAIN) / 2);
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define N 10
|
||||
#define SCALE (1.0/N)
|
||||
#define NOISE() (0.1*SCALE*g_random_double_range(-1,1))
|
||||
vertex_x = malloc (sizeof (double) * (N + 1) * (N + 1));
|
||||
vertex_y = malloc (sizeof (double) * (N + 1) * (N + 1));
|
||||
for (j = 0; j < N + 1; j++) {
|
||||
for (i = 0; i < N + 1; i++) {
|
||||
vertex_x[j * (N + 1) + i] = i * SCALE + NOISE ();
|
||||
vertex_y[j * (N + 1) + i] = j * SCALE + NOISE ();
|
||||
}
|
||||
}
|
||||
for (j = 0; j < N; j++) {
|
||||
for (i = 0; i < N; i++) {
|
||||
glBegin (GL_QUADS);
|
||||
glNormal3f (0, 0, -1);
|
||||
glTexCoord2f (i * SCALE, j * SCALE);
|
||||
glVertex3f (vertex_x[j * (N + 1) + i], vertex_y[j * (N + 1) + i], 0);
|
||||
glTexCoord2f ((i + 1) * SCALE, j * SCALE);
|
||||
glVertex3f (vertex_x[j * (N + 1) + (i + 1)],
|
||||
vertex_y[j * (N + 1) + (i + 1)], 0);
|
||||
glTexCoord2f ((i + 1) * SCALE, (j + 1) * SCALE);
|
||||
glVertex3f (vertex_x[(j + 1) * (N + 1) + (i + 1)],
|
||||
vertex_y[(j + 1) * (N + 1) + (i + 1)], 0);
|
||||
glTexCoord2f (i * SCALE, (j + 1) * SCALE);
|
||||
glVertex3f (vertex_x[(j + 1) * (N + 1) + i],
|
||||
vertex_y[(j + 1) * (N + 1) + i], 0);
|
||||
glEnd ();
|
||||
}
|
||||
}
|
||||
free (vertex_x);
|
||||
free (vertex_y);
|
||||
|
||||
|
||||
glFlush ();
|
||||
|
||||
glMatrixMode (GL_MODELVIEW);
|
||||
glLoadIdentity ();
|
||||
glMatrixMode (GL_TEXTURE);
|
||||
glLoadIdentity ();
|
||||
glMatrixMode (GL_COLOR);
|
||||
glLoadIdentity ();
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_RED_SCALE, 1.0);
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_RED_BIAS, 0);
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_GREEN_BIAS, 0);
|
||||
glPixelTransferf (GL_POST_COLOR_MATRIX_BLUE_BIAS, 0);*/
|
||||
|
||||
return TRUE;
|
||||
}
|
52
gst/gl/gstglfiltercube.h
Normal file
52
gst/gl/gstglfiltercube.h
Normal file
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
* GStreamer
|
||||
* Copyright (C) 2008 Julien Isorce <julien.isorce@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#ifndef _GST_GL_FILTERCUBE_H_
|
||||
#define _GST_GL_FILTERCUBE_H_
|
||||
|
||||
#include "gstglfilter.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
#define GST_TYPE_GL_FILTER_CUBE (gst_gl_filter_cube_get_type())
|
||||
#define GST_GL_FILTER_CUBE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_GL_FILTER_CUBE,GstGLFilterCube))
|
||||
#define GST_IS_GL_FILTER_CUBE(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_GL_FILTER_CUBE))
|
||||
#define GST_GL_FILTER_CUBE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass) ,GST_TYPE_GL_FILTER_CUBE,GstGLFilterCubeClass))
|
||||
#define GST_IS_GL_FILTER_CUBE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass) ,GST_TYPE_GL_FILTER_CUBE))
|
||||
#define GST_GL_FILTER_CUBE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj) ,GST_TYPE_GL_FILTER_CUBE,GstGLFilterCubeClass))
|
||||
typedef struct _GstGLFilterCube GstGLFilterCube;
|
||||
typedef struct _GstGLFilterCubeClass GstGLFilterCubeClass;
|
||||
|
||||
struct _GstGLFilterCube
|
||||
{
|
||||
GstGLFilter filter;
|
||||
|
||||
};
|
||||
|
||||
struct _GstGLFilterCubeClass
|
||||
{
|
||||
GstGLFilterClass filter_class;
|
||||
};
|
||||
|
||||
GType gst_gl_glfiltercube_get_type (void);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* _GST_GLFILTERCUBE_H_ */
|
|
@ -199,7 +199,8 @@ gst_gl_graphicmaker_get_property (GObject* object, guint prop_id,
|
|||
static void
|
||||
gst_gl_graphicmaker_reset (GstGLGraphicmaker* graphicmaker)
|
||||
{
|
||||
if (graphicmaker->display) {
|
||||
if (graphicmaker->display)
|
||||
{
|
||||
g_object_unref (graphicmaker->display);
|
||||
graphicmaker->display = NULL;
|
||||
}
|
||||
|
@ -322,7 +323,8 @@ gst_gl_graphicmaker_set_caps (GstBaseTransform* bt, GstCaps* incaps,
|
|||
ret = gst_video_format_parse_caps (incaps, &graphicmaker->video_format,
|
||||
&graphicmaker->width, &graphicmaker->height);
|
||||
|
||||
if (!ret) {
|
||||
if (!ret)
|
||||
{
|
||||
GST_DEBUG ("bad caps");
|
||||
return FALSE;
|
||||
}
|
||||
|
|
|
@ -280,55 +280,59 @@ gst_glimage_sink_start (GstBaseSink * bsink)
|
|||
static gboolean
|
||||
gst_glimage_sink_stop (GstBaseSink * bsink)
|
||||
{
|
||||
GstGLImageSink *glimage_sink;
|
||||
GstGLImageSink *glimage_sink;
|
||||
|
||||
GST_DEBUG ("stop");
|
||||
GST_DEBUG ("stop");
|
||||
|
||||
glimage_sink = GST_GLIMAGE_SINK (bsink);
|
||||
glimage_sink = GST_GLIMAGE_SINK (bsink);
|
||||
|
||||
if (glimage_sink->stored_buffer) {
|
||||
gst_buffer_unref (glimage_sink->stored_buffer);
|
||||
glimage_sink->stored_buffer = NULL;
|
||||
}
|
||||
if (glimage_sink->display) {
|
||||
gst_gl_display_setVisibleWindow (glimage_sink->display, FALSE);
|
||||
g_object_unref (glimage_sink->display);
|
||||
glimage_sink->display = NULL;
|
||||
}
|
||||
if (glimage_sink->stored_buffer)
|
||||
{
|
||||
gst_buffer_unref (glimage_sink->stored_buffer);
|
||||
glimage_sink->stored_buffer = NULL;
|
||||
}
|
||||
if (glimage_sink->display)
|
||||
{
|
||||
gst_gl_display_setVisibleWindow (glimage_sink->display, FALSE);
|
||||
g_object_unref (glimage_sink->display);
|
||||
glimage_sink->display = NULL;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_glimage_sink_unlock (GstBaseSink * bsink)
|
||||
{
|
||||
//GstGLImageSink* glimage_sink = GST_GLIMAGE_SINK (bsink);
|
||||
//GstGLImageSink* glimage_sink = GST_GLIMAGE_SINK (bsink);
|
||||
|
||||
GST_DEBUG ("unlock");
|
||||
GST_DEBUG ("unlock");
|
||||
|
||||
return TRUE;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
gst_glimage_sink_get_times (GstBaseSink * bsink, GstBuffer * buf,
|
||||
GstClockTime * start, GstClockTime * end)
|
||||
{
|
||||
GstGLImageSink *glimagesink;
|
||||
GstGLImageSink *glimagesink;
|
||||
|
||||
glimagesink = GST_GLIMAGE_SINK (bsink);
|
||||
glimagesink = GST_GLIMAGE_SINK (bsink);
|
||||
|
||||
if (GST_BUFFER_TIMESTAMP_IS_VALID (buf)) {
|
||||
*start = GST_BUFFER_TIMESTAMP (buf);
|
||||
if (GST_BUFFER_DURATION_IS_VALID (buf)) {
|
||||
*end = *start + GST_BUFFER_DURATION (buf);
|
||||
} else {
|
||||
if (glimagesink->fps_n > 0) {
|
||||
*end = *start +
|
||||
gst_util_uint64_scale_int (GST_SECOND, glimagesink->fps_d,
|
||||
glimagesink->fps_n);
|
||||
}
|
||||
if (GST_BUFFER_TIMESTAMP_IS_VALID (buf))
|
||||
{
|
||||
*start = GST_BUFFER_TIMESTAMP (buf);
|
||||
if (GST_BUFFER_DURATION_IS_VALID (buf))
|
||||
*end = *start + GST_BUFFER_DURATION (buf);
|
||||
else
|
||||
{
|
||||
if (glimagesink->fps_n > 0) {
|
||||
*end = *start +
|
||||
gst_util_uint64_scale_int (GST_SECOND, glimagesink->fps_d,
|
||||
glimagesink->fps_n);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
#endif
|
||||
|
||||
#include "gstglgraphicmaker.h"
|
||||
#include "gstglfiltercube.h"
|
||||
#include "gstglvideomaker.h"
|
||||
#include "gstglimagesink.h"
|
||||
|
||||
|
@ -35,13 +36,18 @@ plugin_init (GstPlugin * plugin)
|
|||
{
|
||||
GST_DEBUG_CATEGORY_INIT (gst_gl_gstgl_debug, "gstopengl", 0, "gstopengl");
|
||||
|
||||
if (!gst_element_register (plugin, "glvideomaker",
|
||||
GST_RANK_NONE, GST_TYPE_GL_VIDEOMAKER)) {
|
||||
if (!gst_element_register (plugin, "glgraphicmaker",
|
||||
GST_RANK_NONE, GST_TYPE_GL_GRAPHICMAKER)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (!gst_element_register (plugin, "glgraphicmaker",
|
||||
GST_RANK_NONE, GST_TYPE_GL_GRAPHICMAKER)) {
|
||||
if (!gst_element_register (plugin, "glfiltercube",
|
||||
GST_RANK_NONE, GST_TYPE_GL_FILTER_CUBE)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (!gst_element_register (plugin, "glvideomaker",
|
||||
GST_RANK_NONE, GST_TYPE_GL_VIDEOMAKER)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue