Add Xinerama support for GHOST_GetMainDisplayDimensions() so X11 works as it should (previously would include all monitors).

Now the active monitor size is used on startup. 
Currently the cursor position is checked for intersection with the monitor bounds to find the active screen.
This commit is contained in:
Campbell Barton
2013-01-31 11:05:09 +00:00
parent 73f301c3a8
commit dbf54dacf7
5 changed files with 65 additions and 13 deletions

View File

@@ -166,6 +166,7 @@ unset(PLATFORM_DEFAULT)
if(UNIX AND NOT APPLE)
option(WITH_X11_XINPUT "Enable X11 Xinput (tablet support and unicode input)" ON)
option(WITH_X11_XINERAMA "Enable multi-monitor support" ON)
option(WITH_X11_XF86VMODE "Enable X11 video mode switching" ON)
option(WITH_SYSTEM_GLEW "Use GLEW OpenGL wrapper library provided by the operating system" ON)
@@ -414,6 +415,7 @@ if(WITH_GHOST_SDL OR WITH_HEADLESS)
set(WITH_GHOST_XDND OFF)
set(WITH_X11_XF86VMODE OFF)
set(WITH_X11_XINPUT OFF)
set(WITH_X11_XINERAMA OFF)
endif()
if(MINGW)
@@ -800,6 +802,10 @@ if(UNIX AND NOT APPLE)
set(PLATFORM_LINKLIBS "${PLATFORM_LINKLIBS} ${X11_Xinput_LIB}")
endif()
if(WITH_X11_XINERAMA)
set(PLATFORM_LINKLIBS "${PLATFORM_LINKLIBS} ${X11_Xinerama_LIB}")
endif()
if(WITH_X11_XF86VMODE)
# XXX, why dont cmake make this available?
FIND_LIBRARY(X11_Xxf86vmode_LIB Xxf86vm ${X11_LIB_SEARCH_PATH})

View File

@@ -271,6 +271,16 @@ elseif(UNIX)
if(WITH_X11_XINPUT)
add_definitions(-DWITH_X11_XINPUT)
list(APPEND INC_SYS
${X11_Xinput_INCLUDE_PATH}
)
endif()
if(WITH_X11_XINERAMA)
add_definitions(-DWITH_X11_XINERAMA)
list(APPEND INC_SYS
${X11_Xinerama_INCLUDE_PATH}
)
endif()
elseif(WIN32)

View File

@@ -50,6 +50,10 @@
# include "GHOST_DropTargetX11.h"
#endif
#ifdef WITH_X11_XINERAMA
# include "X11/extensions/Xinerama.h"
#endif
#include "GHOST_Debug.h"
#include <X11/Xatom.h>
@@ -237,8 +241,48 @@ getMainDisplayDimensions(
GHOST_TUns32& height) const
{
if (m_display) {
width = DisplayWidth(m_display, DefaultScreen(m_display));
height = DisplayHeight(m_display, DefaultScreen(m_display));
#ifdef WITH_X11_XINERAMA
GHOST_TInt32 m_x = 1, m_y = 1;
getCursorPosition(m_x, m_y);
/* NOTE, no way to select a primary monitor, uses the first */
bool success = false;
int dummy1, dummy2;
if (XineramaQueryExtension(m_display, &dummy1, &dummy2)) {
if (XineramaIsActive(m_display)) {
int heads = 0;
XineramaScreenInfo *p = XineramaQueryScreens(m_display, &heads);
/* with a single head, all dimensions is fine */
if (heads > 1) {
int i;
for (i = 0; i < heads; i++) {
if ((m_x >= p[i].x_org) && (m_x <= p[i].x_org + p[i].width) &&
(m_y >= p[i].y_org) && (m_y <= p[i].y_org + p[i].height))
{
width = p[i].width;
height = p[i].height;
break;
}
}
/* highly unlikely! */
if (i == heads) {
width = p[0].width;
height = p[0].height;
}
success = true;
}
XFree(p);
}
}
if (success) {
return;
}
#endif
/* fallback to all */
getAllDisplayDimensions(width, height);
}
}

View File

@@ -647,7 +647,6 @@ static FCM_EnvelopeData *rna_FModifierEnvelope_points_add(FModifier *fmod, Repor
fed.f1 = fed.f2 = 0;
if (env->data) {
/* add point to end of control points */
short exists = -1;
i = BKE_fcm_envelope_find_index(env->data, frame, env->totvert, &exists);
if (exists) {

View File

@@ -436,18 +436,11 @@ void wm_window_add_ghostwindows(wmWindowManager *wm)
wm_set_apple_prefsize(wm_init_state.size_x, wm_init_state.size_y);
}
#else
/* default size when un-maximized, unless the screen(s) are smaller */
/* clamp by these arbitrary values because currently wm_get_screensize()
* will span multiple monitors and using xinerama isnt totally reliable
* since we don't which monitor the window manager will put the blender
* window in. */
wm_init_state.size_x = MIN2(1800, wm_init_state.size_x - 100);
wm_init_state.size_y = MIN2(980, wm_init_state.size_y - 100);
/* note!, this isnt quite correct, active screen maybe offset 1000s if PX,
* we'd need a wm_get_screensize like function that gives offset,
* in practice the window manager will likely move to the correct monitor */
wm_init_state.start_x = 0;
wm_init_state.start_y = 0;
#endif
}