I'm interested in using the "Direct 3D 11 on 12" library, but am running into trouble when resizing the window. In particular, I'm modifying the Visual Studio "DirectX 12 App" sample.
I'm creating the ID3D11On12Device just after the sample creates the ID3D12CommandQueue:
ComPtr<ID3D11Device> d3d11Device;
IUnknown* queues[] = { m_commandQueue.Get() };
DX::ThrowIfFailed(D3D11On12CreateDevice(m_d3dDevice.Get(), D3D11_CREATE_DEVICE_BGRA_SUPPORT, nullptr, 0, queues, 1, 0, d3d11Device.GetAddressOf(), m_d3d11DeviceContext.GetAddressOf(), nullptr));
DX::ThrowIfFailed(d3d11Device.As(&m_d3d11On12Device));
Then, when the sample creates its render target views, I've added creation of the wrapped ID3D11Resource:
for (UINT n = 0; n < c_frameCount; n++)
{
// Visual studio template calls m_swapChain->GetBuffer() and m_d3dDevice->CreateRenderTargetView() here
D3D11_RESOURCE_FLAGS d3d11Flags = { D3D11_BIND_RENDER_TARGET };
DX::ThrowIfFailed(m_d3d11On12Device->CreateWrappedResource(m_renderTargets[n].Get(), &d3d11Flags, D3D12_RESOURCE_STATE_RENDER_TARGET, D3D12_RESOURCE_STATE_PRESENT, IID_PPV_ARGS(&m_wrappedBackBuffers[n])));
rtvDescriptor.Offset(m_rtvDescriptorSize);
...
// m_renderTargets[n]->SetName(), etc.
}
Then, after the rest of the D3D12 resources are created, I'm testing out ID3D11On12Device::AcquireWrappedResources() and ID3D11On12Device::ReleaseWrappedResources() (just as a test, to try to make the code as simple as possible)
ID3D11Resource* resources[] = { m_wrappedBackBuffers[0].Get() };
m_d3d11On12Device->AcquireWrappedResources(resources, 1);
m_d3d11On12Device->ReleaseWrappedResources(resources, 1);
So far, everything seems to be working as expected. The problem, however, occurs when resizing the window. In particular, resizing calls IDXGISwapChain3::ResizeBuffers(). When this occurs, ResizeBuffers() returns failure and the following message is displayed on the console:
DXGI ERROR: IDXGISwapChain::ResizeBuffers: Swapchain cannot be resized unless all outstanding buffer references have been released. [ MISCELLANEOUS ERROR #19: ]
I've tried clearing the m_wrappedBackBuffers references before ResizeBuffers():
for (UINT n = 0; n < c_frameCount; n++)
{
m_renderTargets[n] = nullptr;
m_wrappedBackBuffers[n] = nullptr;
}
but this seems to have no effect. I've also tried Flush()ing and ClearState()ing the ID3D11DeviceContext, but these seem to either have no effect or produce the following error:
D3D12 ERROR: ID3D12CommandQueue::ExecuteCommandLists: A command list, which writes to a swapchain back buffer, may only be executed when that back buffer is the back buffer will be presented during the next call to Present*. Such a back buffer is also referred to as the "current back buffer". [ STATE_SETTING ERROR #907: EXECUTECOMMANDLISTS_WRONGSWAPCHAINBUFFERREFERENCE]
D3D12: Removing Device.
Commenting out the ID3D11On12Device::AcquireWrappedResources() and ID3D11On12Device::ReleaseWrappedResources() calls makes ResizeBuffers() return successfully; but it seems that calling these two functions is required to be able to use the library at all.
It seems that somewhere, the ID3D11On12Device or ID3D11DeviceContext is holding on to a reference to the swap chain buffers, but I haven't been able to find any documentation about how to reset this reference without destroying the entire device.
This issue on GitHub seems to be the same issue I'm having; however, the response involves "calling SetTarget(nullptr) on the D2D context" but I haven't touched Direct2D at all in this project (and the Visual Studio template already calls WaitForGpu() before IDXGISwapChain3::ResizeBuffers()).
Microsoft's sample doesn't include swap chain buffer resizing at all. Running the sample causes the swap chain to be stretched to fit the window.
I haven't found anything about resizing in Microsoft's documentation.