1 2 /* 3 * Copyright 2011 Google Inc. 4 * 5 * Use of this source code is governed by a BSD-style license that can be 6 * found in the LICENSE file. 7 */ 8 9 #include "gl/SkNativeGLContext.h" 10 11 #define WIN32_LEAN_AND_MEAN 12 #include <windows.h> 13 14 SkNativeGLContext::AutoContextRestore::AutoContextRestore() { 15 fOldHGLRC = wglGetCurrentContext(); 16 fOldHDC = wglGetCurrentDC(); 17 } 18 19 SkNativeGLContext::AutoContextRestore::~AutoContextRestore() { 20 wglMakeCurrent(fOldHDC, fOldHGLRC); 21 } 22 23 /////////////////////////////////////////////////////////////////////////////// 24 25 ATOM SkNativeGLContext::gWC = 0; 26 27 SkNativeGLContext::SkNativeGLContext() 28 : fWindow(NULL) 29 , fDeviceContext(NULL) 30 , fGlRenderContext(0) 31 , fPbufferContext(NULL) { 32 } 33 34 SkNativeGLContext::~SkNativeGLContext() { 35 this->destroyGLContext(); 36 } 37 38 void SkNativeGLContext::destroyGLContext() { 39 SkSafeSetNull(fPbufferContext); 40 if (fGlRenderContext) { 41 wglDeleteContext(fGlRenderContext); 42 fGlRenderContext = 0; 43 } 44 if (fWindow && fDeviceContext) { 45 ReleaseDC(fWindow, fDeviceContext); 46 fDeviceContext = 0; 47 } 48 if (fWindow) { 49 DestroyWindow(fWindow); 50 fWindow = 0; 51 } 52 } 53 54 const GrGLInterface* SkNativeGLContext::createGLContext(GrGLStandard forcedGpuAPI) { 55 HINSTANCE hInstance = (HINSTANCE)GetModuleHandle(NULL); 56 57 if (!gWC) { 58 WNDCLASS wc; 59 wc.cbClsExtra = 0; 60 wc.cbWndExtra = 0; 61 wc.hbrBackground = NULL; 62 wc.hCursor = LoadCursor(NULL, IDC_ARROW); 63 wc.hIcon = LoadIcon(NULL, IDI_APPLICATION); 64 wc.hInstance = hInstance; 65 wc.lpfnWndProc = (WNDPROC) DefWindowProc; 66 wc.lpszClassName = TEXT("Griffin"); 67 wc.lpszMenuName = NULL; 68 wc.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC; 69 70 gWC = RegisterClass(&wc); 71 if (!gWC) { 72 SkDebugf("Could not register window class.\n"); 73 return NULL; 74 } 75 } 76 77 if (!(fWindow = CreateWindow(TEXT("Griffin"), 78 TEXT("The Invisible Man"), 79 WS_OVERLAPPEDWINDOW, 80 0, 0, 1, 1, 81 NULL, NULL, 82 hInstance, NULL))) { 83 SkDebugf("Could not create window.\n"); 84 return NULL; 85 } 86 87 if (!(fDeviceContext = GetDC(fWindow))) { 88 SkDebugf("Could not get device context.\n"); 89 this->destroyGLContext(); 90 return NULL; 91 } 92 // Requesting a Core profile would bar us from using NVPR. So we request 93 // compatibility profile or GL ES. 94 SkWGLContextRequest contextType = 95 kGLES_GrGLStandard == forcedGpuAPI ? 96 kGLES_SkWGLContextRequest : kGLPreferCompatibilityProfile_SkWGLContextRequest; 97 98 fPbufferContext = SkWGLPbufferContext::Create(fDeviceContext, 0, contextType); 99 100 HDC dc; 101 HGLRC glrc; 102 103 if (NULL == fPbufferContext) { 104 if (!(fGlRenderContext = SkCreateWGLContext(fDeviceContext, 0, contextType))) { 105 SkDebugf("Could not create rendering context.\n"); 106 this->destroyGLContext(); 107 return NULL; 108 } 109 dc = fDeviceContext; 110 glrc = fGlRenderContext; 111 } else { 112 ReleaseDC(fWindow, fDeviceContext); 113 fDeviceContext = 0; 114 DestroyWindow(fWindow); 115 fWindow = 0; 116 117 dc = fPbufferContext->getDC(); 118 glrc = fPbufferContext->getGLRC(); 119 } 120 121 if (!(wglMakeCurrent(dc, glrc))) { 122 SkDebugf("Could not set the context.\n"); 123 this->destroyGLContext(); 124 return NULL; 125 } 126 127 const GrGLInterface* interface = GrGLCreateNativeInterface(); 128 if (NULL == interface) { 129 SkDebugf("Could not create GL interface.\n"); 130 this->destroyGLContext(); 131 return NULL; 132 } 133 134 return interface; 135 } 136 137 void SkNativeGLContext::makeCurrent() const { 138 HDC dc; 139 HGLRC glrc; 140 141 if (NULL == fPbufferContext) { 142 dc = fDeviceContext; 143 glrc = fGlRenderContext; 144 } else { 145 dc = fPbufferContext->getDC(); 146 glrc = fPbufferContext->getGLRC(); 147 } 148 149 if (!wglMakeCurrent(dc, glrc)) { 150 SkDebugf("Could not create rendering context.\n"); 151 } 152 } 153 154 void SkNativeGLContext::swapBuffers() const { 155 HDC dc; 156 157 if (NULL == fPbufferContext) { 158 dc = fDeviceContext; 159 } else { 160 dc = fPbufferContext->getDC(); 161 } 162 if (!SwapBuffers(dc)) { 163 SkDebugf("Could not complete SwapBuffers.\n"); 164 } 165 } 166