I was originally going to use an atlas texture to pass a large number of textures to my shader, but the texture bleed due to mip mapping was unnacceptable. After doing some research, I decided that texture arrays would be perfect.
The code snippet below takes in an array of image buffers at full resolution (mip 0) and an array of pregenerated mipmaps for each one. The code works perfectly with either a set of mip 0 images (ArraySize = n; MipLevels = 1) or a single mip 0 image and its associated mipmaps (ArraySize = 1; MipLevels = n), but the call to CreateTexture2D( ) fails if given both array and mip levels (ArraySize = n; MipLevels = m), returning with code 0x80070057 (invalid parameter).
I have read and re-read the documentation and read every related post on the web I could find, as well as tried everything I could think of. The DirectX 11 documentation says it can be done, so I must be missing something. Any help would be appreciated.
// Setup the description of the texture.
textureDesc.Height = height;
textureDesc.Width = width;
textureDesc.MipLevels = mipLevels;
textureDesc.ArraySize = count;
textureDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
textureDesc.SampleDesc.Count = 1;
textureDesc.SampleDesc.Quality = 0;
textureDesc.Usage = D3D11_USAGE_IMMUTABLE;
textureDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
textureDesc.CPUAccessFlags = 0;
textureDesc.MiscFlags = 0;
D3D11_SUBRESOURCE_DATA* subData = new D3D11_SUBRESOURCE_DATA[count*mipLevels];
for( int i = 0; i < count; i++ ) {
subData[i*mipLevels].pSysMem = imageDataArray[i*mipLevels];
subData[i*mipLevels].SysMemPitch = (UINT)(width*4);
subData[i*mipLevels].SysMemSlicePitch = 0;
int w = width;
for( int m = 0; m < mipLevels-1; m++ ) {
w >>= 1;
subData[i*mipLevels+m+1].pSysMem = mipsPtr[i][m];
subData[i*mipLevels+m+1].SysMemPitch = (UINT)(w*4);
subData[i*mipLevels+m+1].SysMemSlicePitch = 0;
}
}
// Create the empty texture.
hResult = device->CreateTexture2D(&textureDesc, (D3D11_SUBRESOURCE_DATA*)subData, &texture);
if( FAILED(hResult) ) {
return false;
}