Пятница, 29 Марта 2024, 16:14

Приветствую Вас Гость

[ Новые сообщения · Игроделы · Правила · Поиск ]
  • Страница 1 из 1
  • 1
Форум игроделов » Программирование » C/C++ » Курс: "Основы DirectX" (Лекция 1: DirectX. Инициация.)
Курс: "Основы DirectX"
nilremДата: Понедельник, 24 Августа 2009, 13:07 | Сообщение # 1
Просветленный разум
Сейчас нет на сайте
Основы DirectX
DirectX. Инициация.

Инициа́ция (лат. initiatio — совершение таинства, посвящение) — обряд, знаменующий переход на новую ступень развития в рамках какой-либо социальной группы или мистического общества.
Википедия

Как понятно из написанного выше, сейчас я буду приобщать вас к некому таинству, переводить на следующую ступень знаний. Этим таинством будет программирование трехмерной графики и создание собственных игр. Курс будет состоять из нескольких лекций, знакомящих с основами DirectX, необходимыми для создания игр. Постепенно изучая DirectX, на протяжении всего курса мы и будем делать простую игру.

1. Введение

Большинство современных игр написано на зыке программирования С++ в связке с DirectX API. DirectX это разработанный компанией Микрософт интерфейс прикладного программирования (API - Application Programming Interface), который содержит в себе все структуры, константы, функции и объекты, необходимые для программирования игр вообще и трехмерной графики в частности. Ранее, до того, как Микрософт додумалась это сделать, каждому программисту приходилось писать все самостоятельно. Представляете, какой это адский труд. Хотя вряд ли представляете. Ну, можете просто поверить мне на слово.
Первая версия DirectX появилась в далеком 1995 году. На данный момент уже доступна одиннадцатая. Но поскольку официально ни 10 ни 11 версии не работают в Windows ХР, являющейся на данный момент самой распространенной операционной системой из семейства Windows, использовать мы будем DirectX 9. Все новые версии имеют полную совместимость с предыдущими, так что не переживайте на счет того, что мы взяли старую.
Еще стоит упомянуть, что для работы технология DirectX 9 должна поддерживаться видеокартой, но на данный момент это уже неактуально, поскольку вам вряд ли сейчас удастся найти видеокарту, которая его не поддерживает.

DirectX состоит из нескольких компонентов, каждый из которых служит для своих целей.

1. DirectX Graphics – набор интерфейсов для работы с трехмерной графикой.
2. DirectInput: - предназначен для обработки данных, поступающих с устройств ввода – мыши клавиатуры, иных манипуляторов.
3. DirectPlay: - интерфейс поддержки сети.
4. DirectSound: - интерфейс для работы со звуком. Ранее в составе DirectX находился еще один звуковой интерфейс – DirectMusic, но с 2008 года он был исключен. По слухам та же участь ждет и DirectSound.
5. DirectShow: - интерфейс, используемый для ввода/вывода видео и аудиоданных.

На этом знакомство закончим и перейдем к более насущным темам.

2. Что нам понадобится.
Ну, не нам, а вам. В первую очередь вам понадобятся некоторые знания. Для успешного освоение ниже изложенного материала, вы должны знать язык программирования С++ хотя бы на базовом уровне. Излагаться все будет просто и понятно, а все примеры можно тупо скопипастить и они будут работать, но если такие термины как классы, указатели, полиморфизм и т.д., являются для вас пустым звуком, то разобраться в смысле кода вы будете не способны, поэтому дальнейший материал можете и не читать. Лучше возьмите книгу по языку С++, или почитайте мою лекцию на данную тематику.
Кроме знаний нам будут нужны некоторые инструменты. В первую очередь это среда для программирования - Microsof Visual Studio 2008, которую можно взять на официальном сайте Микрософт. Желательно чтобы это была полнофункциональная версия, иначе некоторые аспекты обучения вам будут недоступны.
Второе что нам понадобится это DirectX SDK (Software Development Kit). Это набор средств разработки, предназначенных для работы с DirectX. Он содержит в себе все необходимые заголовочные и библиотечные файлы, а также документацию и множество примеров. Ссылка на последнюю версию SDK - http://www.microsoft.com/downloa....ang=en.
Также нам понадобятся некоторые дополнительные инструменты для роботы с трехмерной графикой, изображениями и звуком. Это могут быть 3ds Мах или Blender для 3D графики:

