Unable to create a DX11 render target view - directx

I'm trying to get started with DirectX 11 game programming, but for some reason I'm simply unable to create a render target view with ID3D11Device::CreateRenderTargetView().
(BTW, I use VS for Desktop 2013, and the highest feature level my GPU supports is 11_0. I'm running Windows 8.1.)
Here's the code I think is relevant:
D3D11_TEXTURE2D_DESC backBufferDesc;
ZeroMemory(&backBufferDesc, sizeof(backBufferDesc));
backBufferDesc.ArraySize = 1;
backBufferDesc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE;
backBufferDesc.CPUAccessFlags = 0;
backBufferDesc.Format = DXGI_FORMAT_R32_FLOAT;
backBufferDesc.Height = nHeight;
backBufferDesc.Width = nWidth;
backBufferDesc.MipLevels = 1;
backBufferDesc.MiscFlags = 0;
backBufferDesc.SampleDesc.Count = 1;
backBufferDesc.SampleDesc.Quality = 0;
backBufferDesc.Usage = D3D11_USAGE_DEFAULT;
ID3D11Texture2D* backBufferTexture;
result = d3dDevice_ -> CreateTexture2D(&backBufferDesc, 0, &backBufferTexture);
if (FAILED(result))
{
MessageBox(0, "Failed to create the back buffer texture!", "DirectX Error", MB_OK);
return false;
}
result = swapChain_->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&backBufferTexture);
if (FAILED(result))
{
MessageBox(0, "Failed to get the swap chain back buffer!", "DirectX Error", MB_OK);
return false;
}
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
ZeroMemory(&rtvDesc, sizeof(rtvDesc));
rtvDesc.Format = backBufferDesc.Format;
result = d3dDevice_->CreateRenderTargetView(backBufferTexture, &rtvDesc, &backBufferTarget_);
if (backBufferTexture)
backBufferTexture->Release();
if (FAILED(result))
{
MessageBox(0, "Failed to create the render target view!", "DirectX Error", MB_OK);
return false;
}

Using the Debug Device would give you a human readable error.
Based on my reading of the code you haven't filled out the ViewDimension field of rtvDesc.

Related

Desktop Duplication API returns empty frame

