Hi,
I have implemented these functions to get single pixel color:
// Get Pixel Color
ID3D11Resource* SourceResource;
ID3D11Texture2D* DestinationTexture2D;
ID3D11DeviceContext* Context = nullptr;
void CreateSourceResource(IDXGISwapChain* pSwapChain)
{
HRESULT hr = 0;
IDXGIResource* backbufferptr = nullptr;
ID3D11DeviceContext* context = nullptr;
hr = pSwapChain->GetBuffer(0, __uuidof(IDXGIResource), (void**)&backbufferptr);
if (hr < 0) {
return;
}
hr = backbufferptr->QueryInterface(__uuidof(ID3D11Resource), (void**)&SourceResource);
if (hr < 0) {
return;
}
return;
}
void CreateDestinationTexture2D(IDXGISwapChain* pSwapChain)
{
HRESULT hr = 0;
ID3D11Device* device = nullptr;
ID3D11Texture2D* DestResource = nullptr;
hr = pSwapChain->GetDevice(__uuidof(ID3D11Device), (void**)&device);
if (hr < 0) {
return;
}
D3D11_TEXTURE2D_DESC TextureDesciption = { };
TextureDesciption.Format = DXGI_FORMAT_R32_UINT;
TextureDesciption.Width = 1;
TextureDesciption.Height = 1;
TextureDesciption.MipLevels = 1;
TextureDesciption.ArraySize = 1;
TextureDesciption.SampleDesc.Count = 1;
TextureDesciption.Usage = D3D11_USAGE_STAGING;
TextureDesciption.BindFlags = 0;
TextureDesciption.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
TextureDesciption.MiscFlags = 0;
hr = device->CreateTexture2D(&TextureDesciption, nullptr, &DestinationTexture2D);
if (hr < 0) {
return;
}
device->GetImmediateContext(&Context);
if (!Context) {
return;
}
return;
}
RGBTRIPLE GetPixelDX11(int X, int Y)
{
RGBTRIPLE rgb;
HRESULT hr = 0;
D3D11_MAPPED_SUBRESOURCE MappedSubresource;
D3D11_BOX srcBox;
srcBox.left = X;
srcBox.right = X + 1;
srcBox.bottom = Y + 1;
srcBox.top = Y;
srcBox.front = 0;
srcBox.back = 1;
Context->CopySubresourceRegion(DestinationTexture2D, 0, 0, 0, 0, SourceResource, 0, &srcBox);
hr = Context->Map(DestinationTexture2D, 0, D3D11_MAP_READ, 0, &MappedSubresource);
uint32_t* pPixels = reinterpret_cast<uint32_t*>(MappedSubresource.pData);
rgb.rgbtRed = (pPixels[0] >> 16) & 0xff;
rgb.rgbtGreen = (pPixels[0] >> 8) & 0xff;
rgb.rgbtBlue = pPixels[0] & 0xff;
return rgb;
}
RGBTRIPLE GetPixelColor(int x, int y)
{
RGBTRIPLE rgb;
HDC dc = GetDC(NULL);
int RealX = round(x * 1);
int RealY = round(y * 1);
RGBTRIPLE color2 = GetPixelDX11(RealX, RealY);
COLORREF color = GetPixel(dc, RealX, RealY);
ReleaseDC(NULL, dc);
rgb.rgbtRed = GetRValue(color);
rgb.rgbtGreen = GetGValue(color);
rgb.rgbtBlue = GetBValue(color);
return rgb;
}
and when I call GetPixel (GDI+) I get the correct color but when I call GetPixelDX11 the result is always zero.
I have checked at debug that all HRESULT are "OK"
I have only a bit experience in DX11 and I'am unsure about these lines:
uint32_t* pPixels = reinterpret_cast<uint32_t*>(MappedSubresource.pData);
rgb.rgbtRed = (pPixels[0] >> 16) & 0xff;
rgb.rgbtGreen = (pPixels[0] >> 8) & 0xff;
rgb.rgbtBlue = pPixels[0] & 0xff;
and about the format:
DXGI_FORMAT_R32_UINT
because this is the initialization:
// this function initializes and prepares Direct3D for use
void InitD3D(HWND hWnd)
{
// create a struct to hold information about the swap chain
DXGI_SWAP_CHAIN_DESC scd;
// clear out the struct for use
ZeroMemory(&scd, sizeof(DXGI_SWAP_CHAIN_DESC));
// fill the swap chain description struct
scd.BufferCount = 1; // one back buffer
scd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; // use 32-bit color
scd.BufferDesc.Width = Screen_Width; // set the back buffer width
scd.BufferDesc.Height = Screen_Height; // set the back buffer height
scd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; // how swap chain is to be used
scd.OutputWindow = hWnd; // the window to be used
scd.SampleDesc.Count = 4; // how many multisamples
scd.Windowed = true; // windowed/full-screen mode
scd.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH; // allow full-screen switching
// create a device, device context and swap chain using the information in the scd struct
D3D11CreateDeviceAndSwapChain(NULL, D3D_DRIVER_TYPE_HARDWARE, NULL, NULL, NULL, NULL, D3D11_SDK_VERSION, &scd, &swapchain, &dev, NULL, &devcon);
// get the address of the back buffer
ID3D11Texture2D* pBackBuffer;
swapchain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&pBackBuffer);
// use the back buffer address to create the render target
dev->CreateRenderTargetView(pBackBuffer, NULL, &backbuffer);
pBackBuffer->Release();
// set the render target as the back buffer
devcon->OMSetRenderTargets(1, &backbuffer, NULL);
// Set the viewport
D3D11_VIEWPORT viewport;
ZeroMemory(&viewport, sizeof(D3D11_VIEWPORT));
viewport.TopLeftX = 0;
viewport.TopLeftY = 0;
viewport.Width = Screen_Width;
viewport.Height = Screen_Height;
devcon->RSSetViewports(1, &viewport);
InitPipeline();
DrawAll();
CreateDestinationTexture2D(swapchain);
CreateSourceResource(swapchain);
GetPixelColor(30, 30);
}
Can you help me please ?
Thanks !