Для работы с изображениями Adobe Photoshop или бесплатный GIMP, а кому-то хватит Paint.net:

А для звука можно использовать Adobe Audition или Sound Forge.

Кроме перечисленных можно взять любые другие, просто с этими я работал и в случае чего могу что-то подсказать. В лекциях описывать методы работы с этими программами я не буду, только в крайнем случае. Если вам это нужно, воспользуйтесь дополнительной литературой.
Ну и на последок. На компьютере, на котором предполагается запуск ваших игр, должен быть установлен DirectX runtime. Это пакет библиотек, необходимых для функционирования DirectX. В вашем случае он установится вместе с SDK. Ну а другим пользователям придется скачать его с интернета, это если он у них еще не установлен, поскольку поставляется с большинством современных игр.
Не думаю, что у вас возникнут какие-то проблемы с установкой всего необходимого ПО, но один момент все же объясню. Установка DirectX SDK должна производится после установки Microsof Visual Studio, чтобы в настройках среды прописались необходимые пути к заголовочным файлам и библиотекам. Если этого по каким-то причинам не произошло(например вам не по трафику скачать полное SDK и вы смогли достать только нужные файлы), то эту работу придется проделать вручную.
Делается это так:
Открываем Microsof Visual Studio и кликаем на пункте меню Сервис→Параметры и видим вот такое окно Параметры:

В левой его части необходимо выбрать пункт Проекты и решения, а в появившемся списке Каталоги VС++. Затем в правой части в выпадающем списке «Показать каталоги для» выбираем Включаемые файлы.
В появившемся ниже списке каталогов должна присутствовать похожая на мою строка, содержащая в себе слово DirectX. Если ее нет, то кликаем на значке папки над этим списком. Затем в появившейся пустой строке нажимаем кнопку с тремя точками и отыскиваем нужную нам папку, в том месте, куда был установлен DirectX. Если при установке вы не задавали особого пути, то чаще всего это каталог C:\Program Files. Нам необходимо найти место где находится DirectX и указать на папку «Include». После этого в списке каталогов появится требуемая нам строчка.
Проделываем аналогичные манипуляции и выбрав в «Показать каталоги для» пункт Файлы библиотек. На этот раз нас интересует папка “lib”. Причем, в зависимоcти от вашей операционной системы в ней нужно выбрать или х86 или х64.
Все, после этого вы готовы приступать к созданию своей первой программы с использованием DirectX.


Windmill 2

WindMill 2D Game Engine
nilremДата: Понедельник, 24 Августа 2009, 13:10 | Сообщение # 2
Просветленный разум
Сейчас нет на сайте
3. Подготовка. Создание проекта и окна
Создание проекта
(Чтобы лучше понять эту часть советую обратится к первой лекции курса Основы С++ для начинающих программистов игр)
Теперь нам необходимо создать новый проект, который в последствии превратится в нашу первую программу.
DirectX был разработан специально для операционной системы Windows, поэтому и проект должен быть соответствующий. Нажимаем Файл → Создать → Проект. Откроется окно Новый проект. В левой его части Типы проектов необходимо кликнуть на плюсике напротив пункта Visual C++ и в открывшемся списке выбрать Win32. После этого в правой части Шаблоны выбрать Проект Win32 а внизу указать имя, например dxini. После нажатия ОК, в следующем окне Мастер приложений Win32 в левой его части выбираем пункт Параметры приложения и в правой отмечаем галочкой Пустой проект. Если этого не сделать будет создан проект с несколькими файлами и пока нежелательными для нас настройками. Жмем на Готово. Ну вот проект создан.
Теперь добавляем к нему файл исходного кода, который также называем dxini.cpp. В принципе, имя не имеет никакого значения, можете называть и проект и файлы с исходным кодом как вам заблагорассудится, лишь бы потом смогли разобраться, что же оно значит.