I am aware that there are already a few questions asking this or similar things and I dived into a few of them, but without any success.
I try to capture a "screenshot" of my display using the Desktop duplication API and process pixeldata of it. Later I would like to do that at least 30 times/second, but thats a different case.
For now, I tried the example of microsoft: https://github.com/microsoftarchive/msdn-code-gallery-microsoft/tree/master/Official%20Windows%20Platform%20Sample/DXGI%20desktop%20duplication%20sample
I successfully saved a picture of the screen and accessed the pixel data with that code.
DirectX::ScratchImage image;
hr = DirectX::CaptureTexture(m_Device, m_DeviceContext, m_AcquiredDesktopImage, image);
hr = DirectX::SaveToDDSFile(image.GetImages(), image.GetImageCount(), image.GetMetadata(), DirectX::DDS_FLAGS_NONE, L"test.dds");
uint8_t* pixels;
pixels = image.GetPixels();
Now I wanted to break the example code down to the basic stuff I need. As I am not familiar with DirectX I have a hard time doing that.
I came up with following code, which runs without error but produces an empty picture. I check hr in Debug Mode, I am aware that this is bad practice and dirty!
int main()
{
HRESULT hr = S_OK;
ID3D11Device* m_Device;
ID3D11DeviceContext* m_DeviceContext;
// Driver types supported
D3D_DRIVER_TYPE DriverTypes[] =
{
D3D_DRIVER_TYPE_HARDWARE,
D3D_DRIVER_TYPE_WARP,
D3D_DRIVER_TYPE_REFERENCE,
};
UINT NumDriverTypes = ARRAYSIZE(DriverTypes);
// Feature levels supported
D3D_FEATURE_LEVEL FeatureLevels[] =
{
D3D_FEATURE_LEVEL_11_0,
D3D_FEATURE_LEVEL_10_1,
D3D_FEATURE_LEVEL_10_0,
D3D_FEATURE_LEVEL_9_1
};
UINT NumFeatureLevels = ARRAYSIZE(FeatureLevels);
D3D_FEATURE_LEVEL FeatureLevel;
// Create device
for (UINT DriverTypeIndex = 0; DriverTypeIndex < NumDriverTypes; ++DriverTypeIndex)
{
hr = D3D11CreateDevice(nullptr, DriverTypes[DriverTypeIndex], nullptr, 0, FeatureLevels, NumFeatureLevels,
D3D11_SDK_VERSION, &m_Device, &FeatureLevel, &m_DeviceContext);
if (SUCCEEDED(hr))
{
// Device creation success, no need to loop anymore
break;
}
}
IDXGIOutputDuplication* m_DeskDupl;
IDXGIOutput1* DxgiOutput1 = nullptr;
IDXGIOutput* DxgiOutput = nullptr;
IDXGIAdapter* DxgiAdapter = nullptr;
IDXGIDevice* DxgiDevice = nullptr;
UINT Output = 0;
hr = m_Device->QueryInterface(__uuidof(IDXGIDevice), reinterpret_cast<void**>(&DxgiDevice));
hr = DxgiDevice->GetParent(__uuidof(IDXGIAdapter), reinterpret_cast<void**>(&DxgiAdapter));
DxgiDevice->Release();
DxgiDevice = nullptr;
hr = DxgiAdapter->EnumOutputs(Output, &DxgiOutput);
DxgiAdapter->Release();
DxgiAdapter = nullptr;
hr = DxgiOutput->QueryInterface(__uuidof(DxgiOutput1), reinterpret_cast<void**>(&DxgiOutput1));
DxgiOutput->Release();
DxgiOutput = nullptr;
hr = DxgiOutput1->DuplicateOutput(m_Device, &m_DeskDupl);
IDXGIResource* DesktopResource = nullptr;
DXGI_OUTDUPL_FRAME_INFO FrameInfo;
hr = m_DeskDupl->AcquireNextFrame(500, &FrameInfo, &DesktopResource);
ID3D11Texture2D* m_AcquiredDesktopImage;
hr = DesktopResource->QueryInterface(__uuidof(ID3D11Texture2D), reinterpret_cast<void**>(&m_AcquiredDesktopImage));
DesktopResource->Release();
DesktopResource = nullptr;
DirectX::ScratchImage image;
hr = DirectX::CaptureTexture(m_Device, m_DeviceContext, m_AcquiredDesktopImage, image);
hr = DirectX::SaveToDDSFile(image.GetImages(), image.GetImageCount(), image.GetMetadata(), DirectX::DDS_FLAGS_NONE, L"test.dds");
uint8_t* pixels;
pixels = image.GetPixels();
hr = m_DeskDupl->ReleaseFrame();
}
Could anyone give me a hint what is wrong with this code?
EDIT:
Just found the code snipet below and integrated it into my code.
Now it works!
Lessons learnt:
-) actully output/process hr!
-) AcquireNextFrame might not work on first try (?)
I might update this post again with better code, with functioning loop.
int lTryCount = 4;
do
{
Sleep(100);
hr = m_DeskDupl->AcquireNextFrame(250, &FrameInfo, &DesktopResource);
if (SUCCEEDED(hr))
break;
if (hr == DXGI_ERROR_WAIT_TIMEOUT)
{
continue;
}
else if (FAILED(hr))
break;
} while (--lTryCount > 0);
AcquireNextFrame is allowed to return null resource (texture) because it returns on either change in desktop image or change related to pointer.
AcquireNextFrame acquires a new desktop frame when the operating system either updates the desktop bitmap image or changes the shape or position of a hardware pointer.
When you start frame acquisition you apparently are to get first desktop image soon, but you can also have a few of pointer notifications too before the image.
You should not limit yourself with 4 attempts and you don't need to sleep within the loop. Just keep polling for the image. To avoid dead loop it makes more sense to track total time spent in the loop and limit it to, for example, one second.
See also:
AcquireNextFrame() never grabs an updated image, always blank

MFC - Printing a CBitmap to printer CDC

