Текущий архив: 2005.11.13;
Скачать: CL | DM;
Вниз
Проблемка с трансформацией меша в DirectX Найти похожие ветки
← →
Мелкий © (2005-06-30 10:51) [0]Здраствуйте, товарищи! Не могу никак разобраться с проблемой (даже проблемкой). Пытаюсь познать DirectX и сейчас у меня цель такая: кубик, созданный как меш (D3DXCreateBox) я хочу заставить крутиться вокруг оси ординат. Кубик вроде создаётся, однако не рисуется. Один просвещённый человек мне чуть-чуть помог и сделал так, что кубик рисуется и крутится. Но только он использовал матрицу проекции типа D3DXMatrixOrthoRH, и кубик крутился вокруг оси, которую он задал сам как вектор. А я же хочу, чтобы кубик крутился вокруг OY и использовать при этом D3DXMatrixPerspectiveFovLH матрицу. Попытался внести необходимые изменения в код – у меня ничего не работает(в смысле кубика не видать). Меня терзают смутные сомнения по поводу того, что он всё-таки есть, но находится за пределами видимости. Пытался менять его размеры и параметры при создании видовой матрицы и матрицы сдвига, но безуспешно! (правда, когда я совсем здоровый размер поставил, то всё окошко заслонило кубиком или просто я так подумал…).
Короче подскажите где у меня ошибка: или я в пространстве его не так разместил, или неправильные параметры при трансформации задал.
← →
Мелкий © (2005-06-30 10:52) [1]Вот код программки (она на С++, но я думаю вас это особо не смутит :-))):
//Included files
#include <windows.h>
#include <stdio.h>
#include <stdarg.h>
#include <d3d8.h>
#include <d3dx8.h>
#include <Mmsystem.h>
//Application window dimensions, type, class and window name
#define WNDWIDTH 400
#define WNDHEIGHT 400
#define WNDTYPE WS_OVERLAPPEDWINDOW
#define WNDTYPE_EX WS_EX_OVERLAPPEDWINDOW
const char g_szClass[] = "FrameClass";
const char g_szCaption[] = "FrameCaption";
#ifndef SAFE_RELEASE
#define SAFE_RELEASE( OBJ ) { if( OBJ ) (OBJ)->Release(); OBJ = NULL; }
#endif
//Main application instances
HINSTANCE g_hInst; //Global instance handle
HWND g_hWnd; //Global window handle
//Global IDirect3D8, IDirect3DDevice8 and ect objects
IDirect3D8 *g_pD3D = NULL;
IDirect3DDevice8 *g_pD3DDevice = NULL;
LPD3DXMESH g_BoxMesh;
//FVF structure
typedef struct
{
FLOAT x, y, z; //3d-coordinates
D3DCOLOR diffuse; //Diffuse color component
} sVertex;
#define VertexFVF (D3DFVF_XYZ | D3DFVF_DIFFUSE)
//Main application prototypes
LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
BOOL RegisterWindowClasses(HINSTANCE hInst);
HWND CreateMainWindow(HINSTANCE hInst);
BOOL DoInit();
BOOL DoShutdown();
BOOL DoFrame();
int WINAPI WinMain(HINSTANCE hInst, HINSTANCE hPrev, LPSTR szCmdLine, int nCmdShow)
{
MSG Msg;
//Save application instance
g_hInst = hInst;
//Checking if there exists a working copy of an application
if((g_hWnd=FindWindow(g_szClass, NULL))!=NULL)
{
if(IsIconic(g_hWnd))
ShowWindow(g_hWnd, SW_RESTORE);
SetForegroundWindow(g_hWnd);
//Copy is found - the work of the new copy is over
return FALSE;
}
//Register window classes - return on FALSE
if (RegisterWindowClasses(hInst) == FALSE)
return FALSE;
//Create window - return on FALSE
if ((g_hWnd = CreateMainWindow(hInst)) == NULL)
return FALSE;
//Do application initialization - return on FALSE
if (DoInit() == TRUE)
{
//Enter the message pump
ZeroMemory(&Msg, sizeof(MSG));
while (Msg.message != WM_QUIT)
{
//Handle Windows messages if any
if (PeekMessage(&Msg, NULL, 0, 0, PM_REMOVE))
{
TranslateMessage(&Msg);
DispatchMessage(&Msg);
}
else
{
//Do per-frame processing, break on FALSE, return value
if (DoFrame() == FALSE)
break;
}
}
}
//Do shutdown functions
DoShutdown();
//Unregister the window class
UnregisterClass(g_szClass, hInst);
return TRUE;
}
BOOL RegisterWindowClasses(HINSTANCE hInst)
{
WNDCLASSEX wcex;
//Create a window class here and register it
wcex.cbSize = sizeof(wcex);
wcex.style = CS_CLASSDC;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInst;
wcex.hIcon = LoadIcon(NULL, IDI_APPLICATION);
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = NULL;
wcex.lpszMenuName = NULL;
wcex.lpszClassName = g_szClass;
wcex.hIconSm = LoadIcon(NULL, IDI_APPLICATION);
return RegisterClassEx(&wcex);
}
HWND CreateMainWindow(HINSTANCE hInst)
{
HWND hWnd;
//Create the main window
hWnd = CreateWindowEx( WNDTYPE_EX, g_szClass, g_szCaption, WNDTYPE,
0, 0, WNDWIDTH, WNDHEIGHT,
NULL, NULL, hInst, NULL );
if (!hWnd)
return NULL;
//Show and update the window
ShowWindow(hWnd, SW_NORMAL);
UpdateWindow(hWnd);
return hWnd;
}
//The message procedure - empty except for destroy message
LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch(uMsg)
{
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hWnd, uMsg, wParam, lParam);
}
// draws the mesh
void drawMesh (LPD3DXMESH mesh)
{
// Rotate the mesh
D3DXMATRIX matRotY;
D3DXMATRIX matTrans;
D3DXMATRIX matView;
D3DXMATRIX matProj;
D3DXMATRIX matWorld;
D3DXMatrixTranslation(&matTrans, 0.0f, 10.0f, 0.0f);
//rotation
D3DXMatrixRotationY(&matRotY, timeGetTime() / 100.0f);
D3DXMatrixIdentity(&matWorld);
D3DXMatrixMultiply(&matWorld, &matWorld, &matRotY);
D3DXMatrixMultiply(&matWorld, &matWorld, &matTrans);
g_pD3DDevice->SetTransform(D3DTS_WORLD, &matWorld);
// view matrix as identity
D3DXMatrixIdentity(&matView);
g_pD3DDevice->SetTransform(D3DTS_VIEW, &matView);
// set projection matrix
/*D3DXMatrixOrthoRH*/
D3DXMatrixPerspectiveFovRH( &matProj, D3DX_PI/4, 1.0f, -10.0f, 10.0f );
g_pD3DDevice->SetTransform( D3DTS_PROJECTION, &matProj );
// Draw the mesh
mesh->DrawSubset(0);
}
← →
Мелкий © (2005-06-30 10:52) [2]BOOL DoInit()
{
//Caption for message box errors
const char MB_Caption[] = "Initialization error";
//Display mode, present parametres stuctures
D3DDISPLAYMODE d3ddm;
D3DPRESENT_PARAMETERS d3dpp;
//Result checking value
HRESULT hRes;
if ((g_pD3D = Direct3DCreate8(D3D_SDK_VERSION)) == NULL)
{
MessageBox(NULL, "Error creating the IDirect3D8 object!", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
if (FAILED(g_pD3D->GetAdapterDisplayMode(D3DADAPTER_DEFAULT, &d3ddm)))
{
MessageBox(NULL, "Error setting up the display mode!", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
ZeroMemory(&d3dpp, sizeof(D3DPRESENT_PARAMETERS));
//Fields for windowed mode
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = d3ddm.Format;
d3dpp.BackBufferCount = 1;
d3dpp.BackBufferHeight = WNDHEIGHT;
d3dpp.BackBufferWidth = WNDWIDTH;
d3dpp.MultiSampleType = D3DMULTISAMPLE_NONE;
/*d3dpp.MultiSampleQuality = 0; */
d3dpp.EnableAutoDepthStencil = TRUE;
d3dpp.hDeviceWindow = g_hWnd;
d3dpp.Flags = 0/*D3DPRESENTFLAG_DISCARD_DEPTHSTENCIL*/;
d3dpp.AutoDepthStencilFormat = D3DFMT_D16;
d3dpp.FullScreen_RefreshRateInHz = 0;
/*d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE;*/
if (FAILED(hRes = g_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL, g_hWnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, &g_pD3DDevice)))
{
MessageBox(NULL, "Error creating device", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
//Mesh initialization
hRes = D3DXCreateBox( g_pD3DDevice, 10, 10, 10, &g_BoxMesh, NULL );
if FAILED(hRes)
return FALSE;
g_pD3DDevice->SetRenderState( D3DRS_ZENABLE, FALSE );
g_pD3DDevice->SetRenderState( D3DRS_LIGHTING, FALSE );
g_pD3DDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, FALSE );
return TRUE;
}
BOOL DoShutdown()
{
SAFE_RELEASE(g_BoxMesh);
SAFE_RELEASE(g_pD3DDevice);
SAFE_RELEASE(g_pD3D);
return TRUE;
}
BOOL DoFrame()
{
//Perform per-frame processing here, such as rendering.
//Return a value of TRUE foe success, FALSE otherwise.
//Caption for message box errors
const char MB_Caption[] = "Rendering error";
if(FAILED(g_pD3DDevice->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_RGBA(0, 0, 255, 0), 1.0f, 0)))
{
MessageBox(NULL, "Error clearing the back buffer", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
if (SUCCEEDED(g_pD3DDevice->BeginScene()))
{
if (FAILED(g_pD3DDevice->SetVertexShader(VertexFVF)))
{
MessageBox(NULL, "Error setting the vertex shader", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
drawMesh(g_BoxMesh);
g_pD3DDevice->EndScene();
}
else
{
MessageBox(NULL, "Error beginning the scene", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
if (FAILED(g_pD3DDevice->Present(NULL, NULL, NULL, NULL)))
{
MessageBox(NULL, "Error presenting the scene", MB_Caption, MB_OK|MB_ICONSTOP);
return FALSE;
}
return TRUE;
}
← →
Мелкий © (2005-06-30 11:08) [3]
> D3DXMatrixPerspectiveFovRH( &matProj, D3DX_PI/4, 1.0f,
> -10.0f, 10.0f );
Пардон, ошибся! Надо LH. Однако, на RH кубик начал отображаться, но обрезанно как-то (на размере начиная с ~15 его сторон). Пробовал увеличить в матрице проекции края обрезания, но не помогло. А с LH вообще не работает. Так что жду ответов!
← →
Мелкий © (2005-06-30 11:20) [4]Всё сам понял. Увидел я свой несчастный кубик. Другой теперь вопрос: я хочу камеру поднять чуть-чуть, т.е. как бы сверху под углом смотреть на кубик. Это мне как замутить? Угол в параметре создания матрицы проекции менять или как?
← →
Мелкий © (2005-06-30 11:59) [5]Эта проблема также решена! Теперь я хочу добавить материалы моему кубику и освещение в сцену. Свет вроде добавился без ошибок, но до этого кубик был белый (т.е. отсутствие материалов как я понимаю), а после добавления directional света он стал абсолютно чёрный, т.е. как я думаю, у кубика нету цвета и материалов, да и нормалей наверное тоже нет. Короче говоря, как мне добавить к кубику-мешу, созданному стандартной функцией D3DXCreateBox (ещё раз напоминаю во избежание misunderstanding) материалы и нормали? В книжке я нашёл создание кубика-меша вручную, взял оттуда функцию по инициализации. Программка компилится, но даже окна не отображается. Вот эта функция:
HRESULT SetupMesh(LPD3DXMESH mesh)
{
HRESULT hr; // variable to hold return codes
///////////////////////////////////////////////////////////////////////
// vertices for the vertex buffer
sVertex g_Vertices[ ] = {
// X Y Z COLOR
{-1.0f,-1.0f,-1.0f, D3DCOLOR_ARGB(0,255,0,0)}, // 0
{-1.0f, 1.0f,-1.0f, D3DCOLOR_ARGB(0,0,0,255)}, // 1
{1.0f, 1.0f,-1.0f, D3DCOLOR_ARGB(0,0,255,0)}, // 2
{ 1.0f,-1.0f,-1.0f, D3DCOLOR_ARGB(0,0,0,255)}, // 3
{-1.0f,-1.0f, 1.0f, D3DCOLOR_ARGB(0,0,255,0)}, // 4
{1.0f,-1.0f, 1.0f, D3DCOLOR_ARGB(0,0,0,255)}, // 5
{ 1.0f, 1.0f, 1.0f, D3DCOLOR_ARGB(0,0,255,0)}, // 6
{-1.0f, 1.0f, 1.0f, D3DCOLOR_ARGB(0,0,0,255)} // 7
};
// Prepare to copy the vertices into the vertex buffer
VOID* pVertices;
// Lock the vertex buffer
hr = mesh->LockVertexBuffer(D3DLOCK_DISCARD, (unsigned char**)&pVertices);
// Check to make sure the vertex buffer can be locked
if FAILED (hr)
return hr;
///////////////////////////////////////////////////////////////////////
// index buffer data
// The index buffer defines the faces of the cube,
// two faces per each side of the cube
WORD IndexData[ ] = {
0,1,2, // 0
2,3,0, // 1
4,5,6, // 2
6,7,4, // 3
0,3,5, // 4
5,4,0, // 5
3,2,6, // 6
6,5,3, // 7
2,1,7, // 8
7,6,2, // 9
1,0,4, // 10
4,7,1 // 11
};
// Copy the vertices into the buffer
memcpy( pVertices, g_Vertices, sizeof(g_Vertices) );
// Unlock the vertex buffer
mesh->UnlockVertexBuffer();
// Prepare to copy the indices into the index buffer
VOID* IndexPtr;
// Lock the index buffer
hr = mesh->LockIndexBuffer( 0, (unsigned char**)&IndexPtr );
// Check to make sure the index buffer can be locked
if FAILED (hr)
return hr;
// Copy the indices into the buffer
memcpy( IndexPtr, IndexData, sizeof(IndexData)*sizeof(WORD) );
// Unlock the buffer
mesh->UnlockIndexBuffer();
return S_OK;
}
Но тут ещё нормалей нет. Так что подскажите пожалуйста что надо в этой функции исправить, либо может ещё какой путь имеется?
← →
Мелкий © (2005-06-30 13:20) [6]Что, неужели никто не знает как организовать прямой доступ к буферам вершин и индексов меша? Не верю...
Страницы: 1 вся ветка
Текущий архив: 2005.11.13;
Скачать: CL | DM;
Память: 0.51 MB
Время: 0.087 c