我有一个使用WS_EX_LAYERED
窗口样式创建的窗口。目前,我正在使用GDI +绘制内存位图,并使用 UpdateLayeredWindow
更新分层窗口的图形内容。
这是我的代码片段:
void Redraw(HWND hWnd, int width, int height) {
static bool floppy = true;
floppy = !floppy;
HDC hScreenDC = GetDC(HWND_DESKTOP);
HDC hMemDC = CreateCompatibleDC(hScreenDC);
HBITMAP hBmp = CreateCompatibleBitmap(hScreenDC, width, height);
HGDIOBJ hObj = SelectObject(hMemDC, hBmp);
Graphics gfx(hMemDC);
SolidBrush b(Color(254, (floppy ? 255 : 0), (floppy ? 0 : 255), 0));
gfx.FillRectangle(&b, Rect(0, 0, width, height));
BLENDFUNCTION blend;
blend.BlendOp = AC_SRC_OVER;
blend.BlendFlags = 0;
blend.SourceConstantAlpha = 255;
blend.AlphaFormat = AC_SRC_ALPHA;
POINT src = { 0, 0 };
SIZE size;
size.cx = width;
size.cy = height;
Assert(UpdateLayeredWindow(
hWnd,
hScreenDC,
NULL,
&size,
hMemDC,
&src,
RGB(0, 0, 0),
&blend,
ULW_ALPHA
));
SelectObject(hMemDC, hObj);
DeleteObject(hBmp);
DeleteDC(hMemDC);
ReleaseDC(HWND_DESKTOP, hScreenDC);
}
创建SolidBrush
时,我为alpha组件指定了254的值。这导致99.6%的不透明填充,这不是我想要的。当我将255指定为alpha分量时,似乎没有填充。我的窗口变得完全透明。这是一个问题,因为我希望绘制100%不透明的形状,但我也希望绘制不透明的形状。
最佳答案
似乎有一些带有FillRectangle
的qwerks。当我们观察到将FillEllipse
与alpha分量为255的SolidBrush
一起使用时,会导致形状完美呈现(不透明),这变得显而易见。
我提出了两个解决方法,分别为我解决了这个问题:
FillRectangle
两次SolidBrush b(Color(254, 255, 0, 0));
gfx.FillRectangle(&b, Rect(0, 0, width, height));
gfx.FillRectangle(&b, Rect(0, 0, width, height));
由于同一区域被填充两次,因此它们将混合并创建RGB(255,0,0),而不管窗口后面的内容如何(现在它是100%不透明的)。我不喜欢这种方法,因为它要求每个矩形都要绘制两次。
FillPolygon
代替与
FillEllipse
一样,FillPolygon
似乎没有颜色问题,除非您这样称呼:SolidBrush b(Color(255, 255, 0, 0));
Point points[4];
points[0] = Point(0, 0);
points[1] = Point(width, 0);
points[2] = Point(width, height);
points[4] = Point(0, height);
gfx.FillPolygon(&b, points, 4); //don't copy and paste - this won't work
上面的代码将导致100%透明的窗口。我猜这是由于某种形式的优化,而是将调用传递给
FillRectangle
所致。或者-很有可能-FillPolygon
出现了问题,被FillRectangle
调用。但是,如果向数组添加额外的Point
,则可以解决该问题:SolidBrush b(Color(255, 255, 0, 0));
Point points[5];
points[0] = Point(0, 0);
points[1] = Point(0, 0); //<-
points[2] = Point(width, 0);
points[3] = Point(width, height);
points[4] = Point(0, height);
gfx.FillPolygon(&b, points, 5);
上面的代码确实将绘制100%不透明的形状,从而解决了我的问题。
关于c++ - 来自FillRectangle的不希望有的透明性,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/19214921/