I am using the following code to print what is inside the clipboard (bitmap).
On the printed paper, I see the black line drawn with MoveTo/LineTo however the bitmap is not drawn.
Using the same drawing code in a CView works perfectly fine.
keybd_event(VK_SNAPSHOT, 1, 0, NULL);
HBITMAP handle = NULL;
if (::OpenClipboard(NULL))
{
handle = (HBITMAP)GetClipboardData(CF_BITMAP);
if (handle)
{
CBitmap* pBmp = CBitmap::FromHandle(handle);
BITMAP bm;
pBmp->GetBitmap(&bm);
int iBmpWidth = bm.bmWidth;
int iBmpHeight = bm.bmHeight;
CPrintDialog* pDlg = new CPrintDialog(FALSE);
CString csText;
CString cTitle;
if (pDlg->GetDefaults() == FALSE)
{
delete pDlg;
return;
}
pDlg->m_pd.Flags &= ~PD_RETURNDEFAULT;
LPDEVMODE pDevMode = pDlg->GetDevMode();
::GlobalUnlock(pDlg->m_pd.hDevMode);
DOCINFO di;
di.cbSize = sizeof(DOCINFO);
pDlg->m_pd.hwndOwner = this->GetSafeHwnd();
if (pDlg->DoModal() == IDOK)
{
HDC hdcPrinter = pDlg->GetPrinterDC();
if (hdcPrinter != NULL)
{
pDevMode = (LPDEVMODE)GlobalLock(pDlg->m_pd.hDevMode);
pDevMode->dmPaperSize = DMPAPER_A4;
pDevMode->dmOrientation = DMORIENT_LANDSCAPE;
ResetDCW(hdcPrinter, pDevMode);
GlobalUnlock(pDlg->m_pd.hDevMode);
// create a CDC and attach it to the default printer
CDC dcPrinter;
dcPrinter.Attach(hdcPrinter);
// call StartDoc() to begin printing
DOCINFO docinfo;
memset(&docinfo, 0, sizeof(docinfo));
docinfo.cbSize = sizeof(docinfo);
docinfo.lpszDocName = _T("CDC::StartDoc() Code Fragment");
// if it fails, complain and exit gracefully
if (dcPrinter.StartDoc(&docinfo) < 0)
{
MessageBox(_T("Printer wouldn't initalize"));
}
else
{
// start a page
if (dcPrinter.StartPage() < 0)
{
MessageBox(_T("Could not start page"));
dcPrinter.AbortDoc();
}
else
{
int PaperWidth = dcPrinter.GetDeviceCaps(HORZRES);
int PaperHeight = dcPrinter.GetDeviceCaps(VERTRES);
CDC memDC;
memDC.CreateCompatibleDC(&dcPrinter);
CBitmap* pOldBit = memDC.SelectObject(pBmp);
dcPrinter.MoveTo(1000, 1000);
dcPrinter.LineTo(PaperWidth - 1000, PaperHeight - 1000);
dcPrinter.StretchBlt(100,
100,
PaperWidth - 100,
PaperHeight - 100,
&memDC,
0,
0,
iBmpWidth,
iBmpHeight,
SRCCOPY);
memDC.SelectObject(pOldBit);
memDC.DeleteDC();
dcPrinter.EndPage();
dcPrinter.EndDoc();
}
}
}
}
delete pDlg;
}
::EmptyClipboard();
::CloseClipboard();
}
Using your code without any changes works for me, I tested using a real printer and CutePDF, both printed the bitmap. It might be an issue with your source DC when you create memDC, either it does not support the correct color space or does not support raster operations. Try the following code instead:
CDC* pDC = GetDesktopWindow()->GetDC();
memDC.CreateCompatibleDC(pDC);
GetDesktopWindow()->ReleaseDC(pDC);

DirectX 12 device suspended immediately after creation