Код для создания пустого окна.
Каждое приложение для Windows должно иметь собственное окно. Поэтому теперь нам необходимо добавить код, который это самое окно создаст и отобразит. Я не буду вдаваться в особые подробности, это бы заняло очень много времени, просто продемонстрирую необходимый код и вкратце объясню, для чего он нужен.
Каждая уважающая себя Windows программа, должна содержать две специальные функции. Вернее одну функцию она должна содержать обязательно, а без второй просто не будет работать так, как нужно. Первая функция - WinMain, и она является обязательной. Название второй не имеет значения, я назову ее - WinProc. Эта функция предназначена для обработки сообщений. Сообщение это такая вещь, несущая информацию о каком-то событии. Например вы переместили мыщь, нажали клавишу на клавиатуре, и ли же программа завершила какую-то операцию. В результате всего этого появляется соответствующее собщение. Операционная система определяет кому предназначено это сообщение и направляет его конкретной прогграмме, которая должна на это сообщение отреагировать предусмотренным образом. WinProc и будет этим заниматься.
Думаю теории пока достаточно, переходим к практике.
В первую очередь подключаем заголовочный файл, в котором содержиться все необходимое для работы с окнами.

Code

#include <windows.h>

Затем объявляем три переменные:
Первая - это структура, содержащая различные параметры окна(Они описаны в комментариях в исходном коде.)

Code

WNDCLASSEX windowsclass;

Далее идентификатор сообщения:

Code

MSG msg;

И уникальный идентификатор окна в системе, так называемый дескриптор:

Code

HWND hWnd;

Теперь объявляем и сразу же описываем определение функции WinProc:

Code

LRESULT CALLBACK WinProc(HWND hWnd,UINT msg,WPARAM wparam,LPARAM lparam)//функция обработки сообщений
{
  switch(msg)
  {
  case WM_DESTROY:    // закрытие(уничтожение) окна
   {
    PostQuitMessage(0);
    return 0;
   }  
  }
  return (DefWindowProc(hWnd,msg,wparam,lparam));
}


В ней предусмотрена обработка всего одного события - WM_DESTROY. Событие это возникает при закрытии окна приложения, и нам оно понадобится для корректного завершения работы всех используемых в дальнейшем устройств и интерфейсов. Все остальное мы будем обрабатывать отдельно.

После этого идет основная функция нашей программы. Опишу вкратце, что в ней происходит. Сначала заполняются параметры, содержащиеся в структуре windowsclass. Затем класс окна регистрируется в системе. На основе этого класса создается и отображается на экране новое окно. А затем программа входит в бесконечный цикл отработки сообщений, который завершается лишь при возникновении события закрытия окна - WM_QUIT. Работает этот цикл так: полученное сообщение передается функции WinProc. Если в ней не предусмотрена обработка этого сообщения, то событие игнорируется и вместо его обработки выполняется помещенный далее код.
Вот вся функция WinMain:

Code

int WINAPI WinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,LPSTR lpCmdLine,int nShowCmd)
{

  // инициализация класа окна
  windowsclass.cbSize = sizeof(windowsclass);    // Размер всей структуры
  windowsclass.hbrBackground = (HBRUSH)GetStockObject(GRAY_BRUSH);    //Цвет фона окна
  windowsclass.hCursor = LoadCursor(NULL, IDC_ARROW);  //Вид курсора
  windowsclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);    //Иконка приложения
  windowsclass.hIconSm = LoadIcon(NULL, IDI_APPLICATION);    // Иконка в заголовке окна
  windowsclass.hInstance = hInstance;      //Экземпляр приложения
  windowsclass.lpfnWndProc = WinProc;      //Наша функция обработки событий
  windowsclass.lpszClassName = L"windowsclass";   //Имя класса окна
  windowsclass.style = CS_DBLCLKS|CS_OWNDC|CS_HREDRAW|CS_VREDRAW;    //Задание стиля окна
   
  RegisterClassEx(&windowsclass);  //Регистрация класа окна в операционной системе

  //Создание окна
  hWnd = CreateWindow(
   L"windowsclass",    //Имя класса окна
   L"DirectX",  // Заголовок окна
   WS_OVERLAPPEDWINDOW|WS_VISIBLE,    //Стиль окна
   100, 100,  // Координаты левого верхнего угла
   600,   // Ширина окна
   600,   // Высота окна
   NULL,   // Дескриптор родительского окна
   NULL,   // Дескриптор меню
   hInstance,  // Экземпляр
   NULL);  // Дополнительные параметры

   ShowWindow(hWnd, nShowCmd);    // Вывод окна
   UpdateWindow(hWnd);   // Обновление окна

   ZeroMemory(&msg,sizeof(msg));    //Очистка сообщений

   while(msg.message!=WM_QUIT)    // Цикл обработки сообщений
   {
    if(PeekMessage(&msg,NULL,0,0,PM_REMOVE))
    {
     TranslateMessage(&msg);
     DispatchMessage(&msg);
    }
    else
    {
     ;    //Наш код
    }
   }
}

