我使用以下代码创建了一个交换链:
DXGI_SWAP_CHAIN_DESC swapchainDesc;
// Clear out the struct for use
ZeroMemory(&swapchainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
// Fill the swap chain description struct
swapchainDesc.BufferCount = 1; // one back buffer
swapchainDesc.BufferDesc.Width = width;
swapchainDesc.BufferDesc.Height = height;
swapchainDesc.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; // use 32-bit color DXGI_FORMAT_R8G8B8A8_UNORM DXGI_FORMAT_R32G32B32_FLOAT
swapchainDesc.BufferDesc.RefreshRate.Numerator = 60;
swapchainDesc.BufferDesc.RefreshRate.Denominator = 1;
swapchainDesc.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; // how swap chain is to be used
swapchainDesc.OutputWindow = hWnd; // the window to be used
swapchainDesc.SampleDesc.Count = 1; // how many multisamples (1-4, above is not guaranteed for DX11 GPUs)
swapchainDesc.SampleDesc.Quality = 0; // multisample quality level
swapchainDesc.Windowed = TRUE; // windowed/full-screen mode
// Configure DX feature level
D3D_FEATURE_LEVEL featureLevels[] =
{
D3D_FEATURE_LEVEL_11_1,
D3D_FEATURE_LEVEL_11_0,
D3D_FEATURE_LEVEL_10_1,
D3D_FEATURE_LEVEL_10_0
};
UINT numFeatureLevels = ARRAYSIZE(featureLevels);
char devname_dx[128];
bool device_ok = getAdapter(&adapter, devname_dx);
DXGI_ADAPTER_DESC adapterDesc;
adapter->GetDesc(&adapterDesc); //devid = 9436, subsysid = 177803304
std::cout << "DirectX GPU " << devname_dx << " : [BusID " << adapterDesc.DeviceId << " | DevID " << adapterDesc.SubSysId << "]" << std::endl;
// Create a device, device context and swap chain using the information in the scd struct
hr = D3D11CreateDeviceAndSwapChain(
adapter, // graphics adapter, which was already checked for CUDA support
D3D_DRIVER_TYPE_UNKNOWN, // If adapter is not NULL, we need to use UNKNOWN, otherwise use D3D_DRIVER_TYPE_HARDWARE
NULL, // software
NULL, // flags
featureLevels, // D3D features to enable
numFeatureLevels, // D3D feature count
D3D11_SDK_VERSION, // D3D SDK version (here 11)
&swapchainDesc, // swap chain description
&swapchain, // swap chain
&device, // D3D device
NULL, // supported feature level (use DXGI_ADAPTER_DESC variable to retrieve the information, e.g. &featureLevel)
&device_context); // D3D device context
if (FAILED(hr))
{
std::string msg = std::string("Failed to create DX device and swap chain: ") + std::to_string(hr);
throw std::exception(msg.c_str());
}
在释放我的适配器后
adapter->Release();
检索我的设备上下文
device->GetImmediateContext(&device_context);
我将2D纹理texture_rgb
Map为唯一的缓冲区
hr = swapchain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&texture_rgb);
由我的呈现目标视图使用
hr = device->CreateRenderTargetView(texture_rgb, nullptr, &rtv);
我想创建一个舞台2D纹理。目前,它将只用于查找一些像素数据,但稍后我会将其与CUDA集成。它反映了我的texture_rgb
的内容-尺寸,颜色格式,像素数据等。
为此,我检索texture_rgb
的描述
D3D11_TEXTURE2D_DESC texture_rgb_debugDesc;
texture_rgb->GetDesc(&texture_rgb_debugDesc);
只修改D3D11_TEXTURE2D_DESC::Usage
组件
texture_rgb_debugDesc.Usage = D3D11_USAGE::D3D11_USAGE_STAGING;
然后我尝试使用修改后的描述创建其他纹理
ID3D11Texture2D* texture_rgb_debug = nullptr;
hr = device->CreateTexture2D(&texture_rgb_debugDesc, nullptr, &texture_rgb_debug);
但是,DirectX失败,并出现以下错误:
E_INVALIDARG一个或多个参数无效。
如果我将D3D11_TEXTURE2D_DESC::Usage
更改为初始值(此处为D3D11_USAGE_DEFAULT
),则纹理将毫无问题地创建。
2条答案
按热度按时间kognpnkq1#
从交换链获得的纹理应该具有
D3D11_BIND_RENDER_TARGET
绑定标志,而使用D3D11_USAGE_STAGING
的纹理不能用作任何渲染阶段的输入或输出,因此与D3D11_BIND_RENDER_TARGET
标志不兼容。你应该覆盖纹理描述中的所有字段,除了尺寸和格式。brvekthn2#
分段纹理不能绑定在管道的任何阶段中,因此BindFlags应为0。
您还需要像以前一样设置使用情况。最后一部分,因为你想把数据读回CPU,也是为了覆盖CPU标志:
另请注意,多采样纹理不能创建为分段,因此如果您希望支持此功能,则还需要首先解析为非多采样资源,然后执行复制操作。
要与CUDA集成,您根本不需要暂存资源,您可以直接使用渲染目标进行互操作。
此外,为了捕获这些错误,您应该在创建设备时使用D3D11_CREATE_DEVICE_DEBUG标志。
这将在visual studio调试输出窗口中出现错误时给予更有意义的错误消息(相对于invalidargs,它没有太大帮助)。