I am getting a strange error when creating the DirectX 12 command queue.
Other DX12 applications are able to launch successfully on the same machine.
My computer uses the D3D_FEATURE_LEVEL_11_0 if block.
The graphics card used for testing is NVIDIA GT 740, with 361.75 drivers
This is the code in use (minimized):
#include <Windows.h>
#include <d3d12.h>
#include <dxgi1_4.h>
#include <comdef.h>
#include <D3d12sdklayers.h>
#include <string>
#pragma comment(lib,"d3d12.lib")
#pragma comment(lib,"dxgi.lib")
#pragma comment(lib,"d3dcompiler.lib")
using namespace std;
LRESULT WINAPI WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) {
switch (msg)
{
case WM_DESTROY:
PostQuitMessage(0);
return 0;
default:
return DefWindowProc(hwnd, msg, wParam, lParam);
}
}
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
LPTSTR lpCmdLine, int nCmdShow) {
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(nCmdShow);
UNREFERENCED_PARAMETER(lpCmdLine);
wchar_t* WindowClass = L"Papergate";
WNDCLASSEX wc;
ZeroMemory(&wc, sizeof(WNDCLASSEX));
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.hInstance = hInstance;
wc.hbrBackground = (HBRUSH)(COLOR_WINDOW + 2);
wc.lpszClassName = WindowClass;
if (!RegisterClassEx(&wc))
{
return 1;
}
HWND hwnd = CreateWindowEx(NULL, wc.lpszClassName, WindowClass,
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT,
CW_USEDEFAULT, CW_USEDEFAULT,
NULL, NULL, hInstance, NULL);
if (!hwnd)
{
UnregisterClass(WindowClass, hInstance);
return 1;
}
ShowWindow(hwnd, SW_SHOWDEFAULT);
UpdateWindow(hwnd);
ID3D12Device* device;
HRESULT result = D3D12CreateDevice(NULL, D3D_FEATURE_LEVEL_12_1,
__uuidof(ID3D12Device), (void**)&device);
if (FAILED(result))
{
result = D3D12CreateDevice(NULL, D3D_FEATURE_LEVEL_12_0,
__uuidof(ID3D12Device), (void**)&device);
if (FAILED(result))
{
result = D3D12CreateDevice(NULL, D3D_FEATURE_LEVEL_11_0,
__uuidof(ID3D12Device), (void**)&device);
if (FAILED(result)) {
_com_error error(result);
MessageBox(hwnd, error.ErrorMessage(),
(wstring(L"Error: ") + to_wstring(__LINE__)).c_str(),
MB_OK);
return 2;
}
}
}
ID3D12Debug* debugInterface;
if (SUCCEEDED(D3D12GetDebugInterface(IID_PPV_ARGS(&debugInterface))))
{
debugInterface->EnableDebugLayer();
}
D3D12_COMMAND_QUEUE_DESC commandQueueDesc;
commandQueueDesc.Flags = D3D12_COMMAND_QUEUE_FLAG_NONE;
commandQueueDesc.NodeMask = 0;
commandQueueDesc.Priority = D3D12_COMMAND_QUEUE_PRIORITY_NORMAL;
commandQueueDesc.Type = D3D12_COMMAND_LIST_TYPE_DIRECT;
ID3D12CommandQueue* commandQueue;
result = device->CreateCommandQueue(&commandQueueDesc, __uuidof(ID3D12CommandQueue), (void**)&commandQueue);
if (FAILED(result)) {
_com_error error(result);
MessageBox(hwnd, error.ErrorMessage(),
(wstring(L"Error: ") + to_wstring(__LINE__)).c_str(), MB_OK);
result = device->GetDeviceRemovedReason();
error = _com_error(result);
MessageBox(hwnd, error.ErrorMessage(),
(wstring(L"Error: ") + to_wstring(__LINE__)).c_str(), MB_OK);
debugInterface->Release(); device->Release(); return 2;
}
MSG msg;
ZeroMemory(&msg, sizeof(MSG));
while (GetMessage(&msg, NULL, 0, 0) && msg.message != WM_QUIT)
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
commandQueue->Release();
device->Release();
UnregisterClass(WindowClass, hInstance);
return 0;
}
I am getting the following errors on lines 97 and 102, respectively:
The GPU device instance has been suspended. Use GetDeviceRemovedReason to determine the appropriate action.
Second error:
The GPU will not respond to more commands, most likely because some other application submitted invalid commands.
The calling application should re-create the device and continue.
This seems quite likely to be a driver bug of some kind. Check to see if there are updated drivers for your hardware. You should try using the Direct3D12 Game templates in this VSIX and see if they hit the same kind of issue (for more details on the templates see this blog post).
Your cascade pattern of calling D3D12CreateDevice for various feature levels is unusual and is not necessary. If your application can run on Direct3D Feature Level 11.0 or greater, then just use D3D_FEATURE_LEVEL_11_0 once. You should pass whatever your minimum supported feature level is to this function.
If the Direct3D 12 device does support a higher feature level, you can discover that by using CheckFeatureSupport either by checking for the individual features or by using D3D12_FEATURE_FEATURE_LEVELS:
// Create the DX12 API device object.
DX::ThrowIfFailed(D3D12CreateDevice(
adapter.Get(),
m_d3dMinFeatureLevel,
IID_PPV_ARGS(&m_d3dDevice)
));
// Determine maximum supported feature level for this device
static const D3D_FEATURE_LEVEL s_featureLevels[] =
{
D3D_FEATURE_LEVEL_12_1,
D3D_FEATURE_LEVEL_12_0,
D3D_FEATURE_LEVEL_11_1,
D3D_FEATURE_LEVEL_11_0,
};
D3D12_FEATURE_DATA_FEATURE_LEVELS featLevels =
{
_countof(s_featureLevels), s_featureLevels, D3D_FEATURE_LEVEL_11_0
};
HRESULT hr = m_d3dDevice->CheckFeatureSupport(D3D12_FEATURE_FEATURE_LEVELS,
&featLevels, sizeof(featLevels));
if (SUCCEEDED(hr))
{
m_d3dFeatureLevel = featLevels.MaxSupportedFeatureLevel;
}
else
{
m_d3dFeatureLevel = m_d3dMinFeatureLevel;
}
Keep in mind that D3D_FEATURE_LEVEL_12_0 and D3D_FEATURE_LEVEL_12_1 are essentially just D3D_FEATURE_LEVEL_11_1 with a few optional features made mandatory. If your app is already checking for them at 11.x then there's no reason to 'require' 12.0 or 12.1. See MSDN.
For the vast majority of Direct3D 12 games & applications, D3D_FEATURE_LEVEL_11_0 or D3D_FEATURE_LEVEL_11_1 are good choices. Keep in mind that while AMD/ATI supported Feature Level 11.1 pretty early, NVIDIA DirectX 11 parts only supported 11.0 with some optional features for some time.

