⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 fxwgl.c

📁 winNT技术操作系统,国外开放的原代码和LIUX一样
💻 C
📖 第 1 页 / 共 3 页
字号:
/*
 * Mesa 3-D graphics library
 * Version:  4.0
 *
 * Copyright (C) 1999-2001  Brian Paul   All Rights Reserved.
 *
 * Permission is hereby granted, free of charge, to any person obtaining a
 * copy of this software and associated documentation files (the "Software"),
 * to deal in the Software without restriction, including without limitation
 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
 * and/or sell copies of the Software, and to permit persons to whom the
 * Software is furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included
 * in all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 */

/* Authors:
 *    David Bucciarelli
 *    Brian Paul
 *    Keith Whitwell
 *    Hiroshi Morii
 *    Daniel Borca
 */

/* fxwgl.c - Microsoft wgl functions emulation for
 *           3Dfx VooDoo/Mesa interface
 */


#ifdef _WIN32

#ifdef __cplusplus
extern "C" {
#endif

#include <windows.h>
#define GL_GLEXT_PROTOTYPES
#include "GL/gl.h"
#include "GL/glext.h"

#ifdef __cplusplus
}
#endif

#include "GL/fxmesa.h"
#include "glheader.h"
#include "glapi.h"
#include "imports.h"
#include "../../glide/fxdrv.h"

#define MAX_MESA_ATTRS  20

#if (_MSC_VER >= 1200)
#pragma warning( push )
#pragma warning( disable : 4273 )
#endif

struct __extensions__ {
   PROC proc;
   char *name;
};

struct __pixelformat__ {
   PIXELFORMATDESCRIPTOR pfd;
   GLint mesaAttr[MAX_MESA_ATTRS];
};

WINGDIAPI void GLAPIENTRY gl3DfxSetPaletteEXT(GLuint *);
static GLushort gammaTable[3 * 256];

struct __pixelformat__ pix[] = {
   /* 16bit RGB565 single buffer with depth */
   {
    {sizeof(PIXELFORMATDESCRIPTOR), 1,
     PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL,
     PFD_TYPE_RGBA,
     16,
     5, 0, 6, 5, 5, 11, 0, 0,
     0, 0, 0, 0, 0,
     16,
     0,
     0,
     PFD_MAIN_PLANE,
     0, 0, 0, 0}
    ,
    {FXMESA_COLORDEPTH, 16,
     FXMESA_ALPHA_SIZE, 0,
     FXMESA_DEPTH_SIZE, 16,
     FXMESA_STENCIL_SIZE, 0,
     FXMESA_ACCUM_SIZE, 0,
     FXMESA_NONE}
   }
   ,
   /* 16bit RGB565 double buffer with depth */
   {
    {sizeof(PIXELFORMATDESCRIPTOR), 1,
     PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL |
     PFD_DOUBLEBUFFER | PFD_SWAP_COPY,
     PFD_TYPE_RGBA,
     16,
     5, 0, 6, 5, 5, 11, 0, 0,
     0, 0, 0, 0, 0,
     16,
     0,
     0,
     PFD_MAIN_PLANE,
     0, 0, 0, 0}
    ,
    {FXMESA_COLORDEPTH, 16,
     FXMESA_DOUBLEBUFFER,
     FXMESA_ALPHA_SIZE, 0,
     FXMESA_DEPTH_SIZE, 16,
     FXMESA_STENCIL_SIZE, 0,
     FXMESA_ACCUM_SIZE, 0,
     FXMESA_NONE}
   }
   ,
   /* 16bit ARGB1555 single buffer with depth */
   {
    {sizeof(PIXELFORMATDESCRIPTOR), 1,
     PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL,
     PFD_TYPE_RGBA,
     16,
     5, 0, 5, 5, 5, 10, 1, 15,
     0, 0, 0, 0, 0,
     16,
     0,
     0,
     PFD_MAIN_PLANE,
     0, 0, 0, 0}
    ,
    {FXMESA_COLORDEPTH, 15,
     FXMESA_ALPHA_SIZE, 1,
     FXMESA_DEPTH_SIZE, 16,
     FXMESA_STENCIL_SIZE, 0,
     FXMESA_ACCUM_SIZE, 0,
     FXMESA_NONE}
   }
   ,
   /* 16bit ARGB1555 double buffer with depth */
   {
    {sizeof(PIXELFORMATDESCRIPTOR), 1,
     PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL |
     PFD_DOUBLEBUFFER | PFD_SWAP_COPY,
     PFD_TYPE_RGBA,
     16,
     5, 0, 5, 5, 5, 10, 1, 15,
     0, 0, 0, 0, 0,
     16,
     0,
     0,
     PFD_MAIN_PLANE,
     0, 0, 0, 0}
    ,
    {FXMESA_COLORDEPTH, 15,
     FXMESA_DOUBLEBUFFER,
     FXMESA_ALPHA_SIZE, 1,
     FXMESA_DEPTH_SIZE, 16,
     FXMESA_STENCIL_SIZE, 0,
     FXMESA_ACCUM_SIZE, 0,
     FXMESA_NONE}
   }
   ,
   /* 32bit ARGB8888 single buffer with depth */
   {
    {sizeof(PIXELFORMATDESCRIPTOR), 1,
     PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL,
     PFD_TYPE_RGBA,
     32,
     8, 0, 8, 8, 8, 16, 8, 24,
     0, 0, 0, 0, 0,
     24,
     8,
     0,
     PFD_MAIN_PLANE,
     0, 0, 0, 0}
    ,
    {FXMESA_COLORDEPTH, 32,
     FXMESA_ALPHA_SIZE, 8,
     FXMESA_DEPTH_SIZE, 24,
     FXMESA_STENCIL_SIZE, 8,
     FXMESA_ACCUM_SIZE, 0,
     FXMESA_NONE}
   }
   ,
   /* 32bit ARGB8888 double buffer with depth */
   {
    {sizeof(PIXELFORMATDESCRIPTOR), 1,
     PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL |
     PFD_DOUBLEBUFFER | PFD_SWAP_COPY,
     PFD_TYPE_RGBA,
     32,
     8, 0, 8, 8, 8, 16, 8, 24,
     0, 0, 0, 0, 0,
     24,
     8,
     0,
     PFD_MAIN_PLANE,
     0, 0, 0, 0}
    ,
    {FXMESA_COLORDEPTH, 32,
     FXMESA_DOUBLEBUFFER,
     FXMESA_ALPHA_SIZE, 8,
     FXMESA_DEPTH_SIZE, 24,
     FXMESA_STENCIL_SIZE, 8,
     FXMESA_ACCUM_SIZE, 0,
     FXMESA_NONE}
   }
};

