   Lighting & normals:
  I'm trying use lighting on a mesh that has no normal or adjacancy info at all.  I understand I need to use D3DXComputeNormals at some point but I heared that this needs face normals before it can calculate the vertex normals.  So, does it calculate the face normals and then output the vertex normals or do I have to work out the face mormals manually?  If I have to get them manually, what's a fast way of doing that?Also, I tried using lighting and some attempts at using the vertex / magnitude or just (1, 1, 1) as the normals and I know, that doesn't work now, but that shouldn't cause the mesh I'd displaying to become transparant, should it?  I can change the colour but I can always see the polygons behind the ones I'm looking at as if the model was made of glass.  I tried changing the alpha value of the lighting and the material, and turning off alpha blending comnpletly, but neither of those seemed to help.  Is there anything else it could be?  I'm using a SetupLights function similar to the one in the msdn tutorial.   
Quote:Original post by CodeReaverI'm trying use lighting on a mesh that has no normal or adjacancy info at all.  I understand I need to use D3DXComputeNormals at some point but I heared that this needs face normals before it can calculate the vertex normals.  So, does it calculate the face normals and then output the vertex normals or do I have to work out the face mormals manually?  If I have to get them manually, what's a fast way of doing that?I'm in a bit of a hurry, but here's something to get you started:This is some code I knocked up a couple of days ago that generates normals for a given mesh:DWORD *pAdj = new DWORD[ pBaseMesh->GetNumFaces() * 3 ];if( FAILED( pBaseMesh->GenerateAdjacency( 0.01f, pAdj ) ) ){SAFE_DELETE_ARRAY( pAdj );return E_FAIL;}// Compute normalsif( FAILED( D3DXComputeNormals( pBaseMesh, pAdj ) ) ){SAFE_DELETE_ARRAY( pAdj );return E_FAIL;}SAFE_DELETE_ARRAY( pAdj );;  I saw it mentioned somewhere that not having something like this could cause the polygons to be translucent:D3DFORMAT depthFormat = D3DFMT_D16;if (d3ddm.Format == D3DFMT_R8G8B8 || d3ddm.Format == D3DFMT_X8R8G8B8) depthFormat = D3DFMT_D24X8;d3dpp.AutoDepthStencilFormat = depthFormat;d3dpp.EnableAutoDepthStencil = true;My program only has:bool InitD3D (HWND hWnd) {// Create the D3D Object.if((g_pD3D = Direct3DCreate9(D3D_SDK_VERSION)) == NULL) return false;// Set the presentation paramaters.D3DPRESENT_PARAMETERS D3Dpp = {0};if(!fullscreen){D3Dpp.Windowed = TRUE;D3Dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;D3Dpp.BackBufferWidth   = 0;D3Dpp.BackBufferHeight  = 0;D3Dpp.BackBufferFormat = D3DFMT_UNKNOWN;}else// I'm not using fullscreen mode this time.{D3Dpp.Windowed= FALSE;D3Dpp.SwapEffect   = D3DSWAPEFFECT_DISCARD;RECT deskTopRect;GetClientRect(GetDesktopWindow(), &deskTopRect);D3Dpp.BackBufferWidth   = deskTopRect.right-deskTopRect.left;D3Dpp.BackBufferHeight  = deskTopRect.bottom-deskTopRect.top;D3Dpp.BackBufferFormat  = D3DFMT_A8R8G8B8;}// Create the Direct3D device.if (FAILED(g_pD3D->CreateDevice(D3DADAPTER_DEFAULT,D3DDEVTYPE_HAL,hWnd,D3DCREATE_SOFTWARE_VERTEXPROCESSING,// Can use D3DCREATE_HARDWARE_VERTEXPROCESSING instead    &D3Dpp,&g_pD3DDevice))) return false;    g_pD3DDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE);    g_pD3DDevice->SetRenderState(D3DRS_LIGHTING, FALSE);return true;}So would that be causing the problem with translucent polygons?   ;  Hi. You have to set lighting render state to true if you want to use lights.I don't see any other strange things in your code and I wonder if that's the cause;  I used this and tried a few different values for the alphas and the light vector.  Maybe it could just be that the normals were wrong.void SetupLights() {    D3DMATERIAL9 mtrl;    ZeroMemory(&mtrl, sizeof(D3DMATERIAL9));    mtrl.Diffuse.r = mtrl.Ambient.r = 1.0f;    mtrl.Diffuse.g = mtrl.Ambient.g = 1.0f;    mtrl.Diffuse.b = mtrl.Ambient.b = 1.0f;    mtrl.Diffuse.a = mtrl.Ambient.a = 1.0f;    g_pD3DDevice->SetMaterial(&mtrl);    D3DXVECTOR3 vecDir;    D3DLIGHT9 light;    ZeroMemory(&light, sizeof(D3DLIGHT9));    light.Type  = D3DLIGHT_DIRECTIONAL;    light.Diffuse.r  = 1.0f;    light.Diffuse.g  = 1.0f;    light.Diffuse.b  = 1.0f;    light.Diffuse.a  = 0.0f;vecDir = D3DXVECTOR3(0.0f, //cosf(timeGetTime()/350.0f),0.0f,1.0f  //sinf(timeGetTime()/350.0f));    D3DXVec3Normalize((D3DXVECTOR3*)&light.Direction, &vecDir);    light.Range = 1000.0f;    g_pD3DDevice->SetLight(0, &light);    g_pD3DDevice->LightEnable(0, TRUE);    g_pD3DDevice->SetRenderState(D3DRS_LIGHTING, TRUE);    g_pD3DDevice->SetRenderState(D3DRS_AMBIENT, 0x00808080);};  I switched the lighting on at a later point (in the SetpLights function called every frame), but I got rid of the part that was turning the lights off and tried that thing with the z buffer.  Nothing seemed to help and the z buffer seemed to make things worse.  I included a couple more of libraries that the tutorial had and switched to hardware vertex processing and that got me back to the glass effect, but the polys still appeared translucent.I'll post the whole file, so you can see exactly what I have.  I commented out most of the stuff dealing with normals so I could get it back to the version that was closest.  The libraries in this weren't the ones I added.  I had to bring it here on disk to post on the internet.#pragma comment(lib,"d3d9.lib")#pragma comment(lib,"d3dx9.lib")#pragma comment(lib,"winmm.lib")#include "AMF_Window.h"#include <mmsystem.h>#include <d3dx9.h>/******************************************************************************************//*  DIRECTX STUFF   *//******************************************************************************************/struct SR_POLYGON {WORD v1, v2, v3, unknown;VOID* textureData;  // TEXTUREDATA*};struct SR_EX_POLYGON {WORD v1, v2, v3; };struct SR_SEGMENT {DWORD unknown1;WORD unknown2, unknown3;WORD vFirst, vLast;signed short x, y, z;WORD parentID;VOID* unknown5;};struct SR_EX_SEGMENT {WORD vFirst, vLast;float x, y, z;SR_EX_SEGMENT* parent;};struct SR_VERTEX {signed short x, y, z;WORD normalID;};struct SR_EX_VERTEX {    D3DXVECTOR3pos;DWORD colour;    //D3DXVECTOR3 norm;};#define D3DFVF_SR_EX_VERTEX (D3DFVF_XYZ | D3DFVF_DIFFUSE/* | D3DFVF_NORMAL*/)LPDIRECT3D9g_pD3D= NULL;// D3D ObjectLPDIRECT3DDEVICE9g_pD3DDevice= NULL;// D3D DeviceLPDIRECT3DVERTEXBUFFER9g_pVB= NULL; // D3D Vertex BufferLPD3DXMESHg_pD3DXMesh= NULL; // D3D X-MeshD3DXVECTOR3centrePos= D3DXVECTOR3(0,0,0);D3DXVECTOR3cameraPos= D3DXVECTOR3(0,0,0);intmodelRotX= 0;intmodelRotY= 0;floatradius= 0;boolfullscreen= false;boolInitD3D(HWND hWnd);voidCleanup();voidRender();voidSetupMatrices();voidSetupLights();bool InitD3D (HWND hWnd) {// Create the D3D Object.if((g_pD3D = Direct3DCreate9(D3D_SDK_VERSION)) == NULL) return false;// Set the presentation paramaters.D3DPRESENT_PARAMETERS D3Dpp = {0};// Get the display modeD3DDISPLAYMODE D3Ddm;if(FAILED(g_pD3D->GetAdapterDisplayMode(D3DADAPTER_DEFAULT, &D3Ddm))) return false;if(!fullscreen) {D3Dpp.Windowed= TRUE;D3Dpp.SwapEffect= D3DSWAPEFFECT_DISCARD;D3Dpp.BackBufferWidth= 0;D3Dpp.BackBufferHeight= 0;D3Dpp.BackBufferFormat= D3DFMT_UNKNOWN;  //D3Ddm.Format;// D3Dpp.EnableAutoDepthStencil = TRUE;// D3Dpp.AutoDepthStencilFormat = D3DFMT_D16;}else {// I'm not using fullscreen mode this time.D3Dpp.Windowed= FALSE;D3Dpp.SwapEffect   = D3DSWAPEFFECT_DISCARD;RECT deskTopRect;GetClientRect(GetDesktopWindow(), &deskTopRect);D3Dpp.BackBufferWidth   = deskTopRect.right-deskTopRect.left;D3Dpp.BackBufferHeight  = deskTopRect.bottom-deskTopRect.top;D3Dpp.BackBufferFormat  = D3DFMT_A8R8G8B8;}// Create the Direct3D device.if (FAILED(g_pD3D->CreateDevice(D3DADAPTER_DEFAULT,D3DDEVTYPE_HAL,hWnd,D3DCREATE_SOFTWARE_VERTEXPROCESSING,// Can use D3DCREATE_HARDWARE_VERTEXPROCESSING instead&D3Dpp,&g_pD3DDevice))) return false;// Turn off culling, so we see the front and back of the triangle// Side effect: Allows vertices to be listed anti-clockwise.g_pD3DDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE);// Turn off D3D lighting, since we are providing our own vertex colors// It doesn't seem to matter when using RHWg_pD3DDevice->SetRenderState(D3DRS_LIGHTING, TRUE);// Turn on the zbufferg_pD3DDevice->SetRenderState(D3DRS_ZENABLE, TRUE);return true;}void Cleanup() {    if (g_pD3DXMesh != NULL) g_pD3DXMesh->Release();// Release the mesh.    if (g_pVB != NULL) g_pVB->Release();// Release the vertex buffer.    if (g_pD3DDevice != NULL)   g_pD3DDevice->Release();// Release the D3D device.    if (g_pD3D != NULL)   g_pD3D->Release();// Release the D3D object.}void SetupMatrices() {D3DXMATRIXA16 matWorld, matWorldRotX, matWorldRotY;// Rotate once per second.//DWORD dwTime = timeGetTime() % 10000;//float fAngle = dwTime * (2.0f * D3DX_PI) / 10000.0f;//D3DXMatrixRotationY(&matWorldRot, fAngle);// Rotation set by  usermodelRotX= modelRotX % 100;float angle = modelRotX * (2.0f * D3DX_PI) / 100.0f;D3DXMatrixRotationZ(&matWorldRotX, angle);modelRotY= modelRotY % 100;angle= modelRotY * (2.0f * D3DX_PI) / 100.0f;D3DXMatrixRotationY(&matWorldRotY, angle);D3DXMatrixIdentity(&matWorld);matWorld._11 /= (2*radius);matWorld._22 /= (2*radius);matWorld._33 /= (2*radius);matWorld._41 -= (centrePos.x / (2*radius));matWorld._42 -= (centrePos.y / (2*radius));matWorld._43 -= (centrePos.z / (2*radius));D3DXMatrixMultiply(&matWorld, &matWorld, &matWorldRotX);D3DXMatrixMultiply(&matWorld, &matWorld, &matWorldRotY);g_pD3DDevice->SetTransform(D3DTS_WORLD, &matWorld);// Create the view matrix.D3DXMATRIXA16matView;// The direction the camera is facing.D3DXVECTOR3vLookatPt( 0.0f, 0.0f, 0.0f);// The y axis represents up.D3DXVECTOR3vUpVec( 0.0f, 1.0f, 0.0f);D3DXMatrixLookAtLH(&matView, &cameraPos, &vLookatPt, &vUpVec);// Transform the view matrix.g_pD3DDevice->SetTransform(D3DTS_VIEW, &matView);D3DXMATRIXA16 matProj;D3DXMatrixPerspectiveFovLH(&matProj, D3DX_PI/4, 1.0f, 0.0f, 100.0f);g_pD3DDevice->SetTransform(D3DTS_PROJECTION, &matProj);}void SetupLights() {D3DMATERIAL9 mtrl;ZeroMemory(&mtrl, sizeof(D3DMATERIAL9));mtrl.Diffuse.r = mtrl.Ambient.r = 1.0f;mtrl.Diffuse.g = mtrl.Ambient.g = 1.0f;mtrl.Diffuse.b = mtrl.Ambient.b = 1.0f;mtrl.Diffuse.a = mtrl.Ambient.a = 1.0f;g_pD3DDevice->SetMaterial(&mtrl);D3DXVECTOR3 vecDir;D3DLIGHT9 light;ZeroMemory(&light, sizeof(D3DLIGHT9));light.Type  = D3DLIGHT_DIRECTIONAL;light.Diffuse.r  = 1.0f;light.Diffuse.g  = 1.0f;light.Diffuse.b  = 1.0f;light.Diffuse.a  = 1.0f;vecDir = D3DXVECTOR3(1.0f,1.0f,1.0f);D3DXVec3Normalize((D3DXVECTOR3*)&light.Direction, &vecDir);light.Range = 1000.0f;g_pD3DDevice->SetLight(0, &light);g_pD3DDevice->LightEnable(0, TRUE);// Finally, turn on some ambient light.g_pD3DDevice->SetRenderState(D3DRS_AMBIENT, 0xFFFFFFFF);}void Render() {if (g_pD3DDevice == NULL) return;// Clear the backbuffer to blackg_pD3DDevice->Clear(0,NULL,D3DCLEAR_TARGET,D3DCOLOR_XRGB(0,0,0),1.0f,0);// Begin the sceneif(SUCCEEDED(g_pD3DDevice->BeginScene())) {SetupLights();   SetupMatrices();if (g_pD3DXMesh != NULL) g_pD3DXMesh->DrawSubset(0);g_pD3DDevice->EndScene();}g_pD3DDevice->Present(NULL, NULL, NULL, NULL);}/******************************************************************************************//*  WINDOWS STUFF   *//******************************************************************************************/enum {ID_DX_VIEW=1, ID_SUBWIN, ID_LOAD, ID_MLOAD, ID_SAVE, ID_MSAVE, ID_MEXIT}; HWNDsubWin, dxView,loadButton, saveButton;HMENUhMenu,hFileSubMenu;void CreateSubWindows();bool LoadSR1Object();bool SaveSR1Object();intWINAPI WinMain (HINSTANCE hInst,HINSTANCE hPrev,LPSTR line,int CmdShow) {SetUpWindow("SR1-ModelEx", hInst);ShowWindow(g_hWnd, SW_SHOW);CreateSubWindows();MSG msg ={0};if(InitD3D(dxView)) {while(msg.message != WM_QUIT) {if(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)) {TranslateMessage(&msg);DispatchMessage(&msg);}Render();}}Cleanup();return (int) msg.wParam;}LRESULTWINAPI MsgProc(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam) {switch(msg) {case WM_DESTROY: {PostQuitMessage(NULL);break;}case WM_COMMAND: {if (wParam==ID_MLOAD) LoadSR1Object();if (wParam==ID_MSAVE) SaveSR1Object();if (wParam==ID_MEXIT) PostQuitMessage(NULL);switch(HIWORD(wParam)) {case BN_CLICKED:if ((LOWORD(wParam))==ID_LOAD)LoadSR1Object();if ((LOWORD(wParam))==ID_SAVE)SaveSR1Object();break;}break;}case WM_KEYDOWN:switch (wParam) {case VK_ADD:case VK_OEM_PLUS:cameraPos.x+=0.10f;break;case VK_SUBTRACT:case VK_OEM_MINUS:cameraPos.x-=0.10f;break;case VK_LEFT:case VK_NUMPAD4:modelRotY--;break;case VK_RIGHT:case VK_NUMPAD6:modelRotY++;break;case VK_UP:case VK_NUMPAD8:modelRotX++;break;case VK_DOWN:case VK_NUMPAD2:modelRotX--;break;}break;case WM_SIZE: {RECT rcClient;GetClientRect(g_hWnd, &rcClient);LPRECT rcParent = (LPRECT)(LPARAM)&rcClient;MoveWindow(subWin, 0, 0, rcParent->right, rcParent->bottom, TRUE);UpdateWindow(subWin);break;}}return DefWindowProc(hwnd,msg,wParam,lParam);}void CreateSubWindows() {// Main MenuhMenu = CreateMenu();hFileSubMenu = CreatePopupMenu();AppendMenu(hFileSubMenu, MF_STRING, ID_MLOAD, "Load");AppendMenu(hFileSubMenu, MF_STRING, ID_MSAVE, "Save");AppendMenu(hFileSubMenu, MF_STRING, ID_MEXIT, "Exit");AppendMenu(hMenu, MF_STRING | MF_POPUP, (UINT_PTR)hFileSubMenu, "File");SetMenu(g_hWnd, hMenu);// Model view windowsubWin = CreateWindowEx(  WS_EX_CLIENTEDGE, "Static", "", WS_VISIBLE | WS_CHILD | WS_MAXIMIZE,50,25,300,300, g_hWnd, (HMENU) ID_SUBWIN, g_hInst, 0);ShowWindow(subWin, SW_SHOW);dxView = CreateWindowEx(  WS_EX_CLIENTEDGE, "Static", "", WS_VISIBLE | WS_CHILD,50,25,300,300, subWin, (HMENU) ID_DX_VIEW, g_hInst, 0);ShowWindow(dxView, SW_SHOW);// Load button/*loadButton = CreateWindowEx(  0, "Button", "Load", BS_PUSHBUTTON | WS_VISIBLE | WS_CHILD,10,10,50,20, g_hWnd, (HMENU) ID_LOAD, g_hInst, 0);SendDlgItemMessage(g_hWnd, ID_LOAD ,WM_SETFONT, (WPARAM) g_hFont, FALSE);ShowWindow(loadButton, SW_SHOW);*/// Save button/*saveButton = CreateWindowEx(  0, "Button", "Save", BS_PUSHBUTTON | WS_VISIBLE | WS_CHILD,10,30,50,20, g_hWnd, (HMENU) ID_SAVE, g_hInst, 0);SendDlgItemMessage(g_hWnd, ID_SAVE ,WM_SETFONT, (WPARAM) g_hFont, FALSE);ShowWindow(saveButton, SW_SHOW);*/return;}bool LoadSR1Object() {OPENFILENAME ofn = {0};char fileName[MAX_PATH] = "";ofn.lStructSize = sizeof(ofn);ofn.hwndOwner = g_hWnd;ofn.lpstrFilter = "Soul Reaver Object Files (*.SRObj)\0*.SRObj\0All Files (*.*)\0*.*\0";ofn.lpstrFile = fileName;ofn.nMaxFile = MAX_PATH;ofn.Flags = OFN_EXPLORER | OFN_FILEMUSTEXIST | OFN_HIDEREADONLY;ofn.lpstrDefExt = "SRObj";if(!GetOpenFileName(&ofn)) {return false;}// Open the fileHANDLE SRObj = CreateFile(fileName, GENERIC_READ, FILE_SHARE_READ,NULL, OPEN_EXISTING, NULL, NULL);if (!SRObj) {MessageBox(g_hWnd, "Couldn't open the file", "Error", MB_ICONERROR | MB_OK);return false;}// Load File into MemoryDWORD fileSize = 0, bytesRead;fileSize = GetFileSize(SRObj, NULL);VOID* SRObjData = GlobalAlloc(GPTR, fileSize);// malloc(fileSize);if (!SRObjData) {MessageBox(g_hWnd, "Couldn't allocate memory", "Error", MB_ICONERROR | MB_OK);return false;}if (!ReadFile(SRObj, SRObjData, fileSize, &bytesRead, NULL)) {MessageBox(g_hWnd, "Couldn't read the file", "Error", MB_ICONERROR | MB_OK);delete SRObjData;CloseHandle(SRObj);return false;}CloseHandle(SRObj);// Build map of fileDWORD loadPoint= (((*(DWORD*) SRObjData)>>9)<<11)+0x00000800;VOID* dataStart= (BYTE*)SRObjData+loadPoint;VOID* modelData= (BYTE*)dataStart+*(DWORD*)((BYTE*)dataStart+*((BYTE*)dataStart+0x0000000C));DWORD vertexCount= *(DWORD*)modelData;SR_VERTEX* vertices= (SR_VERTEX*)((BYTE*)dataStart+*(DWORD*)((BYTE*)modelData+0x00000004));DWORD polygonCount= *(DWORD*)((BYTE*)modelData+0x00000010);SR_POLYGON* polygons= (SR_POLYGON*)((BYTE*)dataStart+*(DWORD*)((BYTE*)modelData+0x00000014));DWORD segmentCount= *(DWORD*)((BYTE*)modelData+0x00000018);SR_SEGMENT* segments= (SR_SEGMENT*)((BYTE*)dataStart+*(DWORD*)((BYTE*)modelData+0x0000001C));// Extract the verticesSR_EX_VERTEX* exVertices = new SR_EX_VERTEX[vertexCount];for (DWORD v=0; v<vertexCount; v++) {exVertices[v].pos.x = (float) vertices[v].y;exVertices[v].pos.y = (float) vertices[v].z;exVertices[v].pos.z = (float) vertices[v].x;exVertices[v].colour = 0xFFFFFFFF;// exVertices[v].norm  = D3DXVECTOR3(0,0,0);}// Extract the segment dataSR_EX_SEGMENT*exSegments= new SR_EX_SEGMENT[segmentCount];SR_EX_SEGMENT*currentSegment= NULL;D3DXVECTOR3currentTrans= D3DXVECTOR3(0,0,0);for (DWORD s=0; s<segmentCount; s++) {exSegments.x = (<span class="cpp-keyword">float</span>) segments.y;<br>exSegments.y = (<span class="cpp-keyword">float</span>) segments.z;<br>exSegments.z = (<span class="cpp-keyword">float</span>) segments.x;<br>exSegments.vFirst = segments.vFirst;<br>exSegments.vLast = segments.vLast;<br><span class="cpp-keyword">if</span> (segments.parentID==0xFFFF) exSegments.parent = NULL;<br><span class="cpp-keyword">else</span> exSegments.parent = &amp;exSegments[segments.parentID];<br>}<br><span class="cpp-keyword">for</span> (DWORD s=<span class="cpp-number">0</span>; s&lt;segmentCount; s++) {<br>ZeroMemory(&amp;currentTrans, <span class="cpp-keyword">sizeof</span>(currentTrans));<br>currentSegment = &amp;exSegments;<br><span class="cpp-keyword">while</span> (currentSegment) {<br>currentTrans.x += currentSegment-&gt;x;<br>currentTrans.y += currentSegment-&gt;y;<br>currentTrans.z += currentSegment-&gt;z;<br>currentSegment = currentSegment-&gt;parent;<br>}<br><span class="cpp-keyword">if</span> ((exSegments.vFirst!=0xFFFF) &amp;&amp; (exSegments.vLast!=0xFFFF)) {<br><span class="cpp-keyword">for</span> (WORD v=exSegments.vFirst; v&lt;=exSegments.vLast; v++) {<br>exVertices[v].pos.x += currentTrans.x;<br>exVertices[v].pos.y += currentTrans.y;<br>exVertices[v].pos.z += currentTrans.z;<br>}<br>}<br>}<br><br><span class="cpp-comment">// Extract the polygons</span><br>SR_EX_POLYGON* exPolygons = <span class="cpp-keyword">new</span> SR_EX_POLYGON[polygonCount];<br><span class="cpp-keyword">for</span> (DWORD p=<span class="cpp-number">0</span>; p&lt;polygonCount; p++) {<br>exPolygons<p>.v1 = polygons<p>.v1;<br>exPolygons<p>.v2 = polygons<p>.v2;<br>exPolygons<p>.v3 = polygons<p>.v3;<br>}<br><br><span class="cpp-comment">// Do the scaling</span><br><span class="cpp-keyword">for</span> (DWORD v=<span class="cpp-number">0</span>; v&lt;vertexCount; v++) {<br>exVertices[v].pos.x /= <span class="cpp-number">100</span>.0f;<br>exVertices[v].pos.y /= <span class="cpp-number">100</span>.0f;<br>exVertices[v].pos.z /= <span class="cpp-number">100</span>.0f;<br>}<br>D3DXComputeBoundingSphere(<br>&amp;(*exVertices).pos,<br>vertexCount,<br><span class="cpp-keyword">sizeof</span>(SR_EX_VERTEX),<br>&amp;centrePos,<br>&amp;radius<br>);<br><br><span class="cpp-comment">// Get rid of any existing mesh</span><br><span class="cpp-keyword">if</span> (g_pD3DXMesh != NULL)   <br>    g_pD3DXMesh-&gt;Release();<br><br><span class="cpp-comment">// Create Mesh</span><br><span class="cpp-keyword">if</span>(FAILED(<br>D3DXCreateMeshFVF(<br>polygonCount,<br>vertexCount,<br><span class="cpp-number">0</span>,<br>D3DFVF_SR_EX_VERTEX,<br>g_pD3DDevice,<br>&amp;g_pD3DXMesh<br>)<br>)) {<br>MessageBox(g_hWnd,<br><span class="cpp-literal">"Doesn't work!"</span>,<br><span class="cpp-literal">"Error"</span>, MB_ICONERROR | MB_OK | MB_SETFOREGROUND<br>);<br><span class="cpp-keyword">return</span> <span class="cpp-keyword">false</span>;<br>}<br><br><span class="cpp-comment">// Do Vertex Buffer</span><br><span class="cpp-keyword">void</span>* outVertices = NULL;<br><span class="cpp-keyword">if</span>(FAILED(g_pD3DXMesh-&gt;LockVertexBuffer(<span class="cpp-number">0</span>,(<span class="cpp-keyword">void</span>**)&amp;outVertices))) {<br>MessageBox(g_hWnd,<br><span class="cpp-literal">"Doesn't work!"</span>,<br><span class="cpp-literal">"Error"</span>, MB_ICONERROR | MB_OK | MB_SETFOREGROUND<br>);<br><span class="cpp-keyword">return</span> <span class="cpp-keyword">false</span>;<br>}<br>memcpy(outVertices, exVertices, vertexCount*<span class="cpp-keyword">sizeof</span>(SR_EX_VERTEX));<br>g_pD3DXMesh-&gt;UnlockVertexBuffer();<br><br><span class="cpp-comment">// Do Index Buffer</span><br><span class="cpp-keyword">void</span>* outPolygons = NULL;<br><span class="cpp-keyword">if</span>(FAILED(g_pD3DXMesh-&gt;LockIndexBuffer(<span class="cpp-number">0</span>,(<span class="cpp-keyword">void</span>**)&amp;outPolygons))) {<br>MessageBox(g_hWnd,<br><span class="cpp-literal">"Doesn't work!"</span>,<br><span class="cpp-literal">"Error"</span>, MB_ICONERROR | MB_OK | MB_SETFOREGROUND<br>);<br><span class="cpp-keyword">return</span> <span class="cpp-keyword">false</span>;<br>}<br>memcpy(outPolygons, exPolygons, polygonCount*<span class="cpp-keyword">sizeof</span>(SR_EX_POLYGON));<br>g_pD3DXMesh-&gt;UnlockIndexBuffer();<br><br><span class="cpp-comment">// Compute normals</span><br><span class="cpp-comment">/*DWORD *pAdj = new DWORD[g_pD3DXMesh-&gt;GetNumFaces()*3];<br>if(FAILED(g_pD3DXMesh-&gt;GenerateAdjacency(0.01f, pAdj))) {<br>delete pAdj;<br>return false;<br>}<br>if(FAILED(D3DXComputeNormals(g_pD3DXMesh, pAdj))) {<br>delete pAdj;<br>return false;<br>}<br>delete pAdj;*/</span><br><br><span class="cpp-keyword">delete</span> exVertices;<br><span class="cpp-keyword">delete</span> exSegments;<br><span class="cpp-keyword">delete</span> exPolygons;<br>GlobalFree(SRObjData);<span class="cpp-comment">// free(SRObjData);</span><br>cameraPos.x = -<span class="cpp-number">1</span>.5f;<br>modelRotX = <span class="cpp-number">0</span>;<br>modelRotY = <span class="cpp-number">0</span>;<br><span class="cpp-keyword">return</span> <span class="cpp-keyword">true</span>;<br>}<br><br><span class="cpp-keyword">bool</span> SaveSR1Object() {<br><br>OPENFILENAME ofn = {<span class="cpp-number">0</span>};<br><span class="cpp-keyword">char</span> fileName[MAX_PATH] = <span class="cpp-literal">""</span>;<br><br>ofn.lStructSize = <span class="cpp-keyword">sizeof</span>(ofn);<br>ofn.hwndOwner = g_hWnd;<br>ofn.lpstrFilter = <span class="cpp-literal">"DirectX Mesh Files (*.x)\0*.x\0All Files (*.*)\0*.*\0"</span>;<br>ofn.lpstrFile = fileName;<br>ofn.nMaxFile = MAX_PATH;<br>ofn.Flags = OFN_EXPLORER | OFN_FILEMUSTEXIST | OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT;<br>ofn.lpstrDefExt = <span class="cpp-literal">"SRObj"</span>;<br><br><span class="cpp-keyword">if</span>(GetSaveFileName(&amp;ofn)) {<br><span class="cpp-comment">// D3DXF_FILEFORMAT_BINARY, D3DXF_FILEFORMAT_COMPRESSED</span><br>D3DXSaveMeshToX(fileName, g_pD3DXMesh, NULL, NULL, NULL, <span class="cpp-number">0</span>, D3DXF_FILEFORMAT_TEXT);<br><span class="cpp-keyword">return</span> <span class="cpp-keyword">true</span>;<br>}<br><span class="cpp-keyword">return</span> <span class="cpp-keyword">false</span>;<br>}<br><br></pre></div><!–ENDSCRIPT–> 