◆ 윈도우즈 OPENGL - 창 만들기
장치 컨텍스트 얻기 및 해제
- 장치 컨텍스를 얻고 드로잉 후 가능한 빨리 해제 하는 것이 좋음 (시스템 자원 관리)
HDC hDC = GetDC(hWnd);
ReleaseDC(hWnd, hDC);
윈도우즈 OPenGL 프로그램을 만들기 위한 단계를 다음과 같다.
[step 1] 랜더링 컨텍스트 초기화
[step 2] 픽셀 포맷 지정
[step 3] 랜더링 컨텍스트 활성화
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | int COpenGLView::OnCreate(LPCREATESTRUCT lpCreateStruct) { if (CView::OnCreate(lpCreateStruct) == -1) return -1; int nPixelFormat; // Pixel format index m_hDC = ::GetDC(m_hWnd); // Get the Device context static PIXELFORMATDESCRIPTOR pfd = { sizeof(PIXELFORMATDESCRIPTOR), // Size of this structure 1, // Version of this structure PFD_DRAW_TO_WINDOW | // Draw to Window (not to bitmap) PFD_SUPPORT_OPENGL | // Support OpenGL calls in window PFD_DOUBLEBUFFER, // Double buffered mode PFD_TYPE_RGBA, // RGBA Color mode 24, // Want 24bit color 0,0,0,0, 0,0,0,0, 0,0,0,0,0, // Not used to select mode 32, // Size of depth buffer 0,0, PFD_MAIN_PLANE, // Draw in main plane 0,0,0,0}; // Not used to select mode // Choose a pixel format that best matches that described in pfd nPixelFormat = ChoosePixelFormat(m_hDC, &pfd); // Set the pixel format for the device context VERIFY(SetPixelFormat(m_hDC, nPixelFormat, &pfd)); // Create the rendering context m_hRC = wglCreateContext(m_hDC); // Make the rendering context current, perform initialization, then // deselect it VERIFY(wglMakeCurrent(m_hDC,m_hRC)); GLSetupRC(m_hDC); wglMakeCurrent(NULL,NULL); // Create the palette if needed InitializePalette(); return 0; } |
[step 4] 드로잉 코드 호출
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | void COpenGLView::OnDraw(CDC* /*pDC*/) { CProjectOpenGLDoc* pDoc = GetDocument(); ASSERT_VALID(pDoc); if (!pDoc) return; // TODO: 여기에 원시 데이터에 대한 그리기 코드를 추가합니다. // Make the rendering context current wglMakeCurrent(m_hDC,m_hRC); // Call our external OpenGL code GLRenderScene(); // Swap our scene to the front SwapBuffers(m_hDC); // Allow other rendering contexts to co-exist wglMakeCurrent(m_hDC,NULL); } |
1 2 3 4 5 | // OpenGL의 영역을 그립니다. void GLRenderScene() { //OpenGL 드로잉 코드 } |
[step 5] 종료시 현재 렌더링 컨텍스트 해제 및 제거
1 2 3 4 5 6 7 8 9 | void OnDestroy() { // Clean up rendering context stuff wglDeleteContext(m_hRC); ::ReleaseDC(m_hWnd,m_hDC); CView::OnDestroy(); // TODO: 여기에 메시지 처리기 코드를 추가합니다. } |
주의사항
윈도우즈 프로그래밍에서 창을 만들때 반드시 아래 스타일을 선언해야 함
- WS_CLIPCHILDREN | WS_CLIPSIBLINGS
- OpenGL 랜더링 컨텍스트가 다른 창에 렌더링 하는 것을 막기 위함
GDI 렌더링과 OpenGL 이중 버퍼 페이지 전환 시 모든 장치 컨텍스트가 필요하기 때문에 창스타일에 CS_OWNDC 설정 필요
1 2 3 4 5 6 7 | BOOL PreCreateWindow(CREATESTRUCT& cs) { // TODO: CREATESTRUCT cs를 수정하여 여기에서 // Window 클래스 또는 스타일을 수정합니다. cs.style |= (WS_CLIPCHILDREN | WS_CLIPSIBLINGS | CS_OWNDC); return CView::PreCreateWindow(cs); } |
1 2 3 4 5 6 7 | BOOL COpenGLView::OnEraseBkgnd(CDC* pDC) { // TODO: 여기에 메시지 처리기 코드를 추가 및/또는 기본값을 호출합니다. // return CView::OnEraseBkgnd(pDC); return true; } |
'OpenGL' 카테고리의 다른 글
OpenGL: Setting Clipping region (0) | 2014.04.19 |
---|---|
OpenGL: Basic knowledge for 3D programing (0) | 2014.04.19 |
Windows OpenGL: Rendering Context (0) | 2014.04.19 |
Windows OpenGL: Setting and selecting Pixel format (0) | 2014.04.19 |
OPENGL color define (0) | 2014.04.16 |
◆ 윈도우즈 OPENGL - 랜더링 컨텍스트
OpenGL 렌더링 컨텍스트: OpenGL 설정과 명령을 기억함
OpenGL 명령은 작업할 목적지 창을 알아야 한 스레드 당 하나의 렌더링 컨텍스트만을 활성화 할 수 있음
- 따라서 OpenGL 명령 이전 렌더링 창을 지정해야 함
[step 1] HGLRC hRC; // OpenGL 랜더링 컨텍스트 핸들러 변수 선언
[step 2] HDC hDC; // 개별적인 윈도우즈 장치 컨텍스트 선언
[step 3] 픽셀 포맷 지정 // 표현할 창의 속성 정의
[step 4] hRC = wglCreateContext(hDC); // OpenGL 랜더링 컨텍스트 핸들러 생성(개별적인 윈도우즈 장치 컨텍스트)
[step 5] wglMakeCurrent(hDC, hRC); // OpenGL 렌더링 컨텍스를 활성화하고 창의 장치컨텍스트와 연결
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | HGLRC m_hRC; //Rendering Context HDC m_hDC; // Device Context m_hDC = ::GetDC(m_hWnd); // Get the Device context int nPixelFormat; // Pixel format index static PIXELFORMATDESCRIPTOR pfd = { sizeof(PIXELFORMATDESCRIPTOR),// Size of this structure 1, // Version of this structure PFD_DRAW_TO_WINDOW | // Draw to Window (not to bitmap) PFD_SUPPORT_OPENGL | // Support OpenGL calls in window PFD_DOUBLEBUFFER, // Double buffered mode PFD_TYPE_RGBA, // RGBA Color mode 24, // Want 24bit color 0,0,0,0, 0,0,0,0, 0,0,0,0,0, // Not used to select mode 32, // Size of depth buffer 0,0, PFD_MAIN_PLANE, // Draw in main plane 0,0,0,0}; // Not used to select mode // Choose a pixel format that best matches that described in pfd nPixelFormat = ChoosePixelFormat(m_hDC, &pfd); // Set the pixel format for the device context VERIFY(SetPixelFormat(m_hDC, nPixelFormat, &pfd)); // Create the rendering context m_hRC = wglCreateContext(m_hDC); // Make the rendering context current, perform initialization, then // deselect it VERIFY(wglMakeCurrent(m_hDC,m_hRC)); |
윈도우즈 프로그램은 다수의 창을 포함함. 즉, 각각 창들이 자신의 장치 컨텍스트를 가지고 이는 개별적은 픽셀 포맷을 가질 수 있음
- 윈도우즈 GDI 함수(장치 컨텍스트): GDI를 위한 드로잉 모드와 명령을 기억함 즉, OPenGL 랜더링 컨텍스트와 유사함
결론: OpenGL 랜더링 컨텍스트를 통해서 화면을 제어하는데 윈도우즈 프로그램에서 이를 활용하기 위해서는 윈도우즈 장비 컨텍스트를 OpenGL 랜더링 컨텍스트와 연결 해줘야 제어가 가능함.
'OpenGL' 카테고리의 다른 글
OpenGL: Basic knowledge for 3D programing (0) | 2014.04.19 |
---|---|
Windows OpenGL: Making Window Application with OpenGL (0) | 2014.04.19 |
Windows OpenGL: Setting and selecting Pixel format (0) | 2014.04.19 |
OPENGL color define (0) | 2014.04.16 |
Setting Up OpenGL in an MFC control (0) | 2014.04.15 |
◆ 윈도우즈 OPENGL - 픽셀 포맷 설정
필요에 맞는 픽셀 포맷을 찾기 위해 모든 픽셀 포맷을 나열하고 하나씩 확인하는 과정은 상당히 복잡함
따라서 단축함수 ChoosePixelFormat를 제공
- 먼저 사용자가 원하는 3D 창의 속성들을 포함하는 픽셀 포맷 구조체를 만듬
- ChoosePixelFormat는 만들어진 사용자 요구 픽셀 포맷 구조체에 가장 유사한 픽셀 포맷을 찾아 이에 해당하는 Index를 리턴함
- 이 index를 SetPixelFormat에 전달하여 픽셀 포맷을 지정함
[step 1] 원하는 PIXELFORMATDESCRIPTOR을 만듬
[step 2] ChoosePixelFormat 로 유사한 픽셀 포맷 Index를 얻음
[step 3] SetPixelFormat에 획득한 index를 넣어 픽셀 포맷을 지정
----소스 코드
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | // Select the pixel format for a given device context void SetDCPixelFormat(HDC hDC) { int nPixelFormat; static PIXELFORMATDESCRIPTOR pfd = { sizeof(PIXELFORMATDESCRIPTOR), // Size of this structure 1, // Version of this structure PFD_DRAW_TO_WINDOW | // Draw to Window (not to bitmap) PFD_SUPPORT_OPENGL | // Support OpenGL calls in window PFD_DOUBLEBUFFER, // Double buffered mode PFD_TYPE_RGBA, // RGBA Color mode 8, // Want 8 bit color 0,0,0,0,0,0, // Not used to select mode 0,0, // Not used to select mode 0,0,0,0,0, // Not used to select mode 16, // Size of depth buffer 0, // Not used to select mode 0, // Not used to select mode PFD_MAIN_PLANE, // Draw in main plane 0, // Not used to select mode 0,0,0 }; // Not used to select mode // Choose a pixel format that best matches that described in pfd nPixelFormat = ChoosePixelFormat(hDC, &pfd); // Set the pixel format for the device context SetPixelFormat(hDC, nPixelFormat, &pfd); } |
'OpenGL' 카테고리의 다른 글
OpenGL: Basic knowledge for 3D programing (0) | 2014.04.19 |
---|---|
Windows OpenGL: Making Window Application with OpenGL (0) | 2014.04.19 |
Windows OpenGL: Rendering Context (0) | 2014.04.19 |
OPENGL color define (0) | 2014.04.16 |
Setting Up OpenGL in an MFC control (0) | 2014.04.15 |