static fxMesaContext ctx = NULL;
static WNDPROC hWNDOldProc;
static int curPFD = 0;
static HDC hDC;
static HWND hWND;

static GLboolean haveDualHead;

/* For the in-window-rendering hack */

#ifndef GR_CONTROL_RESIZE
/* Apparently GR_CONTROL_RESIZE can be ignored. OK? */
#define GR_CONTROL_RESIZE -1
#endif

static GLboolean gdiWindowHack;
static void *dibSurfacePtr;
static BITMAPINFO *dibBMI;
static HBITMAP dibHBM;
static HWND dibWnd;

static int
env_check (const char *var, int val)
{
   const char *env = getenv(var);
   return (env && (env[0] == val));
}

static LRESULT APIENTRY
__wglMonitor (HWND hwnd, UINT message, UINT wParam, LONG lParam)
{
   long ret;                    /* Now gives the resized window at the end to hWNDOldProc */

   if (ctx && hwnd == hWND) {
      switch (message) {
         case WM_PAINT:
         case WM_MOVE:
            break;
         case WM_DISPLAYCHANGE:
         case WM_SIZE:
#if 0
            if (wParam != SIZE_MINIMIZED) {
               static int moving = 0;
               if (!moving) {
                  if (!FX_grSstControl(GR_CONTROL_RESIZE)) {
                     moving = 1;
                     SetWindowPos(hwnd, 0, 0, 0, 300, 300, SWP_NOMOVE | SWP_NOZORDER);
                     moving = 0;
                     if (!FX_grSstControl(GR_CONTROL_RESIZE)) {
                        /*MessageBox(0,_T("Error changing windowsize"),_T("fxMESA"),MB_OK);*/
                        PostMessage(hWND, WM_CLOSE, 0, 0);
                     }
                  }
                  /* Do the clipping in the glide library */
                  grClipWindow(0, 0, FX_grSstScreenWidth(), FX_grSstScreenHeight());
                  /* And let the new size set in the context */
                  fxMesaUpdateScreenSize(ctx);
               }
            }
#endif
            break;
         case WM_ACTIVATE:
            break;
         case WM_SHOWWINDOW:
            break;
         case WM_SYSKEYDOWN:
         case WM_SYSCHAR:
            break;
      }
   }

   /* Finally call the hWNDOldProc, which handles the resize with the
    * now changed window sizes */
   ret = CallWindowProc(hWNDOldProc, hwnd, message, wParam, lParam);

   return ret;
}

