summaryrefslogtreecommitdiffstats
path: root/video
diff options
context:
space:
mode:
authorLaserEyess <lasereyess@users.noreply.github.com>2022-11-15 20:52:56 -0500
committerDudemanguy <random342@airmail.cc>2022-11-20 19:13:59 +0000
commita62f71bfbeb8f35bf5f09f12e48b63505c475750 (patch)
tree019ec5e071e6ca90214f6f3623037eb2b540a696 /video
parent303178e6451da7072aa71ce5e3cbffc233d6dbd1 (diff)
downloadmpv-a62f71bfbeb8f35bf5f09f12e48b63505c475750.tar.bz2
mpv-a62f71bfbeb8f35bf5f09f12e48b63505c475750.tar.xz
vo_dmabuf_wayland: use single-pixel-buffer-v1
The new single-pixel-buffer protocol is designed to optimize the case for using a solid color as an underlay wl_surface. It works the same as the wl_shm 1x1 pixel trick currently used, but it allows the compositor to make optimizations with more certainty than the wl_shm trick.
Diffstat (limited to 'video')
-rw-r--r--video/out/vo_dmabuf_wayland.c48
-rw-r--r--video/out/wayland_common.c15
-rw-r--r--video/out/wayland_common.h4
3 files changed, 49 insertions, 18 deletions
diff --git a/video/out/vo_dmabuf_wayland.c b/video/out/vo_dmabuf_wayland.c
index 24ced832ab..e6ce97f643 100644
--- a/video/out/vo_dmabuf_wayland.c
+++ b/video/out/vo_dmabuf_wayland.c
@@ -41,9 +41,15 @@
#include "present_sync.h"
#include "wayland_common.h"
#include "wlbuf_pool.h"
+
+// Generated from wayland-protocols
#include "generated/wayland/linux-dmabuf-unstable-v1.h"
#include "generated/wayland/viewporter.h"
+#if HAVE_WAYLAND_PROTOCOLS_1_27
+#include "generated/wayland/single-pixel-buffer-v1.h"
+#endif
+
struct priv {
struct mp_log *log;
struct ra_ctx *ctx;
@@ -238,24 +244,6 @@ static int query_format(struct vo *vo, int format)
static int reconfig(struct vo *vo, struct mp_image_params *params)
{
- struct priv *p = vo->priv;
- struct vo_wayland_state *wl = vo->wl;
-
- if (!p->solid_buffer_pool) {
- int width = 1;
- int height = 1;
- int stride = MP_ALIGN_UP(width * 4, 16);
- int fd = vo_wayland_allocate_memfd(vo, stride);
- if (fd < 0)
- return VO_ERROR;
- p->solid_buffer_pool = wl_shm_create_pool(wl->shm, fd, height * stride);
- if (!p->solid_buffer_pool)
- return VO_ERROR;
- p->solid_buffer = wl_shm_pool_create_buffer(p->solid_buffer_pool, 0, width, height, stride, WL_SHM_FORMAT_XRGB8888);
- if (!p->solid_buffer)
- return VO_ERROR;
- wl_surface_attach(wl->surface, p->solid_buffer, 0, 0);
- }
if (!vo_wayland_reconfig(vo))
return VO_ERROR;
@@ -354,6 +342,30 @@ static int preinit(struct vo *vo)
return VO_ERROR;
}
+
+ if (vo->wl->single_pixel_manager) {
+#if HAVE_WAYLAND_PROTOCOLS_1_27
+ p->solid_buffer = wp_single_pixel_buffer_manager_v1_create_u32_rgba_buffer(
+ vo->wl->single_pixel_manager, 0, 0, 0, UINT32_MAX); /* R, G, B, A */
+#endif
+ } else {
+ int width = 1;
+ int height = 1;
+ int stride = MP_ALIGN_UP(width * 4, 16);
+ int fd = vo_wayland_allocate_memfd(vo, stride);
+ if (fd < 0)
+ return VO_ERROR;
+ p->solid_buffer_pool = wl_shm_create_pool(vo->wl->shm, fd, height * stride);
+ if (!p->solid_buffer_pool)
+ return VO_ERROR;
+ p->solid_buffer = wl_shm_pool_create_buffer(
+ p->solid_buffer_pool, 0, width, height, stride, WL_SHM_FORMAT_XRGB8888);
+ }
+ if (!p->solid_buffer)
+ return VO_ERROR;
+
+ wl_surface_attach(vo->wl->surface, p->solid_buffer, 0, 0);
+
vo->hwdec_devs = hwdec_devices_create();
hwdec_devices_set_loader(vo->hwdec_devs, call_request_hwdec_api, vo);
assert(!p->hwdec_ctx.ra);
diff --git a/video/out/wayland_common.c b/video/out/wayland_common.c
index ebcce69df2..7987dcef44 100644
--- a/video/out/wayland_common.c
+++ b/video/out/wayland_common.c
@@ -44,6 +44,7 @@
#if HAVE_WAYLAND_PROTOCOLS_1_27
#include "generated/wayland/content-type-v1.h"
+#include "generated/wayland/single-pixel-buffer-v1.h"
#endif
#if WAYLAND_VERSION_MAJOR > 1 || WAYLAND_VERSION_MINOR >= 20
@@ -1240,6 +1241,10 @@ static void registry_handle_add(void *data, struct wl_registry *reg, uint32_t id
if (!strcmp(interface, wp_content_type_manager_v1_interface.name) && found++) {
wl->content_type_manager = wl_registry_bind(reg, id, &wp_content_type_manager_v1_interface, 1);
}
+
+ if (!strcmp(interface, wp_single_pixel_buffer_manager_v1_interface.name) && found++) {
+ wl->single_pixel_manager = wl_registry_bind(reg, id, &wp_single_pixel_buffer_manager_v1_interface, 1);
+ }
#endif
if (!strcmp(interface, wp_presentation_interface.name) && found++) {
@@ -2007,6 +2012,11 @@ int vo_wayland_init(struct vo *vo)
MP_VERBOSE(wl, "Compositor doesn't support the %s protocol!\n",
wp_content_type_manager_v1_interface.name);
}
+
+ if (!wl->single_pixel_manager) {
+ MP_VERBOSE(wl, "Compositor doesn't support the %s protocol!\n",
+ wp_single_pixel_buffer_manager_v1_interface.name);
+ }
#endif
if (wl->dnd_devman && wl->seat) {
@@ -2225,6 +2235,11 @@ void vo_wayland_uninit(struct vo *vo)
if (wl->shm)
wl_shm_destroy(wl->shm);
+#if HAVE_WAYLAND_PROTOCOLS_1_27
+ if (wl->single_pixel_manager)
+ wp_single_pixel_buffer_manager_v1_destroy(wl->single_pixel_manager);
+#endif
+
if (wl->surface)
wl_surface_destroy(wl->surface);
diff --git a/video/out/wayland_common.h b/video/out/wayland_common.h
index 627ea0d057..4f505b903b 100644
--- a/video/out/wayland_common.h
+++ b/video/out/wayland_common.h
@@ -106,6 +106,10 @@ struct vo_wayland_state {
int64_t refresh_interval;
bool use_present;
+ /* single-pixel-buffer */
+ /* TODO: unvoid this if required wayland-protocols is bumped to 1.27+ */
+ void *single_pixel_manager;
+
/* xdg-decoration */
struct zxdg_decoration_manager_v1 *xdg_decoration_manager;
struct zxdg_toplevel_decoration_v1 *xdg_toplevel_decoration;