Model<VertexPosNormTanTex>* TerrainLoader::Load(ID3D10Device* pDXDevice, const tstring& key) { Model<VertexPosNormTanTex>* ret = 0; if ( m_pAssets->IsAssetPresent(key)) { ret = m_pAssets->GetAsset(key); } else { vector<VertexPosNormTanTex> vertices; vector<DWORD> indices; Texture2D* heightMap = Content->LoadTexture2D(key, true); ID3D10Texture2D* pTex2D = heightMap->GetTextureResource(); vertices.reserve(heightMap->GetWidth() * heightMap->GetHeight()); indices.reserve((heightMap->GetWidth()-1) * (heightMap->GetHeight()-1) * 6); D3D10_MAPPED_TEXTURE2D pMappedTex2D; pTex2D->Map(0, D3D10_MAP_READ, 0, &pMappedTex2D); float heightMult = 1.0f; float planarMult = 1.0f / max(heightMap->GetWidth(), heightMap->GetHeight()); BYTE* pData = static_cast<BYTE*>(pMappedTex2D.pData); for (UINT x = 0; x < heightMap->GetHeight(); ++x) { for (UINT z = 0; z < heightMap->GetWidth(); ++z) { float height = pData[z * 4 + x * pMappedTex2D.RowPitch + 0] / 255.0f; //get red vertices.push_back(VertexPosNormTanTex( static_cast<float>(x) * planarMult, height * heightMult, static_cast<float>(z) * planarMult, 0, 0, 0, 0, 0, 0, static_cast<float>(z) / heightMap->GetWidth(), static_cast<float>(x) / heightMap->GetHeight())); if (z != heightMap->GetWidth() - 1 && x != heightMap->GetHeight() - 1) { indices.push_back(z + x * heightMap->GetWidth()); indices.push_back(z + x * heightMap->GetWidth() + 1); indices.push_back(z + (x + 1) * heightMap->GetWidth()); indices.push_back(z + x * heightMap->GetWidth() + 1); indices.push_back(z + (x + 1) * heightMap->GetWidth() + 1); indices.push_back(z + (x + 1) * heightMap->GetWidth()); } } } pTex2D->Unmap(0); CalculateNormals(vertices, indices); CalculateTangents(vertices, indices); Model<VertexPosNormTanTex>* pModel = new Model<VertexPosNormTanTex>(pDXDevice); ModelMesh<VertexPosNormTanTex>* pMesh = pModel->AddMesh(_T("")); pMesh->SetVertices(vertices); pMesh->SetIndices(indices); m_pAssets->AddAsset(key, pModel); ret = pModel; } return ret; }