Directx Window keeps Crashing

My problem with this code is that when I run it in visual C++ A window pops up
but then it just crashes. It is not responding and I cannot click exit. I have to pull up the
task manager to get rid of the window. I am new to windows programming and direct X.
Below I will post were I think the problem is.
#include <d3d9.h>
#include <time.h>
#define APPTITLE "Direct3D_Windowed"
LRESULT WINAPI WinProc(HWND, UINT, WPARAM, LPARAM);
ATOM MyRegisterClass(HINSTANCE);
int Game_Init(HWND);
void GAME_RUN(HWND);
void GAME_END(HWND);
LPDIRECT3D9 d3d = NULL;
LPDIRECT3DDEVICE9 d3ddev = NULL;
// Over here, after GAME_END() is called, I tried separating the POSTQUITMESSAGE But I
I just got an error.
LRESULT WINAPI WinProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg )
{
case WM_DESTROY:
GAME_END(hWnd);
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hWnd, msg, wParam, lParam);
}
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = (WNDPROC)WinProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = NULL;
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = APPTITLE;
wc.hIconSm = NULL;
return RegisterClassEx(&wc);
}
// I got this code from a book that I am reading and realized that WinProc is not being
called in this function. Is this the potential problem? Were would I put the WinProc
function call if it is supposed to be here in WinMain
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
MSG msg = {0};
MyRegisterClass(hInstance);
HWND hWnd;
hWnd = CreateWindow(
APPTITLE,
APPTITLE,
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
500,
400,
NULL,
NULL,
hInstance,
NULL);
if(!hWnd)
return FALSE;
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
if(!Game_Init(hWnd))
return 0;
int done = 0;
while(!done)
{
if(msg.message == WM_QUIT)
{
if(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{
MessageBox(hWnd, "Recieve WM_QUIT message", "WinMain", MB_OK);
done = 1;
}
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else
GAME_RUN(hWnd);
}
return msg.wParam;
}
int Game_Init(HWND hWnd)
{
MessageBox(hWnd, "Program is about to start", "Game_Init", MB_OK);
d3d = Direct3DCreate9(D3D_SDK_VERSION);
if(d3d == NULL)
{
MessageBox(hWnd, "Error initializing Direct3D", "Error", MB_OK);
return 0;
}
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory(&d3dpp, sizeof(d3dpp));
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
d3d->CreateDevice(
D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL,
hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp,
&d3ddev);
if(d3ddev == NULL)
{
MessageBox(hWnd, "Error creating Direct device", "Error", MB_OK);
return 0;
}
srand(time(NULL));
return 1;
}
void GAME_RUN(HWND hWnd)
{
if(d3ddev == NULL)
return;
d3ddev->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 255, 255), 1.0f, 0);
if(d3ddev->BeginScene())
{
d3ddev->EndScene();
}
d3ddev->Present(NULL, NULL, NULL, NULL);
}
void GAME_END(HWND hWnd)
{
MessageBox(hWnd, "Program is about to end", "Game End", MB_OK);
if(d3ddev != NULL)
d3ddev->Release();
if(d3d != NULL)
d3d->Release();
}
Have a look at this?
if(msg.message == WM_QUIT)
In your while-loop.
Perhaps change that to, say:
if(true)
Reason: you want your application to pass on all messages, not just the ones that cause it to quit. Say for instance when windows wants your application to draw itself. Basically, your current code doenst allow your application to do anything except quitting.
If you want to do something special when the application quits, add another case WM_QUIT: after the already existing case WM_DESTROY: in WinProc().
The current location for GAME_RUN(hWnd); will not work out for you.
You want to either put that in a seperate thread (easiest, and highest performance). Or you want to use some timers, and handle it with case WM_TIMER: after your case WM_DESTROY:. Or alternatively make up your own user defined message.

