Use true fullscreen in X/EGL.

This commit is contained in:
Themaister 2012-09-29 10:47:55 +02:00
parent 65fa84d3b7
commit f8de693eef
6 changed files with 89 additions and 11 deletions

View File

@ -207,8 +207,8 @@ endif
ifeq ($(HAVE_X11), 1)
OBJ += input/x11_input.o gfx/context/x11_common.o
LIBS += $(X11_LIBS) $(XEXT_LIBS)
DEFINES += $(X11_CFLAGS) $(XEXT_CFLAGS)
LIBS += $(X11_LIBS) $(XEXT_LIBS) $(XF86VM_LIBS)
DEFINES += $(X11_CFLAGS) $(XEXT_CFLAGS) $(XF86VM_CFLAGS)
endif
ifeq ($(HAVE_CG), 1)

View File

@ -89,3 +89,51 @@ void x11_suspend_screensaver(Window wnd)
RARCH_WARN("Could not suspend screen saver.\n");
}
static bool get_video_mode(Display *dpy, unsigned width, unsigned height, XF86VidModeModeInfo *mode, XF86VidModeModeInfo *desktop_mode)
{
XF86VidModeModeInfo **modes = NULL;
int num_modes = 0;
XF86VidModeGetAllModeLines(dpy, DefaultScreen(dpy), &num_modes, &modes);
if (!num_modes)
{
XFree(modes);
return false;
}
*desktop_mode = *modes[0];
bool ret = false;
for (int i = 0; i < num_modes; i++)
{
if (modes[i]->hdisplay == width && modes[i]->vdisplay == height)
{
*mode = *modes[i];
ret = true;
break;
}
}
XFree(modes);
return ret;
}
bool x11_enter_fullscreen(Display *dpy, unsigned width, unsigned height, XF86VidModeModeInfo *desktop_mode)
{
XF86VidModeModeInfo mode;
if (get_video_mode(dpy, width, height, &mode, desktop_mode))
{
XF86VidModeSwitchToMode(dpy, DefaultScreen(dpy), &mode);
XF86VidModeSetViewPort(dpy, DefaultScreen(dpy), 0, 0);
return true;
}
else
return false;
}
void x11_exit_fullscreen(Display *dpy, XF86VidModeModeInfo *desktop_mode)
{
XF86VidModeSwitchToMode(dpy, DefaultScreen(dpy), desktop_mode);
XF86VidModeSetViewPort(dpy, DefaultScreen(dpy), 0, 0);
}

View File

@ -19,10 +19,14 @@
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/extensions/xf86vmode.h>
#include "../../boolean.h"
void x11_hide_mouse(Display *dpy, Window win);
void x11_windowed_fullscreen(Display *dpy, Window win);
void x11_suspend_screensaver(Window win);
bool x11_enter_fullscreen(Display *dpy, unsigned width, unsigned height, XF86VidModeModeInfo *desktop_mode);
void x11_exit_fullscreen(Display *dpy, XF86VidModeModeInfo *desktop_mode);
#endif

View File

