render_state: add DDS texture image loading
This commit is contained in:
parent
b9cfcde9c7
commit
2118b1fbd9
1
Makefile
1
Makefile
@ -80,6 +80,7 @@ OBJS = \
|
||||
$(BUILD_TYPE)/print.obj \
|
||||
$(BUILD_TYPE)/render_state.obj \
|
||||
$(BUILD_TYPE)/input.obj \
|
||||
$(BUILD_TYPE)/dds_validate.obj \
|
||||
$(BUILD_TYPE)/collada.obj \
|
||||
$(BUILD_TYPE)/collada_scene.obj \
|
||||
$(BUILD_TYPE)/scenes/curve_interpolation/curve_interpolation.obj
|
||||
|
||||
124
include/dds.h
Normal file
124
include/dds.h
Normal file
@ -0,0 +1,124 @@
|
||||
//--------------------------------------------------------------------------------------
|
||||
// dds.h
|
||||
//
|
||||
// This header defines constants and structures that are useful when parsing
|
||||
// DDS files. DDS files were originally designed to use several structures
|
||||
// and constants that are native to DirectDraw and are defined in ddraw.h,
|
||||
// such as DDSURFACEDESC2 and DDSCAPS2. This file defines similar
|
||||
// (compatible) constants and structures so that one can use DDS files
|
||||
// without needing to include ddraw.h.
|
||||
//--------------------------------------------------------------------------------------
|
||||
|
||||
#ifndef _DDS_H_
|
||||
#define _DDS_H_
|
||||
|
||||
#include <dxgiformat.h>
|
||||
#include <d3d10.h>
|
||||
|
||||
#pragma pack(push,1)
|
||||
|
||||
#define DDS_MAGIC 0x20534444 // "DDS "
|
||||
|
||||
struct DDS_PIXELFORMAT
|
||||
{
|
||||
DWORD dwSize;
|
||||
DWORD dwFlags;
|
||||
DWORD dwFourCC;
|
||||
DWORD dwRGBBitCount;
|
||||
DWORD dwRBitMask;
|
||||
DWORD dwGBitMask;
|
||||
DWORD dwBBitMask;
|
||||
DWORD dwABitMask;
|
||||
};
|
||||
|
||||
#define DDS_FOURCC 0x00000004 // DDPF_FOURCC
|
||||
#define DDS_RGB 0x00000040 // DDPF_RGB
|
||||
#define DDS_RGBA 0x00000041 // DDPF_RGB | DDPF_ALPHAPIXELS
|
||||
#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE
|
||||
#define DDS_ALPHA 0x00000002 // DDPF_ALPHA
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_DXT1 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_DXT2 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','2'), 0, 0, 0, 0, 0 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_DXT3 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','3'), 0, 0, 0, 0, 0 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_DXT4 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','4'), 0, 0, 0, 0, 0 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_DXT5 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','5'), 0, 0, 0, 0, 0 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_A8R8G8B8 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_A1R5G5B5 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00007c00, 0x000003e0, 0x0000001f, 0x00008000 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_A4R4G4B4 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00000f00, 0x000000f0, 0x0000000f, 0x0000f000 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_R8G8B8 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 24, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000 };
|
||||
|
||||
const DDS_PIXELFORMAT DDSPF_R5G6B5 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x0000f800, 0x000007e0, 0x0000001f, 0x00000000 };
|
||||
|
||||
// This indicates the DDS_HEADER_DXT10 extension is present (the format is in dxgiFormat)
|
||||
const DDS_PIXELFORMAT DDSPF_DX10 =
|
||||
{ sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','1','0'), 0, 0, 0, 0, 0 };
|
||||
|
||||
#define DDS_HEADER_FLAGS_TEXTURE 0x00001007 // DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT
|
||||
#define DDS_HEADER_FLAGS_MIPMAP 0x00020000 // DDSD_MIPMAPCOUNT
|
||||
#define DDS_HEADER_FLAGS_VOLUME 0x00800000 // DDSD_DEPTH
|
||||
#define DDS_HEADER_FLAGS_PITCH 0x00000008 // DDSD_PITCH
|
||||
#define DDS_HEADER_FLAGS_LINEARSIZE 0x00080000 // DDSD_LINEARSIZE
|
||||
|
||||
#define DDS_SURFACE_FLAGS_TEXTURE 0x00001000 // DDSCAPS_TEXTURE
|
||||
#define DDS_SURFACE_FLAGS_MIPMAP 0x00400008 // DDSCAPS_COMPLEX | DDSCAPS_MIPMAP
|
||||
#define DDS_SURFACE_FLAGS_CUBEMAP 0x00000008 // DDSCAPS_COMPLEX
|
||||
|
||||
#define DDS_CUBEMAP_POSITIVEX 0x00000600 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEX
|
||||
#define DDS_CUBEMAP_NEGATIVEX 0x00000a00 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEX
|
||||
#define DDS_CUBEMAP_POSITIVEY 0x00001200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEY
|
||||
#define DDS_CUBEMAP_NEGATIVEY 0x00002200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEY
|
||||
#define DDS_CUBEMAP_POSITIVEZ 0x00004200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEZ
|
||||
#define DDS_CUBEMAP_NEGATIVEZ 0x00008200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEZ
|
||||
|
||||
#define DDS_CUBEMAP_ALLFACES ( DDS_CUBEMAP_POSITIVEX | DDS_CUBEMAP_NEGATIVEX |\
|
||||
DDS_CUBEMAP_POSITIVEY | DDS_CUBEMAP_NEGATIVEY |\
|
||||
DDS_CUBEMAP_POSITIVEZ | DDS_CUBEMAP_NEGATIVEZ )
|
||||
|
||||
#define DDS_FLAGS_VOLUME 0x00200000 // DDSCAPS2_VOLUME
|
||||
|
||||
typedef struct
|
||||
{
|
||||
DWORD dwSize;
|
||||
DWORD dwHeaderFlags;
|
||||
DWORD dwHeight;
|
||||
DWORD dwWidth;
|
||||
DWORD dwPitchOrLinearSize;
|
||||
DWORD dwDepth; // only if DDS_HEADER_FLAGS_VOLUME is set in dwHeaderFlags
|
||||
DWORD dwMipMapCount;
|
||||
DWORD dwReserved1[11];
|
||||
DDS_PIXELFORMAT ddspf;
|
||||
DWORD dwSurfaceFlags;
|
||||
DWORD dwCubemapFlags;
|
||||
DWORD dwReserved2[3];
|
||||
} DDS_HEADER;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
DXGI_FORMAT dxgiFormat;
|
||||
D3D10_RESOURCE_DIMENSION resourceDimension;
|
||||
UINT miscFlag;
|
||||
UINT arraySize;
|
||||
UINT reserved;
|
||||
} DDS_HEADER_DXT10;
|
||||
|
||||
#pragma pack(pop)
|
||||
|
||||
#endif // _DDS_H
|
||||
11
include/dds_validate.hpp
Normal file
11
include/dds_validate.hpp
Normal file
@ -0,0 +1,11 @@
|
||||
#pragma once
|
||||
|
||||
#include "dds.h"
|
||||
|
||||
struct DDS_FILE {
|
||||
DWORD dwMagic;
|
||||
DDS_HEADER header;
|
||||
};
|
||||
|
||||
void dds_validate(DDS_FILE const * const buf, unsigned int size,
|
||||
D3D10_SUBRESOURCE_DATA * subresourceData);
|
||||
@ -8,6 +8,9 @@ HRESULT LoadTexture2D(const wchar_t * resourceName,
|
||||
const DXGI_FORMAT format,
|
||||
ID3D10ShaderResourceView ** pTextureShaderResourceView);
|
||||
|
||||
HRESULT LoadDDSTexture2D(const wchar_t * resourceName,
|
||||
ID3D10ShaderResourceView ** pTextureShaderResourceView);
|
||||
|
||||
HRESULT LoadTexture3D(const wchar_t * resourceName,
|
||||
const int width,
|
||||
const int height,
|
||||
|
||||
2
main.rc
2
main.rc
@ -4,7 +4,7 @@ RES_VOLUME_FXO RCDATA "volume.fxo"
|
||||
RES_BLOOM_FXO RCDATA "bloom.fxo"
|
||||
RES_STATIC_FXO RCDATA "static.fxo"
|
||||
RES_PERLIN RCDATA "texture/perlin.data"
|
||||
RES_ROBOT_PLAYER RCDATA "models/robot_player/robot_player.data"
|
||||
RES_ROBOT_PLAYER RCDATA "models/robot_player/robot_player.DDS"
|
||||
RES_FONT_TERMINUS_6X12 RCDATA "font/terminus_128x64_6x12.data"
|
||||
|
||||
RES_COLLADA_FXO RCDATA "collada.fxo"
|
||||
|
||||
BIN
models/robot_player/robot_player.DDS
Executable file
BIN
models/robot_player/robot_player.DDS
Executable file
Binary file not shown.
66
src/dds_validate.cpp
Normal file
66
src/dds_validate.cpp
Normal file
@ -0,0 +1,66 @@
|
||||
#include <assert.h>
|
||||
#include <d3d10.h>
|
||||
|
||||
#include "dds_validate.hpp"
|
||||
|
||||
static inline unsigned int max(unsigned int a, unsigned int b)
|
||||
{
|
||||
return (a > b) ? a : b;
|
||||
}
|
||||
|
||||
struct dds_size_levels {
|
||||
unsigned int const size;
|
||||
unsigned int const levels;
|
||||
};
|
||||
|
||||
static inline unsigned int dim(unsigned int d)
|
||||
{
|
||||
return max(1, (d / 4));
|
||||
}
|
||||
|
||||
static inline dds_size_levels dds_mip_total_size(uintptr_t data,
|
||||
unsigned int height,
|
||||
unsigned int width,
|
||||
unsigned int max_mip_levels,
|
||||
D3D10_SUBRESOURCE_DATA * subresourceData)
|
||||
{
|
||||
unsigned int mip_total_size = 0;
|
||||
unsigned int mip_levels = 0;
|
||||
while (true) {
|
||||
unsigned int mip_size = dim(height) * dim(width) * 8;
|
||||
mip_total_size += mip_size;
|
||||
subresourceData[mip_levels].pSysMem = (const void *)data;
|
||||
subresourceData[mip_levels].SysMemPitch = dim(width) * 8;
|
||||
mip_levels += 1;
|
||||
assert(mip_levels <= max_mip_levels);
|
||||
data += mip_size;
|
||||
|
||||
if (width == 1 && height == 1)
|
||||
break;
|
||||
|
||||
height /= 2;
|
||||
width /= 2;
|
||||
}
|
||||
|
||||
return (dds_size_levels){mip_total_size, mip_levels};
|
||||
}
|
||||
|
||||
void dds_validate(DDS_FILE const * const dds, unsigned int size,
|
||||
D3D10_SUBRESOURCE_DATA * subresourceData)
|
||||
{
|
||||
assert(dds->dwMagic == DDS_MAGIC);
|
||||
assert(dds->header.dwSize == 124);
|
||||
assert(dds->header.ddspf.dwSize == 32);
|
||||
assert(dds->header.ddspf.dwFlags == DDS_FOURCC);
|
||||
assert(dds->header.ddspf.dwFourCC == MAKEFOURCC('D','X','T','1'));
|
||||
|
||||
assert(dds->header.dwDepth == 0);
|
||||
|
||||
dds_size_levels ret = dds_mip_total_size(((uintptr_t)dds) + (sizeof (DDS_FILE)),
|
||||
dds->header.dwHeight,
|
||||
dds->header.dwWidth,
|
||||
dds->header.dwMipMapCount,
|
||||
subresourceData);
|
||||
assert(ret.size + (sizeof (DDS_FILE)) == size);
|
||||
assert(ret.levels == dds->header.dwMipMapCount);
|
||||
}
|
||||
@ -58,14 +58,18 @@ PS_INPUT VS(VS_INPUT input)
|
||||
float4 PS(PS_INPUT input) : SV_Target
|
||||
{
|
||||
float3 normal = normalize(input.Norm);
|
||||
float3 view_dir = normalize(ViewEye.xyz - input.Pos.xyz);
|
||||
float3 view_dir = normalize(ViewEye.xyz - input.WPos.xyz);
|
||||
|
||||
float3 color = Emission.xyz;
|
||||
|
||||
for (int i = 0; i < 2; i++) {
|
||||
float3 light_dir = normalize(-LightDir[i].xyz);
|
||||
float diffuse_intensity = max(dot(normal, light_dir), 0.0);
|
||||
color += Diffuse.xyz * diffuse_intensity * LightColor[i].xyz;
|
||||
|
||||
float distance = length(LightPos[i].xyz - input.WPos.xyz);
|
||||
float attenuation = 1.0 / (0.02 * distance * distance);
|
||||
|
||||
color += Diffuse.xyz * diffuse_intensity * LightColor[i].xyz * attenuation;
|
||||
}
|
||||
|
||||
return float4(color.xyz, 1);
|
||||
|
||||
15
src/main.cpp
15
src/main.cpp
@ -503,12 +503,8 @@ HRESULT LoadMesh()
|
||||
// textures
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
hr = LoadTexture2D(L"RES_ROBOT_PLAYER",
|
||||
64, // width
|
||||
64, // height
|
||||
64 * 4, // pitch
|
||||
DXGI_FORMAT_R8G8B8A8_UNORM,
|
||||
&g_pTextureShaderResourceView);
|
||||
hr = LoadDDSTexture2D(L"RES_ROBOT_PLAYER",
|
||||
&g_pTextureShaderResourceView);
|
||||
if (FAILED(hr)) {
|
||||
print("LoadTexture2D\n");
|
||||
return hr;
|
||||
@ -1412,7 +1408,7 @@ void RenderModel(float t)
|
||||
XMMATRIX rx = XMMatrixRotationX(XM_PI * -0.0f);
|
||||
XMMATRIX ry = XMMatrixRotationY(XM_PI * -1.0f + t);
|
||||
XMMATRIX mWorldTranslate = XMMatrixTranslation(0.0f, 0.0f, 2.0f);
|
||||
g_World1 = XMMatrixMultiply(rx, ry) * mWorldTranslate;
|
||||
g_World1 = XMMatrixScaling(5, 5, 5), XMMatrixMultiply(rx, ry) * mWorldTranslate;
|
||||
|
||||
// matrices
|
||||
g_pViewVariable->SetMatrix((float *)&g_View);
|
||||
@ -1701,7 +1697,8 @@ void RenderBloom()
|
||||
|
||||
float deadzone(float f)
|
||||
{
|
||||
const float threshold = 0.25f;
|
||||
//const float threshold = 0.25f;
|
||||
const float threshold = 0.01f;
|
||||
if (fabsf(f) <= threshold)
|
||||
return 0.0f;
|
||||
else {
|
||||
@ -1825,7 +1822,7 @@ void Render(float t, float dt)
|
||||
g_pd3dDevice->ClearDepthStencilView(g_pDepthStencilView, D3D10_CLEAR_DEPTH, 1.0f, 0);
|
||||
|
||||
// render
|
||||
//RenderModel(t);
|
||||
RenderModel(t);
|
||||
|
||||
const float ClearColorZero[4] = { 0.0f, 0.0f, 0.0f, 1.0f };
|
||||
ID3D10RenderTargetView * RenderTargets[] = {
|
||||
|
||||
@ -6,6 +6,7 @@
|
||||
#include "globals.hpp"
|
||||
#include "print.hpp"
|
||||
#include "render_state.hpp"
|
||||
#include "dds_validate.hpp"
|
||||
|
||||
HRESULT LoadTexture2D(const wchar_t * resourceName,
|
||||
const int width,
|
||||
@ -54,7 +55,60 @@ HRESULT LoadTexture2D(const wchar_t * resourceName,
|
||||
descSRV.Format = textureDesc.Format;
|
||||
descSRV.ViewDimension = D3D10_SRV_DIMENSION_TEXTURE2D;
|
||||
descSRV.Texture2D.MostDetailedMip = 0;
|
||||
descSRV.Texture2D.MipLevels = 1;
|
||||
descSRV.Texture2D.MipLevels = textureDesc.MipLevels;
|
||||
hr = g_pd3dDevice->CreateShaderResourceView(pTexture, &descSRV, pTextureShaderResourceView);
|
||||
if (FAILED(hr)) {
|
||||
print("CreateShaderResourceView\n");
|
||||
return hr;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT LoadDDSTexture2D(const wchar_t * resourceName,
|
||||
ID3D10ShaderResourceView ** pTextureShaderResourceView)
|
||||
{
|
||||
HRESULT hr;
|
||||
|
||||
printW(L"LoadDDSTexture2D %s\n", resourceName);
|
||||
|
||||
// texture
|
||||
HRSRC hRes = FindResource(NULL, resourceName, RT_RCDATA);
|
||||
if (hRes == NULL) {
|
||||
print("FindResource %s\n", resourceName);
|
||||
return -1;
|
||||
}
|
||||
DWORD dwResourceSize = SizeofResource(NULL, hRes);
|
||||
void const * data = LockResource(LoadResource(NULL, hRes));
|
||||
DDS_FILE const * dds = (DDS_FILE const *)data;
|
||||
D3D10_SUBRESOURCE_DATA subresourceData[dds->header.dwMipMapCount];
|
||||
dds_validate(dds, dwResourceSize, subresourceData);
|
||||
|
||||
D3D10_TEXTURE2D_DESC textureDesc;
|
||||
textureDesc.Width = dds->header.dwWidth;
|
||||
textureDesc.Height = dds->header.dwHeight;
|
||||
textureDesc.MipLevels = dds->header.dwMipMapCount;
|
||||
textureDesc.ArraySize = 1;
|
||||
textureDesc.Format = DXGI_FORMAT_BC1_UNORM;
|
||||
textureDesc.SampleDesc.Count = 1;
|
||||
textureDesc.SampleDesc.Quality = 0;
|
||||
textureDesc.Usage = D3D10_USAGE_IMMUTABLE;
|
||||
textureDesc.BindFlags = D3D10_BIND_SHADER_RESOURCE;
|
||||
textureDesc.CPUAccessFlags = 0;
|
||||
textureDesc.MiscFlags = 0;
|
||||
|
||||
ID3D10Texture2D * pTexture;
|
||||
hr = g_pd3dDevice->CreateTexture2D(&textureDesc, subresourceData, &pTexture);
|
||||
if (FAILED(hr)) {
|
||||
print("DDS CreateTexture2D\n");
|
||||
return hr;
|
||||
}
|
||||
|
||||
D3D10_SHADER_RESOURCE_VIEW_DESC descSRV;
|
||||
descSRV.Format = textureDesc.Format;
|
||||
descSRV.ViewDimension = D3D10_SRV_DIMENSION_TEXTURE2D;
|
||||
descSRV.Texture2D.MostDetailedMip = 0;
|
||||
descSRV.Texture2D.MipLevels = textureDesc.MipLevels;
|
||||
hr = g_pd3dDevice->CreateShaderResourceView(pTexture, &descSRV, pTextureShaderResourceView);
|
||||
if (FAILED(hr)) {
|
||||
print("CreateShaderResourceView\n");
|
||||
@ -113,7 +167,7 @@ HRESULT LoadTexture3D(const wchar_t * resourceName,
|
||||
descSRV.Format = textureDesc.Format;
|
||||
descSRV.ViewDimension = D3D10_SRV_DIMENSION_TEXTURE3D;
|
||||
descSRV.Texture3D.MostDetailedMip = 0;
|
||||
descSRV.Texture3D.MipLevels = 1;
|
||||
descSRV.Texture3D.MipLevels = textureDesc.MipLevels;
|
||||
hr = g_pd3dDevice->CreateShaderResourceView(pTexture, &descSRV, pTextureShaderResourceView);
|
||||
if (FAILED(hr)) {
|
||||
print("CreateShaderResourceView\n");
|
||||
@ -161,7 +215,7 @@ HRESULT CreateTextureRenderTargetView(const int width,
|
||||
descSRV.Format = textureDesc.Format;
|
||||
descSRV.ViewDimension = D3D10_SRV_DIMENSION_TEXTURE2D;
|
||||
descSRV.Texture2D.MostDetailedMip = 0;
|
||||
descSRV.Texture2D.MipLevels = 1;
|
||||
descSRV.Texture2D.MipLevels = textureDesc.MipLevels;
|
||||
hr = g_pd3dDevice->CreateShaderResourceView(pTexture, &descSRV, pTextureShaderResourceView);
|
||||
if (FAILED(hr)) {
|
||||
print("CreateShaderResourceView\n");
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user