static void
wgl_error (long error)
{
#define WGL_INVALID_PIXELFORMAT ERROR_INVALID_PIXEL_FORMAT
   SetLastError(0xC0000000      /* error severity */
               |0x00070000      /* error facility (who we are) */
               |error);
}

GLAPI BOOL GLAPIENTRY
wglCopyContext (HGLRC hglrcSrc, HGLRC hglrcDst, UINT mask)
{
   return FALSE;
}

GLAPI HGLRC GLAPIENTRY
wglCreateContext (HDC hdc)
{
   HWND hWnd;
   WNDPROC oldProc;
   int error;

   if (ctx) {
      SetLastError(0);
      return NULL;
   }

   if (!(hWnd = WindowFromDC(hdc))) {
      SetLastError(0);
      return NULL;
   }

   if (curPFD == 0) {
      wgl_error(WGL_INVALID_PIXELFORMAT);
      return NULL;
   }

   if ((oldProc = (WNDPROC)GetWindowLong(hWnd, GWL_WNDPROC)) != __wglMonitor) {
      hWNDOldProc = oldProc;
      SetWindowLong(hWnd, GWL_WNDPROC, (LONG)__wglMonitor);
   }

   /* always log when debugging, or if user demands */
   if (TDFX_DEBUG || env_check("MESA_FX_INFO", 'r')) {
      freopen("MESA.LOG", "w", stderr);
   }

   {
      RECT cliRect;
      ShowWindow(hWnd, SW_SHOWNORMAL);
      SetForegroundWindow(hWnd);
      Sleep(100);               /* a hack for win95 */
      if (env_check("MESA_GLX_FX", 'w') && !(GetWindowLong(hWnd, GWL_STYLE) & WS_POPUP)) {
         /* XXX todo - windowed modes */
         error = !(ctx = fxMesaCreateContext((GLuint) hWnd, GR_RESOLUTION_NONE, GR_REFRESH_NONE, pix[curPFD - 1].mesaAttr));
      } else {
         GetClientRect(hWnd, &cliRect);
         error = !(ctx = fxMesaCreateBestContext((GLuint) hWnd, cliRect.right, cliRect.bottom, pix[curPFD - 1].mesaAttr));
      }
   }

   /*if (getenv("SST_DUALHEAD"))
      haveDualHead =
         ((atoi(getenv("SST_DUALHEAD")) == 1) ? GL_TRUE : GL_FALSE);
   else
      haveDualHead = GL_FALSE;*/

   if (error) {
      SetLastError(0);
      return NULL;
   }

   hDC = hdc;
   hWND = hWnd;

   /* Required by the OpenGL Optimizer 1.1 (is it a Optimizer bug ?) */
   wglMakeCurrent(hdc, (HGLRC)1);

   return (HGLRC)1;
}

GLAPI HGLRC GLAPIENTRY
wglCreateLayerContext (HDC hdc, int iLayerPlane)
{
   SetLastError(0);
   return NULL;
}

GLAPI BOOL GLAPIENTRY
wglDeleteContext (HGLRC hglrc)
{
   if (ctx && hglrc == (HGLRC)1) {

      fxMesaDestroyContext(ctx);

      SetWindowLong(WindowFromDC(hDC), GWL_WNDPROC, (LONG) hWNDOldProc);

      ctx = NULL;
      hDC = 0;
      return TRUE;
   }

   SetLastError(0);

   return FALSE;
}

GLAPI HGLRC GLAPIENTRY
wglGetCurrentContext (VOID)
{
   if (ctx)
      return (HGLRC)1;

   SetLastError(0);
   return NULL;
}

GLAPI HDC GLAPIENTRY
wglGetCurrentDC (VOID)
{
   if (ctx)
      return hDC;

   SetLastError(0);
   return NULL;
}

GLAPI BOOL GLAPIENTRY
wglSwapIntervalEXT (int interval)
{
   if (ctx == NULL) {
      return FALSE;
   }
   if (interval < 0) {
      interval = 0;
   } else if (interval > 3) {
      interval = 3;
   }
   ctx->swapInterval = interval;
   return TRUE;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -