summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJulien Moutte <julien@moutte.net>2003-11-17 16:32:29 +0000
committerJulien Moutte <julien@moutte.net>2003-11-17 16:32:29 +0000
commit9ddf040472fce83eadb9630b90b535a7105a643f (patch)
tree1f93d94a937b26accc840020c9d97b903c85b7dd
parenta58a759d9ca0a0341a97f8d4bc445a5bd5cbdf4e (diff)
downloadgstreamer-plugins-base-9ddf040472fce83eadb9630b90b535a7105a643f.tar.gz
Lot of small fixes.
Original commit message from CVS: Lot of small fixes. Implemented XOverlay interface.
-rw-r--r--sys/ximage/ximagesink.c216
-rw-r--r--sys/ximage/ximagesink.h1
-rw-r--r--sys/xvimage/xvimagesink.c196
-rw-r--r--sys/xvimage/xvimagesink.h1
4 files changed, 240 insertions, 174 deletions
diff --git a/sys/ximage/ximagesink.c b/sys/ximage/ximagesink.c
index 9b60baad2..94a7a9bff 100644
--- a/sys/ximage/ximagesink.c
+++ b/sys/ximage/ximagesink.c
@@ -56,63 +56,6 @@ static GstElementClass *parent_class = NULL;
/* */
/* ============================================================= */
-/* Interfaces stuff */
-
-static gboolean
-gst_ximagesink_interface_supported (GstInterface *iface, GType type)
-{
- g_assert (type == GST_TYPE_NAVIGATION ||
- type == GST_TYPE_X_OVERLAY);
-
- return (GST_STATE (iface) != GST_STATE_NULL);
-}
-
-static void
-gst_ximagesink_interface_init (GstInterfaceClass *klass)
-{
- klass->supported = gst_ximagesink_interface_supported;
-}
-
-static void
-gst_ximagesink_navigation_send_event (GstNavigation *navigation, GstStructure *structure)
-{
- GstXImageSink *ximagesink = GST_XIMAGESINK (navigation);
- GstEvent *event;
- gint x_offset, y_offset;
- double x,y;
-
- event = gst_event_new (GST_EVENT_NAVIGATION);
- event->event_data.structure.structure = structure;
-
- /* We are not converting the pointer coordinates as there's no hardware
- scaling done here. The only possible scaling is done by videoscale and
- videoscale will have to catch those events and tranform the coordinates
- to match the applied scaling. So here we just add the offset if the image
- is centered in the window. */
-
- x_offset = ximagesink->xwindow->width - ximagesink->width;
- y_offset = ximagesink->xwindow->height - ximagesink->height;
-
- if (gst_structure_get_double (structure, "pointer_x", &x))
- {
- x += x_offset;
- gst_structure_set (structure, "pointer_x", G_TYPE_DOUBLE, x, NULL);
- }
- if (gst_structure_get_double (structure, "pointer_y", &y))
- {
- y += y_offset;
- gst_structure_set (structure, "pointer_y", G_TYPE_DOUBLE, y, NULL);
- }
-
- gst_pad_send_event (gst_pad_get_peer (ximagesink->sinkpad), event);
-}
-
-static void
-gst_ximagesink_navigation_init (GstNavigationInterface *iface)
-{
- iface->send_event = gst_ximagesink_navigation_send_event;
-}
-
/* X11 stuff */
/* This function handles GstXImage creation depending on XShm availability */
@@ -281,7 +224,6 @@ static GstXWindow *
gst_ximagesink_xwindow_new (GstXImageSink *ximagesink, gint width, gint height)
{
GstXWindow *xwindow = NULL;
- XGCValues values;
g_return_val_if_fail (ximagesink != NULL, NULL);
g_return_val_if_fail (GST_IS_XIMAGESINK (ximagesink), NULL);
@@ -290,6 +232,7 @@ gst_ximagesink_xwindow_new (GstXImageSink *ximagesink, gint width, gint height)
xwindow->width = width;
xwindow->height = height;
+ xwindow->internal = TRUE;
g_mutex_lock (ximagesink->x_lock);
@@ -303,7 +246,7 @@ gst_ximagesink_xwindow_new (GstXImageSink *ximagesink, gint width, gint height)
KeyReleaseMask | ButtonPressMask | ButtonReleaseMask);
xwindow->gc = XCreateGC (ximagesink->xcontext->disp,
- xwindow->win, 0, &values);
+ xwindow->win, 0, NULL);
XMapRaised (ximagesink->xcontext->disp, xwindow->win);
@@ -322,7 +265,9 @@ gst_ximagesink_xwindow_destroy (GstXImageSink *ximagesink, GstXWindow *xwindow)
g_mutex_lock (ximagesink->x_lock);
- XDestroyWindow (ximagesink->xcontext->disp, xwindow->win);
+ /* If we did not create that window we just free the GC and let it live */
+ if (xwindow->internal)
+ XDestroyWindow (ximagesink->xcontext->disp, xwindow->win);
XFreeGC (ximagesink->xcontext->disp, xwindow->gc);
@@ -331,22 +276,6 @@ gst_ximagesink_xwindow_destroy (GstXImageSink *ximagesink, GstXWindow *xwindow)
g_free (xwindow);
}
-/* This function resizes a GstXWindow */
-/*static void
-gst_ximagesink_xwindow_resize (GstXImageSink *ximagesink, GstXWindow *xwindow,
- gint width, gint height)
-{
- g_return_if_fail (xwindow != NULL);
- g_return_if_fail (ximagesink != NULL);
- g_return_if_fail (GST_IS_XIMAGESINK (ximagesink));
-
- g_mutex_lock (ximagesink->x_lock);
-
- XResizeWindow (ximagesink->xcontext->disp, xwindow->win, width, height);
-
- g_mutex_unlock (ximagesink->x_lock);
-} */
-
/* This function handles XEvents that might be in the queue. It generates
GstEvent that will be sent upstream in the pipeline to handle interactivity
and navigation. It will also listen for configure events on the window to
@@ -420,6 +349,10 @@ gst_ximagesink_handle_xevents (GstXImageSink *ximagesink, GstPad *pad)
ximagesink->width,
ximagesink->height);
}
+
+ gst_x_overlay_got_video_size (
+ GST_X_OVERLAY (ximagesink),
+ ximagesink->width, ximagesink->height);
}
}
break;
@@ -640,14 +573,6 @@ gst_ximagesink_sinkconnect (GstPad *pad, GstCaps *caps)
ximagesink->xwindow = gst_ximagesink_xwindow_new (ximagesink,
ximagesink->width,
ximagesink->height);
- else
- { /* We resize our window only if size has changed, preventing us from
- infinite loops with XConfigure events.
- if ( (ximagesink->width != ximagesink->xwindow->width) ||
- (ximagesink->height != ximagesink->xwindow->height) )
- gst_ximagesink_xwindow_resize (ximagesink, ximagesink->xwindow,
- ximagesink->width, ximagesink->height);*/
- }
if ( (ximagesink->ximage) &&
( (ximagesink->width != ximagesink->ximage->width) ||
@@ -664,6 +589,9 @@ gst_ximagesink_sinkconnect (GstPad *pad, GstCaps *caps)
ximagesink->width,
ximagesink->height);
+ gst_x_overlay_got_video_size (GST_X_OVERLAY (ximagesink),
+ ximagesink->width, ximagesink->height);
+
return GST_PAD_LINK_OK;
}
@@ -677,7 +605,8 @@ gst_ximagesink_change_state (GstElement *element)
switch (GST_STATE_TRANSITION (element)) {
case GST_STATE_NULL_TO_READY:
/* Initializing the XContext */
- ximagesink->xcontext = gst_ximagesink_xcontext_get (ximagesink);
+ if (!ximagesink->xcontext)
+ ximagesink->xcontext = gst_ximagesink_xcontext_get (ximagesink);
if (!ximagesink->xcontext)
return GST_STATE_FAILURE;
break;
@@ -897,6 +826,111 @@ gst_ximagesink_get_bufferpool (GstPad *pad)
return ximagesink->bufferpool;
}
+/* Interfaces stuff */
+
+static gboolean
+gst_ximagesink_interface_supported (GstInterface *iface, GType type)
+{
+ g_assert (type == GST_TYPE_NAVIGATION || type == GST_TYPE_X_OVERLAY);
+ return TRUE;
+}
+
+static void
+gst_ximagesink_interface_init (GstInterfaceClass *klass)
+{
+ klass->supported = gst_ximagesink_interface_supported;
+}
+
+static void
+gst_ximagesink_navigation_send_event (GstNavigation *navigation, GstStructure *structure)
+{
+ GstXImageSink *ximagesink = GST_XIMAGESINK (navigation);
+ GstEvent *event;
+ gint x_offset, y_offset;
+ double x,y;
+
+ event = gst_event_new (GST_EVENT_NAVIGATION);
+ event->event_data.structure.structure = structure;
+
+ /* We are not converting the pointer coordinates as there's no hardware
+ scaling done here. The only possible scaling is done by videoscale and
+ videoscale will have to catch those events and tranform the coordinates
+ to match the applied scaling. So here we just add the offset if the image
+ is centered in the window. */
+
+ x_offset = ximagesink->xwindow->width - ximagesink->width;
+ y_offset = ximagesink->xwindow->height - ximagesink->height;
+
+ if (gst_structure_get_double (structure, "pointer_x", &x))
+ {
+ x += x_offset;
+ gst_structure_set (structure, "pointer_x", G_TYPE_DOUBLE, x, NULL);
+ }
+ if (gst_structure_get_double (structure, "pointer_y", &y))
+ {
+ y += y_offset;
+ gst_structure_set (structure, "pointer_y", G_TYPE_DOUBLE, y, NULL);
+ }
+
+ gst_pad_send_event (gst_pad_get_peer (ximagesink->sinkpad), event);
+}
+
+static void
+gst_ximagesink_navigation_init (GstNavigationInterface *iface)
+{
+ iface->send_event = gst_ximagesink_navigation_send_event;
+}
+
+static void
+gst_ximagesink_set_xwindow_id (GstXOverlay *overlay, XID xwindow_id)
+{
+ GstXImageSink *ximagesink = GST_XIMAGESINK (overlay);
+ GstXWindow *xwindow = NULL;
+ XWindowAttributes attr;
+
+ g_return_if_fail (ximagesink != NULL);
+ g_return_if_fail (GST_IS_XIMAGESINK (ximagesink));
+
+ if (!ximagesink->xcontext)
+ {
+ ximagesink->xcontext = gst_ximagesink_xcontext_get (ximagesink);
+ }
+
+ if ( (ximagesink->xwindow) && (ximagesink->ximage) )
+ { /* If we are replacing a window we destroy pictures and window as they
+ are associated */
+ gst_ximagesink_ximage_destroy (ximagesink, ximagesink->ximage);
+ gst_ximagesink_imagepool_clear (ximagesink);
+ gst_ximagesink_xwindow_destroy (ximagesink, ximagesink->xwindow);
+ }
+
+ xwindow = g_new0 (GstXWindow, 1);
+
+ xwindow->win = xwindow_id;
+
+ /* We get window geometry, set the event we want to receive, and create a GC */
+ g_mutex_lock (ximagesink->x_lock);
+ XGetWindowAttributes (ximagesink->xcontext->disp, xwindow->win, &attr);
+ xwindow->width = attr.width;
+ xwindow->height = attr.height;
+ xwindow->internal = FALSE;
+ XSelectInput (ximagesink->xcontext->disp, xwindow->win, ExposureMask |
+ StructureNotifyMask | PointerMotionMask | KeyPressMask |
+ KeyReleaseMask /*| ButtonPressMask | ButtonReleaseMask*/);
+
+ xwindow->gc = XCreateGC (ximagesink->xcontext->disp,
+ xwindow->win, 0, NULL);
+ g_mutex_unlock (ximagesink->x_lock);
+
+ ximagesink->xwindow = xwindow;
+}
+
+static void
+gst_ximagesink_xoverlay_init (GstXOverlayClass *iface)
+{
+ iface->set_xwindow_id = gst_ximagesink_set_xwindow_id;
+}
+
/* =========================================== */
/* */
/* Init & Class init */
@@ -1039,22 +1073,22 @@ gst_ximagesink_get_type (void)
NULL,
NULL,
};
- /*static const GInterfaceInfo xoverlay_info = {
+ static const GInterfaceInfo overlay_info = {
(GInterfaceInitFunc) gst_ximagesink_xoverlay_init,
NULL,
NULL,
- };*/
+ };
ximagesink_type = g_type_register_static (GST_TYPE_ELEMENT,
"GstXImageSink",
&ximagesink_info, 0);
g_type_add_interface_static (ximagesink_type, GST_TYPE_INTERFACE,
- &iface_info);
+ &iface_info);
g_type_add_interface_static (ximagesink_type, GST_TYPE_NAVIGATION,
- &navigation_info);
- /*g_type_add_interface_static (ximagesink_type, GST_TYPE_X_OVERLAY,
- &xoverlay_info);*/
+ &navigation_info);
+ g_type_add_interface_static (ximagesink_type, GST_TYPE_X_OVERLAY,
+ &overlay_info);
}
return ximagesink_type;
diff --git a/sys/ximage/ximagesink.h b/sys/ximage/ximagesink.h
index 45a3a1901..69b372e2f 100644
--- a/sys/ximage/ximagesink.h
+++ b/sys/ximage/ximagesink.h
@@ -86,6 +86,7 @@ struct _GstXContext {
struct _GstXWindow {
Window win;
gint width, height;
+ gboolean internal;
GC gc;
};
diff --git a/sys/xvimage/xvimagesink.c b/sys/xvimage/xvimagesink.c
index 828855a0b..deb66783f 100644
--- a/sys/xvimage/xvimagesink.c
+++ b/sys/xvimage/xvimagesink.c
@@ -60,56 +60,6 @@ static GstElementClass *parent_class = NULL;
/* */
/* ============================================================= */
-/* Interfaces stuff */
-
-static gboolean
-gst_xvimagesink_interface_supported (GstInterface *iface, GType type)
-{
- g_assert (type == GST_TYPE_NAVIGATION ||
- type == GST_TYPE_X_OVERLAY);
-
- return (GST_STATE (iface) != GST_STATE_NULL);
-}
-
-static void
-gst_xvimagesink_interface_init (GstInterfaceClass *klass)
-{
- klass->supported = gst_xvimagesink_interface_supported;
-}
-
-static void
-gst_xvimagesink_navigation_send_event (GstNavigation *navigation, GstStructure *structure)
-{
- GstXvImageSink *xvimagesink = GST_XVIMAGESINK (navigation);
- GstEvent *event;
- double x,y;
-
- event = gst_event_new (GST_EVENT_NAVIGATION);
- event->event_data.structure.structure = structure;
-
- /* Converting pointer coordinates to the non scaled geometry */
- if (gst_structure_get_double (structure, "pointer_x", &x))
- {
- x *= xvimagesink->width;
- x /= xvimagesink->xwindow->width;
- gst_structure_set (structure, "pointer_x", G_TYPE_DOUBLE, x, NULL);
- }
- if (gst_structure_get_double (structure, "pointer_y", &y))
- {
- y *= xvimagesink->height;
- y /= xvimagesink->xwindow->height;
- gst_structure_set (structure, "pointer_y", G_TYPE_DOUBLE, y, NULL);
- }
-
- gst_pad_send_event (gst_pad_get_peer (xvimagesink->sinkpad), event);
-}
-
-static void
-gst_xvimagesink_navigation_init (GstNavigationInterface *iface)
-{
- iface->send_event = gst_xvimagesink_navigation_send_event;
-}
-
/* X11 stuff */
/* This function handles GstXvImage creation depending on XShm availability */
@@ -293,6 +243,7 @@ gst_xvimagesink_xwindow_new (GstXvImageSink *xvimagesink,
xwindow->width = width;
xwindow->height = height;
+ xwindow->internal = TRUE;
g_mutex_lock (xvimagesink->x_lock);
@@ -325,7 +276,9 @@ gst_xvimagesink_xwindow_destroy (GstXvImageSink *xvimagesink, GstXWindow *xwindo
g_mutex_lock (xvimagesink->x_lock);
- XDestroyWindow (xvimagesink->xcontext->disp, xwindow->win);
+ /* If we did not create that window we just free the GC and let it live */
+ if (xwindow->internal)
+ XDestroyWindow (xvimagesink->xcontext->disp, xwindow->win);
XFreeGC (xvimagesink->xcontext->disp, xwindow->gc);
@@ -334,23 +287,6 @@ gst_xvimagesink_xwindow_destroy (GstXvImageSink *xvimagesink, GstXWindow *xwindo
g_free (xwindow);
}
-/* This function resizes a GstXWindow */
-/*static void
-gst_xvimagesink_xwindow_resize (GstXvImageSink *xvimagesink,
- GstXWindow *xwindow,
- gint width, gint height)
-{
- g_return_if_fail (xwindow != NULL);
- g_return_if_fail (xvimagesink != NULL);
- g_return_if_fail (GST_IS_XVIMAGESINK (xvimagesink));
-
- g_mutex_lock (xvimagesink->x_lock);
-
- XResizeWindow (xvimagesink->xcontext->disp, xwindow->win, width, height);
-
- g_mutex_unlock (xvimagesink->x_lock);
-} */
-
/* This function handles XEvents that might be in the queue. It generates
GstEvent that will be sent upstream in the pipeline to handle interactivity
and navigation. It will also listen for configure events on the window to
@@ -709,14 +645,6 @@ gst_xvimagesink_sinkconnect (GstPad *pad, GstCaps *caps)
xvimagesink->xwindow = gst_xvimagesink_xwindow_new (xvimagesink,
xvimagesink->width,
xvimagesink->height);
- else
- { /* We resize our window only if size has changed, preventing us from
- infinite loops with XConfigure events.
- if ( (xvimagesink->width != xvimagesink->xwindow->width) ||
- (xvimagesink->height != xvimagesink->xwindow->height) )
- gst_xvimagesink_xwindow_resize (xvimagesink, xvimagesink->xwindow,
- xvimagesink->width, xvimagesink->height);*/
- }
if ( (xvimagesink->xvimage) &&
( (xvimagesink->width != xvimagesink->xvimage->width) ||
@@ -733,6 +661,9 @@ gst_xvimagesink_sinkconnect (GstPad *pad, GstCaps *caps)
xvimagesink->width,
xvimagesink->height);
+ gst_x_overlay_got_video_size (GST_X_OVERLAY (xvimagesink),
+ xvimagesink->width, xvimagesink->height);
+
return GST_PAD_LINK_OK;
}
@@ -746,7 +677,8 @@ gst_xvimagesink_change_state (GstElement *element)
switch (GST_STATE_TRANSITION (element)) {
case GST_STATE_NULL_TO_READY:
/* Initializing the XContext */
- xvimagesink->xcontext = gst_xvimagesink_xcontext_get (xvimagesink);
+ if (!xvimagesink->xcontext)
+ xvimagesink->xcontext = gst_xvimagesink_xcontext_get (xvimagesink);
if (!xvimagesink->xcontext)
return GST_STATE_FAILURE;
break;
@@ -966,6 +898,104 @@ gst_xvimagesink_get_bufferpool (GstPad *pad)
return xvimagesink->bufferpool;
}
+/* Interfaces stuff */
+
+static gboolean
+gst_xvimagesink_interface_supported (GstInterface *iface, GType type)
+{
+ g_assert (type == GST_TYPE_NAVIGATION || type == GST_TYPE_X_OVERLAY);
+ return TRUE;
+}
+
+static void
+gst_xvimagesink_interface_init (GstInterfaceClass *klass)
+{
+ klass->supported = gst_xvimagesink_interface_supported;
+}
+
+static void
+gst_xvimagesink_navigation_send_event (GstNavigation *navigation, GstStructure *structure)
+{
+ GstXvImageSink *xvimagesink = GST_XVIMAGESINK (navigation);
+ GstEvent *event;
+ double x,y;
+
+ event = gst_event_new (GST_EVENT_NAVIGATION);
+ event->event_data.structure.structure = structure;
+
+ /* Converting pointer coordinates to the non scaled geometry */
+ if (gst_structure_get_double (structure, "pointer_x", &x))
+ {
+ x *= xvimagesink->width;
+ x /= xvimagesink->xwindow->width;
+ gst_structure_set (structure, "pointer_x", G_TYPE_DOUBLE, x, NULL);
+ }
+ if (gst_structure_get_double (structure, "pointer_y", &y))
+ {
+ y *= xvimagesink->height;
+ y /= xvimagesink->xwindow->height;
+ gst_structure_set (structure, "pointer_y", G_TYPE_DOUBLE, y, NULL);
+ }
+
+ gst_pad_send_event (gst_pad_get_peer (xvimagesink->sinkpad), event);
+}
+
+static void
+gst_xvimagesink_navigation_init (GstNavigationInterface *iface)
+{
+ iface->send_event = gst_xvimagesink_navigation_send_event;
+}
+
+static void
+gst_xvimagesink_set_xwindow_id (GstXOverlay *overlay, XID xwindow_id)
+{
+ GstXvImageSink *xvimagesink = GST_XVIMAGESINK (overlay);
+ GstXWindow *xwindow = NULL;
+ XWindowAttributes attr;
+
+ g_return_if_fail (xvimagesink != NULL);
+ g_return_if_fail (GST_IS_XVIMAGESINK (xvimagesink));
+
+ if (!xvimagesink->xcontext)
+ {
+ xvimagesink->xcontext = gst_xvimagesink_xcontext_get (xvimagesink);
+ }
+
+ if ( (xvimagesink->xwindow) && (xvimagesink->xvimage) )
+ { /* If we are replacing a window we destroy pictures and window as they
+ are associated */
+ gst_xvimagesink_xvimage_destroy (xvimagesink, xvimagesink->xvimage);
+ gst_xvimagesink_imagepool_clear (xvimagesink);
+ gst_xvimagesink_xwindow_destroy (xvimagesink, xvimagesink->xwindow);
+ }
+
+ xwindow = g_new0 (GstXWindow, 1);
+
+ xwindow->win = xwindow_id;
+
+ /* We get window geometry, set the event we want to receive, and create a GC */
+ g_mutex_lock (xvimagesink->x_lock);
+ XGetWindowAttributes (xvimagesink->xcontext->disp, xwindow->win, &attr);
+ xwindow->width = attr.width;
+ xwindow->height = attr.height;
+ xwindow->internal = FALSE;
+ XSelectInput (xvimagesink->xcontext->disp, xwindow->win, ExposureMask |
+ StructureNotifyMask | PointerMotionMask | KeyPressMask |
+ KeyReleaseMask /*| ButtonPressMask | ButtonReleaseMask*/);
+
+ xwindow->gc = XCreateGC (xvimagesink->xcontext->disp,
+ xwindow->win, 0, NULL);
+ g_mutex_unlock (xvimagesink->x_lock);
+
+ xvimagesink->xwindow = xwindow;
+}
+
+static void
+gst_xvimagesink_xoverlay_init (GstXOverlayClass *iface)
+{
+ iface->set_xwindow_id = gst_xvimagesink_set_xwindow_id;
+}
+
/* =========================================== */
/* */
/* Init & Class init */
@@ -1108,22 +1138,22 @@ gst_xvimagesink_get_type (void)
NULL,
NULL,
};
- /*static const GInterfaceInfo xoverlay_info = {
+ static const GInterfaceInfo overlay_info = {
(GInterfaceInitFunc) gst_xvimagesink_xoverlay_init,
NULL,
NULL,
- };*/
+ };
xvimagesink_type = g_type_register_static (GST_TYPE_ELEMENT,
"GstXvImageSink",
&xvimagesink_info, 0);
g_type_add_interface_static (xvimagesink_type, GST_TYPE_INTERFACE,
- &iface_info);
+ &iface_info);
g_type_add_interface_static (xvimagesink_type, GST_TYPE_NAVIGATION,
- &navigation_info);
- /*g_type_add_interface_static (xvimagesink_type, GST_TYPE_X_OVERLAY,
- &xoverlay_info);*/
+ &navigation_info);
+ g_type_add_interface_static (xvimagesink_type, GST_TYPE_X_OVERLAY,
+ &overlay_info);
}
return xvimagesink_type;
diff --git a/sys/xvimage/xvimagesink.h b/sys/xvimage/xvimagesink.h
index 4296a0ee3..070f269a7 100644
--- a/sys/xvimage/xvimagesink.h
+++ b/sys/xvimage/xvimagesink.h
@@ -94,6 +94,7 @@ struct _GstXContext {
struct _GstXWindow {
Window win;
gint width, height;
+ gboolean internal;
GC gc;
};