static image::Image * getRenderTargetImage(IDirect3DDevice9 *pDevice, IDirect3DSurface9 *pRenderTarget) { image::Image *image = NULL; D3DSURFACE_DESC Desc; IDirect3DSurface9 *pStagingSurface = NULL; HRESULT hr; if (!pRenderTarget) { return NULL; } hr = pRenderTarget->GetDesc(&Desc); assert(SUCCEEDED(hr)); hr = pDevice->CreateOffscreenPlainSurface(Desc.Width, Desc.Height, Desc.Format, D3DPOOL_SYSTEMMEM, &pStagingSurface, NULL); if (FAILED(hr)) { goto no_staging; } hr = pDevice->GetRenderTargetData(pRenderTarget, pStagingSurface); if (FAILED(hr)) { goto no_rendertargetdata; } image = getSurfaceImage(pDevice, pStagingSurface); no_rendertargetdata: pStagingSurface->Release(); no_staging: return image; }
static image::Image * getRenderTargetImage(IDirect3DDevice8 *pDevice, IDirect3DSurface8 *pRenderTarget) { HRESULT hr; if (!pRenderTarget) { return NULL; } D3DSURFACE_DESC Desc; hr = pRenderTarget->GetDesc(&Desc); assert(SUCCEEDED(hr)); com_ptr<IDirect3DSurface8> pStagingSurface; hr = pDevice->CreateImageSurface(Desc.Width, Desc.Height, Desc.Format, &pStagingSurface); if (FAILED(hr)) { return NULL; } hr = pDevice->CopyRects(pRenderTarget, NULL, 0, pStagingSurface, NULL); if (FAILED(hr)) { std::cerr << "warning: GetRenderTargetData failed\n"; return NULL; } return getSurfaceImage(pDevice, pStagingSurface); }
void dumpFramebuffer(JSONWriter &json, IDirect3DDevice7 *pDevice) { HRESULT hr; json.beginMember("framebuffer"); json.beginObject(); com_ptr<IDirectDrawSurface7> pRenderTarget; hr = pDevice->GetRenderTarget(&pRenderTarget); if (SUCCEEDED(hr) && pRenderTarget) { image::Image *image; image = getSurfaceImage(pDevice, pRenderTarget); if (image) { json.beginMember("RENDER_TARGET_0"); json.writeImage(image); json.endMember(); // RENDER_TARGET_* } // Search for a depth-stencil attachment DDSCAPS2 ddsCaps; ZeroMemory(&ddsCaps, sizeof ddsCaps); ddsCaps.dwCaps = DDSCAPS_ZBUFFER; com_ptr<IDirectDrawSurface7> pDepthStencil; hr = pRenderTarget->GetAttachedSurface(&ddsCaps, &pDepthStencil); if (SUCCEEDED(hr) && pDepthStencil) { std::cerr << "found ZS!!\n"; image = getSurfaceImage(pDevice, pDepthStencil); if (image) { json.beginMember("DEPTH_STENCIL"); json.writeImage(image); json.endMember(); // DEPTH_STENCIL } } } json.endObject(); json.endMember(); // framebuffer }
image::Image * getRenderTargetImage(IDirect3DDevice7 *pDevice) { HRESULT hr; com_ptr<IDirectDrawSurface7> pRenderTarget; hr = pDevice->GetRenderTarget(&pRenderTarget); if (FAILED(hr)) { return NULL; } assert(pRenderTarget); return getSurfaceImage(pDevice, pRenderTarget); }
void dumpFramebuffer(JSONWriter &json, IDirect3DDevice9 *pDevice) { HRESULT hr; json.beginMember("framebuffer"); json.beginObject(); D3DCAPS9 Caps; pDevice->GetDeviceCaps(&Caps); for (UINT i = 0; i < Caps.NumSimultaneousRTs; ++i) { IDirect3DSurface9 *pRenderTarget = NULL; hr = pDevice->GetRenderTarget(i, &pRenderTarget); if (FAILED(hr)) { continue; } if (!pRenderTarget) { continue; } image::Image *image; image = getRenderTargetImage(pDevice, pRenderTarget); if (image) { char label[64]; _snprintf(label, sizeof label, "RENDER_TARGET_%u", i); json.beginMember(label); json.writeImage(image, "UNKNOWN"); json.endMember(); // RENDER_TARGET_* } pRenderTarget->Release(); } IDirect3DSurface9 *pDepthStencil = NULL; hr = pDevice->GetDepthStencilSurface(&pDepthStencil); if (SUCCEEDED(hr) && pDepthStencil) { image::Image *image; image = getSurfaceImage(pDevice, pDepthStencil); if (image) { json.beginMember("DEPTH_STENCIL"); json.writeImage(image, "UNKNOWN"); json.endMember(); // RENDER_TARGET_* } } json.endObject(); json.endMember(); // framebuffer }
static image::Image * getTextureImage(IDirect3DDevice8 *pDevice, IDirect3DBaseTexture8 *pTexture, D3DCUBEMAP_FACES FaceType, UINT Level) { HRESULT hr; if (!pTexture) { return NULL; } com_ptr<IDirect3DSurface8> pSurface; D3DRESOURCETYPE Type = pTexture->GetType(); switch (Type) { case D3DRTYPE_TEXTURE: assert(FaceType == D3DCUBEMAP_FACE_POSITIVE_X); hr = reinterpret_cast<IDirect3DTexture8 *>(pTexture)->GetSurfaceLevel(Level, &pSurface); break; case D3DRTYPE_CUBETEXTURE: hr = reinterpret_cast<IDirect3DCubeTexture8 *>(pTexture)->GetCubeMapSurface(FaceType, Level, &pSurface); break; default: /* TODO: support volume textures */ return NULL; } if (FAILED(hr) || !pSurface) { return NULL; } D3DSURFACE_DESC Desc; hr = pSurface->GetDesc(&Desc); assert(SUCCEEDED(hr)); if (Desc.Pool != D3DPOOL_DEFAULT || Desc.Usage & D3DUSAGE_DYNAMIC) { // Lockable texture return getSurfaceImage(pDevice, pSurface); } else if (Desc.Usage & D3DUSAGE_RENDERTARGET) { // Rendertarget texture return getRenderTargetImage(pDevice, pSurface); } else { // D3D constraints are such there is not much else that can be done. return NULL; } }
void dumpFramebuffer(StateWriter &writer, IDirect3DDevice8 *pDevice) { HRESULT hr; writer.beginMember("framebuffer"); writer.beginObject(); com_ptr<IDirect3DSurface8> pRenderTarget; hr = pDevice->GetRenderTarget(&pRenderTarget); if (SUCCEEDED(hr) && pRenderTarget) { image::Image *image; image = getRenderTargetImage(pDevice, pRenderTarget); if (image) { writer.beginMember("RENDER_TARGET_0"); writer.writeImage(image); writer.endMember(); // RENDER_TARGET_* delete image; } } com_ptr<IDirect3DSurface8> pDepthStencil; hr = pDevice->GetDepthStencilSurface(&pDepthStencil); if (SUCCEEDED(hr) && pDepthStencil) { image::Image *image; image = getSurfaceImage(pDevice, pDepthStencil); if (image) { writer.beginMember("DEPTH_STENCIL"); writer.writeImage(image); writer.endMember(); // RENDER_TARGET_* delete image; } } writer.endObject(); writer.endMember(); // framebuffer }