Главная страница

Руководство по работе с графической библиотекой OpenGL. Руководство разработано с учетом опыта чтения курса Компьютерная графика


Скачать 0.66 Mb.
НазваниеРуководство по работе с графической библиотекой OpenGL. Руководство разработано с учетом опыта чтения курса Компьютерная графика
Дата21.10.2022
Размер0.66 Mb.
Формат файлаdocx
Имя файла221937-83556.docx
ТипРуководство
#747097
страница20 из 30
1   ...   16   17   18   19   20   21   22   23   ...   30
sizeof ( pfd ));

// заполняем структуру

pfd.nSize = sizeof(pfd);

pfd . nVersion = 1;

// флаги показывают, что мы будем использовать

// дублирующую буферизацию OpenGL в этом окне

Pfd . dwFlags = Pro_DMW_TO_WINDOW |

PFD_SUPPORT_OPENGL |

PFD_DOUBLEBUFFER; pfd.iPixelType = PFD_TYPE_RGBA; // полноцветный буфер цвета (8 бит на канал) pfd. cColorBits = 24;

// запрашиваем 16 бит на пиксель для буфера глубины pfd.cDepthBits = 16; pfd . iLayerType = PFD_MAIN_PLANE; int iFormat = ChoosePixelFormat (hDC, &pfd ); SetPixelFormat (hDC, iFormat, &pfd );

Рассмотрим подробнее функции, которые используются для установки формата пикселя:

int ChoosePixelFormat ( HDC hdc, CONST PDCELFORMATDESCRIPTOR * ppfd );

148

Глава П. Использование OPENGL в MFC и VCL

Эта функция позволяет по контексту графического устрой­ства найти пиксельный формат, максимально удовлетворяющий нашим требованиям, и возвращает его дескриптор. Например, если запрошен 24-битный буфер цвета, а контекст графического устройства предоставляет только 8-битный буфер, то функция возвратит формат пикселя с 8-битным буфером.

Функция SetPixelFormat устанавливает формат пикселя в кон­текст графического устройства:

BOOL SetPixelFormat (

HDC hdc , int iPixelFormat ,

CONST PrXELFORMATDESCRIPTOR * ppfd );

Поскольку мы используем контекст графического устройства с двойным буфером, OpenGL-рисование в контекст происходит в невидимое на экране место в памяти. Это необходимо для предотвращения мерцания. Для того, чтобы изображение появи­лось на экране, нужно вызвать следующую функцию:

SwapBufiers( hDC );

11.3. Контекст рисования (render context)

Контекст рисования определяет в какой контекст устройства будут направляться команды OpenGL. Например, если в про­грамме есть несколько окон OpenGL, то перед вызовом команд OpenGL необходимо указать окно, в которое будут направлены эти команды. С контекстом рисования ассоциировано текущее состояние OpenGL, текстуры, дисплейные списки и т.п.

Создание контекста рисования hRC:

HGLRC hRC;

hRC = wglCreateContext (hDC);

Перед использованием контекста необходимо сделать его те­кущим:

114- Класс GLRC

149

wglMakeCurrent(hDC, hRC);

Далее можно свободно использовать команды OpenGL, не за­бывая вызывать SwapBuffers после окончания рисования кадра.

После использования контекста рисования его нужно освобо­дить (обычно перед освобождением соответствующего контекста устройства):

wglDeleteContext (hRC);

11.4. Класс GLRC

В п.Б.5 приведен пример класса GLRC, реализующий пере­численные операции. Цикл инициализации и рисования с исполь­зованием этого класса выглядит следующим образом:

GLRC* m_pGLRC;

// 1. инициализация окна m_pGLRC = new GLRC(hWnd) ; bool res = m_pGLRG->Create (); if (! res)

Error ("Невозможно„создать„контекст„ОрепСЬ" );

// 2. рисование

// (обычно в обработчиках события WM_PAMT)

bool res = m_pGLRG->MakeCurrent ();

if (! res)

