Sample from nVidia.
But I can't understand why my code doesn't work. I already managed to pass all the matrices for um animation frame.
But since I need to use intancing that is not sufficient. But when I try to pass the matrices in a texture somehow it doesn't load correctly, the matrices are all different from how they were. Even if I try to pass only 1 animation frame with the texture.
So, is there any other way to pass a large amount of data without using textures??
And here is my code:
Class that holds the animationTexture
class CAnimationTexture11
{
protected:
ID3D11ShaderResourceView* m_texture;
ID3D11Texture2D* m_renderTargetTexture;
public:
bool create(ID3D11Device* device, D3DXMATRIX* matrices, int numKeys, int numClusters)
{
D3D11_TEXTURE2D_DESC textureDesc;
HRESULT result;
D3D11_SHADER_RESOURCE_VIEW_DESC shaderResourceViewDesc;
// Initialize the render target texture description.
ZeroMemory(&textureDesc, sizeof(textureDesc));
// Setup the render target texture description.
textureDesc.Width = 512;
textureDesc.Height = 128;
textureDesc.MipLevels = 1;
textureDesc.ArraySize = 1;
textureDesc.Format = DXGI_FORMAT_R32G32B32A32_FLOAT;
textureDesc.SampleDesc.Count = 1;
textureDesc.Usage = D3D11_USAGE_IMMUTABLE;
textureDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
textureDesc.CPUAccessFlags = 0;
textureDesc.MiscFlags = 0;
D3DXVECTOR4* pData = new D3DXVECTOR4[512*128];
D3DXVECTOR4* pCurrentData = pData;
for(int i=0;i<numClusters;++i)
{
D3DXVECTOR4* pCurrentMatrice = (D3DXVECTOR4*)&matrices[numClusters];
memcpy(pCurrentData++, pCurrentMatrice++, sizeof(D3DXVECTOR4));
}
D3D11_SUBRESOURCE_DATA srd;
srd.pSysMem = (void*)pData;
srd.SysMemPitch = 512*(sizeof(D3DXVECTOR4));
srd.SysMemSlicePitch = 1;
// Create the render target texture.
result = device->CreateTexture2D(&textureDesc, &srd, &m_renderTargetTexture);
if(FAILED(result))
{
return false;
}
// Setup the description of the shader resource view.
shaderResourceViewDesc.Format = textureDesc.Format;
shaderResourceViewDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
shaderResourceViewDesc.Texture2D.MostDetailedMip = 0;
shaderResourceViewDesc.Texture2D.MipLevels = 1;
// Create the shader resource view.
result = device->CreateShaderResourceView(m_renderTargetTexture, &shaderResourceViewDesc, &m_texture);
if(FAILED(result))
{
return false;
}
return true;
}
void set(UINT num, ID3D11DeviceContext* deviceContext)
{
deviceContext->VSSetShaderResources(num, 1, &m_texture);
}
CAnimationTexture11(void);
~CAnimationTexture11(void);
};
Shader:
cbuffer view
{
float4x4 view;
float4x4 rotation;
}
cbuffer animationData
{
float4x4 matrizes[60];
}
struct VOut
{
float4 color : COLOR;
float4 position : SV_POSITION;
};
struct VIn
{
float4 position : POSITION;
float4 normal : NORMAL;
uint instanceId : SV_InstanceID;
uint4 bones : BONES;
float4 weights : WEIGHTS;
};
Texture2D animationTexture;
SamplerState ss;
VOut VShader(VIn input)
{
VOut output;
input.position.w = 1.0f;
//output.position = input.position;
output.position = mul(view, input.position);
output.color = float4(0.2f, 0.2f, 0.2f, 0.2f);
input.normal = normalize(mul(rotation, input.normal));
float4 lightVector = {1.0f, 1.0f, -1.0f, 0.0f};
float4 lightColor = {0.5f, 0.5f, 0.5f, 1.0f};
float lightMult = saturate(dot(input.normal, lightVector));
output.color += lightMult * lightColor;
if(input.weights.x > 0.0f)
{
float4 mat1 = animationTexture.Load(uint3(input.bones.x*4, 0, 0));
float4 mat2 = animationTexture.Load(uint3(input.bones.x*4+1, 0, 0));
float4 mat3 = animationTexture.Load(uint3(input.bones.x*4+2, 0, 0));
float4 mat4 = animationTexture.Load(uint3(input.bones.x*4+3, 0, 0));
float4x4 finalDecoded = float4x4(mat1, mat2, mat3, mat4);//matrizes[input.bones.x] * input.weights.x;
float4x4 matrixFinal = mul(view, finalDecoded);
output.position = mul(matrixFinal, input.position);
}
return output;
}
if I use the constant buffer it works, but its too small to pass all the data.