@ -41,6 +41,9 @@ static EGLSurface g_egl_surf;
static EGLDisplay g_egl_dpy;
static EGLConfig g_config;
static XF86VidModeModeInfo g_desktop_mode;
static bool g_should_reset_mode;
static volatile sig_atomic_t g_quit;
static bool g_inited;
static unsigned g_interval;
@ -52,6 +55,13 @@ static void sighandler(int sig)
g_quit = 1;
}
static Bool egl_wait_notify(Display *d, XEvent *e, char *arg)
{
(void)d;
(void)e;
return e->type == MapNotify && e->xmap.window == g_win;
}
static void gfx_ctx_get_video_size(unsigned *width, unsigned *height);
static void gfx_ctx_destroy(void);
@ -264,11 +274,18 @@ static bool gfx_ctx_set_video_mode(
swa.colormap = g_cmap = XCreateColormap(g_dpy, RootWindow(g_dpy, vi->screen),
vi->visual, AllocNone);
swa.event_mask = StructureNotifyMask;
swa.override_redirect = fullscreen ? True : False;
if (fullscreen)
{
if (x11_enter_fullscreen(g_dpy, width, height, &g_desktop_mode))
g_should_reset_mode = true;
}
g_win = XCreateWindow(g_dpy, RootWindow(g_dpy, vi->screen),
0, 0, width ? width : 200, height ? height : 200, 0,
vi->depth, InputOutput, vi->visual,
CWBorderPixel | CWColormap | CWEventMask, &swa);
CWBorderPixel | CWColormap | CWEventMask | (fullscreen ? CWOverrideRedirect : 0), &swa);
XSetWindowBackground(g_dpy, g_win, 0);
// GLES 2.0. Don't use for any other API.
@ -294,8 +311,9 @@ static bool gfx_ctx_set_video_mode(
x11_hide_mouse(g_dpy, g_win);
XMapWindow(g_dpy, g_win);
if (fullscreen)
x11_windowed_fullscreen(g_dpy, g_win);
XEvent event;
XIfEvent(g_dpy, &event, egl_wait_notify, NULL);
XSetInputFocus(g_dpy, g_win, RevertToNone, CurrentTime);
g_quit_atom = XInternAtom(g_dpy, "WM_DELETE_WINDOW", False);
if (g_quit_atom)
@ -354,6 +372,12 @@ static void gfx_ctx_destroy(void)
g_cmap = None;
}
if (g_should_reset_mode)
{
x11_exit_fullscreen(g_dpy, &g_desktop_mode);
g_should_reset_mode = false;
}
if (g_dpy)
{
XCloseDisplay(g_dpy);

View File

@ -295,8 +295,8 @@ static void x_input_poll(void *data)
{
x11_input_t *x11 = (x11_input_t*)data;
Window win;
int rev;
Window win = None;
int rev = 0;
XGetInputFocus(x11->display, &win, &rev);
if (win == x11->win)

View File

@ -163,13 +163,15 @@ fi
check_pkgconf XML libxml-2.0
check_pkgconf FREETYPE freetype2
check_pkgconf X11 x11
[ "$HAVE_X11" = "no" ] && HAVE_XEXT=no
[ "$HAVE_X11" = "no" ] && HAVE_XEXT=no && HAVE_XF86VM=no
check_pkgconf XEXT xext
if [ "$HAVE_X11" = 'yes' ] && [ "$HAVE_XEXT" = 'yes' ]; then
check_pkgconf XF86VM xxf86vm
if [ "$HAVE_X11" = 'yes' ] && [ "$HAVE_XEXT" = 'yes' ] && [ "$HAVE_XF86VM" = 'yes' ]; then
check_pkgconf XVIDEO xv
else
echo "X11 or Xext not present. Skipping XVideo."
echo "X11, Xext or xf86vm not present. Skipping X11."
HAVE_X11='no'
HAVE_XVIDEO='no'
fi
@ -180,6 +182,6 @@ check_pkgconf PYTHON python3
add_define_make OS "$OS"
# Creates config.mk and config.h.
VARS="ALSA OSS OSS_BSD OSS_LIB AL RSOUND ROAR JACK COREAUDIO PULSE SDL OPENGL GLES VG EGL KMS GBM DRM DYLIB GETOPT_LONG THREADS CG XML SDL_IMAGE LIBPNG DYNAMIC FFMPEG AVCODEC AVFORMAT AVUTIL CONFIGFILE FREETYPE XVIDEO X11 XEXT NETPLAY NETWORK_CMD STDIN_CMD COMMAND SOCKET_LEGACY FBO PBO STRL PYTHON FFMPEG_ALLOC_CONTEXT3 FFMPEG_AVCODEC_OPEN2 FFMPEG_AVIO_OPEN FFMPEG_AVFORMAT_WRITE_HEADER FFMPEG_AVFORMAT_NEW_STREAM FFMPEG_AVCODEC_ENCODE_AUDIO2 FFMPEG_AVCODEC_ENCODE_VIDEO2 SINC FIXED_POINT BSV_MOVIE VIDEOCORE"
VARS="ALSA OSS OSS_BSD OSS_LIB AL RSOUND ROAR JACK COREAUDIO PULSE SDL OPENGL GLES VG EGL KMS GBM DRM DYLIB GETOPT_LONG THREADS CG XML SDL_IMAGE LIBPNG DYNAMIC FFMPEG AVCODEC AVFORMAT AVUTIL CONFIGFILE FREETYPE XVIDEO X11 XEXT XF86VM NETPLAY NETWORK_CMD STDIN_CMD COMMAND SOCKET_LEGACY FBO PBO STRL PYTHON FFMPEG_ALLOC_CONTEXT3 FFMPEG_AVCODEC_OPEN2 FFMPEG_AVIO_OPEN FFMPEG_AVFORMAT_WRITE_HEADER FFMPEG_AVFORMAT_NEW_STREAM FFMPEG_AVCODEC_ENCODE_AUDIO2 FFMPEG_AVCODEC_ENCODE_VIDEO2 SINC FIXED_POINT BSV_MOVIE VIDEOCORE"
create_config_make config.mk $VARS
create_config_header config.h $VARS