我正在尝试在C ++中创建一个简单的代码来制作屏幕截图并获取像素缓冲区(RGB)。 我正在使用DirectX但是我遇到了分段错误。我遵循了一些我发现的代码,但没有。
这是我的代码:
static void* pBits;
static IDirect3DDevice9* g_pd3dDevice;
void Screenshot::dxCaptureScreen() {
IDirect3DSurface9* pSurface;
g_pd3dDevice->CreateOffscreenPlainSurface(_screenWidth, _screenHeight, D3DFMT_A8R8G8B8, D3DPOOL_SCRATCH, &pSurface, NULL); //Segfault here.
g_pd3dDevice->GetFrontBufferData(0, pSurface);
D3DLOCKED_RECT lockedRect;
pSurface->LockRect(&lockedRect, NULL, D3DLOCK_NO_DIRTY_UPDATE | D3DLOCK_NOSYSLOCK | D3DLOCK_READONLY);
for (int i = 0; i < _screenHeight; i++) {
memcpy((BYTE*)pBits + i * _screenWidth * 32 / 8, (BYTE*) lockedRect.pBits + i * lockedRect.Pitch, _screenWidth * 32 / 8);
}
pSurface->UnlockRect();
pSurface->Release();
}
有人能帮助我吗?
答案 0 :(得分:0)
如果你有一个QQuickWindow及其句柄,并且想要捕获该窗口中可见的内容,你可以这样做:
QQuickWindow* window = qobject_cast<QQuickWindow*>(mYourWindowHandle);
QPixmap screenshot = window->grabWindow();
答案 1 :(得分:0)
我解决了如何使用DirectX截屏的问题,这是我的代码:
int Screenshot::dxCaptureScreen() {
int ret = 0;
IDirect3DDevice9 *g_pd3dDevice;
D3DPRESENT_PARAMETERS d3dpp;
IDirect3D9 *g_pD3D = NULL;
IDirect3DSurface9 *pSurface;
D3DLOCKED_RECT lockedRect;
g_pD3D = Direct3DCreate9(D3D_SDK_VERSION);
if (g_pD3D == NULL)
return 0;
ZeroMemory(&d3dpp, sizeof(d3dpp));
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_COPY;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
d3dpp.BackBufferCount = 1;
d3dpp.MultiSampleType = D3DMULTISAMPLE_NONE;
d3dpp.MultiSampleQuality = 0;
d3dpp.EnableAutoDepthStencil = TRUE;
d3dpp.AutoDepthStencilFormat = D3DFMT_D16;
d3dpp.hDeviceWindow = hDesktopWnd;
d3dpp.Flags = D3DPRESENTFLAG_LOCKABLE_BACKBUFFER;
d3dpp.FullScreen_RefreshRateInHz = D3DPRESENT_RATE_DEFAULT;
d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_DEFAULT;
if ((ret = g_pD3D->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hDesktopWnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp, &g_pd3dDevice)) != D3D_OK)
return ret;
if ((ret = g_pd3dDevice->CreateOffscreenPlainSurface(_screenWidth, _screenHeight, D3DFMT_A8R8G8B8, D3DPOOL_SCRATCH, &pSurface, NULL)) != D3D_OK)
return ret;
if ((ret = g_pd3dDevice->GetFrontBufferData(0, pSurface)) != D3D_OK)
return ret;
pSurface->LockRect(&lockedRect, NULL, D3DLOCK_NO_DIRTY_UPDATE | D3DLOCK_NOSYSLOCK | D3DLOCK_READONLY);
for (int i = 0; i < _screenHeight; i++) {
memcpy(pPixels + i * _screenWidth * 32 / 8, (BYTE*) lockedRect.pBits + i * lockedRect.Pitch, _screenWidth * 32 / 8);
}
我注意到它不是很快......使用GDI Windows需要的时间更少。