Skip to content
Permalink
Browse files

Implement initial Wayland support

This commit creates a new "wayland" backend, which can be
activated at configure time with "-DFREEGLUT_WAYLAND=ON".

If done so, it will be used instead of X11 (building both
and doing runtime detection may become possible later).
Please note that if you choose to use GL instead of GLES
(by not specifying "-DFREEGLUT_GLES=ON"), then libX11
will still be pulled as an indirect dependency.

Following features are still WIP :
- menus (not implemented, TODO) ;
- client-side decorations (not implemented, required
  because Wayland shells do not draw title bars nor
  resize grips, TODO) ;
- game mode (code is commented out, depends on WIP
  protocols tested upstream, WAIT FOR UPSTREAM) ;
- window visibility states (code is commented out,
  depends on xdg-shell protocol, TODO).

Signed-off-by: Manuel Bachmann <tarnyko@tarnyko.net>
  • Loading branch information
Manuel Bachmann
Manuel Bachmann committed Mar 30, 2015
1 parent 27d5d26 commit 9b30564b6d9c9f106c7d079d6cf9207363a49111
@@ -52,8 +52,10 @@ ENDIF()
# OpenGL ES support
OPTION(FREEGLUT_GLES "Use OpenGL ES (requires EGL)" OFF)

# option to build either as "glut" (ON) or "freeglut" (OFF)
IF(NOT WIN32)
# Wayland support
OPTION(FREEGLUT_WAYLAND "Use Wayland (no X11)" OFF)
# option to build either as "glut" (ON) or "freeglut" (OFF)
OPTION(FREEGLUT_REPLACE_GLUT "Be a replacement for GLUT" ON)
ENDIF()

@@ -167,36 +169,60 @@ ELSEIF(ANDROID OR BLACKBERRY)
src/blackberry/fg_window_blackberry.c
)
ENDIF()

ELSE()
LIST(APPEND FREEGLUT_SRCS
src/x11/fg_cursor_x11.c
src/x11/fg_ext_x11.c
src/x11/fg_gamemode_x11.c
src/x11/fg_glutfont_definitions_x11.c
src/x11/fg_init_x11.c
src/x11/fg_internal_x11.h
src/x11/fg_input_devices_x11.c
src/x11/fg_joystick_x11.c
src/x11/fg_main_x11.c
src/x11/fg_menu_x11.c
src/x11/fg_spaceball_x11.c
src/x11/fg_state_x11.c
src/x11/fg_structure_x11.c
src/x11/fg_window_x11.c
src/x11/fg_xinput_x11.c
)
IF(NOT(FREEGLUT_GLES))
# UNIX (Wayland)
IF(FREEGLUT_WAYLAND)
LIST(APPEND FREEGLUT_SRCS
src/wayland/fg_cursor_wl.c
src/wayland/fg_ext_wl.c
src/wayland/fg_gamemode_wl.c
src/wayland/fg_init_wl.c
src/wayland/fg_internal_wl.h
src/wayland/fg_input_devices_wl.c
src/wayland/fg_main_wl.c
src/wayland/fg_state_wl.c
src/wayland/fg_structure_wl.c
src/wayland/fg_window_wl.c
# font, serial port & joystick code are agnostic
src/x11/fg_glutfont_definitions_x11.c
src/x11/fg_input_devices_x11.c
src/x11/fg_joystick_x11.c
)
# UNIX (X11)
ELSE()
LIST(APPEND FREEGLUT_SRCS
src/x11/fg_internal_x11_glx.h
src/x11/fg_display_x11_glx.c
src/x11/fg_state_x11_glx.c
src/x11/fg_state_x11_glx.h
src/x11/fg_window_x11_glx.c
src/x11/fg_window_x11_glx.h
src/x11/fg_cursor_x11.c
src/x11/fg_ext_x11.c
src/x11/fg_gamemode_x11.c
src/x11/fg_glutfont_definitions_x11.c
src/x11/fg_init_x11.c
src/x11/fg_internal_x11.h
src/x11/fg_input_devices_x11.c
src/x11/fg_joystick_x11.c
src/x11/fg_main_x11.c
src/x11/fg_menu_x11.c
src/x11/fg_spaceball_x11.c
src/x11/fg_state_x11.c
src/x11/fg_structure_x11.c
src/x11/fg_window_x11.c
src/x11/fg_xinput_x11.c
)
IF(NOT(FREEGLUT_GLES))
LIST(APPEND FREEGLUT_SRCS
src/x11/fg_internal_x11_glx.h
src/x11/fg_display_x11_glx.c
src/x11/fg_state_x11_glx.c
src/x11/fg_state_x11_glx.h
src/x11/fg_window_x11_glx.c
src/x11/fg_window_x11_glx.h
)
ENDIF()
ENDIF()
ENDIF()
IF(FREEGLUT_GLES)

