[087/906] glfilter can accept to have an input size different than the out put size : video/x-raw-gl, width=w1, height=w1 ! glfilter ! video/x-raw-gl, width=w2, height=w2 ! (fix every examples)

git-svn-id: svn://svn.wobow.com/GStreamer_playground/gst-plugins-gl@499 93df14bb-0f41-7a43-8087-d3e2a2f0e464
This commit is contained in:
Julien Isorce 2008-06-10 19:07:43 +00:00 committed by Tim-Philipp Müller
parent 2c12b6f41e
commit 1e2ca1dfde
4 changed files with 145 additions and 86 deletions

View file

@ -44,12 +44,14 @@ gst_gl_buffer_init (GstGLBuffer* buffer, gpointer g_class)
{
buffer->display = NULL;
buffer->video_format = 0;
buffer->width = 0;
buffer->height = 0;
buffer->texture = 0;
buffer->texture_u = 0;
buffer->texture_v = 0;
buffer->widthGL = 0;
buffer->heightGL = 0;
buffer->textureGL = 0;
buffer->width = 0;
buffer->height = 0;
}
static void
@ -107,6 +109,8 @@ gst_gl_buffer_new_from_video_format (GstGLDisplay* display,
buffer->width = width;
buffer->height = height;
buffer->video_format = video_format;
buffer->widthGL = context_width;
buffer->heightGL = context_height;
GST_BUFFER_SIZE (buffer) = gst_gl_buffer_format_get_size (video_format, context_width, context_height);
//blocking call, init texture

View file

@ -42,13 +42,15 @@ struct _GstGLBuffer {
GstVideoFormat video_format;
gint width;
gint height;
GLuint texture;
GLuint texture_u;
GLuint texture_v;
GLuint textureGL;
gint width;
gint height;
gint widthGL;
gint heightGL;
GLuint textureGL;
};
GType gst_gl_buffer_get_type (void);
@ -66,8 +68,8 @@ gboolean gst_gl_buffer_format_parse_caps (GstCaps* caps, GstVideoFormat* format,
#define GST_GL_VIDEO_CAPS \
"video/x-raw-gl," \
"width=(int)[1,1920]," \
"height=(int)[1,1080]," \
"width=(int)[1,8000]," \
"height=(int)[1,6000]," \
"pixel-aspect-ratio=(fraction)1/1," \
"framerate=(fraction)[0/1,100/1]"

View file

@ -28,11 +28,13 @@
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_gldisplay_glutGenerateOutputVideoFBO (GstGLDisplay *display);
static void gst_gl_display_glutGenerateFBO (GstGLDisplay *display);
static void gst_gl_display_glutUseFBO (GstGLDisplay *display);
static void gst_gl_display_glutDestroyFBO (GstGLDisplay *display);
static void gst_gl_display_glutDestroyWindow (GstGLDisplay* display);
static void gst_gl_display_glutSetVisibleWindow (GstGLDisplay* display);
static void gst_gl_display_glutReshapeWindow (GstGLDisplay* display);
static void gst_gl_display_glutPrepareTexture (GstGLDisplay* display);
static void gst_gl_display_glutUpdateTexture (GstGLDisplay* display);
static void gst_gl_display_glutCleanTexture (GstGLDisplay* display);
@ -101,6 +103,7 @@ gst_gl_display_init (GstGLDisplay *display, GstGLDisplayClass *klass)
display->cond_destroyFBO = g_cond_new ();
display->cond_create = g_cond_new ();
display->cond_destroy = g_cond_new ();
display->cond_download = g_cond_new ();
display->fbo = 0;
display->depthBuffer = 0;
@ -221,7 +224,7 @@ gst_gl_display_init (GstGLDisplay *display, GstGLDisplayClass *klass)
"void main(void) {\n"
" float r,g,b,y,u,v;\n"
" vec2 nxy=gl_TexCoord[0].xy;\n"
" y=texture2DRect(Ytex,nxy*).r;\n"
" y=texture2DRect(Ytex,nxy).r;\n"
" u=texture2DRect(Utex,nxy*0.5).r;\n"
" v=texture2DRect(Vtex,nxy*0.5).r;\n"
" y=1.1643*(y-0.0625);\n"
@ -358,6 +361,10 @@ gst_gl_display_finalize (GObject *object)
g_cond_free (display->cond_video);
display->cond_video = NULL;
}
if (display->cond_download) {
g_cond_free (display->cond_download);
display->cond_download = NULL;
}
if (display->cond_generateFBO) {
g_cond_free (display->cond_generateFBO);
display->cond_generateFBO = NULL;
@ -519,6 +526,70 @@ gst_gl_display_glutCreateWindow (GstGLDisplay *display)
//unbind the FBO
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
}
else
{
GST_DEBUG ("Context %d, EXT_framebuffer_object supported: no", glutWinId);
g_assert_not_reached ();
}
//check if fragment program is available, then load them
if (GLEW_ARB_vertex_program)
{
gchar program[2048];
GST_DEBUG ("Context %d, ARB_fragment_program supported: yes", glutWinId);
//from video to texture
sprintf (program, display->textFProgram_YUY2_UYVY, 'r', 'g', 'a');
display->GLSLProgram_YUY2 = gst_gl_display_loadGLSLprogram (program);
sprintf (program, display->textFProgram_YUY2_UYVY, 'a', 'b', 'r');
display->GLSLProgram_UYVY = gst_gl_display_loadGLSLprogram (program);
display->GLSLProgram_I420_YV12 = gst_gl_display_loadGLSLprogram (display->textFProgram_I420_YV12);
display->GLSLProgram_AYUV = gst_gl_display_loadGLSLprogram (display->textFProgram_AYUV);
}
else
{
GST_DEBUG ("Context %d, ARB_fragment_program supported: no", glutWinId);
g_assert_not_reached ();
}
//setup callbacks
glutReshapeFunc (gst_gl_display_onReshape);
glutDisplayFunc (gst_gl_display_draw);
glutCloseFunc (gst_gl_display_onClose);
//insert glut context to the map
display->glutWinId = glutWinId;
g_hash_table_insert (gst_gl_display_map, GUINT_TO_POINTER (glutWinId), display);
//check glut id validity
g_assert (glutGetWindow() == glutWinId);
GST_DEBUG ("Context %d initialized", display->glutWinId);
//release display constructor
g_cond_signal (display->cond_create);
}
/* Called by the idle funtion */
static void
gst_gldisplay_glutGenerateOutputVideoFBO (GstGLDisplay *display)
{
glutSetWindow (display->glutWinId);
if (GLEW_EXT_framebuffer_object)
{
GST_DEBUG ("Context %d, EXT_framebuffer_object supported: yes", display->glutWinId);
//-- init graphic frame buffer object (GL texture -> GL scene)
//setup FBO
@ -627,35 +698,17 @@ gst_gl_display_glutCreateWindow (GstGLDisplay *display)
display->multipleRT[0] = GL_COLOR_ATTACHMENT0_EXT;
display->multipleRT[1] = GL_COLOR_ATTACHMENT1_EXT;
display->multipleRT[2] = GL_COLOR_ATTACHMENT2_EXT;
}
else
{
GST_DEBUG ("Context %d, EXT_framebuffer_object supported: no", glutWinId);
GST_DEBUG ("Context %d, EXT_framebuffer_object supported: no", display->glutWinId);
g_assert_not_reached ();
}
//check if fragment program is available, then load them
if (GLEW_ARB_vertex_program)
if (GLEW_ARB_vertex_program)
{
gchar program[2048];
GST_DEBUG ("Context %d, ARB_fragment_program supported: yes", glutWinId);
//from video to texture
sprintf (program, display->textFProgram_YUY2_UYVY, 'r', 'g', 'a');
display->GLSLProgram_YUY2 = gst_gl_display_loadGLSLprogram (program);
sprintf (program, display->textFProgram_YUY2_UYVY, 'a', 'b', 'r');
display->GLSLProgram_UYVY = gst_gl_display_loadGLSLprogram (program);
display->GLSLProgram_I420_YV12 = gst_gl_display_loadGLSLprogram (display->textFProgram_I420_YV12);
display->GLSLProgram_AYUV = gst_gl_display_loadGLSLprogram (display->textFProgram_AYUV);
//from texture to video
sprintf (program, display->textFProgram_to_YUY2_UYVY, "y2,u,y1,v");
@ -667,28 +720,14 @@ gst_gl_display_glutCreateWindow (GstGLDisplay *display)
display->GLSLProgram_to_I420_YV12 = gst_gl_display_loadGLSLprogram (display->textFProgram_to_I420_YV12);
display->GLSLProgram_to_AYUV = gst_gl_display_loadGLSLprogram (display->textFProgram_to_AYUV);
}
else
}
else
{
GST_DEBUG ("Context %d, ARB_fragment_program supported: no", glutWinId);
GST_DEBUG ("Context %d, ARB_fragment_program supported: no", display->glutWinId);
g_assert_not_reached ();
}
//setup callbacks
glutReshapeFunc (gst_gl_display_onReshape);
glutDisplayFunc (gst_gl_display_draw);
glutCloseFunc (gst_gl_display_onClose);
//insert glut context to the map
display->glutWinId = glutWinId;
g_hash_table_insert (gst_gl_display_map, GUINT_TO_POINTER (glutWinId), display);
//check glut id validity
g_assert (glutGetWindow() == glutWinId);
GST_DEBUG ("Context %d initialized", display->glutWinId);
//release display constructor
g_cond_signal (display->cond_create);
g_cond_signal (display->cond_download);
}
@ -877,6 +916,16 @@ gst_gl_display_glutSetVisibleWindow (GstGLDisplay *display)
}
/* Called by the idle function */
static void
gst_gl_display_glutReshapeWindow (GstGLDisplay* display)
{
glutSetWindow (display->glutWinId);
glutReshapeWindow (display->glcontext_width, display->glcontext_height);
//should reset glcontext_width and height
}
/* Called by the idle function */
static void
gst_gl_display_glutPrepareTexture (GstGLDisplay * display)
@ -985,6 +1034,9 @@ gst_gl_display_glutDispatchAction (GstGLDisplayMsg* msg)
case GST_GL_DISPLAY_ACTION_VISIBLE:
gst_gl_display_glutSetVisibleWindow (msg->display);
break;
case GST_GL_DISPLAY_ACTION_RESHAPE:
gst_gl_display_glutReshapeWindow (msg->display);
break;
case GST_GL_DISPLAY_ACTION_PREPARE:
gst_gl_display_glutPrepareTexture (msg->display);
break;
@ -1009,6 +1061,9 @@ gst_gl_display_glutDispatchAction (GstGLDisplayMsg* msg)
case GST_GL_DISPLAY_ACTION_USEFBO:
gst_gl_display_glutUseFBO (msg->display);
break;
case GST_GL_DISPLAY_ACTION_OVFBO:
gst_gldisplay_glutGenerateOutputVideoFBO (msg->display);
break;
default:
g_assert_not_reached ();
}
@ -1029,7 +1084,8 @@ gst_gl_display_checkMsgValidity (GstGLDisplayMsg *msg)
valid = TRUE;
break;
case GST_GL_DISPLAY_ACTION_DESTROY:
case GST_GL_DISPLAY_ACTION_VISIBLE:
case GST_GL_DISPLAY_ACTION_VISIBLE:
case GST_GL_DISPLAY_ACTION_RESHAPE:
case GST_GL_DISPLAY_ACTION_PREPARE:
case GST_GL_DISPLAY_ACTION_CHANGE:
case GST_GL_DISPLAY_ACTION_CLEAR:
@ -1038,6 +1094,7 @@ gst_gl_display_checkMsgValidity (GstGLDisplayMsg *msg)
case GST_GL_DISPLAY_ACTION_GENFBO:
case GST_GL_DISPLAY_ACTION_DELFBO:
case GST_GL_DISPLAY_ACTION_USEFBO:
case GST_GL_DISPLAY_ACTION_OVFBO:
//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;
@ -1148,7 +1205,7 @@ gst_gl_display_setClientDrawCallback (GstGLDisplay * display, CDCB cb)
/* Called by gst gl elements */
void
gst_gl_display_setVisibleWindow (GstGLDisplay * display, gboolean visible)
gst_gl_display_setVisibleWindow (GstGLDisplay* display, gboolean visible)
{
gst_gl_display_lock (display);
if (display->visible != visible)
@ -1160,11 +1217,23 @@ gst_gl_display_setVisibleWindow (GstGLDisplay * display, gboolean visible)
}
/* Called by gst gl elements */
void
gst_gl_display_resizeWindow (GstGLDisplay* display, gint width, gint height)
{
gst_gl_display_lock (display);
display->glcontext_width = width;
display->glcontext_height = height;
gst_gl_display_postMessage (GST_GL_DISPLAY_ACTION_RESHAPE, display);
gst_gl_display_unlock (display);
}
/* Called by gstglbuffer */
void
gst_gl_display_textureRequested (GstGLDisplay * display, GstVideoFormat video_format,
gint width, gint height, guint *texture,
guint *texture_u, guint *texture_v)
gst_gl_display_textureRequested (GstGLDisplay* display, GstVideoFormat video_format,
gint width, gint height, guint* texture,
guint* texture_u, guint* texture_v)
{
gst_gl_display_lock (display);
display->requestedVideo_format = video_format;
@ -1311,6 +1380,19 @@ gst_gl_display_rejectFBO (GstGLDisplay* display, guint fbo,
}
/* Called by gst_gl elements */
void
gst_gl_display_initDonwloadFBO (GstGLDisplay* display, gint width, gint height)
{
gst_gl_display_lock (display);
display->glcontext_width = width;
display->glcontext_height = height;
gst_gl_display_postMessage (GST_GL_DISPLAY_ACTION_OVFBO, display);
g_cond_wait (display->cond_download, display->mutex);
gst_gl_display_unlock (display);
}
/* Called by gst_gl elements */
void
gst_gl_display_set_windowId (GstGLDisplay* display, gulong winId)
@ -1342,38 +1424,6 @@ gst_gl_display_set_windowId (GstGLDisplay* display, gulong winId)
}
/* Called by gst_gl elements */
void
gst_gl_display_resetGLcontext (GstGLDisplay* display,
gint glcontext_width, gint glcontext_height)
{
static gint glheight = 0;
gst_gl_display_lock (display);
gst_gl_display_postMessage (GST_GL_DISPLAY_ACTION_DESTROY, display);
g_cond_wait (display->cond_destroy, display->mutex);
gst_gl_display_unlock (display);
if (g_hash_table_size (gst_gl_display_map) == 0)
{
g_thread_join (gst_gl_display_glutThread);
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);
gst_gl_display_map = NULL;
}
//init opengl context
gst_gl_display_initGLContext (display,
50, glheight++ * (glcontext_height+50) + 50,
glcontext_width, glcontext_height,
display->textureFBOWidth, display->textureFBOHeight,
display->winId,
FALSE);
}
/* glutReshapeFunc callback */
void
gst_gl_display_onReshape(gint width, gint height)

