Commit c7514e8f authored by Kristian Høgsberg's avatar Kristian Høgsberg

Merge branch 'gdk-backend-wayland'

Conflicts:
	Makefile.am
	configure.ac
	gdk/Makefile.am
	gtk/gtksettings.c
	gtk/gtkwindow.c
parents 85c1c22d fcd58b0f
......@@ -55,11 +55,11 @@ MAINTAINERCLEANFILES = \
## Copy .pc files to target-specific names
gtk+-x11-3.0.pc gtk+-win32-3.0.pc gtk+-quartz-3.0.pc gtk+-broadway-3.0.pc: gtk+-3.0.pc
gtk+-x11-3.0.pc gtk+-win32-3.0.pc gtk+-quartz-3.0.pc gtk+-broadway-3.0.pc gtk+-wayland-3.0.pc: gtk+-3.0.pc
rm -f $@ && \
cp gtk+-3.0.pc $@
gdk-x11-3.0.pc gdk-win32-3.0.pc gdk-quartz-3.0.pc gdk-broadway-3.0.pc: gdk-3.0.pc
gdk-x11-3.0.pc gdk-win32-3.0.pc gdk-quartz-3.0.pc gdk-broadway-3.0.pc gdk-wayland-3.0.pc: gdk-3.0.pc
rm -f $@ && \
cp gdk-3.0.pc $@
......
......@@ -301,6 +301,10 @@ AC_ARG_ENABLE(broadway-backend,
[AC_HELP_STRING([--enable-broadway-backend],
[enable the broadway (HTML5) gdk backend])],
[backend_set=yes])
AC_ARG_ENABLE(wayland-backend,
[AC_HELP_STRING([--enable-wayland-backend],
[enable the wayland gdk backend])],
[backend_set=yes])
if test -z "$backend_set"; then
if test "$platform_win32" = yes; then
......@@ -356,6 +360,7 @@ else
AM_CONDITIONAL(USE_QUARTZ, false)
fi
if test "x$enable_broadway_backend" == xyes; then
GDK_BACKENDS="$GDK_BACKENDS broadway"
cairo_backends="$cairo_backends cairo"
......@@ -367,6 +372,19 @@ else
AM_CONDITIONAL(USE_BROADWAY, false)
fi
if test "x$enable_wayland_backend" == "xyes"; then
# Wayland uses cairo-gl
cairo_backends="$cairo_backends cairo-gl"
GDK_BACKENDS="$GDK_BACKENDS wayland"
GIO_PACKAGE=gio-unix-2.0
GDK_WINDOWING="$GDK_WINDOWING
#define GDK_WINDOWING_WAYLAND"
WAYLAND_PACKAGES="wayland-client xkbcommon wayland-egl"
AM_CONDITIONAL(USE_WAYLAND, true)
else
AM_CONDITIONAL(USE_WAYLAND, false)
fi
# strip leading space
GDK_BACKENDS=${GDK_BACKENDS#* }
......@@ -1223,7 +1241,7 @@ fi
CFLAGS="$saved_cflags"
LDFLAGS="$saved_ldflags"
GDK_PACKAGES="$PANGO_PACKAGES $GIO_PACKAGE $X_PACKAGES gdk-pixbuf-2.0 $cairo_backends cairo-gobject"
GDK_PACKAGES="$PANGO_PACKAGES $GIO_PACKAGE $X_PACKAGES $WAYLAND_PACKAGES gdk-pixbuf-2.0 $cairo_backends cairo-gobject"
GDK_DEP_LIBS="$GDK_EXTRA_LIBS `$PKG_CONFIG --libs $GDK_PACKAGES`"
GDK_DEP_CFLAGS="`$PKG_CONFIG --cflags gthread-2.0 $GDK_PACKAGES` $GDK_EXTRA_CFLAGS"
......@@ -1651,6 +1669,7 @@ gdk/win32/Makefile
gdk/win32/rc/Makefile
gdk/win32/rc/gdk.rc
gdk/quartz/Makefile
gdk/wayland/Makefile
gdk/tests/Makefile
gtk/Makefile
gtk/makefile.msc
......
......@@ -11,7 +11,7 @@ INTROSPECTION_COMPILER_ARGS = \
SUBDIRS = $(GDK_BACKENDS) . tests
DIST_SUBDIRS = win32 x11 quartz broadway tests
DIST_SUBDIRS = win32 x11 quartz broadway wayland tests
CLEANFILES =
......@@ -177,6 +177,10 @@ if USE_BROADWAY
libgdk_3_la_LIBADD += broadway/libgdk-broadway.la
endif # USE_BROADWAY
if USE_WAYLAND
libgdk_3_la_LIBADD += wayland/libgdk-wayland.la
endif
if HAVE_INTROSPECTION
introspection_files = \
......
......@@ -52,6 +52,10 @@
#include "win32/gdkwin32.h"
#endif
#ifdef GDK_WINDOWING_WAYLAND
#include "wayland/gdkwayland.h"
#endif
/**
* SECTION:gdkdisplaymanager
* @Short_description: Maintains a list of all open GdkDisplays
......@@ -239,6 +243,11 @@ gdk_display_manager_get (void)
manager = g_object_new (gdk_win32_display_manager_get_type (), NULL);
else
#endif
#ifdef GDK_WINDOWING_WAYLAND
if (backend == NULL || strcmp (backend, "wayland") == 0)
manager = g_object_new (gdk_wayland_display_manager_get_type (), NULL);
else
#endif
#ifdef GDK_WINDOWING_X11
if (backend == NULL || strcmp (backend, "x11") == 0)
manager = g_object_new (gdk_x11_display_manager_get_type (), NULL);
......
## Process this file with automake to produce Makefile.in
include $(top_srcdir)/Makefile.decl
libgdkincludedir = $(includedir)/gtk-3.0/gdk
INCLUDES = \
-DG_LOG_DOMAIN=\"Gdk\" \
-DGDK_COMPILATION \
-I$(top_srcdir) \
-I$(top_srcdir)/gdk \
-I$(top_builddir)/gdk \
$(GTK_DEBUG_FLAGS) \
$(GDK_DEP_CFLAGS)
LDADDS = $(GDK_DEP_LIBS)
noinst_LTLIBRARIES = \
libgdk-wayland.la
libgdk_wayland_la_SOURCES = \
gdkapplaunchcontext-wayland.c \
gdkcursor-wayland.c \
gdkdevice-wayland.c \
gdkdisplay-wayland.c \
gdkdisplay-wayland.h \
gdkdisplaymanager-wayland.c \
gdkdnd-wayland.c \
gdkeventsource.c \
gdkkeys-wayland.c \
gdkscreen-wayland.c \
gdkscreen-wayland.h \
gdkselection-wayland.c \
gdkwindow-wayland.c \
gdkwayland.h \
gdkprivate-wayland.h
libgdkinclude_HEADERS = \
gdkwayland.h
-include $(top_srcdir)/git.mk
/*
* Copyright © 2010 Intel Corporation
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser 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.
*/
#include "config.h"
#include <string.h>
#include <unistd.h>
#include <glib.h>
#include <gio/gdesktopappinfo.h>
#include "gdkwayland.h"
#include "gdkprivate-wayland.h"
#include "gdkapplaunchcontextprivate.h"
#include "gdkscreen.h"
#include "gdkinternals.h"
#include "gdkintl.h"
static char *
gdk_wayland_app_launch_context_get_startup_notify_id (GAppLaunchContext *context,
GAppInfo *info,
GList *files)
{
return NULL;
}
static void
gdk_wayland_app_launch_context_launch_failed (GAppLaunchContext *context,
const char *startup_notify_id)
{
}
typedef struct _GdkWaylandAppLaunchContext GdkWaylandAppLaunchContext;
typedef struct _GdkWaylandAppLaunchContextClass GdkWaylandAppLaunchContextClass;
struct _GdkWaylandAppLaunchContext
{
GdkAppLaunchContext base;
gchar *name;
guint serial;
};
struct _GdkWaylandAppLaunchContextClass
{
GdkAppLaunchContextClass base_class;
};
G_DEFINE_TYPE (GdkWaylandAppLaunchContext, gdk_wayland_app_launch_context, GDK_TYPE_APP_LAUNCH_CONTEXT)
static void
gdk_wayland_app_launch_context_class_init (GdkWaylandAppLaunchContextClass *klass)
{
GAppLaunchContextClass *ctx_class = G_APP_LAUNCH_CONTEXT_CLASS (klass);
ctx_class->get_startup_notify_id = gdk_wayland_app_launch_context_get_startup_notify_id;
ctx_class->launch_failed = gdk_wayland_app_launch_context_launch_failed;
}
static void
gdk_wayland_app_launch_context_init (GdkWaylandAppLaunchContext *ctx)
{
}
GdkAppLaunchContext *
_gdk_wayland_display_get_app_launch_context (GdkDisplay *display)
{
GdkAppLaunchContext *ctx;
ctx = g_object_new (gdk_wayland_app_launch_context_get_type (),
"display", display,
NULL);
return ctx;
}
/* GDK - The GIMP Drawing Kit
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser 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.
*/
/*
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
* file for a list of people on the GTK+ Team. See the ChangeLog
* files for a list of changes. These files are distributed with
* GTK+ at ftp://ftp.gtk.org/pub/gtk/.
*/
#include "config.h"
#define GDK_PIXBUF_ENABLE_BACKEND
#include <string.h>
#include "gdkprivate-wayland.h"
#include "gdkcursorprivate.h"
#include "gdkdisplay-wayland.h"
#include "gdkwayland.h"
#include <gdk-pixbuf/gdk-pixbuf.h>
#include <sys/mman.h>
#define GDK_TYPE_WAYLAND_CURSOR (_gdk_wayland_cursor_get_type ())
#define GDK_WAYLAND_CURSOR(object) (G_TYPE_CHECK_INSTANCE_CAST ((object), GDK_TYPE_WAYLAND_CURSOR, GdkWaylandCursor))
#define GDK_WAYLAND_CURSOR_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GDK_TYPE_WAYLAND_CURSOR, GdkWaylandCursorClass))
#define GDK_IS_WAYLAND_CURSOR(object) (G_TYPE_CHECK_INSTANCE_TYPE ((object), GDK_TYPE_WAYLAND_CURSOR))
#define GDK_IS_WAYLAND_CURSOR_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GDK_TYPE_WAYLAND_CURSOR))
#define GDK_WAYLAND_CURSOR_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GDK_TYPE_WAYLAND_CURSOR, GdkWaylandCursorClass))
typedef struct _GdkWaylandCursor GdkWaylandCursor;
typedef struct _GdkWaylandCursorClass GdkWaylandCursorClass;
struct _GdkWaylandCursor
{
GdkCursor cursor;
gchar *name;
guint serial;
int x, y, width, height, size;
void *map;
struct wl_buffer *buffer;
};
struct _GdkWaylandCursorClass
{
GdkCursorClass cursor_class;
};
G_DEFINE_TYPE (GdkWaylandCursor, _gdk_wayland_cursor, GDK_TYPE_CURSOR)
static guint theme_serial = 0;
static void
gdk_wayland_cursor_finalize (GObject *object)
{
GdkWaylandCursor *cursor = GDK_WAYLAND_CURSOR (object);
g_free (cursor->name);
G_OBJECT_CLASS (_gdk_wayland_cursor_parent_class)->finalize (object);
}
static GdkPixbuf*
gdk_wayland_cursor_get_image (GdkCursor *cursor)
{
return NULL;
}
struct wl_buffer *
_gdk_wayland_cursor_get_buffer (GdkCursor *cursor, int *x, int *y)
{
GdkWaylandCursor *wayland_cursor = GDK_WAYLAND_CURSOR (cursor);
*x = wayland_cursor->x;
*y = wayland_cursor->y;
return wayland_cursor->buffer;
}
static void
_gdk_wayland_cursor_class_init (GdkWaylandCursorClass *wayland_cursor_class)
{
GdkCursorClass *cursor_class = GDK_CURSOR_CLASS (wayland_cursor_class);
GObjectClass *object_class = G_OBJECT_CLASS (wayland_cursor_class);
object_class->finalize = gdk_wayland_cursor_finalize;
cursor_class->get_image = gdk_wayland_cursor_get_image;
}
static void
_gdk_wayland_cursor_init (GdkWaylandCursor *cursor)
{
}
static void
set_pixbuf (GdkWaylandCursor *cursor, GdkPixbuf *pixbuf)
{
int stride, i, n_channels;
unsigned char *pixels, *end, *argb_pixels, *s, *d;
stride = gdk_pixbuf_get_rowstride(pixbuf);
pixels = gdk_pixbuf_get_pixels(pixbuf);
n_channels = gdk_pixbuf_get_n_channels(pixbuf);
argb_pixels = cursor->map;
#define MULT(_d,c,a,t) \
do { t = c * a + 0x7f; _d = ((t >> 8) + t) >> 8; } while (0)
if (n_channels == 4)
{
for (i = 0; i < cursor->height; i++)
{
s = pixels + i * stride;
end = s + cursor->width * 4;
d = argb_pixels + i * cursor->width * 4;
while (s < end)
{
unsigned int t;
MULT(d[0], s[2], s[3], t);
MULT(d[1], s[1], s[3], t);
MULT(d[2], s[0], s[3], t);
d[3] = s[3];
s += 4;
d += 4;
}
}
}
else if (n_channels == 3)
{
for (i = 0; i < cursor->height; i++)
{
s = pixels + i * stride;
end = s + cursor->width * 3;
d = argb_pixels + i * cursor->width * 4;
while (s < end)
{
d[0] = s[2];
d[1] = s[1];
d[2] = s[0];
d[3] = 0xff;
s += 3;
d += 4;
}
}
}
}
static GdkCursor *
create_cursor(GdkDisplayWayland *display, GdkPixbuf *pixbuf, int x, int y)
{
GdkWaylandCursor *cursor;
struct wl_visual *visual;
int stride, fd;
char *filename;
GError *error = NULL;
cursor = g_object_new (GDK_TYPE_WAYLAND_CURSOR,
"cursor-type", GDK_CURSOR_IS_PIXMAP,
"display", display,
NULL);
cursor->name = NULL;
cursor->serial = theme_serial;
cursor->x = x;
cursor->y = y;
if (pixbuf)
{
cursor->width = gdk_pixbuf_get_width (pixbuf);
cursor->height = gdk_pixbuf_get_height (pixbuf);
}
else
{
cursor->width = 1;
cursor->height = 1;
}
stride = cursor->width * 4;
cursor->size = stride * cursor->height;
fd = g_file_open_tmp("wayland-shm-XXXXXX", &filename, &error);
if (fd < 0) {
fprintf(stderr, "g_file_open_tmp failed: %s\n", error->message);
g_error_free (error);
return NULL;
}
unlink (filename);
g_free (filename);
if (ftruncate(fd, cursor->size) < 0) {
fprintf(stderr, "ftruncate failed: %m\n");
close(fd);
return NULL;
}
cursor->map = mmap(NULL, cursor->size,
PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
if (cursor->map == MAP_FAILED) {
fprintf(stderr, "mmap failed: %m\n");
close(fd);
return NULL;
}
if (pixbuf)
set_pixbuf (cursor, pixbuf);
else
memset (cursor->map, 0, 4);
visual = wl_display_get_premultiplied_argb_visual(display->wl_display);
cursor->buffer = wl_shm_create_buffer(display->shm,
fd,
cursor->width,
cursor->height,
stride, visual);
close(fd);
return GDK_CURSOR (cursor);
}
#define DATADIR "/usr/share/wayland"
static const struct {
GdkCursorType type;
const char *filename;
int hotspot_x, hotspot_y;
} cursor_definitions[] = {
{ GDK_BLANK_CURSOR, NULL, 0, 0 },
{ GDK_HAND1, DATADIR "/hand1.png", 18, 11 },
{ GDK_HAND2, DATADIR "/hand2.png", 14, 8 },
{ GDK_LEFT_PTR, DATADIR "/left_ptr.png", 10, 5 },
{ GDK_SB_H_DOUBLE_ARROW, DATADIR "/sb_h_double_arrow.png", 15, 15 },
{ GDK_SB_V_DOUBLE_ARROW, DATADIR "/sb_v_double_arrow.png", 15, 15 },
{ GDK_XTERM, DATADIR "/xterm.png", 15, 15 },
{ GDK_BOTTOM_RIGHT_CORNER, DATADIR "/bottom_right_corner.png", 28, 28 }
};
GdkCursor *
_gdk_wayland_display_get_cursor_for_type (GdkDisplay *display,
GdkCursorType cursor_type)
{
GdkDisplayWayland *wayland_display;
GdkPixbuf *pixbuf;
GError *error = NULL;
int i;
for (i = 0; i < G_N_ELEMENTS (cursor_definitions); i++)
{
if (cursor_definitions[i].type == cursor_type)
break;
}
if (i == G_N_ELEMENTS (cursor_definitions))
{
g_warning("unhandled cursor type %d, falling back to blank\n",
cursor_type);
i = 0;
}
wayland_display = GDK_DISPLAY_WAYLAND (display);
if (!wayland_display->cursors)
wayland_display->cursors =
g_new0 (GdkCursor *, G_N_ELEMENTS(cursor_definitions));
if (wayland_display->cursors[i])
return g_object_ref (wayland_display->cursors[i]);
GDK_NOTE (CURSOR,
g_message ("creating new cursor for type %d, filename %s",
cursor_type, cursor_definitions[i].filename));
if (cursor_type != GDK_BLANK_CURSOR)
pixbuf = gdk_pixbuf_new_from_file(cursor_definitions[i].filename, &error);
else
pixbuf = NULL;
if (error != NULL)
{
GDK_NOTE (CURSOR,
g_message ("failed to load %s: %s",
cursor_definitions[i].filename, error->message));
g_error_free(error);
return NULL;
}
wayland_display->cursors[i] =
create_cursor(wayland_display, pixbuf,
cursor_definitions[i].hotspot_x,
cursor_definitions[i].hotspot_y);
if (pixbuf)
g_object_unref (pixbuf);
return g_object_ref (wayland_display->cursors[i]);
}
GdkCursor*
_gdk_wayland_display_get_cursor_for_name (GdkDisplay *display,
const gchar *name)
{
GdkWaylandCursor *private;
g_return_val_if_fail (GDK_IS_DISPLAY (display), NULL);
private = g_object_new (GDK_TYPE_WAYLAND_CURSOR,
"cursor-type", GDK_CURSOR_IS_PIXMAP,
"display", display,
NULL);
private->name = g_strdup (name);
private->serial = theme_serial;
return GDK_CURSOR (private);
}
GdkCursor *
_gdk_wayland_display_get_cursor_for_pixbuf (GdkDisplay *display,
GdkPixbuf *pixbuf,
gint x,
gint y)
{
GdkWaylandCursor *private;
g_return_val_if_fail (GDK_IS_DISPLAY (display), NULL);
g_return_val_if_fail (GDK_IS_PIXBUF (pixbuf), NULL);
g_return_val_if_fail (0 <= x && x < gdk_pixbuf_get_width (pixbuf), NULL);
g_return_val_if_fail (0 <= y && y < gdk_pixbuf_get_height (pixbuf), NULL);
private = g_object_new (GDK_TYPE_WAYLAND_CURSOR,
"cursor-type", GDK_CURSOR_IS_PIXMAP,
"display", display,
NULL);
private->name = NULL;
private->serial = theme_serial;
return GDK_CURSOR (private);
}
void
_gdk_wayland_display_get_default_cursor_size (GdkDisplay *display,
guint *width,
guint *height)
{
/* FIXME: wayland settings? */
*width = 64;
*height = 64;
}
void
_gdk_wayland_display_get_maximal_cursor_size (GdkDisplay *display,
guint *width,
guint *height)
{
*width = 256;
*height = 256;
}
gboolean
_gdk_wayland_display_supports_cursor_alpha (GdkDisplay *display)
{
return TRUE;
}
gboolean
_gdk_wayland_display_supports_cursor_color (GdkDisplay *display)
{
return TRUE;
}
This diff is collapsed.
/*
* Copyright © 2010 Intel Corporation
*
* 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.
*/
#include "config.h"
#include <wayland-egl.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
#include <fcntl.h>
#include <glib.h>
#include "gdkwayland.h"
#include "gdkdisplay.h"
#include "gdkdisplay-wayland.h"
#include "gdkscreen.h"
#include "gdkinternals.h"
#include "gdkdeviceprivate.h"
#include "gdkdevicemanager.h"
#include "gdkkeysprivate.h"
#include "gdkprivate-wayland.h"
G_DEFINE_TYPE (GdkDisplayWayland, _gdk_display_wayland, GDK_TYPE_DISPLAY)
static void
gdk_input_init (GdkDisplay *display)
{
GdkDisplayWayland *display_wayland;
GdkDeviceManager *device_manager;
GdkDevice *device;
GList *list, *l;
display_wayland = GDK_DISPLAY_WAYLAND (display);
device_manager = gdk_display_get_device_manager (display);
/* For backwards compatibility, just add
* floating devices that are not keyboards.
*/
list = gdk_device_manager_list_devices (device_manager, GDK_DEVICE_TYPE_FLOATING);
for (l = list; l; l = l->next)
{
device = l->data;
if (gdk_device_get_source (device) == GDK_SOURCE_KEYBOARD)
continue;
display_wayland->input_devices = g_list_prepend (display_wayland->input_devices, l->data);
}
g_list_free (list);
/* Now set "core" pointer to the first
* master device that is a pointer.
*/
list = gdk_device_manager_list_devices (device_manager, GDK_DEVICE_TYPE_MASTER);
for (l = list; l; l = l->next)
{
device = list->data;
if (gdk_device_get_source (device) != GDK_SOURCE_MOUSE)
continue;
display->core_pointer = device;
break;
}
/* Add the core pointer to the devices list */
display_wayland->input_devices = g_list_prepend (display_wayland->input_devices, display->core_pointer);
g_list_free (list);
}
static void
shell_handle_configure(void *data, struct wl_shell *shell,
uint32_t time, uint32_t edges,
struct wl_surface *surface,
int32_t width, int32_t height)
{
GdkWindow *window;
GdkDisplay *display;
GdkEvent *event;
window = wl_surface_get_user_data(surface);
display = gdk_window_get_display (window);
event = gdk_event_new (GDK_CONFIGURE);
event->configure.window = window;
event->configure.send_event = FALSE;
event->configure.width = width;
event->configure.height = height;
_gdk_window_update_size (window);