Копируем этот код, в порядке изложения, в нашу программу и запускаем.
В зависимости от операционной системы может появиться или не появиться вот такое окно:

Лечится эта ошибка установкой на компьютере специально редистрибутивного пакета с необходимыми компонентами, или включением не найденной библиотеки в вашу программу. Этот метод называется статической линковкой, и им мы и воспользуемся.
Кликаем правой кнопкой в обозревателе решений на названии проекта(не решения - решение может содержать в себе несколько проектов), и в появившемся меню выбираем Свойства:

В появившемся окне Свойства в левой половине выбираем Свойства конфигурации → С/С++ → Создание кода. Затем в правой половине в выпадающем списке Библиотека времени выполнения выбираем Многопоточное с возможностью отладки (/MTd).

Нажимаем ОК, сохраняя внесенные изменения. После этого все обязательно заработает. И даже если у вас все заработало и без внесения дополнительных настроек, все равно рекомендую это сделать. Таким образом будет гарантироваться работоспособность вашей программы на других компьютерах.
После того как все откомпилируется и запуститься вы должны увидеть вот такое окно:

Ну, вот и все. На этом подготовительные операции выполнены. Можно переходить к изучению DirectX.


Windmill 2

WindMill 2D Game Engine
nilremДата: Понедельник, 24 Августа 2009, 13:12 | Сообщение # 3
Просветленный разум
Сейчас нет на сайте
4. Инициализация.
Инициализация DirectX – это несколько последовательных действий, в процессе которых DirectX подготавливается к работе. Я не буду особо вдаваться в теорию, а прямо перейду к изложению кода, лишь в самых важных местах делая необходимые объяснения.
Для того чтобы наша программа могла использовать DIRECTX к ней необходимо подключить специальные заголовочные файлы d3d9.h и d3dx9.h, а также библиотеки. Заголовочные файлы подключаются добавлением в нашу программу с пустым окном, после #include таких строк:

Code

#include <d3d9.h>
#include <d3dx9.h>


А для подключения библиотек, вслед за подключением заголовочных файлов используются следующие директивы:

Code

#pragma comment (lib,"d3d9.lib")
#pragma comment (lib,"d3dx9.lib")

