如何正确捕获 Aero/DWM 上的特定窗口
背景资料: 我编写了这个 MFC 应用程序并使用了很长时间,当用户按下 Print Screen/Alt+Print Screen 键时,它几乎会自动将屏幕截图保存到硬盘。 我一直推迟使用任何与 Aero 相关的东西,直到现在我已经使用 Windows 7 RC 几个星期了。
问题: 我使用标准 GetDC/BitBlt 方法来捕获窗口内容。 在进行常规全屏抓取时(无论打开多少个窗口等),我对这种方法没有任何问题。 当我尝试捕获前景窗口(Alt+PrintScreen)时出现问题。 下面是两个示例:
示例 1 http://indiecodelabs.com/extern/example1.jpg
示例 2 http://indiecodelabs.com/extern/example2.jpg
如您所见,我'我在应该有边界的地方发现了垃圾。 这在顶部更加明显,我们可以在两个屏幕截图中看到工具栏的一些重复。
我已经在谷歌上搜索了几个小时,我能找到的都是文章说在 DWM 下 BitBtl/GetDC 方法不起作用,但找不到一篇文章解释我们(开发人员)应该做什么在 DWM 上运行时能够在我们的应用程序中保持相同的功能。
任何帮助、指点、建议将不胜感激。
Background info:
I have this MFC application I coded and been using for a long time that pretty much automatically saves screenshots to the hard disk when the user hits the Print Screen/Alt+Print Screen key. I have been putting off using anything related to Aero until now that I've been using Windows 7 RC for a couple of weeks.
The problem:
I'm using the standard GetDC/BitBlt method to capture the window contents. I have no problems with this method while doing regular full-screen grabs (no matter how many windows are opened etc). The problem arises when I try capturing the foreground window (Alt+PrintScreen). Here are two examples:
Example 1
http://indiecodelabs.com/extern/example1.jpg
Example 2
http://indiecodelabs.com/extern/example2.jpg
As you can see, I'm getting garbage where the borders should be. This is more noticeable towards the top, where we can see some duplication of the toolbar in both screenshots.
I've been googling about this for hours now and all I can find are articles saying that under DWM the BitBtl/GetDC method won't work, but can't find a single one explaining what we (the developers) should do to be able to maintain the same functionality in our apps when running on DWM.
Any help, pointers, suggestions will be greatly appreciated.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
供参考:DumpImage 几乎使用 Gdi::Bitmap 的 Save 方法。 它已被省略,因为它具有一些与示例无关的特定于应用程序的代码。 另外一个额外的好处是,如果您想知道如何将光标包含在屏幕截图中,那么代码也在那里。 希望能帮助到你。 另外值得一提的是,与传统方法相反,这还将包括捕获窗口顶部可能有的任何重叠窗口。 另外,如果您使用此代码进行全屏捕获,请注意它不会捕获视频游戏窗口。 我实际上想知道如何正确地做到这一点,而不必求助于 DirectX。 这仅影响在 Aero 模式下运行的 Windows Vista/7。
For reference: DumpImage pretty much uses the Gdi::Bitmap's Save method. It has been omitted because it has some app-specific code that isn't relevant to the example. Also an added bonus is that if you were wondering how to include the cursor in your screengrab then the code is also there. Hope it helps. Also worth mentioning, contrary to the traditional approach, this will also include any overlaid windows you might have on top of the captured window. Also, if you use this code for full screen captures, be warned that it will not capture video game windows. I'm actually wondering how to do that properly without having to resort to DirectX. This only affects Windows Vista/7 when running in Aero mode.
这是一个很好的问题,不幸的是我不知道确切的答案。 我的第一个想法是抓取整个桌面并从中删除有趣的部分。
我深入研究了 QT 4.5 源代码,看看他们是如何做到这一点的,并发现了类似的东西。 如果您将 GetClientRect 切换到 GetWindowRect 并剥离 QT 样板代码,您应该会得到您想要的。 不过它看起来像是一个黑客:)
It's an excellent question that I unfortuneatly don't know exact answer to. My first idea was to grab the whole desktop and cut interesting part out of it.
I've dug into QT 4.5 sources to see how they do it, and found something like this. If you switch GetClientRect to GetWindowRect and strip QT boilerplate code you should get what you want. It looks like a hack though :)