// From ClanLib, LGPL (x11_resolution.cpp) static XF86VidModeModeInfo GetXF86Mode(Display *dpy, int scr, int width, int height) { XF86VidModeModeInfo **modes; XF86VidModeModeLine mode; int nmodes; int i; if ( XF86VidModeGetModeLine(dpy, scr, &i, &mode) && XF86VidModeGetAllModeLines(dpy, scr, &nmodes, &modes)) { qsort(modes, nmodes, sizeof *modes, cmpmodes); for (i=nmodes-1; i>= 0; --i) { if ( (modes[i]->hdisplay >= width) && (modes[i]->vdisplay >= height) ) break; } if (i>=0) { if ( (modes[i]->hdisplay != mode.hdisplay) || (modes[i]->vdisplay != mode.vdisplay) ) { return *modes[i]; } XFree(modes); } } XF86VidModeModeInfo dummy_mode; memset(&dummy_mode, 0, sizeof(dummy_mode)); return dummy_mode; }
void _glfwPlatformRefreshWindowParams(_GLFWwindow* window) { // Retrieve refresh rate if possible if (_glfwLibrary.X11.RandR.available) { #if defined(_GLFW_HAS_XRANDR) XRRScreenConfiguration* sc; sc = XRRGetScreenInfo(_glfwLibrary.X11.display, _glfwLibrary.X11.root); window->refreshRate = XRRConfigCurrentRate(sc); XRRFreeScreenConfigInfo(sc); #endif /*_GLFW_HAS_XRANDR*/ } else if (_glfwLibrary.X11.VidMode.available) { #if defined(_GLFW_HAS_XF86VIDMODE) XF86VidModeModeLine modeline; int dotclock; float pixels_per_second, pixels_per_frame; // Use the XF86VidMode extension to get current video mode XF86VidModeGetModeLine(_glfwLibrary.X11.display, _glfwLibrary.X11.screen, &dotclock, &modeline); pixels_per_second = 1000.0f * (float) dotclock; pixels_per_frame = (float) modeline.htotal * modeline.vtotal; window->refreshRate = (int) (pixels_per_second / pixels_per_frame + 0.5); #endif /*_GLFW_HAS_XF86VIDMODE*/ } else { // Zero means unknown according to the GLFW spec window->refreshRate = 0; } }
float PsychGetNominalFramerate(int screenNumber) { // Information returned by the XF86VidModeExtension: XF86VidModeModeLine mode_line; // The mode line of the current video mode. int dot_clock; // The RAMDAC / TDMS pixel clock frequency. // We start with a default vrefresh of zero, which means "couldn't query refresh from OS": float vrefresh = 0; if(screenNumber>=numDisplays) PsychErrorExitMsg(PsychError_internal, "screenNumber passed to PsychGetScreenDepths() is out of range"); if (!XF86VidModeSetClientVersion(displayCGIDs[screenNumber])) { // Failed to use VidMode-Extension. We just return a vrefresh of zero. return(0); } // Query vertical refresh rate. If it fails we default to the last known good value... if (XF86VidModeGetModeLine(displayCGIDs[screenNumber], PsychGetXScreenIdForScreen(screenNumber), &dot_clock, &mode_line)) { // Vertical refresh rate is: RAMDAC pixel clock / width of a scanline in clockcylces / // number of scanlines per videoframe. vrefresh = (((dot_clock * 1000) / mode_line.htotal) * 1000) / mode_line.vtotal; // Divide vrefresh by 1000 to get real Hz - value: vrefresh = vrefresh / 1000.0f; } // Done. return(vrefresh); }
gboolean xmms_fullscreen_init(GtkWidget * win) { int event_base, error_base, dummy; fullscreen_window_t *fwin; gint i; XF86VidModeModeLine origmode; FULL_LOCK(); fwin = getwindow(win); if (!XF86VidModeQueryExtension (fwin->display->display, &event_base, &error_base)) { FULL_UNLOCK(); return FALSE; } if (!fwin->display->modes) { XF86VidModeGetAllModeLines(fwin->display->display, DefaultScreen(fwin->display->display), &fwin->display->num_modes, &fwin->display->modes); if (!fwin->display->origmode) { XF86VidModeGetModeLine(fwin->display->display, DefaultScreen(fwin->display->display), &dummy, &origmode); for (i = 0; i < fwin->display->num_modes; i++) { if (fwin->display->modes[i]->hdisplay == origmode.hdisplay && fwin->display->modes[i]->vdisplay == origmode.vdisplay) { fwin->display->origmode = fwin->display->modes[i]; break; } } if (!fwin->display->origmode) { fprintf(stderr, "ERROR: Could not determine original mode.\n"); FULL_UNLOCK(); return FALSE; } } fwin->display->can_full = (fwin->display->num_modes > 1); } FULL_UNLOCK(); return fwin->display->can_full; }
static Bool GetModeLine(Bool save) { if (XF86VidModeGetModeLine(XtDisplay(toplevel), vidtune->screen, &dot_clock, &modeline)) { if (save) memcpy(&orig_modeline, &modeline, sizeof(XF86VidModeModeLine)); UpdateSyncRates(False); return (True); } return (False); }
float MythXDisplay::GetRefreshRate(void) { XF86VidModeModeLine mode_line; int dot_clock; MythXLocker locker(this); if (!XF86VidModeGetModeLine(m_disp, m_screen_num, &dot_clock, &mode_line)) { VERBOSE(VB_IMPORTANT, "MythXGetRefreshRate(): " "X11 ModeLine query failed"); return -1; } double rate = mode_line.htotal * mode_line.vtotal; // Catch bad data from video drivers (divide by zero causes return of NaN) if (rate == 0.0 || dot_clock == 0) { VERBOSE(VB_IMPORTANT, "MythXGetRefreshRate(): " "X11 ModeLine query returned zeroes"); return -1; } rate = (dot_clock * 1000.0) / rate; if (((mode_line.flags & V_INTERLACE) != 0) && rate > 24.5 && rate < 30.5) { VERBOSE(VB_PLAYBACK, "MythXGetRefreshRate(): " "Doubling refresh rate for interlaced display."); rate *= 2.0; } // Assume 60Hz if rate isn't good: if (rate < 20 || rate > 200) { VERBOSE(VB_PLAYBACK, QString("MythXGetRefreshRate(): " "Unreasonable refresh rate %1Hz reported by X").arg(rate)); rate = 60; } rate = 1000000.0 / rate; return rate; }
static int X11DRV_XF86VM_GetCurrentMode(void) { XF86VidModeModeLine line; int dotclock; unsigned int i; DDHALMODEINFO cmode; DWORD dwBpp = screen_bpp; TRACE("Querying XVidMode current mode\n"); wine_tsx11_lock(); XF86VidModeGetModeLine(gdi_display, DefaultScreen(gdi_display), &dotclock, &line); wine_tsx11_unlock(); convert_modeline(dotclock, &line, &cmode, dwBpp); for (i=0; i<dd_mode_count; i++) if (memcmp(&dd_modes[i], &cmode, sizeof(cmode)) == 0) { TRACE("mode=%d\n", i); return i; } ERR("In unknown mode, returning default\n"); return 0; }
float x11_get_refresh_rate(void *data) { XWindowAttributes attr; XF86VidModeModeLine modeline; Screen *screen; int screenid; int dotclock; if (!g_x11_dpy || g_x11_win == None) return 0.0f; if (!XGetWindowAttributes(g_x11_dpy, g_x11_win, &attr)) return 0.0f; screen = attr.screen; screenid = XScreenNumberOfScreen(screen); XF86VidModeGetModeLine(g_x11_dpy, screenid, &dotclock, &modeline); return (float) dotclock * 1000.0f / modeline.htotal / modeline.vtotal; }
float X11Display::queryRefreshRate() { ::Display * pDisplay = XOpenDisplay(0); int pixelClock; XF86VidModeModeLine modeLine; bool bOK = XF86VidModeGetModeLine(pDisplay, DefaultScreen(pDisplay), &pixelClock, &modeLine); if (!bOK) { AVG_LOG_INFO( "Could not get current refresh rate (XF86VidModeGetModeLine failed)."); AVG_LOG_INFO("Defaulting to 60 Hz refresh rate."); return 60; } float hSyncRate = (pixelClock * 1000.0) / modeLine.htotal; float refreshRate = hSyncRate / modeLine.vtotal; XCloseDisplay(pDisplay); if ( refreshRate < 20 || refreshRate > 200 || !(boost::math::isnormal(refreshRate))){ AVG_LOG_INFO("Could not get valid refresh rate"); AVG_LOG_INFO("Defaulting to 60 Hz refresh rate."); return 60; } return refreshRate; }
// needs to be run after SelectEGLConfiguration() // for gEglConfig to be valid int PVRShellInitOS::OpenX11Window(const PVRShell &shell) { XSetWindowAttributes wa; XSizeHints sh; XEvent event; unsigned long mask; #ifdef BUILD_OGL XF86VidModeModeInfo **modes; // modes of display int numModes; // number of modes of display int chosenMode; int edimx,edimy; //established width and height of the chosen modeline int i; #endif MyHints mwmhints; Atom prop; int depth = DefaultDepth(x11display, x11screen); x11visual = new XVisualInfo; XMatchVisualInfo( x11display, x11screen, depth, TrueColor, x11visual); if( !x11visual ) { shell.PVRShellOutputDebug( "Unable to acquire visual" ); return false; } x11colormap = XCreateColormap( x11display, RootWindow(x11display, x11screen), x11visual->visual, AllocNone ); #ifdef BUILD_OGL originalMode_dotclock = XF86VidModeBadClock; if(shell.m_pShellData->bFullScreen) { // Get mode lines to see if there is requested modeline XF86VidModeGetAllModeLines(x11display, x11screen, &numModes, &modes); /* look for mode with requested resolution */ chosenMode = -1; i=0; while((chosenMode == -1)&&(i<numModes)) { if ((modes[i]->hdisplay == shell.m_pShellData->nShellDimX) && (modes[i]->vdisplay == shell.m_pShellData->nShellDimY)) { chosenMode = i; } ++i; } // If there is no requested resolution among modelines then terminate if(chosenMode == -1) { shell.PVRShellOutputDebug( "Chosen resolution for full screen mode does not match any modeline available.\n" ); return false; } /* save desktop-resolution before switching modes */ XF86VidModeGetModeLine(x11display,x11screen, &originalMode_dotclock, &originalMode ); XF86VidModeSwitchToMode(x11display, x11screen, modes[chosenMode]); XF86VidModeSetViewPort(x11display, x11screen, 0, 0); edimx = modes[chosenMode]->hdisplay; edimy = modes[chosenMode]->vdisplay; printf("Fullscreen Resolution %dx%d (chosen mode = %d)\n", edimx, edimy,chosenMode); XFree(modes); //to musi byc globalne wa.colormap = x11colormap; wa.background_pixel = 0xFFFFFFFF; wa.border_pixel = 0; wa.override_redirect = true; // add to these for handling other events wa.event_mask = StructureNotifyMask | ExposureMask | ButtonPressMask | ButtonReleaseMask | KeyPressMask | KeyReleaseMask; // The diffrence is that we want to ignore influence of window manager for outr fullscreen window mask = CWBackPixel | CWBorderPixel | CWEventMask | CWColormap | CWOverrideRedirect; x11window = XCreateWindow( x11display, RootWindow(x11display, x11screen), 0, 0, edimx, edimy, 0, CopyFromParent, InputOutput, CopyFromParent, mask, &wa); // keeping the pointer of mouse and keyboard in window to prevent from scrolling the virtual screen XWarpPointer(x11display, None ,x11window, 0, 0, 0, 0, 0, 0); // Map and then wait till mapped, grabbing should be after mapping the window XMapWindow( x11display, x11window ); XGrabKeyboard(x11display, x11window, True, GrabModeAsync, GrabModeAsync, CurrentTime); XGrabPointer(x11display, x11window, True, ButtonPressMask, GrabModeAsync, GrabModeAsync, x11window, None, CurrentTime); XIfEvent( x11display, &event, WaitForMapNotify, (char*)x11window ); } else { #endif wa.colormap = x11colormap; wa.background_pixel = 0xFFFFFFFF; wa.border_pixel = 0; // add to these for handling other events wa.event_mask = StructureNotifyMask | ExposureMask | ButtonPressMask | ButtonReleaseMask | KeyPressMask | KeyReleaseMask; mask = CWBackPixel | CWBorderPixel | CWEventMask | CWColormap ; x11window = XCreateWindow( x11display, RootWindow(x11display, x11screen), shell.m_pShellData->nShellPosX, shell.m_pShellData->nShellPosY, shell.m_pShellData->nShellDimX, shell.m_pShellData->nShellDimY, 0, CopyFromParent, InputOutput, CopyFromParent, mask, &wa); // todo:meh remove this? sh.flags = USPosition; sh.x = shell.m_pShellData->nShellPosX; sh.y = shell.m_pShellData->nShellPosY; XSetStandardProperties( x11display, x11window, szTitle, szTitle, None, 0, 0, &sh ); // Map and then wait till mapped XMapWindow( x11display, x11window ); XIfEvent( x11display, &event, WaitForMapNotify, (char*)x11window ); // An attempt to hide a border for fullscreen on non OGL apis (OGLES,OGLES2) if(shell.m_pShellData->bFullScreen) { memset(&mwmhints, 0, sizeof(mwmhints)); prop = XInternAtom(x11display, "_MOTIF_WM_HINTS", False); mwmhints.flags = 2;//MWM_HINTS_DECORATIONS; mwmhints.decorations = 0; XChangeProperty(x11display, x11window, prop, prop, 32, PropModeReplace, (unsigned char *) &mwmhints,5); } // Atom wmDelete = XInternAtom(x11display, "WM_DELETE_WINDOW", True); XSetWMProtocols(x11display, x11window, &wmDelete, 1); XSetWMColormapWindows( x11display, x11window, &x11window, 1 ); #ifdef BUILD_OGL } #endif XFlush( x11display ); return true; }
/* * Remembers the current visual settings, so that * we can change them and restore later... */ static void fghRememberState( void ) { #if TARGET_HOST_UNIX_X11 /* * This highly depends on the XFree86 extensions, * not approved as X Consortium standards */ # ifdef X_XF86VidModeGetModeLine /* * Remember the current ViewPort location of the screen to be able to * restore the ViewPort on LeaveGameMode(): */ if( !XF86VidModeGetViewPort( fgDisplay.Display, fgDisplay.Screen, &fgDisplay.DisplayViewPortX, &fgDisplay.DisplayViewPortY ) ) fgWarning( "XF86VidModeGetViewPort failed" ); /* * Remember the current pointer location before going fullscreen * for restoring it later: */ { Window junk_window; unsigned int mask; XQueryPointer( fgDisplay.Display, fgDisplay.RootWindow, &junk_window, &junk_window, &fgDisplay.DisplayPointerX, &fgDisplay.DisplayPointerY, &fgDisplay.DisplayPointerX, &fgDisplay.DisplayPointerY, &mask ); } /* Query the current display settings: */ fgDisplay.DisplayModeValid = XF86VidModeGetModeLine( fgDisplay.Display, fgDisplay.Screen, &fgDisplay.DisplayModeClock, &fgDisplay.DisplayMode ); if( !fgDisplay.DisplayModeValid ) fgWarning( "XF86VidModeGetModeLine failed" ); # else /* * XXX warning fghRememberState: missing XFree86 video mode extensions, * XXX game mode will not change screen resolution when activated */ # endif #elif TARGET_HOST_WIN32 || TARGET_HOST_WINCE /* DEVMODE devMode; */ /* Grab the current desktop settings... */ /* hack to get around my stupid cross-gcc headers */ #define FREEGLUT_ENUM_CURRENT_SETTINGS -1 EnumDisplaySettings( NULL, FREEGLUT_ENUM_CURRENT_SETTINGS, &fgDisplay.DisplayMode ); /* Make sure we will be restoring all settings needed */ fgDisplay.DisplayMode.dmFields |= DM_PELSWIDTH | DM_PELSHEIGHT | DM_BITSPERPEL | DM_DISPLAYFREQUENCY; #endif }
// Sections From ClanLib (LGPL) (x11_resolution.cpp) void ResizeGlut ( int width, int height ) { Display *dpy = __glutDisplay; int scr = DefaultScreen(dpy); // Save the video mode memset(&origMode, 0, sizeof(origMode)); XF86VidModeModeLine *l = (XF86VidModeModeLine*)((char*) &origMode + sizeof(origMode.dotclock)); XF86VidModeGetModeLine(dpy, scr, (int*) &origMode.dotclock, l); // Set the new video mode XF86VidModeModeInfo mode = GetXF86Mode(dpy, scr, width, height); XWarpPointer(dpy, None, RootWindow(dpy, scr), 0, 0, 0, 0, 0, 0); XF86VidModeSwitchToMode(dpy, scr, &mode); XWarpPointer(dpy, None, RootWindow(dpy, scr), 0, 0, 0, 0, 0, 0); XSync(dpy, False); __glutScreenWidth = width; __glutScreenHeight = height; Window realRoot = RootWindow(dpy, scr); XSetWindowAttributes attr; attr.override_redirect = False; attr.background_pixel = BlackPixel(dpy, scr); attr.backing_store = Always; int attr_flags = CWOverrideRedirect | CWBackPixel | CWBackingStore; Window rootWindow = XCreateWindow(__glutDisplay, realRoot, 0, 0, width, height, 0, CopyFromParent, CopyFromParent, CopyFromParent, attr_flags, &attr); XSizeHints size_hints; size_hints.x = 0; size_hints.y = 0; size_hints.width = width; size_hints.height = height; size_hints.flags = PSize | PMinSize | PMaxSize; size_hints.min_width = width; size_hints.min_height = height; size_hints.max_width = width; size_hints.max_height = height; XSetWMProperties(dpy, rootWindow, NULL, NULL, 0, 0, &size_hints, 0, 0); XMapRaised(dpy, rootWindow); XSync(dpy,False); // XSetInputFocus(dpy, rootWindow, RevertToParent, CurrentTime); XGrabPointer(dpy, rootWindow, true, 0, GrabModeAsync, GrabModeAsync, rootWindow, None, CurrentTime); XWarpPointer(dpy, None, rootWindow, 0, 0, 0, 0, width, height); XSync(dpy,False); __glutRoot = rootWindow; }
/* * Remembers the current visual settings, so that * we can change them and restore later... */ void fgPlatformRememberState( void ) { int event_base, error_base; /* * Remember the current pointer location before going fullscreen * for restoring it later: */ Window junk_window; unsigned int junk_mask; XQueryPointer(fgDisplay.pDisplay.Display, fgDisplay.pDisplay.RootWindow, &junk_window, &junk_window, &fgDisplay.pDisplay.DisplayPointerX, &fgDisplay.pDisplay.DisplayPointerY, &fgDisplay.pDisplay.DisplayPointerX, &fgDisplay.pDisplay.DisplayPointerY, &junk_mask); # ifdef HAVE_X11_EXTENSIONS_XRANDR_H if(XRRQueryExtension(fgDisplay.pDisplay.Display, &event_base, &error_base)) { XRRScreenConfiguration *xrr_config; XRRScreenSize *ssizes; Rotation rot; int ssize_count, curr; if((xrr_config = XRRGetScreenInfo(fgDisplay.pDisplay.Display, fgDisplay.pDisplay.RootWindow))) { ssizes = XRRConfigSizes(xrr_config, &ssize_count); curr = XRRConfigCurrentConfiguration(xrr_config, &rot); fgDisplay.pDisplay.prev_xsz = ssizes[curr].width; fgDisplay.pDisplay.prev_ysz = ssizes[curr].height; fgDisplay.pDisplay.prev_refresh = -1; # if ( RANDR_MAJOR > 1 ) || ( ( RANDR_MAJOR == 1 ) && ( RANDR_MINOR >= 1 ) ) if(fgState.GameModeRefresh != -1) { fgDisplay.pDisplay.prev_refresh = XRRConfigCurrentRate(xrr_config); } # endif fgDisplay.pDisplay.prev_size_valid = 1; XRRFreeScreenConfigInfo(xrr_config); } } # endif /* * This highly depends on the XFree86 extensions, * not approved as X Consortium standards */ # ifdef HAVE_X11_EXTENSIONS_XF86VMODE_H if(!XF86VidModeQueryExtension(fgDisplay.pDisplay.Display, &event_base, &error_base)) { return; } /* * Remember the current ViewPort location of the screen to be able to * restore the ViewPort on LeaveGameMode(): */ if( !XF86VidModeGetViewPort( fgDisplay.pDisplay.Display, fgDisplay.pDisplay.Screen, &fgDisplay.pDisplay.DisplayViewPortX, &fgDisplay.pDisplay.DisplayViewPortY ) ) fgWarning( "XF86VidModeGetViewPort failed" ); /* Query the current display settings: */ fgDisplay.pDisplay.DisplayModeValid = XF86VidModeGetModeLine( fgDisplay.pDisplay.Display, fgDisplay.pDisplay.Screen, &fgDisplay.pDisplay.DisplayModeClock, &fgDisplay.pDisplay.DisplayMode ); if( !fgDisplay.pDisplay.DisplayModeValid ) fgWarning( "XF86VidModeGetModeLine failed" ); # endif }
void wsXInit( void* mDisplay ) { int eventbase; int errorbase; if(mDisplay){ wsDisplay=mDisplay; } else { char * DisplayName = ":0.0"; if ( getenv( "DISPLAY" ) ) DisplayName=getenv( "DISPLAY" ); wsDisplay=XOpenDisplay( DisplayName ); if ( !wsDisplay ) { mp_msg( MSGT_GPLAYER,MSGL_FATAL,MSGTR_WS_CouldNotOpenDisplay ); exit( 0 ); } } /* enable DND atoms */ wsXDNDInitialize(); { /* on remote display XShm will be disabled - LGB */ char *dispname=DisplayString(wsDisplay); int localdisp=1; if (dispname&&*dispname!=':') { localdisp=0; wsUseXShm=0; } mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"[ws] display name: %s => %s display.\n",dispname,localdisp?"local":"REMOTE"); if (!localdisp) mp_msg( MSGT_GPLAYER,MSGL_V,MSGTR_WS_RemoteDisplay ); } if ( !XShmQueryExtension( wsDisplay ) ) { mp_msg( MSGT_GPLAYER,MSGL_ERR,MSGTR_WS_NoXshm ); wsUseXShm=0; } #ifdef HAVE_XSHAPE if ( !XShapeQueryExtension( wsDisplay,&eventbase,&errorbase ) ) { mp_msg( MSGT_GPLAYER,MSGL_ERR,MSGTR_WS_NoXshape ); wsUseXShape=0; } #else wsUseXShape=0; #endif XSynchronize( wsDisplay,True ); wsScreen=DefaultScreen( wsDisplay ); wsRootWin=RootWindow( wsDisplay,wsScreen ); #ifdef HAVE_XF86VM { int clock; XF86VidModeModeLine modeline; XF86VidModeGetModeLine( wsDisplay,wsScreen,&clock ,&modeline ); wsMaxX=modeline.hdisplay; wsMaxY=modeline.vdisplay; } #endif { wsOrgX = wsOrgY = 0; if ( !wsMaxX ) wsMaxX=DisplayWidth( wsDisplay,wsScreen ); if ( !wsMaxY ) wsMaxY=DisplayHeight( wsDisplay,wsScreen ); } vo_screenwidth = wsMaxX; vo_screenheight = wsMaxY; xinerama_x = wsOrgX; xinerama_y = wsOrgY; update_xinerama_info(); wsMaxX = vo_screenwidth; wsMaxY = vo_screenheight; wsOrgX = xinerama_x; wsOrgY = xinerama_y; wsGetDepthOnScreen(); #ifdef DEBUG { int minor,major,shp; mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] Screen depth: %d\n",wsDepthOnScreen ); mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] size: %dx%d\n",wsMaxX,wsMaxY ); #ifdef HAVE_XINERAMA mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] origin: +%d+%d\n",wsOrgX,wsOrgY ); #endif mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] red mask: 0x%x\n",wsRedMask ); mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] green mask: 0x%x\n",wsGreenMask ); mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] blue mask: 0x%x\n",wsBlueMask ); if ( wsUseXShm ) { XShmQueryVersion( wsDisplay,&major,&minor,&shp ); mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] XShm version is %d.%d\n",major,minor ); } #ifdef HAVE_XSHAPE if ( wsUseXShape ) { XShapeQueryVersion( wsDisplay,&major,&minor ); mp_msg( MSGT_GPLAYER,MSGL_DBG2,"[ws] XShape version is %d.%d\n",major,minor ); } #endif } #endif wsOutMask=wsGetOutMask(); mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"[ws] Initialized converter: " ); sws_rgb2rgb_init(get_sws_cpuflags()); switch ( wsOutMask ) { case wsRGB32: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to rgb32\n" ); wsConvFunc=rgb32torgb32; break; case wsBGR32: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to bgr32\n" ); wsConvFunc=rgb32tobgr32; break; case wsRGB24: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to rgb24\n" ); wsConvFunc=rgb32to24; break; case wsBGR24: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to bgr24\n" ); wsConvFunc=rgb32tobgr24; break; case wsRGB16: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to rgb16\n" ); wsConvFunc=rgb32to16; break; case wsBGR16: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to bgr16\n" ); wsConvFunc=rgb32tobgr16; break; case wsRGB15: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to rgb15\n" ); wsConvFunc=rgb32to15; break; case wsBGR15: mp_dbg( MSGT_GPLAYER,MSGL_DBG2,"rgb32 to bgr15\n" ); wsConvFunc=rgb32tobgr15; break; } XSetErrorHandler( wsErrorHandler ); }
/* * Changes the current display mode to match user's settings */ GLboolean fgPlatformChangeDisplayMode( GLboolean haveToTest ) { GLboolean success = GL_FALSE; /* first try to use XRandR, then fallback to XF86VidMode */ # ifdef HAVE_X11_EXTENSIONS_XRANDR_H if(xrandr_resize(fgState.GameModeSize.X, fgState.GameModeSize.Y, fgState.GameModeRefresh, haveToTest) != -1) { return GL_TRUE; } # endif /* * This highly depends on the XFree86 extensions, * not approved as X Consortium standards */ # ifdef HAVE_X11_EXTENSIONS_XF86VMODE_H /* * This is also used by applications which check modes by calling * glutGameModeGet(GLUT_GAME_MODE_POSSIBLE), so allow the check: */ if( haveToTest || fgDisplay.pDisplay.DisplayModeValid ) { XF86VidModeModeInfo** displayModes; int i, displayModesCount; /* If we don't have a valid modeline in the display structure, which * can happen if this is called from glutGameModeGet instead of * glutEnterGameMode, then we need to query the current mode, to make * unspecified settings to default to their current values. */ if(!fgDisplay.pDisplay.DisplayModeValid) { if(!XF86VidModeGetModeLine(fgDisplay.pDisplay.Display, fgDisplay.pDisplay.Screen, &fgDisplay.pDisplay.DisplayModeClock, &fgDisplay.pDisplay.DisplayMode)) { return success; } } if (fgState.GameModeSize.X == -1) { fgState.GameModeSize.X = fgDisplay.pDisplay.DisplayMode.hdisplay; } if (fgState.GameModeSize.Y == -1) { fgState.GameModeSize.Y = fgDisplay.pDisplay.DisplayMode.vdisplay; } if (fgState.GameModeDepth == -1) { /* can't get color depth from this, nor can we change it, do nothing * TODO: get with XGetVisualInfo()? but then how to set? */ } if (fgState.GameModeRefresh == -1) { /* Compute the displays refresh rate, dotclock comes in kHz. */ int refresh = ( fgDisplay.pDisplay.DisplayModeClock * 1000 ) / ( fgDisplay.pDisplay.DisplayMode.htotal * fgDisplay.pDisplay.DisplayMode.vtotal ); fgState.GameModeRefresh = refresh; } /* query all possible display modes */ if( !XF86VidModeGetAllModeLines( fgDisplay.pDisplay.Display, fgDisplay.pDisplay.Screen, &displayModesCount, &displayModes ) ) { fgWarning( "XF86VidModeGetAllModeLines failed" ); return success; } /* * Check every of the modes looking for one that matches our demands, * ignoring the refresh rate if no exact match could be found. */ i = fghCheckDisplayModes( GL_TRUE, displayModesCount, displayModes ); if( i < 0 ) { i = fghCheckDisplayModes( GL_FALSE, displayModesCount, displayModes ); } success = ( i < 0 ) ? GL_FALSE : GL_TRUE; if( !haveToTest && success ) { if( !XF86VidModeSwitchToMode( fgDisplay.pDisplay.Display, fgDisplay.pDisplay.Screen, displayModes[ i ] ) ) fgWarning( "XF86VidModeSwitchToMode failed" ); } XFree( displayModes ); } # endif return success; }
void CL_DisplayWindow_OpenGL::set_fullscreen(int width, int height, int bpp, int refresh_rate) { if(fullscreen) return; // Vid-mode Switching XF86VidModeModeLine cur_mode; XF86VidModeGetModeLine(disp, 0, &dotclock, &cur_mode); old_mode.dotclock = dotclock; old_mode.hdisplay = cur_mode.hdisplay; old_mode.hsyncstart = cur_mode.hsyncstart; old_mode.hsyncend = cur_mode.hsyncend; old_mode.htotal = cur_mode.htotal; old_mode.vdisplay = cur_mode.vdisplay; old_mode.vsyncstart = cur_mode.vsyncstart; old_mode.vsyncend = cur_mode.vsyncend; old_mode.vtotal = cur_mode.vtotal; old_mode.flags = cur_mode.flags; old_mode.privsize = 0; int num_modes; XF86VidModeModeInfo **modes; XF86VidModeGetAllModeLines(disp, 0, &num_modes, &modes); std::list<XF86VidModeModeInfo *> usable_modes; for(int i = 0; i < num_modes; i++) { if(modes[i]->hdisplay == width && modes[i]->vdisplay == height) { CL_Log::log("debug", "Useable fullscreen mode found: %1x%2", width, height); usable_modes.push_back(modes[i]); } } if (usable_modes.empty()) { CL_Log::log("debug", "No useable fullscreen modes available!"); } else { if(!width) width = get_width(); if(!height) height = get_height(); if(!bpp) bpp = glx_bpp; //Hide Window if (0) { // FIXME: allow_override doesn't play together with // GrabPointer, not sure what is wrong but it simply doesn't // work. // // The code outside the 'if(0)' as it is now, works mostly, // however it doesn't work when the window or a part of it is // outside of the screen, since the window isn't moved // fullscreen will only show half the window, shouldn't be a // problem for most of the time, but will be tricky if the // window has equal size as the desktop. // Move the window into the right position, this must happen // BEFORE we remove control from the window manager XMoveResizeWindow(disp, window, 0, 0, width, height); // Move the mouse and switch moves XWarpPointer(disp, None, None, 0, 0, 0, 0, width/2, height/2); XUnmapWindow(disp, window); { // Wait for window to disapear XEvent event; do { XMaskEvent(disp, StructureNotifyMask, &event); } while ( (event.type != UnmapNotify) || (event.xunmap.event != window) ); } // Turn off WM control attributes.override_redirect = True; XChangeWindowAttributes(disp, window, CWBorderPixel | CWColormap | CWOverrideRedirect, &attributes); // Re-appear window XMapRaised(disp, window); } // Get input focus //XSetInputFocus(disp,window, RevertToNone, CurrentTime); while (1) { int result = XGrabPointer(disp, window, True, 0, GrabModeAsync, GrabModeAsync, window, None, CurrentTime); if ( result == GrabSuccess ) { break; } CL_System::sleep(100); } XF86VidModeGetViewPort(disp, DefaultScreen(disp), &old_x, &old_y); XF86VidModeSwitchToMode(disp, 0, *(usable_modes.begin())); Window child_window; int x, y; // Get the windows absolute position (aka relative to // the root window) XTranslateCoordinates(disp, window, DefaultRootWindow(disp), 0, 0, &x, &y, &child_window); XF86VidModeSetViewPort(disp, DefaultScreen(disp), x, y); XSync(disp, True); fullscreen = true; } }
static int xf86_dga_vidmode_find_best_vidmode(void) { int i; int bestmode = -1; int score, best_score = 0; #ifdef TDFX_DGA_WORKAROUND int dotclock; XF86VidModeModeLine modeline; XF86VidModeGetModeLine(display, xf86ctx.screen, &dotclock, &modeline); #endif if (!xf86ctx.modes) { xf86ctx.modes = XDGAQueryModes(display, xf86ctx.screen, &xf86ctx.mode_count); fprintf(stderr, "XDGA: info: found %d modes:\n", xf86ctx.mode_count); } /* also determine the max size of the display */ sysdep_display_properties.max_width = 0; sysdep_display_properties.max_height = 0; for(i=0;i<xf86ctx.mode_count;i++) { #ifdef TDFX_DGA_WORKAROUND if ((xf86ctx.current_mode == -1) && xf86ctx.modes[i].viewportWidth == modeline.hdisplay && xf86ctx.modes[i].viewportHeight == modeline.vdisplay) xf86ctx.current_X11_mode = xf86ctx.modes[i].num; #endif #if 0 /* DEBUG */ fprintf(stderr, "XDGA: info: (%d) %s\n", xf86ctx.modes[i].num, xf86ctx.modes[i].name); fprintf(stderr, " : VRefresh = %f [Hz]\n", xf86ctx.modes[i].verticalRefresh); /* flags */ fprintf(stderr, " : viewport = %dx%d\n", xf86ctx.modes[i].viewportWidth, xf86ctx.modes[i].viewportHeight); fprintf(stderr, " : image = %dx%d\n", xf86ctx.modes[i].imageWidth, xf86ctx.modes[i].imageHeight); if (xf86ctx.modes[i].flags & XDGAPixmap) fprintf(stderr, " : pixmap = %dx%d\n", xf86ctx.modes[i].pixmapWidth, xf86ctx.modes[i].pixmapHeight); fprintf(stderr, " : bytes/scanline = %d\n", xf86ctx.modes[i].bytesPerScanline); fprintf(stderr, " : byte order = %s\n", xf86ctx.modes[i].byteOrder == MSBFirst ? "MSBFirst" : xf86ctx.modes[i].byteOrder == LSBFirst ? "LSBFirst" : "Unknown"); fprintf(stderr, " : bpp = %d, depth = %d\n", xf86ctx.modes[i].bitsPerPixel, xf86ctx.modes[i].depth); fprintf(stderr, " : RGBMask = (%lx, %lx, %lx)\n", xf86ctx.modes[i].redMask, xf86ctx.modes[i].greenMask, xf86ctx.modes[i].blueMask); fprintf(stderr, " : visual class = %s\n", xf86ctx.modes[i].visualClass == TrueColor ? "TrueColor": xf86ctx.modes[i].visualClass == DirectColor ? "DirectColor" : xf86ctx.modes[i].visualClass == PseudoColor ? "PseudoColor" : "Unknown"); fprintf(stderr, " : xViewportStep = %d, yViewportStep = %d\n", xf86ctx.modes[i].xViewportStep, xf86ctx.modes[i].yViewportStep); fprintf(stderr, " : maxViewportX = %d, maxViewportY = %d\n", xf86ctx.modes[i].maxViewportX, xf86ctx.modes[i].maxViewportY); /* viewportFlags */ #endif /* we only support TrueColor visuals */ if(xf86ctx.modes[i].visualClass != TrueColor) continue; score = mode_match(xf86ctx.modes[i].viewportWidth, xf86ctx.modes[i].viewportHeight, xf86ctx.modes[i].bytesPerScanline * 8 / xf86ctx.modes[i].bitsPerPixel, xf86ctx.modes[i].depth, xf86ctx.modes[i].bitsPerPixel); if(score > best_score) { best_score = score; bestmode = xf86ctx.modes[i].num; } /* also determine the max size of the display */ if(xf86ctx.modes[i].viewportWidth > sysdep_display_properties.max_width) sysdep_display_properties.max_width = xf86ctx.modes[i].viewportWidth; if(xf86ctx.modes[i].viewportHeight > sysdep_display_properties.max_height) sysdep_display_properties.max_height = xf86ctx.modes[i].viewportHeight; } return bestmode; }
static int SwitchRes(char inout, int x, int y, int w, int h, int *dw, int *dh) { static int vp_x, vp_y; XF86VidModeModeInfo *mode; int scr; scr = Dpy.screen; if (inout) { XF86VidModeModeLine curmode; int dotclock; int rx, ry; if (!XF86VidModeGetModeLine(disp, scr, &dotclock, &curmode)) return 0; XF86VidModeGetViewPort(disp, scr, &vp_x, &vp_y); mode = FindMode(w, h); if (mode) { #if USE_XRANDR int vw, vh; vw = WinGetW(VROOT); vh = WinGetH(VROOT); /* x and y relative to unrotated display */ if (Mode.screen.rotation == RR_Rotate_90) { rx = y; ry = vw - mode->vdisplay - x; } else if (Mode.screen.rotation == RR_Rotate_270) { rx = vh - mode->hdisplay - y; ry = x; } else if (Mode.screen.rotation == RR_Rotate_180) { rx = vw - mode->hdisplay - x; ry = vh - mode->vdisplay - y; } else #endif { rx = x; ry = y; } #if USE_XRANDR if ((Mode.screen.rotation == RR_Rotate_90) || (Mode.screen.rotation == RR_Rotate_270)) { *dw = mode->vdisplay; *dh = mode->hdisplay; } else #endif { *dw = mode->hdisplay; *dh = mode->vdisplay; } XF86VidModeLockModeSwitch(disp, scr, 0); std_vid_mode_cur = GetModeIndex(dotclock, &curmode); XF86VidModeSwitchToMode(disp, scr, mode); XF86VidModeSetViewPort(disp, scr, rx, ry); XF86VidModeLockModeSwitch(disp, scr, 1); return 1; } } else { mode = std_vid_modes[std_vid_mode_cur]; XF86VidModeLockModeSwitch(disp, scr, 0); XF86VidModeSwitchToMode(disp, scr, mode); XF86VidModeSetViewPort(disp, scr, vp_x, vp_y); #if 0 /* No, don't lock or we can't switch resolution */ XF86VidModeLockModeSwitch(disp, scr, 1); #endif } return 0; }
void gl_thread::Runnable3DVision() { try { assert(_vo_qt_widget->context()->isValid()); _vo_qt_widget->makeCurrent(); assert(QGLContext::currentContext() == _vo_qt_widget->context()); // initialize communications with the usb emitter nv_ctx = nvstusb_init(); if (nv_ctx == NULL) { fprintf(stderr, "Could not initialize NVIDIA 3D Vision IR emitter!\n"); exit(EXIT_FAILURE); } Display *display = XOpenDisplay(0); double display_num = DefaultScreen(display); XF86VidModeModeLine mode_line; int pixel_clk = 0; XF86VidModeGetModeLine(display, display_num, &pixel_clk, &mode_line); double frame_rate = (double) pixel_clk * 1000.0 / mode_line.htotal / mode_line.vtotal; printf("Detected refresh rate of %f Hz.\n", (frame_rate)); nvstusb_set_rate(nv_ctx, frame_rate); bool odd = false; struct timeval start, end; long useconds; gettimeofday(&start, NULL); GLuint count; while (_render) { { _wait_mutex.lock(); if (_action_activate) { try { _vo_qt->video_output::activate_next_frame(); } catch (std::exception& e) { _e = e; _render = false; _failure = true; } _action_activate = false; _wait_cond.wake_one(); } _wait_mutex.unlock(); } if (_failure) break; _wait_mutex.lock(); if (_action_prepare) { try { _vo_qt->video_output::prepare_next_frame(_next_frame, _next_subtitle); } catch (std::exception& e) { _e = e; _render = false; _failure = true; } _action_prepare = false; _wait_cond.wake_one(); } _wait_mutex.unlock(); if (_failure) break; if (_w > 0 && _h > 0 && (_vo_qt->full_display_width() != _w || _vo_qt->full_display_height() != _h)) { _vo_qt->reshape(_w, _h); } { _vo_qt->display_current_frame(0); _vo_qt_widget->swapBuffers(); gettimeofday(&end, NULL); useconds = end.tv_usec - start.tv_usec; nvstusb_swap_eye(nv_ctx, (nvstusb_eye) (0), useconds); gettimeofday(&start, NULL); //glXGetVideoSyncSGI(&count); //glXWaitVideoSyncSGI(2, (count +1)%2, &count); _vo_qt->display_current_frame(1); _vo_qt_widget->swapBuffers(); gettimeofday(&end, NULL); useconds = end.tv_usec - start.tv_usec; nvstusb_swap_eye(nv_ctx, (nvstusb_eye) (1), useconds); gettimeofday(&start, NULL); } } } catch (std::exception& e) { _e = e; _render = false; _failure = true; } _wait_mutex.lock(); if (_action_activate || _action_prepare) { while (!_action_finished) { _wait_cond.wake_one(); _wait_mutex.unlock(); _wait_mutex.lock(); } } _wait_mutex.unlock(); _vo_qt_widget->doneCurrent(); #if QT_VERSION >= 0x050000 _vo_qt_widget->context()->moveToThread(QCoreApplication::instance()->thread()); #endif nvstusb_deinit(nv_ctx); }
/*!*********************************************************************** @Function OpenX11Window @Return true on success @Description Opens an X11 window. This must be called after SelectEGLConfiguration() for gEglConfig to be valid *************************************************************************/ int PVRShellInitOS::OpenX11Window(const PVRShell &shell) { XSetWindowAttributes WinAttibutes; XSizeHints sh; XEvent event; unsigned long mask; #ifdef BUILD_OGL XF86VidModeModeInfo **modes; // modes of display int numModes; // number of modes of display int chosenMode; int edimx,edimy; //established width and height of the chosen modeline int i; #endif int depth = DefaultDepth(m_X11Display, m_X11Screen); m_X11Visual = new XVisualInfo; XMatchVisualInfo( m_X11Display, m_X11Screen, depth, TrueColor, m_X11Visual); if( !m_X11Visual ) { shell.PVRShellOutputDebug( "Unable to acquire visual" ); return false; } m_X11ColorMap = XCreateColormap( m_X11Display, RootWindow(m_X11Display, m_X11Screen), m_X11Visual->visual, AllocNone ); #ifdef BUILD_OGL m_i32OriginalModeDotClock = XF86VidModeBadClock; if(shell.m_pShellData->bFullScreen) { // Get mode lines to see if there is requested modeline XF86VidModeGetAllModeLines(m_X11Display, m_X11Screen, &numModes, &modes); // look for mode with requested resolution chosenMode = -1; i=0; while((chosenMode == -1)&&(i<numModes)) { if ((modes[i]->hdisplay == shell.m_pShellData->nShellDimX) && (modes[i]->vdisplay == shell.m_pShellData->nShellDimY)) { chosenMode = i; } ++i; } // If there is no requested resolution among modelines then terminate if(chosenMode == -1) { shell.PVRShellOutputDebug( "Chosen resolution for full screen mode does not match any modeline available.\n" ); return false; } // save desktop-resolution before switching modes XF86VidModeGetModeLine(m_X11Display,m_X11Screen, &m_i32OriginalModeDotClock, &m_OriginalMode ); XF86VidModeSwitchToMode(m_X11Display, m_X11Screen, modes[chosenMode]); XF86VidModeSetViewPort(m_X11Display, m_X11Screen, 0, 0); edimx = modes[chosenMode]->hdisplay; edimy = modes[chosenMode]->vdisplay; printf("Fullscreen Resolution %dx%d (chosen mode = %d)\n", edimx, edimy,chosenMode); XFree(modes); WinAttibutes.colormap = m_X11ColorMap; WinAttibutes.background_pixel = 0xFFFFFFFF; WinAttibutes.border_pixel = 0; WinAttibutes.override_redirect = true; // add to these for handling other events WinAttibutes.event_mask = StructureNotifyMask | ExposureMask | ButtonPressMask | ButtonReleaseMask | Button1MotionMask | KeyPressMask | KeyReleaseMask; // The diffrence is that we want to ignore influence of window manager for our fullscreen window mask = CWBackPixel | CWBorderPixel | CWEventMask | CWColormap | CWOverrideRedirect; m_X11Window = XCreateWindow( m_X11Display, RootWindow(m_X11Display, m_X11Screen), 0, 0, edimx, edimy, 0, CopyFromParent, InputOutput, CopyFromParent, mask, &WinAttibutes); // keeping the pointer of mouse and keyboard in window to prevent from scrolling the virtual screen XWarpPointer(m_X11Display, None ,m_X11Window, 0, 0, 0, 0, 0, 0); // Map and then wait till mapped, grabbing should be after mapping the window XMapWindow( m_X11Display, m_X11Window ); XGrabKeyboard(m_X11Display, m_X11Window, True, GrabModeAsync, GrabModeAsync, CurrentTime); XGrabPointer(m_X11Display, m_X11Window, True, ButtonPressMask, GrabModeAsync, GrabModeAsync, m_X11Window, None, CurrentTime); XIfEvent( m_X11Display, &event, WaitForMapNotify, (char*)m_X11Window ); } else #endif { // For OGLES we assume that chaning of video mode is not available (freedesktop does not allow to do it) // so if requested resolution differs from the display dims then we quit #ifndef BUILD_OGL int display_width = XDisplayWidth(m_X11Display,m_X11Screen); int display_height = XDisplayHeight(m_X11Display,m_X11Screen); if((shell.m_pShellData->bFullScreen)&&((shell.m_pShellData->nShellDimX != display_width)||(shell.m_pShellData->nShellDimY != display_height)) ) { shell.PVRShellOutputDebug( "Chosen resolution for full screen mode does not match available modeline.\n" ); return false; } #endif WinAttibutes.colormap = m_X11ColorMap; WinAttibutes.background_pixel = 0xFFFFFFFF; WinAttibutes.border_pixel = 0; // add to these for handling other events WinAttibutes.event_mask = StructureNotifyMask | ExposureMask | ButtonPressMask | ButtonReleaseMask | Button1MotionMask | KeyPressMask | KeyReleaseMask; // The attribute mask mask = CWBackPixel | CWBorderPixel | CWEventMask | CWColormap ; m_X11Window = XCreateWindow( m_X11Display, // Display RootWindow(m_X11Display, m_X11Screen), // Parent shell.m_pShellData->nShellPosX, // X position of window shell.m_pShellData->nShellPosY, // Y position of window shell.m_pShellData->nShellDimX, // Window width shell.m_pShellData->nShellDimY, // Window height 0, // Border width CopyFromParent, // Depth (taken from parent) InputOutput, // Window class CopyFromParent, // Visual type (taken from parent) mask, // Attributes mask &WinAttibutes); // Attributes // Set the window position sh.flags = USPosition; sh.x = shell.m_pShellData->nShellPosX; sh.y = shell.m_pShellData->nShellPosY; XSetStandardProperties( m_X11Display, m_X11Window, shell.m_pShellData->pszAppName, shell.m_pShellData->pszAppName, None, 0, 0, &sh ); // Map and then wait till mapped XMapWindow( m_X11Display, m_X11Window ); XIfEvent( m_X11Display, &event, WaitForMapNotify, (char*)m_X11Window ); // An attempt to hide a border for fullscreen on non OGL apis (OGLES,OGLES2) if(shell.m_pShellData->bFullScreen) { XEvent xev; Atom wmState = XInternAtom(m_X11Display, "_NET_WM_STATE", False); Atom wmStateFullscreen = XInternAtom(m_X11Display, "_NET_WM_STATE_FULLSCREEN", False); memset(&xev, 0, sizeof(XEvent)); xev.type = ClientMessage; xev.xclient.window = m_X11Window; xev.xclient.message_type = wmState; xev.xclient.format = 32; xev.xclient.data.l[0] = 1; xev.xclient.data.l[1] = wmStateFullscreen; xev.xclient.data.l[2] = 0; XSendEvent(m_X11Display, RootWindow(m_X11Display, m_X11Screen), False, SubstructureNotifyMask, &xev); } Atom wmDelete = XInternAtom(m_X11Display, "WM_DELETE_WINDOW", True); XSetWMProtocols(m_X11Display, m_X11Window, &wmDelete, 1); XSetWMColormapWindows( m_X11Display, m_X11Window, &m_X11Window, 1 ); } XFlush( m_X11Display ); return true; }
/* * Remembers the current visual settings, so that * we can change them and restore later... */ static void fghRememberState( void ) { #if TARGET_HOST_POSIX_X11 int event_base, error_base; /* * Remember the current pointer location before going fullscreen * for restoring it later: */ Window junk_window; unsigned int junk_mask; XQueryPointer(fgDisplay.Display, fgDisplay.RootWindow, &junk_window, &junk_window, &fgDisplay.DisplayPointerX, &fgDisplay.DisplayPointerY, &fgDisplay.DisplayPointerX, &fgDisplay.DisplayPointerY, &junk_mask); # ifdef HAVE_X11_EXTENSIONS_XRANDR_H if(XRRQueryExtension(fgDisplay.Display, &event_base, &error_base)) { XRRScreenConfiguration *xrr_config; XRRScreenSize *ssizes; Rotation rot; int ssize_count, curr; if((xrr_config = XRRGetScreenInfo(fgDisplay.Display, fgDisplay.RootWindow))) { ssizes = XRRConfigSizes(xrr_config, &ssize_count); curr = XRRConfigCurrentConfiguration(xrr_config, &rot); fgDisplay.prev_xsz = ssizes[curr].width; fgDisplay.prev_ysz = ssizes[curr].height; fgDisplay.prev_refresh = -1; # if ( RANDR_MAJOR >= 1 ) || ( ( RANDR_MAJOR == 1 ) && ( RANDR_MINOR >= 1 ) ) if(fgState.GameModeRefresh != -1) { fgDisplay.prev_refresh = XRRConfigCurrentRate(xrr_config); } # endif fgDisplay.prev_size_valid = 1; XRRFreeScreenConfigInfo(xrr_config); } } # endif /* * This highly depends on the XFree86 extensions, * not approved as X Consortium standards */ # ifdef HAVE_X11_EXTENSIONS_XF86VMODE_H if(!XF86VidModeQueryExtension(fgDisplay.Display, &event_base, &error_base)) { return; } /* * Remember the current ViewPort location of the screen to be able to * restore the ViewPort on LeaveGameMode(): */ if( !XF86VidModeGetViewPort( fgDisplay.Display, fgDisplay.Screen, &fgDisplay.DisplayViewPortX, &fgDisplay.DisplayViewPortY ) ) fgWarning( "XF86VidModeGetViewPort failed" ); /* Query the current display settings: */ fgDisplay.DisplayModeValid = XF86VidModeGetModeLine( fgDisplay.Display, fgDisplay.Screen, &fgDisplay.DisplayModeClock, &fgDisplay.DisplayMode ); if( !fgDisplay.DisplayModeValid ) fgWarning( "XF86VidModeGetModeLine failed" ); # endif #elif TARGET_HOST_MS_WINDOWS /* DEVMODE devMode; */ /* Grab the current desktop settings... */ /* hack to get around my stupid cross-gcc headers */ #define FREEGLUT_ENUM_CURRENT_SETTINGS -1 EnumDisplaySettings( fgDisplay.DisplayName, FREEGLUT_ENUM_CURRENT_SETTINGS, &fgDisplay.DisplayMode ); /* Make sure we will be restoring all settings needed */ fgDisplay.DisplayMode.dmFields |= DM_PELSWIDTH | DM_PELSHEIGHT | DM_BITSPERPEL | DM_DISPLAYFREQUENCY; #endif }
/* * Changes the current display mode to match user's settings */ static GLboolean fghChangeDisplayMode( GLboolean haveToTest ) { GLboolean success = GL_FALSE; #if TARGET_HOST_POSIX_X11 /* first try to use XRandR, then fallback to XF86VidMode */ # ifdef HAVE_X11_EXTENSIONS_XRANDR_H if(xrandr_resize(fgState.GameModeSize.X, fgState.GameModeSize.Y, fgState.GameModeRefresh, haveToTest) != -1) { return GL_TRUE; } # endif /* * This highly depends on the XFree86 extensions, * not approved as X Consortium standards */ # ifdef HAVE_X11_EXTENSIONS_XF86VMODE_H /* * This is also used by applications which check modes by calling * glutGameModeGet(GLUT_GAME_MODE_POSSIBLE), so allow the check: */ if( haveToTest || fgDisplay.DisplayModeValid ) { XF86VidModeModeInfo** displayModes; int i, displayModesCount; /* If we don't have a valid modeline in the display structure, which * can happen if this is called from glutGameModeGet instead of * glutEnterGameMode, then we need to query the current mode, to make * unspecified settings to default to their current values. */ if(!fgDisplay.DisplayModeValid) { if(!XF86VidModeGetModeLine(fgDisplay.Display, fgDisplay.Screen, &fgDisplay.DisplayModeClock, &fgDisplay.DisplayMode)) { return success; } } if (fgState.GameModeSize.X == -1) { fgState.GameModeSize.X = fgDisplay.DisplayMode.hdisplay; } if (fgState.GameModeSize.Y == -1) { fgState.GameModeSize.Y = fgDisplay.DisplayMode.vdisplay; } if (fgState.GameModeDepth == -1) { /* can't get color depth from this, nor can we change it, do nothing * TODO: get with XGetVisualInfo()? but then how to set? */ } if (fgState.GameModeRefresh == -1) { /* Compute the displays refresh rate, dotclock comes in kHz. */ int refresh = ( fgDisplay.DisplayModeClock * 1000 ) / ( fgDisplay.DisplayMode.htotal * fgDisplay.DisplayMode.vtotal ); fgState.GameModeRefresh = refresh; } /* query all possible display modes */ if( !XF86VidModeGetAllModeLines( fgDisplay.Display, fgDisplay.Screen, &displayModesCount, &displayModes ) ) { fgWarning( "XF86VidModeGetAllModeLines failed" ); return success; } /* * Check every of the modes looking for one that matches our demands, * ignoring the refresh rate if no exact match could be found. */ i = fghCheckDisplayModes( GL_TRUE, displayModesCount, displayModes ); if( i < 0 ) { i = fghCheckDisplayModes( GL_FALSE, displayModesCount, displayModes ); } success = ( i < 0 ) ? GL_FALSE : GL_TRUE; if( !haveToTest && success ) { if( !XF86VidModeSwitchToMode( fgDisplay.Display, fgDisplay.Screen, displayModes[ i ] ) ) fgWarning( "XF86VidModeSwitchToMode failed" ); } XFree( displayModes ); } # endif #elif TARGET_HOST_MS_WINDOWS DEVMODE devMode; char *fggmstr = NULL; char displayMode[300]; success = GL_FALSE; EnumDisplaySettings( fgDisplay.DisplayName, -1, &devMode ); devMode.dmFields = 0; if (fgState.GameModeSize.X!=-1) { devMode.dmPelsWidth = fgState.GameModeSize.X; devMode.dmFields |= DM_PELSWIDTH; } if (fgState.GameModeSize.Y!=-1) { devMode.dmPelsHeight = fgState.GameModeSize.Y; devMode.dmFields |= DM_PELSHEIGHT; } if (fgState.GameModeDepth!=-1) { devMode.dmBitsPerPel = fgState.GameModeDepth; devMode.dmFields |= DM_BITSPERPEL; } if (fgState.GameModeRefresh!=-1) { devMode.dmDisplayFrequency = fgState.GameModeRefresh; devMode.dmFields |= DM_DISPLAYFREQUENCY; } switch ( ChangeDisplaySettingsEx(fgDisplay.DisplayName, &devMode, NULL, haveToTest ? CDS_TEST : CDS_FULLSCREEN , NULL) ) { case DISP_CHANGE_SUCCESSFUL: success = GL_TRUE; if (!haveToTest) { /* update vars in case if windows switched to proper mode */ EnumDisplaySettings( fgDisplay.DisplayName, FREEGLUT_ENUM_CURRENT_SETTINGS, &devMode ); fgState.GameModeSize.X = devMode.dmPelsWidth; fgState.GameModeSize.Y = devMode.dmPelsHeight; fgState.GameModeDepth = devMode.dmBitsPerPel; fgState.GameModeRefresh = devMode.dmDisplayFrequency; } break; case DISP_CHANGE_RESTART: fggmstr = "The computer must be restarted for the graphics mode to work."; break; case DISP_CHANGE_BADFLAGS: fggmstr = "An invalid set of flags was passed in."; break; case DISP_CHANGE_BADPARAM: fggmstr = "An invalid parameter was passed in. This can include an invalid flag or combination of flags."; break; case DISP_CHANGE_FAILED: fggmstr = "The display driver failed the specified graphics mode."; break; case DISP_CHANGE_BADMODE: fggmstr = "The graphics mode is not supported."; break; default: fggmstr = "Unknown error in graphics mode???"; /* dunno if it is possible,MSDN does not mention any other error */ break; } if ( !success ) { /* I'd rather get info whats going on in my program than wonder about */ /* magic happenings behind my back, its lib for devels at last ;) */ /* append display mode to error to make things more informative */ sprintf(displayMode,"%s Problem with requested mode: %ix%i:%i@%i", fggmstr, devMode.dmPelsWidth, devMode.dmPelsHeight, devMode.dmBitsPerPel, devMode.dmDisplayFrequency); fgWarning(displayMode); } #endif return success; }
void wsXInit(Display *mDisplay) { int eventbase; int errorbase; // NOTE TO MYSELF: Use global mDisplay, get rid of wsDisplay. wsDisplay = mDisplay; XSetErrorHandler(wsErrorHandler); /* enable DND atoms */ wsXDNDInitialize(); { /* on remote display XShm will be disabled - LGB */ char *dispname = DisplayString(wsDisplay); int localdisp = 1; if (dispname && *dispname != ':') { localdisp = 0; wsUseXShm = 0; } mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] display name: %s => %s display.\n", dispname, localdisp ? "local" : "REMOTE"); if (!localdisp) mp_msg(MSGT_GPLAYER, MSGL_INFO, MSGTR_WS_RemoteDisplay); } if (!XShmQueryExtension(wsDisplay)) { mp_msg(MSGT_GPLAYER, MSGL_INFO, MSGTR_WS_NoXshm); wsUseXShm = 0; } #ifdef CONFIG_XSHAPE if (!XShapeQueryExtension(wsDisplay, &eventbase, &errorbase)) { mp_msg(MSGT_GPLAYER, MSGL_WARN, MSGTR_WS_NoXshape); wsUseXShape = 0; } #else wsUseXShape = 0; #endif XSynchronize(wsDisplay, True); wsScreen = DefaultScreen(wsDisplay); wsRootWin = RootWindow(wsDisplay, wsScreen); #ifdef CONFIG_XF86VM { int clock; XF86VidModeModeLine modeline; XF86VidModeGetModeLine(wsDisplay, wsScreen, &clock, &modeline); wsMaxX = modeline.hdisplay; wsMaxY = modeline.vdisplay; } #endif { wsOrgX = wsOrgY = 0; if (!wsMaxX) wsMaxX = DisplayWidth(wsDisplay, wsScreen); if (!wsMaxY) wsMaxY = DisplayHeight(wsDisplay, wsScreen); } vo_screenwidth = wsMaxX; vo_screenheight = wsMaxY; xinerama_x = wsOrgX; xinerama_y = wsOrgY; update_xinerama_info(); wsMaxX = vo_screenwidth; wsMaxY = vo_screenheight; wsOrgX = xinerama_x; wsOrgY = xinerama_y; wsGetDepthOnScreen(); mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] Screen depth: %d\n", wsDepthOnScreen); mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] size: %dx%d\n", wsMaxX, wsMaxY); #ifdef CONFIG_XINERAMA mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] origin: +%d+%d\n", wsOrgX, wsOrgY); #endif mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] red mask: 0x%x\n", wsRedMask); mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] green mask: 0x%x\n", wsGreenMask); mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] blue mask: 0x%x\n", wsBlueMask); #ifdef MP_DEBUG if (wsUseXShm) { int minor, major, shp; XShmQueryVersion(wsDisplay, &major, &minor, &shp); mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] XShm version is %d.%d\n", major, minor); } #ifdef CONFIG_XSHAPE if (wsUseXShape) { int minor, major; XShapeQueryVersion(wsDisplay, &major, &minor); mp_dbg(MSGT_GPLAYER, MSGL_DBG2, "[ws] XShape version is %d.%d\n", major, minor); } #endif #endif wsOutMask = wsGetOutMask(); switch (wsOutMask) { case wsRGB32: out_pix_fmt = PIX_FMT_RGB32; break; case wsBGR32: out_pix_fmt = PIX_FMT_BGR32; break; case wsRGB24: out_pix_fmt = PIX_FMT_RGB24; break; case wsBGR24: out_pix_fmt = PIX_FMT_BGR24; break; case wsRGB16: out_pix_fmt = PIX_FMT_RGB565; break; case wsBGR16: out_pix_fmt = PIX_FMT_BGR565; break; case wsRGB15: out_pix_fmt = PIX_FMT_RGB555; break; case wsBGR15: out_pix_fmt = PIX_FMT_BGR555; break; } }
float PsychSetNominalFramerate(int screenNumber, float requestedHz) { // Information returned by/sent to the XF86VidModeExtension: XF86VidModeModeLine mode_line; // The mode line of the current video mode. int dot_clock; // The RAMDAC / TDMS pixel clock frequency. int rc; int event_base; // We start with a default vrefresh of zero, which means "couldn't query refresh from OS": float vrefresh = 0; if(screenNumber>=numDisplays) PsychErrorExitMsg(PsychError_internal, "screenNumber is out of range"); if (!XF86VidModeSetClientVersion(displayCGIDs[screenNumber])) { // Failed to use VidMode-Extension. We just return a vrefresh of zero. return(0); } if (!XF86VidModeQueryExtension(displayCGIDs[screenNumber], &event_base, &x11_errorbase)) { // Failed to use VidMode-Extension. We just return a vrefresh of zero. return(0); } // Attach our error callback handler and reset error-state: x11_errorval = 0; x11_olderrorhandler = XSetErrorHandler(x11VidModeErrorHandler); // Step 1: Query current dotclock and modeline: if (!XF86VidModeGetModeLine(displayCGIDs[screenNumber], PsychGetXScreenIdForScreen(screenNumber), &dot_clock, &mode_line)) { // Restore default error handler: XSetErrorHandler(x11_olderrorhandler); PsychErrorExitMsg(PsychError_internal, "Failed to query video dotclock and modeline!"); } // Step 2: Calculate updated modeline: if (requestedHz > 10) { // Step 2-a: Given current dot-clock and modeline and requested vrefresh, compute // modeline for closest possible match: requestedHz*=1000.0f; vrefresh = (((dot_clock * 1000) / mode_line.htotal) * 1000) / requestedHz; // Assign it to closest modeline setting: mode_line.vtotal = (int)(vrefresh + 0.5f); } else { // Step 2-b: Delta mode. requestedHz represents a direct integral offset // to add or subtract from current modeline setting: mode_line.vtotal+=(int) requestedHz; } // Step 3: Try to set new modeline: if (!XF86VidModeModModeLine(displayCGIDs[screenNumber], PsychGetXScreenIdForScreen(screenNumber), &mode_line)) { // Restore default error handler: XSetErrorHandler(x11_olderrorhandler); // Invalid modeline? Signal this: return(-1); } // We synchronize and wait for X-Request completion. If the modeline was invalid, // this will trigger an invocation of our errorhandler, which in turn will // set the x11_errorval to a non-zero value: XSync(displayCGIDs[screenNumber], FALSE); // Restore default error handler: XSetErrorHandler(x11_olderrorhandler); // Check for error: if (x11_errorval) { // Failed to set new mode! Must be invalid. We return -1 to signal this: return(-1); } // No error... // Step 4: Query new settings and return them: vrefresh = PsychGetNominalFramerate(screenNumber); // Done. return(vrefresh); }
void S9xInitDisplay (int argc, char **argv) { Screen *scrn; XSetWindowAttributes xattr; signal (SIGINT, quit); signal (SIGTERM, quit); if ((ourdisp = XOpenDisplay(NULL)) == NULL) { printf ("Can't connect to X server!\n"); S9xExit (); } ourscreen = DefaultScreen (ourdisp); scrn = DefaultScreenOfDisplay (ourdisp); ourvideo.bitdepth = DefaultDepth (ourdisp, ourscreen); ourvideo.screendepth = ourvideo.bitdepth / 8; rootWindow = RootWindowOfScreen (scrn); xattr.override_redirect = True; inputwin = XCreateWindow (ourdisp, RootWindowOfScreen(scrn), 10, 10, 100, 100, 0, 0, InputOutput, DefaultVisualOfScreen(scrn), CWOverrideRedirect, &xattr); XMapWindow (ourdisp, inputwin); ourvideo.height = HeightOfScreen (scrn); switch (ourvideo.bitdepth) { case 8: Settings.SixteenBit = FALSE; Settings.Transparency = FALSE; cmap = XCreateColormap (ourdisp, rootWindow, DefaultVisualOfScreen (scrn), AllocAll); XSetWindowColormap (ourdisp, inputwin, cmap); for (int i=0; i<256; i++) { colors[i].pixel = i; colors[i].flags = DoRed | DoGreen | DoBlue; } break; case 16: Settings.SixteenBit = TRUE; if (!Settings.ForceNoTransparency) Settings.Transparency = TRUE; break; case 24: if (is32or24 == 32) { ourvideo.bitdepth = 32; ourvideo.screendepth = 4; } Settings.SixteenBit = TRUE; if (!Settings.ForceNoTransparency) Settings.Transparency = TRUE; break; default: printf ("Color depth %d not supported!\n"); S9xExit (); break; } printf ("Found %d bit display\n", ourvideo.bitdepth); XFree(scrn); XF86DGAGetVideo (ourdisp, ourscreen, &(ourvideo.vidMemBegin), &(ourvideo.width), &(ourvideo.banksize), &(ourvideo.memsize)); #ifdef USE_XF86VIDMODE { XF86VidModeModeInfo **all_modes; int mode_count; XF86VidModeModeLine mod_tmp; int dotclock_tmp; int x; XF86VidModeGetModeLine (ourdisp, ourscreen, &dotclock_tmp, &mod_tmp); orig_mode = ModeLine2ModeInfo (mod_tmp, dotclock_tmp); if (orig_mode->hdisplay == 320 && orig_mode->vdisplay == 240) { mod320x240 = orig_mode; } else { XF86VidModeGetAllModeLines (ourdisp,ourscreen, &mode_count, &all_modes); for (x = 0; x < mode_count; x++) if (all_modes[x]->hdisplay == 320 && all_modes[x]->vdisplay == 240) { mod320x240 = (XF86VidModeModeInfo *) malloc ( sizeof(XF86VidModeModeInfo)); *mod320x240 = *(all_modes[x]); break; } else XFree (all_modes[x]->c_private); if (mod320x240 == NULL) { printf ("No 320x240 mode available!\n"); S9xExit (); } } XFree(all_modes); } #endif GFX.Pitch = IMAGE_WIDTH * (Settings.SixteenBit ? 2 : 1); GFX.Screen = (uint8 *) malloc (IMAGE_HEIGHT * GFX.Pitch); if (Settings.Transparency) GFX.SubScreen = (uint8 *) malloc (IMAGE_HEIGHT * GFX.Pitch); switch (ourvideo.bitdepth) { case 8: mWide = IMAGE_WIDTH / 4; mHigh = IMAGE_HEIGHT; mEtoE = (ourvideo.width - IMAGE_WIDTH) /4; break; case 16: mWide = IMAGE_WIDTH / 2; mHigh = IMAGE_HEIGHT; mEtoE = (ourvideo.width - IMAGE_WIDTH) / 2; break; case 24: mWide = IMAGE_WIDTH; mHigh = IMAGE_HEIGHT; mEtoE = (ourvideo.width - IMAGE_WIDTH) * 3; break; case 32: mWide = IMAGE_WIDTH; mHigh = IMAGE_HEIGHT; mEtoE = (ourvideo.width - IMAGE_WIDTH) * 4; default: break; } ourvideo.scrnBegin = ourvideo.vidMemBegin + (320 - IMAGE_WIDTH) * ourvideo.screendepth / 2 + ourvideo.width * ourvideo.screendepth * 8; }
void wsInit(Display *display) { int eventbase; int errorbase; mp_msg(MSGT_GPLAYER, MSGL_V, "X init.\n"); wsDisplay = display; wsSetErrorHandler(); /* enable DND atoms */ wsXDNDInitialize(); { /* on remote display XShm will be disabled - LGB */ char *dispname = DisplayString(wsDisplay); int localdisp = 1; if (dispname && *dispname != ':') { localdisp = 0; wsUseXShm = False; } mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] display name: %s => %s display.\n", dispname, localdisp ? "local" : "REMOTE"); if (!localdisp) mp_msg(MSGT_GPLAYER, MSGL_INFO, MSGTR_WS_RemoteDisplay); } #ifdef HAVE_SHM if (!XShmQueryExtension(wsDisplay)) #endif wsUseXShm = False; if (!wsUseXShm) mp_msg(MSGT_GPLAYER, MSGL_INFO, MSGTR_WS_NoXshm); #ifdef CONFIG_XSHAPE if (!XShapeQueryExtension(wsDisplay, &eventbase, &errorbase)) #endif wsUseXShape = False; if (!wsUseXShape) mp_msg(MSGT_GPLAYER, MSGL_WARN, MSGTR_WS_NoXshape); XSynchronize(wsDisplay, True); wsScreen = DefaultScreen(wsDisplay); wsRootWin = RootWindow(wsDisplay, wsScreen); #ifdef CONFIG_XF86VM { int clock; XF86VidModeModeLine modeline; XF86VidModeGetModeLine(wsDisplay, wsScreen, &clock, &modeline); wsMaxX = modeline.hdisplay; wsMaxY = modeline.vdisplay; } #endif { wsOrgX = wsOrgY = 0; if (!wsMaxX) wsMaxX = DisplayWidth(wsDisplay, wsScreen); if (!wsMaxY) wsMaxY = DisplayHeight(wsDisplay, wsScreen); } wsWindowUpdateXinerama(NULL); wsGetScreenDepth(); mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] Screen depth: %d\n", wsScreenDepth); mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] size: %dx%d\n", wsMaxX, wsMaxY); #ifdef CONFIG_XINERAMA mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] origin: +%d+%d\n", wsOrgX, wsOrgY); #endif mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] red mask: 0x%x\n", wsRedMask); mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] green mask: 0x%x\n", wsGreenMask); mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] blue mask: 0x%x\n", wsBlueMask); #ifdef HAVE_SHM if (wsUseXShm) { int minor, major, shp; XShmQueryVersion(wsDisplay, &major, &minor, &shp); mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] XShm version is %d.%d\n", major, minor); } #endif #ifdef CONFIG_XSHAPE if (wsUseXShape) { int minor, major; XShapeQueryVersion(wsDisplay, &major, &minor); mp_msg(MSGT_GPLAYER, MSGL_DBG2, "[ws] XShape version is %d.%d\n", major, minor); } #endif if (wsScreenDepth == 32 && wsRedMask == 0xff0000 && wsGreenMask == 0x00ff00 && wsBlueMask == 0x0000ff) out_pix_fmt = PIX_FMT_RGB32; else if (wsScreenDepth == 32 && wsRedMask == 0x0000ff && wsGreenMask == 0x00ff00 && wsBlueMask == 0xff0000) out_pix_fmt = PIX_FMT_BGR32; else if (wsScreenDepth == 24 && wsRedMask == 0xff0000 && wsGreenMask == 0x00ff00 && wsBlueMask == 0x0000ff) out_pix_fmt = PIX_FMT_RGB24; else if (wsScreenDepth == 24 && wsRedMask == 0x0000ff && wsGreenMask == 0x00ff00 && wsBlueMask == 0xff0000) out_pix_fmt = PIX_FMT_BGR24; else if (wsScreenDepth == 16 && wsRedMask == 0xf800 && wsGreenMask == 0x7e0 && wsBlueMask == 0x1f) out_pix_fmt = PIX_FMT_RGB565; else if (wsScreenDepth == 16 && wsRedMask == 0x1f && wsGreenMask == 0x7e0 && wsBlueMask == 0xf800) out_pix_fmt = PIX_FMT_BGR565; else if (wsScreenDepth == 15 && wsRedMask == 0x7c00 && wsGreenMask == 0x3e0 && wsBlueMask == 0x1f) out_pix_fmt = PIX_FMT_RGB555; else if (wsScreenDepth == 15 && wsRedMask == 0x1f && wsGreenMask == 0x3e0 && wsBlueMask == 0x7c00) out_pix_fmt = PIX_FMT_BGR555; }
/* Main function */ int main(int argc, char **argv) { Display *dpy; Window win; uint i_swap_cnt = 0; char const * config_fw = NULL; /* Getopt section */ struct option long_options[] = { /* These options set a flag. */ {NULL, 0, 0, 0} }; while (1) { int c; /* getopt_long stores the option index here. */ int option_index = 0; c = getopt_long (argc, argv, "", long_options, &option_index); /* Detect the end of the options. */ if (c == -1) break; switch (c) { case '?': default: usage(); exit(EXIT_FAILURE); } } if (optind < argc) { while (optind < argc) { config_fw = argv[optind++]; } } /* Openning X display */ dpy = XOpenDisplay(0); /* Preparing new X window */ Window s_window; static int attributeList[] = { GLX_RGBA, GLX_DOUBLEBUFFER, GLX_RED_SIZE, 1, GLX_GREEN_SIZE, 1, GLX_BLUE_SIZE, 1, None }; XVisualInfo *vi = glXChooseVisual(dpy, DefaultScreen(dpy), attributeList); s_window = RootWindow(dpy, vi->screen); XSetWindowAttributes swa; swa.colormap = XCreateColormap(dpy, s_window, vi->visual, AllocNone); swa.override_redirect = 1; /* Create X window 1x1 top left of screen */ win = XCreateWindow(dpy, s_window , 0, 0, 1, 1, 0, vi->depth, InputOutput, vi->visual, CWColormap|CWOverrideRedirect, &swa); XMapWindow(dpy, win); /* Create glX context */ GLXContext glx_ctx = glXCreateContext(dpy, vi, 0, 1); glXMakeCurrent(dpy, win, glx_ctx); /* Initialize libnvstusb */ ctx = nvstusb_init(config_fw); if (0 == ctx) { fprintf(stderr, "could not initialize NVIDIA 3D Stereo Controller, aborting\n"); exit(EXIT_FAILURE); } /* Get Vsync rate from X11 */ XF86VidModeModeLine modeline; int pixelclock; XF86VidModeGetModeLine( dpy, DefaultScreen(dpy), &pixelclock, &modeline ); double frameRate=(double) pixelclock*1000/modeline.htotal/modeline.vtotal; printf("Vertical Refresh rate:%f Hz\n",frameRate); nvstusb_set_rate(ctx, frameRate); /* Loop until stop */ while (1) { /* Send swap to usb controler */ nvstusb_swap(ctx, nvstusb_quad, NULL /*f_swap*/); /* Read status from usb controler */ if(!(i_swap_cnt&0xF)) { struct nvstusb_keys k; nvstusb_get_keys(ctx, &k); if (k.toggled3D) { nvstusb_invert_eyes(ctx); } } i_swap_cnt++; } /* Destroy context */ glx_ctx = glXGetCurrentContext(); glXDestroyContext(dpy, glx_ctx); /* Denit libnvstusb */ nvstusb_deinit(ctx); return EXIT_SUCCESS; }
double UIDisplay::GetRefreshRatePriv(void) { double currentrate = -1; bool currentinterlaced = false; XF86VidModeModeLine mode_line; int dot_clock; // TODO use display when needed const char *displaystring = NULL; Display* display = XOpenDisplay(displaystring); if (!display) { LOG(VB_GENERAL, LOG_ERR, "Failed to open X display."); return currentrate; } int screen = DefaultScreen(display); if (XF86VidModeGetModeLine(display, screen, &dot_clock, &mode_line)) { currentrate = mode_line.htotal * mode_line.vtotal; if (currentrate > 0.0 && dot_clock > 0) { currentrate = (dot_clock * 1000.0) / currentrate; if (((mode_line.flags & V_INTERLACE) != 0) && currentrate > 24.5 && currentrate < 30.5) { currentrate *= 2.0f; currentinterlaced = true; } } else { LOG(VB_GENERAL, LOG_ERR, "Modeline query returned zeroes"); } } else { LOG(VB_GENERAL, LOG_ERR, "Failed to get modeline."); } // all rates m_modes.clear(); m_originalModeIndex = -1; if (UIXRandr.m_valid) { XRRScreenResources *resources = UIXRandr.m_getScreenResources(display, RootWindow(display, screen)); if (resources) { for (int i = 0; i < resources->nmode; ++i) { bool interlaced = false; XRRModeInfo mode = resources->modes[i]; double moderate = mode.hTotal * mode.vTotal; if (moderate > 0.0 && mode.dotClock > 0) { moderate = mode.dotClock / moderate; if ((mode.modeFlags & V_INTERLACE) && moderate > 24.5 && moderate < 30.5) { moderate *= 2.0f; interlaced = true; } } bool ignore = false; bool current = false; bool sizematch = mode.width == (uint)m_pixelSize.width() || mode.height == (uint)m_pixelSize.height(); bool realinterlaced = false; double realrate = UINVControl::GetRateForMode(display, (int)(moderate + 0.5f), realinterlaced); if (realrate > 10.0f && realrate < 121.0f) { ignore = !sizematch; current = sizematch && qFuzzyCompare(realrate + 1.0f, currentrate + 1.0f) && (realinterlaced == interlaced); LOG(VB_GUI, LOG_INFO, QString("nvidia Mode %1: %2x%3@%4%5%6%7") .arg(mode.name).arg(mode.width).arg(mode.height).arg(moderate) .arg(realinterlaced ? QString(" Interlaced") : "") .arg(ignore ? QString(" Ignoring") : "") .arg(current ? QString(" Current") : "")); if (!ignore) m_modes.append(UIDisplayMode(mode.width, mode.height, 32, realrate, realinterlaced, i)); } else { ignore = moderate < 10.0f || moderate > 121.0f || !sizematch; current = sizematch && qFuzzyCompare(moderate + 1.0f, currentrate + 1.0f) && (currentinterlaced == interlaced); LOG(VB_GUI, LOG_INFO, QString("Mode %1: %2x%3@%4%5%6%7") .arg(mode.name).arg(mode.width).arg(mode.height).arg(moderate) .arg(mode.modeFlags & V_INTERLACE ? QString(" Interlaced") : "") .arg(ignore ? QString(" Ignoring") : "") .arg(current ? QString(" Current") : "")); if (!ignore) m_modes.append(UIDisplayMode(mode.width, mode.height, 32, moderate, mode.modeFlags & V_INTERLACE, i)); } if (current) m_originalModeIndex = m_modes.size() - 1; } UIXRandr.m_freeScreenResources(resources); } else { LOG(VB_GENERAL, LOG_INFO, "Need XRandr 1.2 or above to query available refresh rates"); } } XCloseDisplay(display); return currentrate; }