From: havoc Date: Wed, 11 Sep 2002 15:05:44 +0000 (+0000) Subject: VID_Init now takes mode settings (fullscreen, width, height) X-Git-Tag: RELEASE_0_2_0_RC1~243 X-Git-Url: https://git.rm.cloudns.org/?a=commitdiff_plain;h=195a5f4e8031dcc37d16fc81e7dc9da044721b33;p=xonotic%2Fdarkplaces.git VID_Init now takes mode settings (fullscreen, width, height) commandline options like -window and -width are now parsed by vid_shared code vid_width, vid_height, and vid_bitsperpixel cvars added, vid_mode removed VID_CompareMode added, for simpler mode matching (returns a double, smaller value is better match) GL_OpenLibrary takes a library name to load GL_OpenLibrary, GL_CloseLibrary, and GL_GetProcAddress have been moved to platform specific vid_ files (wgl and glx) gl_platform added (example values: "WGL", "GLX") gl_platformextensions added (containing any extensions reported by platform specific strings) gl_checkextension renamed to GL_CheckExtension for consistency glXQueryExtensionsString and glXGetProcAddressARB support looks up GLX_SGI_video_sync extension removed halfscreen hack from vid_wgl (the code that tried to identify dual monitor configurations and use only one of them) git-svn-id: svn://svn.icculus.org/twilight/trunk/darkplaces@2363 d7cf8633-e32d-0410-b094-e92efae38249 --- diff --git a/glquake.h b/glquake.h index d945bc9d..bf362edc 100644 --- a/glquake.h +++ b/glquake.h @@ -37,20 +37,8 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. //#include -extern qboolean isG200; -extern qboolean isRagePro; - //==================================================== -extern const char *gl_vendor; -extern const char *gl_renderer; -extern const char *gl_version; -extern const char *gl_extensions; - -void GL_OpenLibrary(void); -void GL_CloseLibrary(void); -void *GL_GetProcAddress(char *name); - // wgl uses APIENTRY #ifndef APIENTRY #define APIENTRY diff --git a/host.c b/host.c index 305fe588..cc7102a8 100644 --- a/host.c +++ b/host.c @@ -869,7 +869,7 @@ void Host_Init (void) #ifndef _WIN32 // on non win32, mouse comes before video for security reasons IN_Init (); #endif - VID_Init (); + VID_Init (vid_fullscreen.integer, vid_width.integer, vid_height.integer); Render_Init(); S_Init (); diff --git a/vid.h b/vid.h index 2ab44435..265d6e0d 100644 --- a/vid.h +++ b/vid.h @@ -42,9 +42,57 @@ extern void (*vid_menukeyfn)(int key); extern int vid_hidden; extern int vid_activewindow; -extern cvar_t vid_mode; -extern cvar_t vid_mouse; extern cvar_t vid_fullscreen; +extern cvar_t vid_width; +extern cvar_t vid_height; +extern cvar_t vid_bitsperpixel; +extern cvar_t vid_mouse; + +// brand of graphics chip +extern const char *gl_vendor; +// graphics chip model and other information +extern const char *gl_renderer; +// begins with 1.0.0, 1.1.0, 1.2.0, 1.2.1, 1.3.0, 1.3.1, or 1.4.0 +extern const char *gl_version; +// extensions list, space separated +extern const char *gl_extensions; +// WGL, GLX, or AGL +extern const char *gl_platform; +// another extensions list, containing platform-specific extensions that are +// not in the main list +extern const char *gl_platformextensions; +// name of driver library (opengl32.dll, libGL.so.1, or whatever) +extern char gl_driver[256]; + +// compatibility hacks +extern qboolean isG200; +extern qboolean isRagePro; + +// LordHavoc: GLX_SGI_video_sync and WGL_EXT_swap_control +extern int gl_videosyncavailable; + +typedef struct +{ + const char *name; + void **funcvariable; +} +gl_extensionfunctionlist_t; + +typedef struct +{ + const char *name; + const gl_extensionfunctionlist_t *funcs; + int *enablevariable; + const char *disableparm; +} +gl_extensioninfo_t; + +int GL_OpenLibrary(const char *name); +void GL_CloseLibrary(void); +void *GL_GetProcAddress(const char *name); +int GL_CheckExtension(const char *name, const gl_extensionfunctionlist_t *funcs, const char *disableparm, int silent); + +double VID_CompareMode(int width1, int height1, int bpp1, int width2, int height2, int bpp2); void VID_InitCvars(void); @@ -52,7 +100,7 @@ void GL_Init (void); void VID_CheckExtensions(void); -void VID_Init (void); +void VID_Init (int fullscreen, int width, int height); // Called at startup void VID_Shutdown (void); diff --git a/vid_glx.c b/vid_glx.c index 1021ff3c..de6c7c44 100644 --- a/vid_glx.c +++ b/vid_glx.c @@ -25,7 +25,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. //#include #include -//#include +#include #include #include @@ -40,12 +40,33 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. #include "quakedef.h" +//GLX prototypes XVisualInfo *(GLAPIENTRY *qglXChooseVisual)(Display *dpy, int screen, int *attribList); GLXContext (GLAPIENTRY *qglXCreateContext)(Display *dpy, XVisualInfo *vis, GLXContext shareList, Bool direct); void (GLAPIENTRY *qglXDestroyContext)(Display *dpy, GLXContext ctx); Bool (GLAPIENTRY *qglXMakeCurrent)(Display *dpy, GLXDrawable drawable, GLXContext ctx); void (GLAPIENTRY *qglXSwapBuffers)(Display *dpy, GLXDrawable drawable); +const char *(GLAPIENTRY *qglXQueryExtensionsString)(Display *dpy, int screen); +//GLX_ARB_get_proc_address +void *(GLAPIENTRY *qglXGetProcAddressARB)(const GLubyte *procName); + +static gl_extensionfunctionlist_t getprocaddressfuncs[] = +{ + {"glXGetProcAddressARB", (void **) &qglXGetProcAddressARB}, + {NULL, NULL} +}; + +//GLX_SGI_video_sync +GLint (GLAPIENTRY *qglXGetVideoSyncSGI)(GLuint *count); +GLint (GLAPIENTRY *qglXWaitVideoSyncSGI)(int divisor, int remainder, unsigned int *count); + +static gl_extensionfunctionlist_t videosyncfuncs[] = +{ + {"glXGetVideoSyncSGI", (void **) &qglXGetVideoSyncSGI}, + {"glXWaitVideoSyncSGI", (void **) &qglXWaitVideoSyncSGI}, + {NULL, NULL} +}; static Display *vidx11_display = NULL; static int scrnum; @@ -613,7 +634,7 @@ int VID_SetGamma(float prescale, float gamma, float scale, float base) #endif } -void VID_Init(void) +void VID_Init(int fullscreen, int width, int height) { int i; // LordHavoc: FIXME: finish this code, we need to allocate colors before we can store them @@ -640,49 +661,18 @@ void VID_Init(void) GLX_DEPTH_SIZE, 1, None }; - int width = 640, height = 480; XSetWindowAttributes attr; unsigned long mask; Window root; XVisualInfo *visinfo; - qboolean fullscreen = true; int MajorVersion, MinorVersion; - GL_OpenLibrary(); + if (!GL_OpenLibrary("libGL.so.1")) + Sys_Error("Unable to load GL driver\n"); Cvar_RegisterVariable (&vid_dga); Cvar_RegisterVariable (&vid_dga_mouseaccel); -// interpret command-line params - -// set vid parameters - if ((i = COM_CheckParm("-window")) != 0) - fullscreen = false; - - if ((i = COM_CheckParm("-width")) != 0) - width = atoi(com_argv[i+1]); - - if ((i = COM_CheckParm("-height")) != 0) - height = atoi(com_argv[i+1]); - - if ((i = COM_CheckParm("-conwidth")) != 0) - vid.conwidth = atoi(com_argv[i+1]); - else - vid.conwidth = 640; - - vid.conwidth &= 0xfff8; // make it a multiple of eight - - if (vid.conwidth < 320) - vid.conwidth = 320; - - // pick a conheight that matches with correct aspect - vid.conheight = vid.conwidth*3 / 4; - - if ((i = COM_CheckParm("-conheight")) != 0) - vid.conheight = atoi(com_argv[i+1]); - if (vid.conheight < 200) - vid.conheight = 200; - if (!(vidx11_display = XOpenDisplay(NULL))) { fprintf(stderr, "Error couldn't open the X display\n"); @@ -705,8 +695,9 @@ void VID_Init(void) if ((qglXChooseVisual = GL_GetProcAddress("glXChooseVisual")) == NULL || (qglXCreateContext = GL_GetProcAddress("glXCreateContext")) == NULL || (qglXMakeCurrent = GL_GetProcAddress("glXMakeCurrent")) == NULL - || (qglXSwapBuffers = GL_GetProcAddress("glXSwapBuffers")) == NULL) - Sys_Error("glX functions not found in libGL.so.1\n"); + || (qglXSwapBuffers = GL_GetProcAddress("glXSwapBuffers")) == NULL + || (qglXQueryExtensionsString = GL_GetProcAddress("glXQueryExtensionsString")) == NULL) + Sys_Error("glX functions not found in %s\n", gl_driver); visinfo = NULL; // LordHavoc: FIXME: finish this code, we need to allocate colors before we can store them @@ -818,10 +809,18 @@ void VID_Init(void) scr_width = width; scr_height = height; - if (vid.conheight > height) - vid.conheight = height; - if (vid.conwidth > width) - vid.conwidth = width; + if ((qglGetString = GL_GetProcAddress("glGetString")) == NULL) + Sys_Error("glGetString not found in %s", gl_driver); + + gl_renderer = qglGetString(GL_RENDERER); + gl_vendor = qglGetString(GL_VENDOR); + gl_version = qglGetString(GL_VERSION); + gl_extensions = qglGetString(GL_EXTENSIONS); + gl_platform = "GLX"; + gl_platformextensions = qglXQueryExtensionsString(vidx11_display, scrnum); + + GL_CheckExtension("GLX_ARB_get_proc_address", getprocaddressfuncs, "-nogetprocaddress", false); + gl_videosyncavailable = GL_CheckExtension("GLX_SGI_video_sync", videosyncfuncs, "-novideosync", false); InitSig(); // trap evil signals @@ -839,7 +838,7 @@ void Sys_SendKeyEvents(void) void IN_Init(void) { - if (COM_CheckParm ("-nomouse")) + if (COM_CheckParm ("-nomouse") || COM_CheckParm("-safe")) mouse_avail = false; } @@ -864,3 +863,39 @@ void IN_Move (usercmd_t *cmd) mouse_y = 0; } +static void *prjobj = NULL; + +int GL_OpenLibrary(const char *name) +{ + Con_Printf("Loading GL driver %s\n", name); + GL_CloseLibrary(); + if (!(prjobj = dlopen(name, RTLD_LAZY))) + { + Con_Printf("Unable to open symbol list for %s\n", name); + return false; + } + strcpy(gl_driver, name); + return true; +} + +void GL_CloseLibrary(void) +{ + if (prjobj) + dlclose(prjobj); + prjobj = NULL; + gl_driver[0] = 0; + qglXGetProcAddressARB = NULL; + gl_extensions = ""; + gl_platform = ""; + gl_platformextensions = ""; +} + +void *GL_GetProcAddress(const char *name) +{ + void *p = NULL; + if (qglXGetProcAddressARB != NULL) + p = (void *) qglXGetProcAddressARB(name); + if (p == NULL) + p = (void *) dlsym(prjobj, name); + return p; +} diff --git a/vid_shared.c b/vid_shared.c index 8ae15b81..a35bb1ed 100644 --- a/vid_shared.c +++ b/vid_shared.c @@ -11,6 +11,8 @@ int gl_textureunits; int gl_combine_extension = false; // LordHavoc: GL_EXT_compiled_vertex_array support int gl_supportslockarrays = false; +// LordHavoc: GLX_SGI_video_sync and WGL_EXT_swap_control +int gl_videosyncavailable = false; // LordHavoc: if window is hidden, don't update screen int vid_hidden = false; @@ -18,9 +20,12 @@ int vid_hidden = false; // let go of the mouse, turn off sound, and restore system gamma ramps... int vid_activewindow = true; -cvar_t vid_mode = {0, "vid_mode", "0"}; -cvar_t vid_mouse = {CVAR_SAVE, "vid_mouse", "1"}; cvar_t vid_fullscreen = {0, "vid_fullscreen", "1"}; +cvar_t vid_width = {0, "vid_width", "640"}; +cvar_t vid_height = {0, "vid_height", "480"}; +cvar_t vid_bitsperpixel = {0, "vid_bitsperpixel", "15"}; + +cvar_t vid_mouse = {CVAR_SAVE, "vid_mouse", "1"}; cvar_t gl_combine = {0, "gl_combine", "1"}; cvar_t in_pitch_min = {0, "in_pitch_min", "-90"}; @@ -28,10 +33,21 @@ cvar_t in_pitch_max = {0, "in_pitch_max", "90"}; cvar_t m_filter = {CVAR_SAVE, "m_filter","0"}; +// brand of graphics chip const char *gl_vendor; +// graphics chip model and other information const char *gl_renderer; +// begins with 1.0.0, 1.1.0, 1.2.0, 1.2.1, 1.3.0, 1.3.1, or 1.4.0 const char *gl_version; +// extensions list, space separated const char *gl_extensions; +// WGL, GLX, or AGL +const char *gl_platform; +// another extensions list, containing platform-specific extensions that are +// not in the main list +const char *gl_platformextensions; +// name of driver library (opengl32.dll, libGL.so.1, or whatever) +char gl_driver[256]; // GL_ARB_multitexture void (GLAPIENTRY *qglMultiTexCoord2f) (GLenum, GLfloat, GLfloat); @@ -132,59 +148,46 @@ void (GLAPIENTRY *qglDrawRangeElementsEXT)(GLenum mode, GLuint start, GLuint end //void (GLAPIENTRY *qglColorTableEXT)(int, int, int, int, int, const void *); -#if WIN32 -int (WINAPI *qwglChoosePixelFormat)(HDC, CONST PIXELFORMATDESCRIPTOR *); -int (WINAPI *qwglDescribePixelFormat)(HDC, int, UINT, LPPIXELFORMATDESCRIPTOR); -//int (WINAPI *qwglGetPixelFormat)(HDC); -BOOL (WINAPI *qwglSetPixelFormat)(HDC, int, CONST PIXELFORMATDESCRIPTOR *); -BOOL (WINAPI *qwglSwapBuffers)(HDC); -HGLRC (WINAPI *qwglCreateContext)(HDC); -BOOL (WINAPI *qwglDeleteContext)(HGLRC); -PROC (WINAPI *qwglGetProcAddress)(LPCSTR); -BOOL (WINAPI *qwglMakeCurrent)(HDC, HGLRC); -//BOOL (WINAPI *qwglSwapIntervalEXT)(int interval); -#endif - - -typedef struct +int GL_CheckExtension(const char *name, const gl_extensionfunctionlist_t *funcs, const char *disableparm, int silent) { - char *name; - void **funcvariable; -} -gl_extensionfunctionlist_t; + int failed = false; + const gl_extensionfunctionlist_t *func; -typedef struct -{ - char *name; - gl_extensionfunctionlist_t *funcs; - int *enablevariable; - char *disableparm; -} -gl_extensioninfo_t; + Con_Printf("checking for %s... ", name); -#if WIN32 -static gl_extensionfunctionlist_t wglfuncs[] = -{ - {"wglChoosePixelFormat", (void **) &qwglChoosePixelFormat}, - {"wglDescribePixelFormat", (void **) &qwglDescribePixelFormat}, -// {"wglGetPixelFormat", (void **) &qwglGetPixelFormat}, - {"wglSetPixelFormat", (void **) &qwglSetPixelFormat}, - {"wglSwapBuffers", (void **) &qwglSwapBuffers}, - {"wglCreateContext", (void **) &qwglCreateContext}, - {"wglDeleteContext", (void **) &qwglDeleteContext}, - {"wglGetProcAddress", (void **) &qwglGetProcAddress}, - {"wglMakeCurrent", (void **) &qwglMakeCurrent}, - {NULL, NULL} -}; + for (func = funcs;func && func->name;func++) + *func->funcvariable = NULL; -/* -static gl_extensionfunctionlist_t wglswapintervalfuncs[] = -{ - {"wglSwapIntervalEXT", (void **) &qwglSwapIntervalEXT}, - {NULL, NULL} -}; -*/ -#endif + if (disableparm && COM_CheckParm(disableparm)) + { + Con_Printf("disabled by commandline\n"); + return false; + } + + if (strstr(gl_extensions, name) || strstr(gl_platformextensions, name) || (strncmp(name, "GL_", 3) && strncmp(name, "WGL_", 4) && strncmp(name, "GLX_", 4) && strncmp(name, "AGL_", 4))) + { + for (func = funcs;func && func->name != NULL;func++) + { + // functions are cleared before all the extensions are evaluated + if (!(*func->funcvariable = (void *) GL_GetProcAddress(func->name))) + { + if (!silent) + Con_Printf("missing function \"%s\" - broken driver!\n", func->name); + failed = true; + } + } + // delay the return so it prints all missing functions + if (failed) + return false; + Con_Printf("enabled\n"); + return true; + } + else + { + Con_Printf("not detected\n"); + return false; + } +} static gl_extensionfunctionlist_t opengl110funcs[] = { @@ -284,140 +287,31 @@ static gl_extensionfunctionlist_t compiledvertexarrayfuncs[] = {NULL, NULL} }; -#ifndef WIN32 -#include -#endif - -#ifdef WIN32 -static HINSTANCE gldll; -#else -static void *prjobj = NULL; -#endif - -void GL_OpenLibrary(void) -{ -#ifdef WIN32 - if (gldll) - FreeLibrary(gldll); - if (!(gldll = LoadLibrary("opengl32.dll"))) - Sys_Error("Unable to LoadLibrary opengl32.dll\n"); -#else - if (prjobj) - dlclose(prjobj); - if (!(prjobj = dlopen("libGL.so.1", RTLD_LAZY))) - Sys_Error("Unable to open symbol list for libGL.so.1\n"); -#endif -} - -void GL_CloseLibrary(void) -{ -#ifdef WIN32 - FreeLibrary(gldll); - gldll = 0; -#else - if (prjobj) - dlclose(prjobj); - prjobj = NULL; -#endif -} - -void *GL_GetProcAddress(char *name) -{ - void *p = NULL; -#ifdef WIN32 - if (qwglGetProcAddress != NULL) - p = (void *) qwglGetProcAddress(name); - if (p == NULL) - p = (void *) GetProcAddress(gldll, name); -#else - p = (void *) dlsym(prjobj, name); -#endif - return p; -} - -static int gl_checkextension(char *name, gl_extensionfunctionlist_t *funcs, char *disableparm, int silent) -{ - int failed = false; - gl_extensionfunctionlist_t *func; - - Con_Printf("checking for %s... ", name); - - for (func = funcs;func && func->name;func++) - *func->funcvariable = NULL; - - if (disableparm && COM_CheckParm(disableparm)) - { - Con_Printf("disabled by commandline\n"); - return false; - } - - if (strncmp(name, "GL_", 3) || strstr(gl_extensions, name)) - { - for (func = funcs;func && func->name != NULL;func++) - { - // functions are cleared before all the extensions are evaluated - if (!(*func->funcvariable = (void *) GL_GetProcAddress(func->name))) - { - if (!silent) - Con_Printf("missing function \"%s\" - broken driver!\n", func->name); - failed = true; - } - } - // delay the return so it prints all missing functions - if (failed) - return false; - Con_Printf("enabled\n"); - return true; - } - else - { - Con_Printf("not detected\n"); - return false; - } -} - void VID_CheckExtensions(void) { - gl_vendor = NULL; - gl_renderer = NULL; - gl_version = NULL; - gl_extensions = NULL; - - Con_Printf("Opening OpenGL library to retrieve functions\n"); - gl_combine_extension = false; gl_supportslockarrays = false; gl_textureunits = 1; -#if WIN32 - if (!gl_checkextension("wgl", wglfuncs, NULL, false)) - Sys_Error("wgl functions not found\n"); - //gl_checkextension("wglSwapIntervalEXT", wglswapintervalfuncs, NULL, false); -#endif - - if (!gl_checkextension("OpenGL 1.1.0", opengl110funcs, NULL, false)) + if (!GL_CheckExtension("OpenGL 1.1.0", opengl110funcs, NULL, false)) Sys_Error("OpenGL 1.1.0 functions not found\n"); - gl_vendor = qglGetString (GL_VENDOR); - gl_renderer = qglGetString (GL_RENDERER); - gl_version = qglGetString (GL_VERSION); - gl_extensions = qglGetString (GL_EXTENSIONS); - Con_Printf ("GL_VENDOR: %s\n", gl_vendor); Con_Printf ("GL_RENDERER: %s\n", gl_renderer); Con_Printf ("GL_VERSION: %s\n", gl_version); Con_Printf ("GL_EXTENSIONS: %s\n", gl_extensions); + Con_Printf ("%s_EXTENSIONS: %s\n", gl_platform, gl_platformextensions); Con_Printf("Checking OpenGL extensions...\n"); - if (!gl_checkextension("glDrawRangeElements", drawrangeelementsfuncs, "-nodrawrangeelements", true)) - gl_checkextension("GL_EXT_draw_range_elements", drawrangeelementsextfuncs, "-nodrawrangeelements", false); + if (!GL_CheckExtension("glDrawRangeElements", drawrangeelementsfuncs, "-nodrawrangeelements", true)) + GL_CheckExtension("GL_EXT_draw_range_elements", drawrangeelementsextfuncs, "-nodrawrangeelements", false); - if (gl_checkextension("GL_ARB_multitexture", multitexturefuncs, "-nomtex", false)) + if (GL_CheckExtension("GL_ARB_multitexture", multitexturefuncs, "-nomtex", false)) { qglGetIntegerv(GL_MAX_TEXTURE_UNITS_ARB, &gl_textureunits); if (gl_textureunits > 1) - gl_combine_extension = gl_checkextension("GL_ARB_texture_env_combine", NULL, "-nocombine", false) || gl_checkextension("GL_EXT_texture_env_combine", NULL, "-nocombine", false); + gl_combine_extension = GL_CheckExtension("GL_ARB_texture_env_combine", NULL, "-nocombine", false) || GL_CheckExtension("GL_EXT_texture_env_combine", NULL, "-nocombine", false); else { Con_Printf("GL_ARB_multitexture with less than 2 units? - BROKEN DRIVER!\n"); @@ -425,13 +319,22 @@ void VID_CheckExtensions(void) } } - gl_supportslockarrays = gl_checkextension("GL_EXT_compiled_vertex_array", compiledvertexarrayfuncs, "-nocva", false); + gl_supportslockarrays = GL_CheckExtension("GL_EXT_compiled_vertex_array", compiledvertexarrayfuncs, "-nocva", false); // we don't care if it's an extension or not, they are identical functions, so keep it simple in the rendering code if (qglDrawRangeElements == NULL) qglDrawRangeElements = qglDrawRangeElementsEXT; } +double VID_CompareMode(int width1, int height1, int bpp1, int width2, int height2, int bpp2) +{ + double dw, dh, db; + dw = ((width2 - width1) / 2048) * 16; + dh = ((height2 - height1) / 1536) * 4; + db = (bpp2 - bpp1) / 32; + return dw * dw + dh * dh + db * db; +} + void Force_CenterView_f (void) { cl.viewangles[PITCH] = 0; @@ -494,13 +397,29 @@ void IN_Mouse(usercmd_t *cmd, float mx, float my) void VID_InitCvars(void) { - Cvar_RegisterVariable(&vid_mode); - Cvar_RegisterVariable(&vid_mouse); + int i; + Cvar_RegisterVariable(&vid_fullscreen); + Cvar_RegisterVariable(&vid_width); + Cvar_RegisterVariable(&vid_height); + Cvar_RegisterVariable(&vid_bitsperpixel); + Cvar_RegisterVariable(&vid_mouse); Cvar_RegisterVariable(&gl_combine); Cvar_RegisterVariable(&in_pitch_min); Cvar_RegisterVariable(&in_pitch_max); Cvar_RegisterVariable(&m_filter); Cmd_AddCommand("force_centerview", Force_CenterView_f); + +// interpret command-line parameters + if ((i = COM_CheckParm("-window")) != 0) + Cvar_SetValueQuick(&vid_fullscreen, false); + if ((i = COM_CheckParm("-fullscreen")) != 0) + Cvar_SetValueQuick(&vid_fullscreen, true); + if ((i = COM_CheckParm("-width")) != 0) + Cvar_SetQuick(&vid_width, com_argv[i+1]); + if ((i = COM_CheckParm("-height")) != 0) + Cvar_SetQuick(&vid_height, com_argv[i+1]); + if ((i = COM_CheckParm("-bpp")) != 0) + Cvar_SetQuick(&vid_bitsperpixel, com_argv[i+1]); } diff --git a/vid_wgl.c b/vid_wgl.c index 578b94a1..f5e2b38d 100644 --- a/vid_wgl.c +++ b/vid_wgl.c @@ -24,6 +24,44 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. #include "resource.h" #include +int (WINAPI *qwglChoosePixelFormat)(HDC, CONST PIXELFORMATDESCRIPTOR *); +int (WINAPI *qwglDescribePixelFormat)(HDC, int, UINT, LPPIXELFORMATDESCRIPTOR); +//int (WINAPI *qwglGetPixelFormat)(HDC); +BOOL (WINAPI *qwglSetPixelFormat)(HDC, int, CONST PIXELFORMATDESCRIPTOR *); +BOOL (WINAPI *qwglSwapBuffers)(HDC); +HGLRC (WINAPI *qwglCreateContext)(HDC); +BOOL (WINAPI *qwglDeleteContext)(HGLRC); +PROC (WINAPI *qwglGetProcAddress)(LPCSTR); +BOOL (WINAPI *qwglMakeCurrent)(HDC, HGLRC); +BOOL (WINAPI *qwglSwapIntervalEXT)(int interval); +const char *(WINAPI *wglGetExtensionsStringARB)(HDC hdc); + +static gl_extensionfunctionlist_t getextensionsstringfuncs[] = +{ + {"wglGetExtensionsString", (void **) &qwglGetExtensionsString}, + {NULL, NULL} +}; + +static gl_extensionfunctionlist_t wglfuncs[] = +{ + {"wglChoosePixelFormat", (void **) &qwglChoosePixelFormat}, + {"wglDescribePixelFormat", (void **) &qwglDescribePixelFormat}, +// {"wglGetPixelFormat", (void **) &qwglGetPixelFormat}, + {"wglSetPixelFormat", (void **) &qwglSetPixelFormat}, + {"wglSwapBuffers", (void **) &qwglSwapBuffers}, + {"wglCreateContext", (void **) &qwglCreateContext}, + {"wglDeleteContext", (void **) &qwglDeleteContext}, + {"wglGetProcAddress", (void **) &qwglGetProcAddress}, + {"wglMakeCurrent", (void **) &qwglMakeCurrent}, + {NULL, NULL} +}; + +static gl_extensionfunctionlist_t wglswapintervalfuncs[] = +{ + {"wglSwapIntervalEXT", (void **) &qwglSwapIntervalEXT}, + {NULL, NULL} +}; + #define MAX_MODE_LIST 30 #define VID_ROW_SIZE 3 #define MAXWIDTH 10000 @@ -41,7 +79,6 @@ typedef struct { int dib; int fullscreen; int bpp; - int halfscreen; char modedesc[17]; } vmode_t; @@ -162,11 +199,6 @@ qboolean VID_SetWindowedMode (int modenum) modestate = MS_WINDOWED; - if (vid.conheight > modelist[modenum].height) - vid.conheight = modelist[modenum].height; - if (vid.conwidth > modelist[modenum].width) - vid.conwidth = modelist[modenum].width; - SendMessage (mainwindow, WM_SETICON, (WPARAM)true, (LPARAM)hIcon); SendMessage (mainwindow, WM_SETICON, (WPARAM)false, (LPARAM)hIcon); @@ -183,7 +215,7 @@ qboolean VID_SetFullDIBMode (int modenum) { gdevmode.dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT; gdevmode.dmBitsPerPel = modelist[modenum].bpp; - gdevmode.dmPelsWidth = modelist[modenum].width << modelist[modenum].halfscreen; + gdevmode.dmPelsWidth = modelist[modenum].width; gdevmode.dmPelsHeight = modelist[modenum].height; gdevmode.dmSize = sizeof (gdevmode); @@ -220,11 +252,6 @@ qboolean VID_SetFullDIBMode (int modenum) ShowWindow (mainwindow, SW_SHOWDEFAULT); UpdateWindow (mainwindow); - if (vid.conheight > modelist[modenum].height) - vid.conheight = modelist[modenum].height; - if (vid.conwidth > modelist[modenum].width) - vid.conwidth = modelist[modenum].width; - // needed because we're not getting WM_MOVE messages fullscreen on NT window_x = 0; window_y = 0; @@ -388,10 +415,10 @@ void VID_Shutdown (void) if (vid_initialized) { vid_canalttab = false; - hRC = wglGetCurrentContext(); - hDC = wglGetCurrentDC(); + hRC = qwglGetCurrentContext(); + hDC = qwglGetCurrentDC(); - wglMakeCurrent(NULL, NULL); + qwglMakeCurrent(NULL, NULL); // LordHavoc: free textures before closing (may help NVIDIA) for (i = 0;i < 8192;i++) @@ -399,7 +426,7 @@ void VID_Shutdown (void) qglDeleteTextures(8192, temp); if (hRC) - wglDeleteContext(hRC); + qwglDeleteContext(hRC); // close the library before we get rid of the window GL_CloseLibrary(); @@ -864,7 +891,7 @@ void VID_DescribeModes_f (void) leavecurrentmode = t; } -void VID_AddMode(int type, int width, int height, int modenum, int halfscreen, int dib, int fullscreen, int bpp) +void VID_AddMode(int type, int width, int height, int modenum, int dib, int fullscreen, int bpp) { int i; if (nummodes >= MAX_MODE_LIST) @@ -873,7 +900,6 @@ void VID_AddMode(int type, int width, int height, int modenum, int halfscreen, i modelist[nummodes].width = width; modelist[nummodes].height = height; modelist[nummodes].modenum = modenum; - modelist[nummodes].halfscreen = halfscreen; modelist[nummodes].dib = dib; modelist[nummodes].fullscreen = fullscreen; modelist[nummodes].bpp = bpp; @@ -925,7 +951,7 @@ void VID_InitDIB (HINSTANCE hInstance) if (h < 240) h = 240; - VID_AddMode(MS_WINDOWED, w, h, 0, 0, 1, 0, 0); + VID_AddMode(MS_WINDOWED, w, h, 0, 1, 0, 0); } @@ -1054,203 +1080,6 @@ void VID_RestoreSystemGamma(void) ReleaseDC (NULL, hdc); } -/* -=================== -VID_Init -=================== -*/ -void VID_Init (void) -{ - int i; - int basenummodes, width, height = 0, bpp, findbpp, done; - HDC hdc; - DEVMODE devmode; - - GL_OpenLibrary(); - - memset(&devmode, 0, sizeof(devmode)); - - Cmd_AddCommand ("vid_nummodes", VID_NumModes_f); - Cmd_AddCommand ("vid_describecurrentmode", VID_DescribeCurrentMode_f); - Cmd_AddCommand ("vid_describemode", VID_DescribeMode_f); - Cmd_AddCommand ("vid_describemodes", VID_DescribeModes_f); - - VID_GetSystemGamma(); - - hIcon = LoadIcon (global_hInstance, MAKEINTRESOURCE (IDI_ICON2)); - - InitCommonControls(); - - VID_InitDIB (global_hInstance); - basenummodes = nummodes = 1; - - VID_InitFullDIB (global_hInstance); - - if (COM_CheckParm("-window")) - { - hdc = GetDC (NULL); - - if (GetDeviceCaps(hdc, RASTERCAPS) & RC_PALETTE) - Sys_Error ("Can't run in non-RGB mode"); - - ReleaseDC (NULL, hdc); - - windowed = true; - - vid_default = MODE_WINDOWED; - } - else - { - if (nummodes == 1) - Sys_Error ("No RGB fullscreen modes available"); - - windowed = false; - - if (COM_CheckParm("-mode")) - vid_default = atoi(com_argv[COM_CheckParm("-mode")+1]); - else - { - if (COM_CheckParm("-current")) - { - modelist[MODE_FULLSCREEN_DEFAULT].width = GetSystemMetrics (SM_CXSCREEN); - modelist[MODE_FULLSCREEN_DEFAULT].height = GetSystemMetrics (SM_CYSCREEN); - vid_default = MODE_FULLSCREEN_DEFAULT; - leavecurrentmode = 1; - } - else - { - if (COM_CheckParm("-width")) - width = atoi(com_argv[COM_CheckParm("-width")+1]); - else - width = 640; - - if (COM_CheckParm("-bpp")) - { - bpp = atoi(com_argv[COM_CheckParm("-bpp")+1]); - findbpp = 0; - } - else - { - bpp = 15; - findbpp = 1; - } - - if (COM_CheckParm("-height")) - height = atoi(com_argv[COM_CheckParm("-height")+1]); - - // if they want to force it, add the specified mode to the list - if (COM_CheckParm("-force") && (nummodes < MAX_MODE_LIST)) - VID_AddMode(MS_FULLDIB, width, height, 0, 0, 1, 1, bpp); - - done = 0; - - do - { - if (COM_CheckParm("-height")) - { - height = atoi(com_argv[COM_CheckParm("-height")+1]); - - for (i=1, vid_default=0 ; i rating) + { + bestrating = rating; + bestmode = i; + } + } + + if (bestmode < 0) + Sys_Error ("Specified video mode not available"); + } + + vid_initialized = true; + + VID_SetMode (vid_default); + + maindc = GetDC(mainwindow); + bSetupPixelFormat(maindc); + + if (!gl_checkextension("wgl", wglfuncs, NULL, false)) + Sys_Error("wgl functions not found\n"); + + baseRC = qwglCreateContext( maindc ); + if (!baseRC) + Sys_Error ("Could not initialize GL (wglCreateContext failed).\n\nMake sure you are in 65536 color mode, and try running -window."); + if (!qwglMakeCurrent( maindc, baseRC )) + Sys_Error ("wglMakeCurrent failed"); + + gl_renderer = qglGetString(GL_RENDERER); + gl_vendor = qglGetString(GL_VENDOR); + gl_version = qglGetString(GL_VERSION); + gl_extensions = qglGetString(GL_EXTENSIONS); + gl_platformname = "WGL"; + gl_platformextensions = ""; + + if (gl_checkextension("WGL_ARB_extensions_string", extensionsstringfuncs, NULL, false)) + gl_platformextensions = qwglGetExtensionsStringARB(maindc); + + gl_videosyncavailable = gl_checkextension("WGL_EXT_swap_control", wglswapintervalfuncs, NULL, false); + + GL_Init (); + + // LordHavoc: special differences for ATI (broken 8bit color when also using 32bit? weird!) + if (strncasecmp(gl_vendor,"ATI",3)==0) + { + if (strncasecmp(gl_renderer,"Rage Pro",8)==0) + isRagePro = true; + } + if (strncasecmp(gl_renderer,"Matrox G200 Direct3D",20)==0) // a D3D driver for GL? sigh... + isG200 = true; + + vid_realmode = vid_modenum; + + vid_menudrawfn = VID_MenuDraw; + vid_menukeyfn = VID_MenuKey; + + strcpy (badmode.modedesc, "Bad mode"); + vid_canalttab = true; + + vid_hidden = false; +} +