# OpenGL ES requires EGL, and so does Wayland
IF(FREEGLUT_GLES OR FREEGLUT_WAYLAND)
LIST(APPEND FREEGLUT_SRCS
src/egl/fg_internal_egl.h
src/egl/fg_display_egl.c
@@ -226,6 +252,12 @@ ELSE()
INCLUDE_DIRECTORIES(${OPENGL_INCLUDE_DIR})
ENDIF()

# For Wayland: compile with -DFREEGLUT_WAYLAND and pull EGL
IF(FREEGLUT_WAYLAND)
ADD_DEFINITIONS(-DFREEGLUT_WAYLAND)
LIST(APPEND LIBS wayland-client wayland-cursor wayland-egl EGL xkbcommon)
ENDIF()

# lib m for math, not needed on windows
IF (NOT WIN32)
# For compilation:
@@ -248,14 +280,14 @@ ENDIF()

IF(CMAKE_COMPILER_IS_GNUCC)
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall")
IF(NOT(ANDROID OR BLACKBERRY))
IF(NOT(ANDROID OR BLACKBERRY OR FREEGLUT_WAYLAND))
# not setting -ansi as EGL/KHR headers doesn't support it
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -pedantic")
ENDIF()
ENDIF(CMAKE_COMPILER_IS_GNUCC)

INCLUDE(CheckIncludeFiles)
IF(UNIX AND NOT(ANDROID OR BLACKBERRY))
IF(UNIX AND NOT(ANDROID OR BLACKBERRY OR FREEGLUT_WAYLAND))
FIND_PACKAGE(X11 REQUIRED)
INCLUDE_DIRECTORIES(${X11_INCLUDE_DIR})
LIST(APPEND LIBS ${X11_LIBRARIES})
@@ -506,11 +538,17 @@ ELSEIF(FREEGLUT_GLES)
ELSE()
SET(PC_LIBS_PRIVATE "-lbps -lslog2 -lscreen -lGLESv2 -lGLESv1_CM -lEGL -lm")
ENDIF()
ELSEIF(FREEGLUT_WAYLAND)
SET(PC_LIBS_PRIVATE "-lwayland-client -lwayland-cursor -lwayland-egl -lGLESv2 -lGLESv1_CM -lEGL -lxkbcommon -lm")
ELSE()
SET(PC_LIBS_PRIVATE "-lX11 -lXxf86vm -lXrandr -lGLESv2 -lGLESv1_CM -lEGL -lm")
ENDIF()
ELSE()
SET(PC_LIBS_PRIVATE "-lX11 -lXxf86vm -lXrandr -lGL -lm")
IF(FREEGLUT_WAYLAND)
SET(PC_LIBS_PRIVATE "-lwayland-client -lwayland-cursor -lwayland-egl -lGL -lxkbcommon -lm")
ELSE()
SET(PC_LIBS_PRIVATE "-lX11 -lXxf86vm -lXrandr -lGL -lm")
ENDIF()
ENDIF()
# Client applications need to define FreeGLUT GLES version to
# bootstrap headers inclusion in freeglut_std.h:
@@ -34,8 +34,13 @@ void fghPlatformInitializeEGL()
{
/* CreateDisplay */
/* Using EGL_DEFAULT_DISPLAY, or a specific native display */
#ifdef FREEGLUT_WAYLAND
fgDisplay.pDisplay.egl.Display = eglGetDisplay(
(EGLNativeDisplayType)fgDisplay.pDisplay.display);
#else
EGLNativeDisplayType nativeDisplay = EGL_DEFAULT_DISPLAY;
fgDisplay.pDisplay.egl.Display = eglGetDisplay(nativeDisplay);
#endif

FREEGLUT_INTERNAL_ERROR_EXIT(fgDisplay.pDisplay.egl.Display != EGL_NO_DISPLAY,
"No display available", "fgPlatformInitialize");
@@ -51,7 +51,11 @@
# define TARGET_HOST_BLACKBERRY 1

#elif defined(__posix__) || defined(__unix__) || defined(__linux__) || defined(__sun)
# define TARGET_HOST_POSIX_X11 1
# if defined(FREEGLUT_WAYLAND)
# define TARGET_HOST_POSIX_WAYLAND 1
# else
# define TARGET_HOST_POSIX_X11 1
# endif

#elif defined(__APPLE__)
/* This is a placeholder until we get native OSX support ironed out -- JFF 11/18/09 */
@@ -70,32 +74,36 @@
#endif

#ifndef TARGET_HOST_MS_WINDOWS
# define TARGET_HOST_MS_WINDOWS 0
# define TARGET_HOST_MS_WINDOWS 0
#endif

#ifndef TARGET_HOST_ANDROID
# define TARGET_HOST_ANDROID 0
# define TARGET_HOST_ANDROID 0
#endif

#ifndef TARGET_HOST_BLACKBERRY
# define TARGET_HOST_BLACKBERRY 0
# define TARGET_HOST_BLACKBERRY 0
#endif

#ifndef TARGET_HOST_POSIX_WAYLAND
# define TARGET_HOST_POSIX_WAYLAND 0
#endif

#ifndef TARGET_HOST_POSIX_X11
# define TARGET_HOST_POSIX_X11 0
# define TARGET_HOST_POSIX_X11 0
#endif

#ifndef TARGET_HOST_MAC_OSX
# define TARGET_HOST_MAC_OSX 0
# define TARGET_HOST_MAC_OSX 0
#endif

#ifndef TARGET_HOST_SOLARIS
# define TARGET_HOST_SOLARIS 0
# define TARGET_HOST_SOLARIS 0
#endif

/* -- FIXED CONFIGURATION LIMITS ------------------------------------------- */

#define FREEGLUT_MAX_MENUS 3
#define FREEGLUT_MAX_MENUS 3

/* These files should be available on every platform. */
#include <stdio.h>
@@ -188,6 +196,9 @@
#endif

/* Platform-specific includes */
#if TARGET_HOST_POSIX_WAYLAND
#include "wayland/fg_internal_wl.h"
#endif
#if TARGET_HOST_POSIX_X11
#include "x11/fg_internal_x11.h"
#endif
@@ -0,0 +1,137 @@
/*
* fg_cursor_wl.c
*
* The Wayland-specific mouse cursor related stuff.
*
* Copyright (c) 2015 Manuel Bachmann. All Rights Reserved.
* Written by Manuel Bachmann, <tarnyko@tarnyko.net>
* Creation date: Thur Mar 19, 2015
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included
* in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* MANUEL BACHMANN BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/

#include <string.h>
#include <GL/freeglut.h>
#include "../fg_internal.h"

/*
* Note: The arrangement of the table below depends on the fact that
* the "normal" GLUT_CURSOR_* values start a 0 and are consecutive.
*/
static char* cursorList[] = {
"UNSUPPORTED", /* GLUT_CURSOR_RIGHT_ARROW */
"left_ptr", /* GLUT_CURSOR_LEFT_ARROW */
"hand1", /* GLUT_CURSOR_INFO */
"UNSUPPORTED", /* GLUT_CURSOR_DESTROY */
"UNSUPPORTED", /* GLUT_CURSOR_HELP */
"UNSUPPORTED", /* GLUT_CURSOR_CYCLE */
"UNSUPPORTED", /* GLUT_CURSOR_SPRAY */
"watch", /* GLUT_CURSOR_WAIT */
"xterm", /* GLUT_CURSOR_TEXT */
"grabbing", /* GLUT_CURSOR_CROSSHAIR */
"UNSUPPORTED", /* GLUT_CURSOR_UP_DOWN */
"UNSUPPORTED", /* GLUT_CURSOR_LEFT_RIGHT */
"top_side", /* GLUT_CURSOR_TOP_SIDE */
"bottom_side", /* GLUT_CURSOR_BOTTOM_SIDE */
"left_side", /* GLUT_CURSOR_LEFT_SIDE */
"right_side", /* GLUT_CURSOR_RIGHT_SIDE */
"top_left_corner", /* GLUT_CURSOR_TOP_LEFT_CORNER */
"top_right_corner", /* GLUT_CURSOR_TOP_RIGHT_CORNER */
"bottom_right_corner", /* GLUT_CURSOR_BOTTOM_RIGHT_CORNER */
"bottom_left_corner" /* GLUT_CURSOR_BOTTOM_LEFT_CORNER */
};

void fgPlatformSetCursor ( SFG_Window *window, int cursorID )
{
/*
* XXX FULL_CROSSHAIR demotes to plain CROSSHAIR. Old GLUT allows
* for this, but if there is a system that easily supports a full-
* window (or full-screen) crosshair, we might consider it.
*/
int cursorIDToUse =
( cursorID == GLUT_CURSOR_FULL_CROSSHAIR ) ? GLUT_CURSOR_CROSSHAIR : cursorID;

char* cursor;

if( ( cursorIDToUse >= 0 ) &&
( cursorIDToUse < sizeof( cursorList ) / sizeof( cursorList[0] ) ) ) {

cursor = cursorList[cursorIDToUse];

/* if the type is UNSUPPORTED, fall back to GLUT_CURSOR_LEFT_ARROW */
if ( ! strcmp( cursor, "UNSUPPORTED" ) )
{
fgWarning( "glutSetCursor(): cursor type unsupported under Wayland : %d",
cursorIDToUse );
cursor = "left_ptr";
}
} else {
switch( cursorIDToUse )
{
case GLUT_CURSOR_NONE:
case GLUT_CURSOR_INHERIT:
cursor = NULL;
break;

default:
fgError( "Unknown cursor type: %d", cursorIDToUse );
return;
}
}

if ( cursorIDToUse == GLUT_CURSOR_INHERIT ) {
if( window->Parent )
window->Window.pContext.cursor =
window->Parent->Window.pContext.cursor;
} else {
window->Window.pContext.cursor = wl_cursor_theme_get_cursor(
fgDisplay.pDisplay.cursor_theme,
cursor );
if ( ! window->Window.pContext.cursor )
fgError( "Failed to create cursor" );
}
}


void fgPlatformWarpPointer ( int x, int y )
{
/* unsupported under Wayland */
fgWarning( "glutWarpPointer(): function unsupported under Wayland" );
}

void fghPlatformGetCursorPos(const SFG_Window *window, GLboolean client, SFG_XYUse *mouse_pos)
{
/* Get current pointer location relative to top-left of client area of window (if client is true and window is not NULL)
* We cannot get current pointer location in screen coordinates under Wayland, so inform the user and return -1 is this case
*/

if (client && window)
{
mouse_pos->X = window->State.MouseX;
mouse_pos->Y = window->State.MouseY;
}
else
{
fgWarning( "glutGetCursorPos(): cannot get screen position under Wayland" );
mouse_pos->X = -1;
mouse_pos->Y = -1;
}

mouse_pos->Use = GL_TRUE;
}

0 comments on commit 9b30564

Please sign in to comment.
You can’t perform that action at this time.