Error ( "Невозможно„сделать„контекст„текущим" );

// команды OpenGL

glClear(GL_COLOR_BUFFER_BLT | GL_DEPTH_BUFFER_BIT)

// завершение кадра m_pGLRG->SwapBuffers () ;

150

Глава П. Использование OPENGL в MFC и VCL

// 3. уничтожение окна

// (обычно в обработчиках события WM_DEJTROY)

m_pGLRG->Destroy () ;

delete m_pGLRC;

11.5. Использование OpenGL с MFC

Если при создании Windows-приложения используется биб­лиотека MFC, то необходимо встроить инициализацию, освобож­дение контекстов и рисование OpenGL в различные обработчики унаследованных классов MFC. Данная книга не является руко­водством по программированию с использованием MFC, поэтому ограничимся советами по использованию OpenGL с этой библио­текой:

  • Код инициализации и рисования теперь должен находиться в методах (или вызываться из этих методов) класса, уна­следованного от класса CWnd напрямую или косвенно.

  • Для инициализации OpenGL лучше всего использовать ме­тод OnCreate, для рисования —OnPaint, OnUpdate, OnDraw или OnTimer (это зависит от разных факторов, например, от какого именно класса унаследован класс OpenGL-окна и что именно изображается).

  • Для предотвращения мерцания необходимо перегрузить обработчик сообщения WM_ERASEBKGND, иначе Windows будет заливать фон окна перед вызовом обработчика OnPaint

  • Для освобождения подойдет обработчик OnDestroy, а для обработки изменений размера окна — OnSize.

  • Получить идентификатор окна можно с помощью метода CWnd::GetSafeHwnd.

11.5. Использование OPENGL С MFC

151

Пример класса окна, рисование в которое осуществляется при помощи OpenGL.

class OpenGLWindow : public CWnd

{ public :

OpenGLWindow () ; // открытые члены класса

private :

// закрытые члены класса

// сигнатуры этих методов определены заранее MFC

// и должны выглядеть именно так

afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct );

afx_msg BOOL OnEraseBkgnd(CDC* pDC);

afx_msg void OnPaintQ;

afx_msg void OnDestroy ();

// объявление карты сообщений Windows DECLARE_MESSAGE_MAP ()

// класс для хранения контекстов OpenGL GLRC* m_pGLRC;

};

Реализация методов:

// конструктор

OpenGLWindow : : OpenGLWindow ()

: m_pGLRC(NULL)

{ }

// заполнение карты сообщений BEGIN_MESSAGE_MAP (OpenGLWindow, CWnd)

// стандартные макросы MFC

ON_WM_CREATE()

ON_WM_PAMT()

152

Глава П. Использование OPENGL в MFC и VCL

ON_WM_DESTROY() ON_WM_ERASEBKGND () END_MES3AGE_MAP ()

// в этом методе реализуем инициализацию afx_msg int OpenGLWindow : : OnCreate (

IPCREATESTRUCT lpCreateStruct) {

m_pGLRC = new GLRC(GetSafeHwnd ()); bool res = m_pGLRG->Create (); if (! res)

return FALSE;

return CWnd: : OnCreate (lpCreateStruct ) ; }

// запрещаем заливку фона

afx_msg BOOL OpenGLWindow :: OnEraseBkgnd (CDC* pDC)

{

return FALSE;

}

// здесь рисуем

afx_msg void OpenGLWindow : : OnPaint ()

{

CWnd:: OnPaint ();

// делаем текущим m_glRC->MakeCurrent () ;

g 1С1 e ar (GL_COLOR_BUFFER_Bir | GL_DEPTH_BUFFER_BrT) ;

// рисуем то, что хотим нарисовать <методы рисования OpenGL>

11.6. Использование OPENGL С VCL

153

m_glRC—>SwapBuffers (); }

// здесь происходит освобождение ресурсов afx_msg
1   ...   16   17   18   19   20   21   22   23   ...   30


написать администратору сайта