stw_wgl_context.c

Go to the documentation of this file.
00001 /**************************************************************************
00002  *
00003  * Copyright 2008 Tungsten Graphics, Inc., Cedar Park, Texas.
00004  * All Rights Reserved.
00005  *
00006  * Permission is hereby granted, free of charge, to any person obtaining a
00007  * copy of this software and associated documentation files (the
00008  * "Software"), to deal in the Software without restriction, including
00009  * without limitation the rights to use, copy, modify, merge, publish,
00010  * distribute, sub license, and/or sell copies of the Software, and to
00011  * permit persons to whom the Software is furnished to do so, subject to
00012  * the following conditions:
00013  *
00014  * The above copyright notice and this permission notice (including the
00015  * next paragraph) shall be included in all copies or substantial portions
00016  * of the Software.
00017  *
00018  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
00019  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
00020  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
00021  * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
00022  * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
00023  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
00024  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
00025  *
00026  **************************************************************************/
00027 
00028 #include <windows.h>
00029 
00030 #include "main/mtypes.h"
00031 #include "main/context.h"
00032 #include "pipe/p_compiler.h"
00033 #include "pipe/p_context.h"
00034 #include "state_tracker/st_context.h"
00035 #include "state_tracker/st_public.h"
00036 #include "stw_device.h"
00037 #include "stw_winsys.h"
00038 #include "stw_framebuffer.h"
00039 #include "stw_pixelformat.h"
00040 #include "stw_wgl_arbmultisample.h"
00041 #include "stw_wgl_context.h"
00042 #include "stw_wgl.h"
00043 
00044 static struct wgl_context *ctx_head = NULL;
00045 
00046 static HDC current_hdc = NULL;
00047 static HGLRC current_hrc = NULL;
00048 
00049 WINGDIAPI BOOL APIENTRY
00050 wglCopyContext(
00051    HGLRC hglrcSrc,
00052    HGLRC hglrcDst,
00053    UINT mask )
00054 {
00055    (void) hglrcSrc;
00056    (void) hglrcDst;
00057    (void) mask;
00058 
00059    return FALSE;
00060 }
00061 
00062 WINGDIAPI HGLRC APIENTRY
00063 wglCreateContext(
00064    HDC hdc )
00065 {
00066    uint pfi;
00067    const struct pixelformat_info *pf;
00068    struct wgl_context *ctx;
00069    GLvisual *visual;
00070    struct pipe_context *pipe;
00071 
00072    pfi = wglGetPixelFormat( hdc );
00073    if (pfi == 0)
00074       return NULL;
00075 
00076    pf = pixelformat_get_info( pfi - 1 );
00077 
00078    ctx = CALLOC_STRUCT( wgl_context );
00079    if (ctx == NULL)
00080       return NULL;
00081 
00082    ctx->hdc = hdc;
00083    ctx->color_bits = GetDeviceCaps( ctx->hdc, BITSPIXEL );
00084 
00085    /* Create visual based on flags
00086     */
00087    visual = _mesa_create_visual(
00088       GL_TRUE,
00089       (pf->flags & PF_FLAG_DOUBLEBUFFER) ? GL_TRUE : GL_FALSE,
00090       GL_FALSE,
00091       pf->color.redbits,
00092       pf->color.greenbits,
00093       pf->color.bluebits,
00094       pf->alpha.alphabits,
00095       0,
00096       pf->depth.depthbits,
00097       pf->depth.stencilbits,
00098       0,
00099       0,
00100       0,
00101       0,
00102       (pf->flags & PF_FLAG_MULTISAMPLED) ? wgl_query_samples() : 0 );
00103    if (visual == NULL) {
00104       FREE( ctx );
00105       return NULL;
00106    }
00107 
00108    pipe = stw_dev->stw_winsys->create_context( stw_dev->screen );
00109    if (!pipe) {
00110       _mesa_destroy_visual( visual );
00111       FREE( ctx );
00112       return NULL;
00113    }
00114 
00115    ctx->st = st_create_context( pipe, visual, NULL );
00116    if (ctx->st == NULL) {
00117       pipe->destroy( pipe );
00118       _mesa_destroy_visual( visual );
00119       FREE( ctx );
00120       return NULL;
00121    }
00122    ctx->st->ctx->DriverCtx = ctx;
00123 
00124    ctx->next = ctx_head;
00125    ctx_head = ctx;
00126 
00127    return (HGLRC) ctx;
00128 }
00129 
00130 WINGDIAPI HGLRC APIENTRY
00131 wglCreateLayerContext(
00132    HDC hdc,
00133    int iLayerPlane )
00134 {
00135    (void) hdc;
00136    (void) iLayerPlane;
00137 
00138    return NULL;
00139 }
00140 
00141 WINGDIAPI BOOL APIENTRY
00142 wglDeleteContext(
00143    HGLRC hglrc )
00144 {
00145    struct wgl_context **link = &ctx_head;
00146    struct wgl_context *ctx = ctx_head;
00147 
00148    while (ctx != NULL) {
00149       if (ctx == (struct wgl_context *) hglrc) {
00150          GLcontext *glctx = ctx->st->ctx;
00151          GET_CURRENT_CONTEXT( glcurctx );
00152          struct stw_framebuffer *fb;
00153 
00154          /* Unbind current if deleting current context.
00155           */
00156          if (glcurctx == glctx)
00157             st_make_current( NULL, NULL, NULL );
00158 
00159          fb = framebuffer_from_hdc( ctx->hdc );
00160          if (fb)
00161             framebuffer_destroy( fb );
00162 
00163          if (WindowFromDC( ctx->hdc ) != NULL)
00164             ReleaseDC( WindowFromDC( ctx->hdc ), ctx->hdc );
00165 
00166          st_destroy_context( ctx->st );
00167 
00168          *link = ctx->next;
00169          FREE( ctx );
00170          return TRUE;
00171       }
00172 
00173       link = &ctx->next;
00174       ctx = ctx->next;
00175    }
00176 
00177    return FALSE;
00178 }
00179 
00180 /* Find the width and height of the window named by hdc.
00181  */
00182 static void
00183 get_window_size( HDC hdc, GLuint *width, GLuint *height )
00184 {
00185    if (WindowFromDC( hdc )) {
00186       RECT rect;
00187 
00188       GetClientRect( WindowFromDC( hdc ), &rect );
00189       *width = rect.right - rect.left;
00190       *height = rect.bottom - rect.top;
00191    }
00192    else {
00193       *width = GetDeviceCaps( hdc, HORZRES );
00194       *height = GetDeviceCaps( hdc, VERTRES );
00195    }
00196 }
00197 
00198 WINGDIAPI HGLRC APIENTRY
00199 wglGetCurrentContext( VOID )
00200 {
00201    return current_hrc;
00202 }
00203 
00204 WINGDIAPI HDC APIENTRY
00205 wglGetCurrentDC( VOID )
00206 {
00207     return current_hdc;
00208 }
00209 
00210 WINGDIAPI BOOL APIENTRY
00211 wglMakeCurrent(
00212    HDC hdc,
00213    HGLRC hglrc )
00214 {
00215    struct wgl_context *ctx = ctx_head;
00216    GET_CURRENT_CONTEXT( glcurctx );
00217    struct stw_framebuffer *fb;
00218    GLuint width = 0;
00219    GLuint height = 0;
00220 
00221    current_hdc = hdc;
00222    current_hrc = hglrc;
00223 
00224    if (hdc == NULL || hglrc == NULL) {
00225       st_make_current( NULL, NULL, NULL );
00226       return TRUE;
00227    }
00228 
00229    while (ctx != NULL) {
00230       if (ctx == (struct wgl_context *) hglrc)
00231          break;
00232       ctx = ctx->next;
00233    }
00234    if (ctx == NULL)
00235       return FALSE;
00236 
00237    /* Return if already current.
00238     */
00239    if (glcurctx != NULL) {
00240       struct wgl_context *curctx = (struct wgl_context *) glcurctx->DriverCtx;
00241 
00242       if (curctx != NULL && curctx == ctx && ctx->hdc == hdc)
00243          return TRUE;
00244    }
00245 
00246    fb = framebuffer_from_hdc( hdc );
00247 
00248    if (hdc != NULL)
00249       get_window_size( hdc, &width, &height );
00250 
00251    /* Lazy creation of framebuffers.
00252     */
00253    if (fb == NULL && ctx != NULL && hdc != NULL) {
00254       GLvisual *visual = &ctx->st->ctx->Visual;
00255 
00256       fb = framebuffer_create( hdc, visual, width, height );
00257       if (fb == NULL)
00258          return FALSE;
00259 
00260       fb->dib_hDC = CreateCompatibleDC( hdc );
00261       fb->hbmDIB = NULL;
00262       fb->pbPixels = NULL;
00263    }
00264 
00265    if (ctx && fb) {
00266       st_make_current( ctx->st, fb->stfb, fb->stfb );
00267       framebuffer_resize( fb, width, height );
00268    }
00269    else {
00270       /* Detach */
00271       st_make_current( NULL, NULL, NULL );
00272    }
00273 
00274    return TRUE;
00275 }
00276 
00277 struct wgl_context *
00278 wgl_context_from_hdc(
00279    HDC hdc )
00280 {
00281    struct wgl_context *ctx = ctx_head;
00282 
00283    while (ctx != NULL) {
00284       if (ctx->hdc == hdc)
00285          return ctx;
00286       ctx = ctx->next;
00287    }
00288    return NULL;
00289 }
00290 
00291 #include "stw_wgl.c"

Generated on Tue Sep 29 06:25:18 2009 for Gallium3D by  doxygen 1.5.4