Подключить библиотеки можно и другим способом, но для этого необходимо вносить изменения в настройки проекта. Вот как это делается.
Кликаем правой кнопкой в обозревателе решений на названии проекта(, и в появившемся меню выбираем Свойства. (Иллюстрация есть выше). В появившемся окне Свойства в левой части выбираем Свойства конфигурации → Компоновщик → Ввод. После этого в правой части в строку Дополнительные зависимости вписываем через пробел названия необходимых библиотек.

Какой способ выбрать решайте сами. Мне нравится первый, потому что при переносе исходных файлов в другой проект, не нужно думать о внесении изменения в настройки. А если моим файлом воспользуется кто-то, понятия не имеющий о необходимости что-то настраивать, то все равно исходники будут работать, так как библиотеки уже подключены в коде.
Кстати, хоть это и пустая трата времени, но никто не запрещает использовать оба способа одновременно.

Возвращаемся к нашей программе. После подключения, нам необходимо объявить две переменные:

Code

LPDIRECT3D9 pDirect3D = 0;   
LPDIRECT3DDEVICE9 pDirect3DDevice = 0;

pDirect3D – это указатель на самый главный интерфейс в DirectX. Без него ничего работать не будет.
pDirect3DDevice – также указатель на устройство, если сильно упростить, то можно считать что это наша видеокарта.
Обоим указателям присвоено нулевое значение.

После переменных объявляем три функции:

Code

HRESULT InitialDX(HWND hWnd);    // Функция инициализации DIRECTX
void Render();    // Функция рендеринга(отрисовки)
void ReleaseDX();   // Функция освобождения устройств.

Для чего они нужны, видно из комментариев, сейчас же рассмотрим их определение и разберем, как они работают.

Функция InitialDX выполняет инициализацию. Процесс инициализации состоит из нескольких этапов:
1. Создание основного интерфейса pDirect3D.
2. Подготовка настроек DirectX устройства. Для этих целей часто предварительно запрашивают информацию о текущих настройках монитора.
3. Создание DirectX устройства.

Вот код этой функции:

Code

HRESULT InitialDX(HWND hWnd)
{
   if(NULL==(pDirect3D=Direct3DCreate9(D3D_SDK_VERSION)))    //создание основного интерфейса
    return E_FAIL;
   D3DDISPLAYMODE Display;    // структура с настройками монитора
   if (FAILED(pDirect3D->GetAdapterDisplayMode(D3DADAPTER_DEFAULT,&Display))) // получение настроек монитора.
    return E_FAIL;

   D3DPRESENT_PARAMETERS Direct3DParametr;  // Структура с настройками
   ZeroMemory(&Direct3DParametr,sizeof(Direct3DParametr)); // Обнуление структуры
   Direct3DParametr.Windowed=TRUE;       // Рeжим отображения приложения(true - оконное, false -полноэкранное)
   Direct3DParametr.SwapEffect=D3DSWAPEFFECT_DISCARD;  // Метод переключения буферов
   Direct3DParametr.BackBufferFormat=Display.Format;  // Формат пикселя(колличество разрядов цвета)
   Direct3DParametr.EnableAutoDepthStencil=TRUE;   // Управление буфером глубины
   Direct3DParametr.AutoDepthStencilFormat=D3DFMT_D16;  // Формат буфера глубины
   Direct3DParametr.BackBufferWidth=Display.Width;   // Ширина буфера
   Direct3DParametr.BackBufferHeight=Display.Height;  // Высота буфера
   //    Direct3DParametr.FullScreen_RefreshRateInHz=Display.RefreshRate;    //Частота обновления экрана(только в полноэкранном режиме)
     
   if (FAILED(pDirect3D->CreateDevice(D3DADAPTER_DEFAULT, // используемая видеокарта
    D3DDEVTYPE_HAL,  // тип устройства
    hWnd,    // дескриптор родительского окна
    D3DCREATE_HARDWARE_VERTEXPROCESSING,    //режим обработки шейдеров
    &Direct3DParametr,    // структура с настройками
    &pDirect3DDevice))) // указатель на устройство

    return E_FAIL;

   return S_OK;
}

Сделаю небольшие пояснения к коду. Поскольку DirectX инициализируется для конкретного окна, функции инициализации должен передаваться его дескриптор. В самой функции используются условные операторы, которые завершат программу, если при создании интерфейсов возникнут какие-то неполадки.
И чтобы лучше ее понять, в частности разобраться с настройками, содержащимися в D3DPRESENT_PARAMETERS, да и просто на будущее, расскажу немного про такое понятие как буфер.
Буфер в DirectX это часть видеопамяти, в которой содержится определенное изображение. Буферы делятся на первичный – тот в котором содержится отображаемое в данный момент изображение, и вторичный(также называют - задний) – в котором содержится следующий кадр изображения. Вторичных буферов может быть несколько. Размер буфера не обязательно должен соответствовать размерам окна, а может быть больше или меньше. Сейчас он у нас равен размерам монитора. Можете сделать его соответствующим окну.

Во второй функции Render(), происходит вывод изображения. Поскольку отображать нам пока нечего, то эта функция просто производит очистку вторичного буфера, закрашивает его в синий цвет, и копирует его содержимое в первичный буфер, то есть выводит на экран. Если бы мы что-то рисовали, то необходимый код был бы помещен в соответствующее место. Вот как выглядит эта функция:

Code

void Render()
{
   pDirect3DDevice->Clear(0,NULL,D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER,D3DCOLOR_XRGB(0,0,255),1.0f,0); //Очистка вторичного буфера
   pDirect3DDevice->BeginScene();    //Начало рендеринга
   // Код отрисовки сцены
   pDirect3DDevice->EndScene();    //Конец рендеринга
   pDirect3DDevice->Present(NULL,NULL,NULL,NULL); // копирование вторичного буфера в первичный
}

Здесь есть интересная структура D3DCOLOR_XRGB(0,0,255). Она отвечает за цвет, которым будет закрашено наше окно. Надеюсь вам извествно, что любой цвет можно получить смешивая три базовых цвета. Так вот эта структура и содержит три значения в диапазоне от 0 до 255: r (red)- отвечает за колличество красного цвета, g – (green)зеленого, b – (blue)синего. Поиграйтесь с этой структурой, меняя значения и получая таким образом различные оттенки своего окна
Ну и последняя функция - ReleaseDX. Поскольку в процессе инициализации мы захватили контроль над некоторыми системными устройствами, она освобождает их и возвращает системе. Но прежде чем это сделать, функция проверяет, действительно ли был сделан захват устройства. Освобождение производится в порядке, лбратном инициализации.

Code

void ReleaseDX()
{
   if(pDirect3DDevice!=NULL)
    pDirect3DDevice->Release();
   if(pDirect3D!=NULL)
    pDirect3D->Release();
}

С функциями разобрались. Теперь все что нам нужно, это вставить их в исходный код нашей программы.

Функцию InitialDX необходимо разместить после создания окна, но до его отображения. Причем если устройство создано некорректно, то окно можно не отображать вообще, а программу закрыть. Делается это с помощью макроса SUCCEEDED совместно с условным оператором if. Вот как это выглядит:

Code

if (SUCCEEDED(InitialDX(hWnd)))
   {   
    ShowWindow(hWnd, nShowCmd);    // Вывод окна
    UpdateWindow(hWnd);   // Обновление окна

    ZeroMemory(&msg,sizeof(msg));    //Очистка сообщений

    while(msg.message!=WM_QUIT)    // Цикл обработки сообщений
    {
     if(PeekMessage(&msg,NULL,0,0,PM_REMOVE))
     {
      TranslateMessage(&msg);
      DispatchMessage(&msg);
     }
     else
     {
      Render();    //Наш код
     }
    }
   }

В приведенном примере также видно, куда нужно поместить функцию Render. В этом месте она будет выполнятся до тех пор, пока не получено сообщение о завершении приложения.
Ну а ReleaseDX, освобождающую устройства, помещаем в функцию WinProc, в блок кода, отвечающий за закрытие окна:

Code

case WM_DESTROY:    // закрытие(уничтожение) окна
    {
     ReleaseDX();
     PostQuitMessage(0);
     return 0;
    }

Вот и все. После запуска программы появится вот такое окно:

Поздравляю! У вас все получилось.

Теперь проведем небольшой эксперимент. В структуре настроек D3DPRESENT_PARAMETERS изменим параметр Windowed на false. После этого программма должна запустится в полноэкранном режиме. Сделали? Молодцы! Как это окно теперь закрыть – додумывайтесь сами) В дальнейшем, чтобы избежать подобных проблемм, мы немного расширим код отображения окна.
А сейчас переходим к еще одной важной теме, также относящейся к инициализации.

