GDI 中位块传送如何工作?

Mar*_*rko 3 c++ mfc gdi

我对位块传输在 gdi 中的工作原理感兴趣。我知道它会根据 dwROP 参数创建基于源位图和目标位图的结果位图,但我感兴趣的是如何实现的?我看到一些示例,其中它用于使用单色蒙版和 SetBkColor() 函数完成的蒙版,我真的很困惑 BkColor 与这些位图有何关系......而在另一个示例中,使用 SetTextColor() ,用于删除背景...这些 DC 属性(bkColor 和 textColor)如何相关?谢谢

xMR*_*MRi 5

你错了 BitBlt 从不使用文本作为背景颜色。BitBlt 光栅操作使用图案(即当前选定的画笔)、源位图和目标位图。

dwRop 代码定义了这 3 个数据源之间的计算。

您可以在 Charles Petzold 的书中找到这个 rop 代码如何工作的很好的解释。这是本书的相应章节。阅读“光栅操作”部分。


Han*_*ant 5

背景和文本颜色不起作用,只有在目标设备上下文中选择的当前画笔起作用。

BitBlt() 迭代源矩形中的像素,并在对像素数据应用数学运算后复制像素。dwRop 值决定该操作。通过运算组合三个像素值来计算目标位图的像素值:

  • 来自源位图的像素。ROP代码标识符包含“SRC”。
  • 画笔的像素。ROP 代码标识符包含“PAT”(如果使用)。
  • 在写入之前来自目标位图的像素,如果使用,您将看到“DST”。

应用于像素值的数学运算非常简单。他们可以

  • 无,dwROP = SRCCOPY 或 PATCOPY。
  • 始终设置为 0,dwROP = BLACKNESS
  • 始终设置为 1,dwROP = 白度
  • NOT 运算符,与 C 程序中的 ~ 相同
  • AND 运算符,与 C 程序中的 & 相同
  • OR 运算符,与 | 相同 在 C 程序中
  • XOR 运算符,与 C 程序中的 ^ 相同

这些操作非常简单,因为这是处理器可以轻松完成的操作。而且它们很容易在硬件中加速。要记住的最重要的事情是它们是运算符,该运算应用于像素值中的每个单独的位。这使得 ROP 成为历史文物,它们仅在单色位图(1 像素 = 1 位)或索引位图格式(如 4bpp 或 8bpp)以及精心选择的调色板上产生有用的结果。这对于 20 世纪 80 年代的机器来说很重要。

您现在使用的视频适配器类型以及位图格式至少为 16bpp,几乎总是 24bpp 或 32bpp。对此类位图的像素执行诸如“NOT”之类的操作只会产生一种截然不同的颜色,人眼无法将其识别为与原始颜色有任何关系。今天您只使用SRCCOPY。也许 PATCOPY 来应用纹理画笔,您可以使用 PatBlt() 代替。有使用多个 BitBlt 来创建透明效果的 hackorama,您可以使用 TransBlt() 或 GDI+ 来代替。