PrintWindow()无法打印Google Chrome窗口(Chrome_WidgetWin_1)

时间:2015-06-21 14:02:06

标签: c windows google-chrome winapi window

我使用的是Microsoft Visual Studio 2010和Windows 7 Professional。 这是我将窗口图像复制到剪贴板的代码:

void PrintWindowEx( HWND hWnd )
{
    HDC hDCMem = CreateCompatibleDC(NULL);
    RECT rect;

    GetWindowRect(hWnd, &rect);

    HBITMAP hBmp = NULL;

    HDC hDC = GetDC(hWnd);

    hBmp = CreateCompatibleBitmap(hDC, rect.right - rect.left, rect.bottom - rect.top);

    HGDIOBJ hOld = SelectObject(hDCMem, hBmp);
    PrintWindow(hWnd, hDCMem, 0);

    SelectObject(hDCMem, hOld);
    DeleteObject(hDCMem);

    OpenClipboard(hWnd);

    EmptyClipboard(); 
    SetClipboardData(CF_BITMAP, hBmp);
    CloseClipboard();

    ReleaseDC(hWnd, hDC);
}

除谷歌Chrome主窗口外,它适用于所有窗口。我认为这是因为Chrome使用直接渲染,所以我在chrome://settings中禁用了硬件加速。仍然无法正常工作。然后我意识到由于Chrome Sandbox中的限制,处理邮件可能会受到限制,因此我使用--no-sandbox命令行选项启动了Chrome。仍然无效。

我怎样才能让它发挥作用?适用于Chrome和Chrome等任何其他窗口。 BitBlt()是不可接受的,因为窗口的某些部分窗口可能会被另一个窗口重叠,窗口可以放在其他桌面上等等。有没有可行的解决方案?也许将DLL加载到另一个进程或类似的东西。

UPD :它会在RedrawWindow()后重绘;所以我可以截取屏幕截图(部分 - 左侧部分(宽度~20px),右侧部分不复制)。那么,它是否支持WM_PRINT?如何获取窗口的完整屏幕截图?

2 个答案:

答案 0 :(得分:12)

我被困多年了,然后发现我可以将PW_RENDERFULLCONTENT参数作为PrintWindow的最后一个参数传递。谷歌搜索显示它是Windows 8.1中的新功能所以可能不适用于7.虽然可能值得尝试,但Winuser.h将其定义为

#if(_WIN32_WINNT >= 0x0603)
#define PW_RENDERFULLCONTENT    0x00000002
#endif /* _WIN32_WINNT >= 0x0603 */

答案 1 :(得分:3)

PrintWindow的工作原理是向目标窗口发送WM_PRINTWM_PRINTCLIENT。虽然DefWindowProc处理标准窗口类的WM_PRINT,但自定义窗口类必须处理WM_PRINT,以便PrintWindow生成所需的结果。如果Chrome无法处理WM_PRINTWM_PRINTCLIENT,那么您无能为力。

在定位Windows Vista及更高版本时,您可以使用DWM Thumbnail API强制窗口将其内容呈现到客户端提供的目标窗口中。