5. DirectX и MFC
С серьезными игровыми проектами часто поставляются различные инструменты, основным из которых является игровой редактор или по-другому редактор уровней. Чаще всего этот редактор представляет из себя работающее в окне приложение, содержащее множество управляющих элементов. Для его реализации в основном используется стандартная библиотека визуальных компонентов от Микрософт называющаяся MFC(Microsoft Foundation Class). В этой части я расскажу, как связать вместе ее и DirectX. Но дальнейший материал предполагает, что вы уже имеете навыки программирования с использованием MFC. MFC довольно сложная тема, чтобы тратить на нее здесь время Если вы понятия не имеете что это такое, советую почитать соответствующую книгу.

Чем же отличается процесс инициализации DirectX в использующей MFC программе? Дело в том, что такая программа содержит в окне множество управляющих элементов. Ранее мы инициализировали DirectX на все окно, в случае с MFC результат будет не совсем корректный. Поэтому нам нужно провести инициализацию в один из элементов этого окна. Для этого вместо дескриптора окна необходимо взять идентификатор этого элемента. Делается это с помощью функции

Code

HWND  GetDlgItem(HWND hWnd, int ID);

В эту функцию передаются дескриптор окна и идентификатор необходимого элемента, а возвращает она дескриптор этого элемента.
Вот как выглядит вся функция инициализации:

Code

