mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-01-11 18:05:37 +00:00
wayland: Add support for RGBx and RGBA formats
Wayland interface could offer two buffers pixels formats: WL_SHM_FORMAT_XRGB8888 and WL_SHM_FORMAT_ARGB8888. Update waylandsink to support them and check if the format is really available. https://bugzilla.gnome.org/show_bug.cgi?id=702112
This commit is contained in:
parent
67e71d7931
commit
3fc6f1d9b7
3 changed files with 77 additions and 10 deletions
|
@ -59,13 +59,17 @@ enum
|
||||||
GST_DEBUG_CATEGORY (gstwayland_debug);
|
GST_DEBUG_CATEGORY (gstwayland_debug);
|
||||||
#define GST_CAT_DEFAULT gstwayland_debug
|
#define GST_CAT_DEFAULT gstwayland_debug
|
||||||
|
|
||||||
|
#if G_BYTE_ORDER == G_BIG_ENDIAN
|
||||||
|
#define CAPS "{xRGB, ARGB}"
|
||||||
|
#else
|
||||||
|
#define CAPS "{BGRx, BGRA}"
|
||||||
|
#endif
|
||||||
|
|
||||||
static GstStaticPadTemplate sink_template = GST_STATIC_PAD_TEMPLATE ("sink",
|
static GstStaticPadTemplate sink_template = GST_STATIC_PAD_TEMPLATE ("sink",
|
||||||
GST_PAD_SINK,
|
GST_PAD_SINK,
|
||||||
GST_PAD_ALWAYS,
|
GST_PAD_ALWAYS,
|
||||||
GST_STATIC_CAPS ("video/x-raw, "
|
GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE (CAPS))
|
||||||
"format = (string) BGRA, "
|
);
|
||||||
"framerate = (fraction) [ 0, MAX ], "
|
|
||||||
"width = (int) [ 1, MAX ], " "height = (int) [ 1, MAX ] "));
|
|
||||||
|
|
||||||
/*Fixme: Add more interfaces */
|
/*Fixme: Add more interfaces */
|
||||||
#define gst_wayland_sink_parent_class parent_class
|
#define gst_wayland_sink_parent_class parent_class
|
||||||
|
@ -97,6 +101,48 @@ static void create_window (GstWaylandSink * sink, struct display *display,
|
||||||
int width, int height);
|
int width, int height);
|
||||||
static void shm_pool_destroy (struct shm_pool *pool);
|
static void shm_pool_destroy (struct shm_pool *pool);
|
||||||
|
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
uint32_t wl_format;
|
||||||
|
GstVideoFormat gst_format;
|
||||||
|
} wl_VideoFormat;
|
||||||
|
|
||||||
|
static const wl_VideoFormat formats[] = {
|
||||||
|
#if G_BYTE_ORDER == G_BIG_ENDIAN
|
||||||
|
{WL_SHM_FORMAT_XRGB8888, GST_VIDEO_FORMAT_xRGB},
|
||||||
|
{WL_SHM_FORMAT_ARGB8888, GST_VIDEO_FORMAT_ARGB},
|
||||||
|
#else
|
||||||
|
{WL_SHM_FORMAT_XRGB8888, GST_VIDEO_FORMAT_BGRx},
|
||||||
|
{WL_SHM_FORMAT_ARGB8888, GST_VIDEO_FORMAT_BGRA},
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
static uint32_t
|
||||||
|
gst_wayland_format_to_wl_format (GstVideoFormat format)
|
||||||
|
{
|
||||||
|
guint i;
|
||||||
|
|
||||||
|
for (i = 0; i < G_N_ELEMENTS (formats); i++)
|
||||||
|
if (formats[i].gst_format == format)
|
||||||
|
return formats[i].wl_format;
|
||||||
|
|
||||||
|
GST_WARNING ("wayland video format not found");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static const gchar *
|
||||||
|
gst_wayland_format_to_string (uint32_t wl_format)
|
||||||
|
{
|
||||||
|
guint i;
|
||||||
|
GstVideoFormat format = GST_VIDEO_FORMAT_UNKNOWN;
|
||||||
|
|
||||||
|
for (i = 0; i < G_N_ELEMENTS (formats); i++)
|
||||||
|
if (formats[i].wl_format == wl_format)
|
||||||
|
format = formats[i].gst_format;
|
||||||
|
|
||||||
|
return gst_video_format_to_string (format);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
gst_wayland_sink_class_init (GstWaylandSinkClass * klass)
|
gst_wayland_sink_class_init (GstWaylandSinkClass * klass)
|
||||||
{
|
{
|
||||||
|
@ -317,16 +363,27 @@ create_display (void)
|
||||||
|
|
||||||
wl_display_roundtrip (display->display);
|
wl_display_roundtrip (display->display);
|
||||||
|
|
||||||
if (!(display->formats & (1 << WL_SHM_FORMAT_XRGB8888))) {
|
|
||||||
GST_ERROR ("WL_SHM_FORMAT_XRGB32 not available");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
wl_display_get_fd (display->display);
|
wl_display_get_fd (display->display);
|
||||||
|
|
||||||
return display;
|
return display;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gst_wayland_sink_format_from_caps (uint32_t * wl_format, GstCaps * caps)
|
||||||
|
{
|
||||||
|
GstStructure *structure;
|
||||||
|
const gchar *format;
|
||||||
|
GstVideoFormat fmt;
|
||||||
|
|
||||||
|
structure = gst_caps_get_structure (caps, 0);
|
||||||
|
format = gst_structure_get_string (structure, "format");
|
||||||
|
fmt = gst_video_format_from_string (format);
|
||||||
|
|
||||||
|
*wl_format = gst_wayland_format_to_wl_format (fmt);
|
||||||
|
|
||||||
|
return (*wl_format != -1);
|
||||||
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
gst_wayland_sink_set_caps (GstBaseSink * bsink, GstCaps * caps)
|
gst_wayland_sink_set_caps (GstBaseSink * bsink, GstCaps * caps)
|
||||||
{
|
{
|
||||||
|
@ -344,6 +401,15 @@ gst_wayland_sink_set_caps (GstBaseSink * bsink, GstCaps * caps)
|
||||||
if (!gst_video_info_from_caps (&info, caps))
|
if (!gst_video_info_from_caps (&info, caps))
|
||||||
goto invalid_format;
|
goto invalid_format;
|
||||||
|
|
||||||
|
if (!gst_wayland_sink_format_from_caps (&sink->format, caps))
|
||||||
|
goto invalid_format;
|
||||||
|
|
||||||
|
if (!(sink->display->formats & (1 << sink->format))) {
|
||||||
|
GST_DEBUG_OBJECT (sink, "%s not available",
|
||||||
|
gst_wayland_format_to_string (sink->format));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
sink->video_width = info.width;
|
sink->video_width = info.width;
|
||||||
sink->video_height = info.height;
|
sink->video_height = info.height;
|
||||||
size = info.size;
|
size = info.size;
|
||||||
|
|
|
@ -103,6 +103,7 @@ struct _GstWaylandSink
|
||||||
|
|
||||||
gint video_width;
|
gint video_width;
|
||||||
gint video_height;
|
gint video_height;
|
||||||
|
uint32_t format;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct _GstWaylandSinkClass
|
struct _GstWaylandSinkClass
|
||||||
|
|
|
@ -233,7 +233,7 @@ gst_buffer_add_wayland_meta (GstBuffer * buffer, GstWaylandBufferPool * wpool)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
wmeta->wbuffer = wl_shm_pool_create_buffer (sink->shm_pool->pool, offset,
|
wmeta->wbuffer = wl_shm_pool_create_buffer (sink->shm_pool->pool, offset,
|
||||||
sink->video_width, sink->video_height, stride, WL_SHM_FORMAT_XRGB8888);
|
sink->video_width, sink->video_height, stride, sink->format);
|
||||||
|
|
||||||
wmeta->data = data;
|
wmeta->data = data;
|
||||||
wmeta->size = size;
|
wmeta->size = size;
|
||||||
|
|
Loading…
Reference in a new issue