how to get Dc from directx3d?

I need to get Device Context (DC ) from directx3d. Here some code snap.
1.CREATE DEVICE:
int windowWidth = 640;
int windowHeight = 480;
IDirect3D9* direct3D9 = Direct3DCreate9(D3D_SDK_VERSION);
if(direct3D9 == NULL)
{
return FALSE;
}
D3DDISPLAYMODE *d3ddisplayMode =(D3DDISPLAYMODE *)calloc(1,sizeof(D3DDISPLAYMODE));
hr = direct3D9->GetAdapterDisplayMode(D3DADAPTER_DEFAULT,d3ddisplayMode);
if(hr != D3D_OK)
{
free(d3ddisplayMode);
direct3D9->Release();
return FALSE;
}
D3DPRESENT_PARAMETERS *d3dpresentParam =(D3DPRESENT_PARAMETERS*)calloc(1,sizeof(D3DPRESENT_PARAMETERS));
d3dpresentParam->Windowed = TRUE;
d3dpresentParam->hDeviceWindow = NULL;
d3dpresentParam->SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpresentParam->BackBufferFormat = d3ddisplayMode->Format;
d3dpresentParam->BackBufferWidth = windowWidth;
d3dpresentParam->BackBufferHeight = windowHeight;
d3dpresentParam->BackBufferCount = 1;
free(d3ddisplayMode);
hr = direct3D9->CreateDevice(D3DADAPTER_DEFAULT,D3DDEVTYPE_HAL,NULL,D3DCREATE_SOFTWARE_VERTEXPROCESSING,d3dpresentParam,&direct3D9Device);
2.CRETAE TEXTURE:
hr = D3DXCreateTexture(direct3D9Device,bmpWidth,bmpHeight,1,0,D3DFMT_X8R8G8B8,D3DPOOL_MANAGED,&pTexture);
3.DISPLAY IMAGE:
float left = 0,top =0,width =640,height=480;
direct3D9Device->BeginScene();
D3DXMATRIX mat;
D3DXVECTOR3 pos;
pos.x = (bmpWidth * left) / width;
pos.y = (bmpHeight * top) / height;
pos.z = 0;
d3dxSprite->Begin(D3DXSPRITE_ALPHABLEND);
D3DXVECTOR2 scaling((width/bmpWidth),(height/bmpHeight));
if(pTexture == direct3DTextureRemote )
{
D3DXVECTOR2 spriteCentre((width/2),(height/2));
D3DXMatrixTransformation2D(&mat,NULL,0.0,&scaling,&spriteCentre,NULL,NULL);
}
else
{
D3DXMatrixTransformation2D(&mat,NULL,0.0,&scaling,NULL,NULL,NULL);
}
d3dxSprite->SetTransform(&mat);
d3dxSprite->Draw(pTexture,NULL,NULL,&pos,0xFFFFFFFF);
d3dxSprite->End();
direct3D9Device->EndScene();
direct3D9Device->Present( NULL, NULL, NULL, NULL );
Now Working probely. I can get dc from window like HDC hdc = ::GetDC(hwnd) but in my case if there is no window(i.e. windowless) then how can i get DC from directx. please give some piece of code get DC from directx device.
Call GetDC with null as argument:
HDC hdc = ::GetDC(0);
Quote from MSDN:
Parameters
hWnd [in]
A handle to the window whose DC is to be retrieved.
If this value is NULL, GetDC retrieves the DC for the entire screen.
Edit:
As we know now that you are using NPAPI, here is a possible solution:
Call NPAPI function NPN_GetValue() with NPNVnetscapeWindow parameter. Returned HWND is a handle to plug-in drawing surface. Use it when create DirectX device and to retrieve HDC.
Alternatively, you could try to retrieve the back buffer (IDirect3DSurface9) via IDirect3DDevice9::GetRenderTarget() method and then retrieve its HDC via IDirect3DSurface9::GetDC() method.

Resources