HRESULT InitialDX(HWND hWnd,int ID)
{
   if(NULL==(pDirect3D=Direct3DCreate9(D3D_SDK_VERSION)))    //создание основного интерфейса
    return E_FAIL;
   D3DDISPLAYMODE Display;    // структура с настройками монитора
   if (FAILED(pDirect3D->GetAdapterDisplayMode(D3DADAPTER_DEFAULT,&Display))) // получение настроек монитора.
    return E_FAIL;

   D3DPRESENT_PARAMETERS Direct3DParametr;  // Структура с настройками
   ZeroMemory(&Direct3DParametr,sizeof(Direct3DParametr)); // Обнуление структуры
   Direct3DParametr.Windowed=TRUE;       // Рeжим отображения приложения(true - оконное, false -полноэкранное)
   Direct3DParametr.SwapEffect=D3DSWAPEFFECT_DISCARD;  // Метод переключения буферов
   Direct3DParametr.BackBufferFormat=Display.Format;  // Формат пикселя(колличество разрядов цвета)
   Direct3DParametr.EnableAutoDepthStencil=TRUE;   // Управление буфером глубины
   Direct3DParametr.AutoDepthStencilFormat=D3DFMT_D16;  // Формат буфера глубины

   if (FAILED(pDirect3D->CreateDevice(D3DADAPTER_DEFAULT, // используемая видеокарта
    D3DDEVTYPE_HAL,  // тип устройства
    GetDlgItem(hWnd,ID),    // дескриптор элемента управления
    D3DCREATE_HARDWARE_VERTEXPROCESSING,    //режим обработки шейдеров
    &Direct3DParametr,    // структура с настройками
    &pDirect3DDevice))) // указатель на устройство

    return E_FAIL;

   return S_OK;
}

Здесь при создании устройства вместо дескриптора окна используется указанная выше функция. Все просто.
Функции отрисовки Render()и освобождения устройств ReleaseDX()остаются неизменными.

Как и в предыдущем примере с простым окном в исходный код MFC проекта необходимо подключить заголовочные файлы и библиотеки и объявить DirectX интерфейсы. После этого нужно поместить наши функции в соответствующие места программы.
Функция InitialDX помещается в код функции инициализации приложения. При этом она принимает вот такой вид:

Code

InitialDX(m_hWnd,IDC_STATIC);

Здесь:
m_hWnd - стандартный дескриптор MFC окна,
IDC_STATIC - уникальный идентификатор элемента управления назначенный средой разработки, если это необходимо, то его можно изменить на что-то более понятное.

Ну и соответственно функция Render() помещается в код функции отображения окна, а ReleaseDX()- в код его «уничтожения».

Вот что должно получится при компиляции нашей программы:

А вот что получится при инициализации DirectX не в элемент управления, а в окно целиком:

На этом тему можно считать завершенной. Поскольку MFC в рамках курса нам больше не понадобится, то и особого упора я на нем не делал.

Скажем DirectX-у нет.
Намного проще и эффективнее для разработки редактора воспользоваться новой платформой .NET, предоставляющей намного большие возможности для визуального программирования. Да и писать программы под нее легче. Но, поскольку на предложенный Микрософтом для работы в связке с .NET, управляемый DirectX (Managed DirectX)большинство разработчиков попросту положило, то и мы не будем обращать на него внимания. Микрософт быстро исправилась, разработав новую технологию ХNА, по сути это тот же управляемый DirectX, но преподнесенный под другой упаковкой.
Изучение XNA в программу курса не входит.

6. Дополнение
Вместе с этой лекцией поставляется исходный код в виде решения к Microsof Visual Studio, для открытия необходимо запустить файл dxini.sln. В решении содержатся два проекта:
dxini – пример инициализации DirectX,
dxini_mfc - пример инициализации DirectX в связке с MFC.
Для выбора проекта, который будет компилироваться, необходимо кликнуть по нему правой кнопкой мыши и в открывшемся меню выбрать пункт Назначить запускаемым проектом.

На этом все. До встречи.

Прикрепления: dxini.rar (49.5 Kb)


Windmill 2

WindMill 2D Game Engine
nilremДата: Понедельник, 24 Августа 2009, 13:27 | Сообщение # 4
Просветленный разум
Сейчас нет на сайте
Для обсуждения, вопросов и замечаний создана отдельная тема.

http://gcup.ru/forum/7-1589-1



Windmill 2

WindMill 2D Game Engine
SaiteiДата: Понедельник, 20 Апреля 2015, 20:57 | Сообщение # 5
старожил
Сейчас нет на сайте
Тему открепляю, так как тема старая + написана всего 1 лекция.
Если автор захочет продолжить курс - убедительная просьба написать в ЛС
Форум игроделов » Программирование » C/C++ » Курс: "Основы DirectX" (Лекция 1: DirectX. Инициация.)
  • Страница 1 из 1
  • 1
Поиск:

Все права сохранены. GcUp.ru © 2008-2024 Рейтинг