gpt4 book ai didi

Delphi TBitmap - 为什么 Pixels 和 ScanLine 不同?

转载 作者:行者123 更新时间:2023-12-03 15:19:05 26 4
gpt4 key购买 nike

在使用 32 位 TBitmap 时,我从 Canvas.Pixels 切换到 ScanLine。

然后我将值设置为红色,却发现它显示为蓝色。

知道为什么吗?

以下是代码摘录:

procedure TForm1.FormPaint(Sender: TObject);
var
varBitmap: TBitmap;
pLock: PIntegerArray;
iColor: integer;
begin
varBitmap := TBitmap.Create;
varBitmap.PixelFormat := pf32bit;
varBitmap.Width := 800;
varBitmap.Height := 600;

// Set Pixels to Red
varBitmap.Canvas.Pixels[0, 0] := $0000FF;

// Shows $FF0000 (blue)
pLock := varBitmap.ScanLine[0];
iColor := pLock[0];
ShowMessageFmt('%x', [iColor]);

// Set ScanLine to Red
pLock[0] := $0000FF;

// Displays a blue pixel
Canvas.Draw(0, 0, varBitmap);
end;

似乎 TColor 与内存中的不一样,但这没有意义。

欢迎任何建议。 ;)

最佳答案

VCL 位图类,TBitmap是 Windows native 设备独立位图 (DIB) 的包装器。这些位图对象可以存储多种不同像素格式的位图。它们可以是单色的,每像素一位,最多每像素 32 位,这是您正在使用的格式。它们还可以用于存储基于调色板的位图,其中每个像素都保存颜色表的索引。

访问您引用的像素数据的两种方法是 Pixels TCanvas的属性(property)和 ScanLine TBitmap的属性(property)。

Pixels TCanvas的属性(property)是 GDI GetPixel 的包装器和 SetPixel 功能。这些是在 COLORREF 上运行的高级函数。值(value)观。 COLORREF 的文档说:

The low-order byte contains a value for the relative intensity of red; the second byte contains a value for green; and the third byte contains a value for blue. The high-order byte must be zero. The maximum value for a single byte is 0xFF.

换句话说,一个 COLORREF value 有固定的像素颜色编码方式。 GetPixelSetPixel函数主要处理固定 COLORREF 之间的转换形式和底层原始位图像素数据。另请注意 COLORREF不能代表alpha值。 COLORREF值的格式为 $00BBGGRR。

另一方面,ScanLine TBitmap的属性(property)返回一个指向底层 DIB 对象的原始像素数据的指针。您此处使用的数据是 32bpp 像素数据,该数据的约定是以 $AARRGGBB 格式存储。 Windows documentation对于 32bpp 数据说:

The bitmap has a maximum of 2^32 colors. If the biCompression member of the BITMAPINFOHEADER is BI_RGB, the bmiColors member of BITMAPINFO is NULL. Each DWORD in the bitmap array represents the relative intensities of blue, green, and red for a pixel. The value for blue is in the least significant 8 bits, followed by 8 bits each for green and red. The high byte in each DWORD is not used.

所以事实上这段文字是不正确的并且已经过时了。每个 DWORD 中的高字节事实上,如果使用的话,就是 Alpha channel 。

关于Delphi TBitmap - 为什么 Pixels 和 ScanLine 不同?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22291162/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com