View file

@ -46,6 +46,7 @@ typedef enum {
GST_GL_DISPLAY_ACTION_CREATE,
GST_GL_DISPLAY_ACTION_DESTROY,
GST_GL_DISPLAY_ACTION_VISIBLE,
GST_GL_DISPLAY_ACTION_RESHAPE,
GST_GL_DISPLAY_ACTION_PREPARE,
GST_GL_DISPLAY_ACTION_CHANGE,
GST_GL_DISPLAY_ACTION_CLEAR,
@ -53,7 +54,8 @@ typedef enum {
GST_GL_DISPLAY_ACTION_REDISPLAY,
GST_GL_DISPLAY_ACTION_GENFBO,
GST_GL_DISPLAY_ACTION_DELFBO,
GST_GL_DISPLAY_ACTION_USEFBO
GST_GL_DISPLAY_ACTION_USEFBO,
GST_GL_DISPLAY_ACTION_OVFBO
} GstGLDisplayAction;
@ -95,6 +97,7 @@ struct _GstGLDisplay {
GCond* cond_generateFBO;
GCond* cond_useFBO;
GCond* cond_destroyFBO;
GCond* cond_download;
GCond* cond_create;
GCond* cond_destroy;
@ -237,6 +240,7 @@ void gst_gl_display_initGLContext (GstGLDisplay* display,
void gst_gl_display_setClientReshapeCallback (GstGLDisplay* display, CRCB cb);
void gst_gl_display_setClientDrawCallback (GstGLDisplay* display, CDCB cb);
void gst_gl_display_setVisibleWindow (GstGLDisplay* display, gboolean visible);
void gst_gl_display_resizeWindow (GstGLDisplay* display, gint width, gint height);
void gst_gl_display_textureRequested (GstGLDisplay* display, GstVideoFormat format,
gint width, gint height, guint* texture,
guint* texture_u, guint* texture_v);
@ -256,8 +260,7 @@ void gst_gl_display_useFBO (GstGLDisplay* display, gint textureFBOWidth, gint te
guint inputTextureWidth, guint inputTextureHeight, guint inputTexture);
void gst_gl_display_rejectFBO (GstGLDisplay* display, guint fbo,
guint depthbuffer, guint texture);
void gst_gl_display_initDonwloadFBO (GstGLDisplay* display, gint width, gint height);
void gst_gl_display_set_windowId (GstGLDisplay* display, gulong winId);
void gst_gl_display_resetGLcontext (GstGLDisplay* display,
gint glcontext_width, gint glcontext_height);
#endif