简体   繁体   中英

Can't go fullscreen under DirectX12

I have an app which uses DirectX12. I wanted to support fullscreen mode in my app. However, each time I called IDXGISwapChain::SetFullscreenState(), I got this error:

DXGI ERROR: IDXGISwapChain::GetContainingOutput: The swapchain's adapter does not control the output on which the swapchain's window resides.

The error code returned by IDXGISwapChain::SetFullscreenState() was

0x887a0004

My computer has two GPU:

Intel(R) HD Graphics 630 and

NVIDIA GeForce GTX 1060

the latter was the adapter used to create d3d12 device when the error occurred. And if the adapter was the former, there would be no error.

The code flow used to create a IDXGISwapChain3 was

//variables used in the code example
ID3D12Device *pDevice;
IDXGIFactory4 *pDXGIFactory;
IDXGIAdapter *pAdapter;
ID3D12CommandQueue *pCommandQueue;
IDXGISwapChain1 *pTempSwapchain;
IDXGISwapChain3 *pSwapchain;

//the code flow
CreateDXGIFactory2();
pDXGIFactory->EnumAdapter();
D3D12CreateDevice(pAdapter, ...);
pD3DDevice->CreateCommandQueue();
pDXGIFactory->CreateSwapChainForHwnd(pCommandQueue, ..., &pTempSwapchain);
pTempSwapchain->QueryInterface(IID_PPV_ARGS(&pSwapChain));

The IDXGISwapChain::SetFullscreenState() should succeed, but it failed.

Note that the problem is a specific combination of a quirk of the DXGI debug layer and the way that the "hybrid graphics" solutions are implemented depending on which device you are using at the time.

The best option here is to just suppress the error:

#if defined(_DEBUG)
    // Enable the debug layer (requires the Graphics Tools "optional feature").
    //
    // NOTE: Enabling the debug layer after device creation will invalidate the active device.
    {
        ComPtr<ID3D12Debug> debugController;
        if (SUCCEEDED(D3D12GetDebugInterface(IID_PPV_ARGS(debugController.GetAddressOf()))))
        {
            debugController->EnableDebugLayer();
        }
        else
        {
            OutputDebugStringA("WARNING: Direct3D Debug Device is not available\n");
        }

        ComPtr<IDXGIInfoQueue> dxgiInfoQueue;
        if (SUCCEEDED(DXGIGetDebugInterface1(0, IID_PPV_ARGS(dxgiInfoQueue.GetAddressOf()))))
        {
            dxgiInfoQueue->SetBreakOnSeverity(DXGI_DEBUG_ALL, DXGI_INFO_QUEUE_MESSAGE_SEVERITY_ERROR, true);
            dxgiInfoQueue->SetBreakOnSeverity(DXGI_DEBUG_ALL, DXGI_INFO_QUEUE_MESSAGE_SEVERITY_CORRUPTION, true);

            DXGI_INFO_QUEUE_MESSAGE_ID hide[] =
            {
                80 /* IDXGISwapChain::GetContainingOutput: The swapchain's adapter does not control the output on which the swapchain's window resides. */,
            };
            DXGI_INFO_QUEUE_FILTER filter = {};
            filter.DenyList.NumIDs = _countof(hide);
            filter.DenyList.pIDList = hide;
            dxgiInfoQueue->AddStorageFilterEntries(DXGI_DEBUG_DXGI, &filter);
        }
    }
#endif

I use this in all my templates on GitHub .

I have found a solution. Use IDXGIFactory6::EnumAdapterByGpuPreference() method instead of IDXGIFactory::EnumAdapter() method then the error will disappear.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM