- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
这是我过去两天尝试调试的代码:
#include <windows.h>
HBITMAP createImageMask(HBITMAP bitmapHandle, const COLORREF transparencyColor) {
// For getting information about the bitmap's height and width in this context
BITMAP bitmap;
// Create the device contexts for the bitmap and its mask
HDC bitmapGraphicsDeviceContext = CreateCompatibleDC(NULL);
HDC bitmapMaskGraphicsDeviceContext = CreateCompatibleDC(NULL);
// For the device contexts to re-select the initial object they initialized with
// and de-select the bitmap and mask
HGDIOBJ bitmapDummyObject;
HGDIOBJ bitmapMaskDummyObject;
// The actual mask
HBITMAP bitmapMaskHandle;
// 1. Generate the mask.
GetObject(bitmapHandle, sizeof(BITMAP), &bitmap);
bitmapMaskHandle = CreateBitmap(bitmap.bmWidth, bitmap.bmHeight, 1, 1, NULL);
// 2. Setup the device context for the mask (and the bitmap)
// — also get the initial selected objects in the device contexts.
bitmapDummyObject = SelectObject(bitmapGraphicsDeviceContext, (HGDIOBJ) (HBITMAP) bitmapHandle);
bitmapMaskDummyObject = SelectObject(bitmapMaskGraphicsDeviceContext, (HGDIOBJ) (HBITMAP) bitmapMaskHandle);
// 3. Set the background color of the mask.
SetBkColor(bitmapGraphicsDeviceContext, transparencyColor);
// 4. Copy the bitmap to the mask and invert it so it blends with the background color.
BitBlt(bitmapMaskGraphicsDeviceContext, 0, 0, bitmap.bmWidth, bitmap.bmHeight, bitmapGraphicsDeviceContext, 0, 0, SRCCOPY);
BitBlt(bitmapGraphicsDeviceContext, 0, 0, bitmap.bmWidth, bitmap.bmHeight, bitmapMaskGraphicsDeviceContext, 0, 0, SRCINVERT);
// 5. Select the bitmaps out before deleting the device contexts to avoid any issues.
SelectObject(bitmapGraphicsDeviceContext, bitmapDummyObject);
SelectObject(bitmapMaskGraphicsDeviceContext, bitmapMaskDummyObject);
// Clean-up
DeleteDC(bitmapGraphicsDeviceContext);
DeleteDC(bitmapMaskGraphicsDeviceContext);
// Voila!
return bitmapMaskHandle;
}
HBITMAP
),并且不会产生任何错误(来自
GetLastError
函数)。
RGB(255, 0, 0)
)的图像:
最佳答案
该代码可以正常工作,尽管它并没有完全按照您的想象做。如果没有看到任何输出,则说明此功能的外部原因是什么。
该代码的作用是设置两个位图,以供一种旧的Win32技术使用,以绘制一个 Sprite ,其中您使用不同的光栅操作代码对BitBlt进行两次调用,一个调用一个蒙版,另一个绘制该 Sprite ,以使 Sprite 的背景将不会被绘制。请注意,它既在创建掩码,也在更改源位图。 (“const HBITMAP bitmapHandle”中的“const”实际上并没有做任何事情。位图句柄就像资源ID一样,指的是Windows所管理的位图,而C++对此一无所知。如果您查看代码,最终的BitBlit将变为源位图,而不是掩码。该调用的作用是使源位图中的键色变黑,这是使用rop代码和两次blit绘制sprite所必需的。
顺便说一句,这项技术是一种非常古老的实现方法,在将MaskBlt引入API之前,该方法将在一次调用中完成您想做的事情。但更进一步,MaskBlt在这一点上已经过时了。您可能想为游戏或类似游戏的游戏绘制 Sprite 。几乎可以肯定,您真正想要的是使用每个像素的Alpha加载PNG,并使用Alpha合成对其进行绘制。您可以使用GDI+或开放源代码图形库(例如FreeImage)来执行此操作。
在下面的任何情况下,最少的代码都会演示此掩码代码的实际工作原理。只需更改以下来源,即可使“D:\test\hex_badge.bmp”成为您在问题中具有该六角形位图的位置的路径。
#include <windows.h>
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);
HBITMAP g_bmp;
HBITMAP g_bmpMask;
HBITMAP createImageMask( HBITMAP bitmapHandle, const COLORREF transparencyColor) {
// For getting information about the bitmap's height and width in this context
BITMAP bitmap;
// Create the device contexts for the bitmap and its mask
HDC bitmapGraphicsDeviceContext = CreateCompatibleDC(NULL);
HDC bitmapMaskGraphicsDeviceContext = CreateCompatibleDC(NULL);
// The actual mask
HBITMAP bitmapMaskHandle;
// 1. Generate the mask.
GetObject(bitmapHandle, sizeof(BITMAP), &bitmap);
bitmapMaskHandle = CreateBitmap(bitmap.bmWidth, bitmap.bmHeight, 1, 1, NULL);
// 2. Setup the device context for the mask (and the bitmap).
SelectObject(bitmapGraphicsDeviceContext, bitmapHandle);
SelectObject(bitmapMaskGraphicsDeviceContext, bitmapMaskHandle);
// 3. Set the background color of the mask.
SetBkColor(bitmapGraphicsDeviceContext, transparencyColor);
// 4. Copy the bitmap to the mask and invert it so it blends with the background color.
BitBlt(bitmapMaskGraphicsDeviceContext, 0, 0, bitmap.bmWidth, bitmap.bmHeight, bitmapGraphicsDeviceContext, 0, 0, SRCCOPY);
BitBlt(bitmapGraphicsDeviceContext, 0, 0, bitmap.bmWidth, bitmap.bmHeight, bitmapMaskGraphicsDeviceContext, 0, 0, SRCINVERT);
// Clean-up
DeleteDC(bitmapGraphicsDeviceContext);
DeleteDC(bitmapMaskGraphicsDeviceContext);
// Voila!
return bitmapMaskHandle;
}
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
MSG msg = { 0 };
WNDCLASS wc = { 0 };
wc.lpfnWndProc = WndProc;
wc.hInstance = hInstance;
wc.hbrBackground = (HBRUSH)(COLOR_BACKGROUND);
wc.lpszClassName = L"minwindowsapp";
g_bmp = (HBITMAP)LoadImage(hInstance, L"D:\\test\\hex_badge.bmp", IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
g_bmpMask = createImageMask(g_bmp, RGB(255, 0, 0));
if (!RegisterClass(&wc))
return 1;
if (!CreateWindow(wc.lpszClassName,
L"Minimal Windows Application",
WS_OVERLAPPEDWINDOW | WS_VISIBLE,
0, 0, 640, 480, 0, 0, hInstance, NULL))
return 2;
while (GetMessage(&msg, NULL, 0, 0) > 0) {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return 0;
}
LRESULT HandleWmPaint(HWND hWnd, WPARAM wParam, LPARAM lParam)
{
PAINTSTRUCT ps;
HDC hdcScr = GetDC(NULL);
HDC hdcBmp = CreateCompatibleDC(hdcScr);
HBITMAP hbmOld = (HBITMAP)SelectObject(hdcBmp, g_bmp);
HDC hdcMask = CreateCompatibleDC(hdcScr);
HBITMAP hbmOldMask = (HBITMAP) SelectObject(hdcMask, g_bmpMask );
HDC hdc = BeginPaint(hWnd, &ps);
BitBlt(hdc, 0, 0, 184, 184, hdcMask, 0, 0, SRCCOPY);
BitBlt(hdc, 184, 0, 184, 184, hdcBmp, 0, 0, SRCCOPY);
EndPaint(hWnd, &ps);
SelectObject(hdcMask, hbmOldMask);
DeleteDC(hdcMask);
SelectObject(hdcBmp, hbmOld);
DeleteDC(hdcBmp);
ReleaseDC(NULL, hdcScr);
return 0;
}
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch (message)
{
case WM_CLOSE:
PostQuitMessage(0);
break;
case WM_PAINT:
return HandleWmPaint(hWnd, wParam, lParam);
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
关于c - 从位图和透明度颜色创建蒙版-Windows GDI,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59422456/
这两个库之间有什么区别吗? 最佳答案 根据the wikipedia article on GDI : With the introduction of Windows XP, GDI was dep
我喜欢 GDI+,因为它具有高性能并且包含在 Windows XP 中。但是,它的模糊类和效果类仅在 GDI+ 1.1 中可用,后者仅随 Windows Vista 或更高版本提供。尽管微软计划很快放
我用 C# 创建了一个图像服务,它采用基础层图像 (JPG),再分层一层更透明的 PNG(32 位),然后输出最终的 JPG 图像。我试图从这个函数中挤出最后一毫秒,但我的代码在 GDI+ 中的 Dr
我正在使用顶点以及 LineTo() 和 MoveTo() 函数制作一系列三角形来表示 3D 形状。 着色/填充这些三角形的最佳方法是什么? 谢谢 最佳答案 MSDN has a sample tha
我在 Win7 系统上注意到过一个问题,以为是 DWM 错误,但在重新启动后已修复。但现在我意识到它在其他人的系统上发生(作为默认行为),并且这也是 Surface Pro 上的正常行为。 如何重现问
是否可以在用户模式下创建自定义 GDI 设备?我们的想法是创建一个设备上下文 (HDC),我们可以将其传递给不透明的组件,这样当组件调用 GDI 函数(如 TextOut)时,我们可以获得实际的文本字
我想知道是否可以枚举所有桌面可见窗口以创建它们的位图并将所有位图组合成一个以便获得桌面的完整屏幕截图? 最有可能使用 GDI/GD+,但也欢迎使用任何外部库。首选语言C\C++。 提前致谢。 最佳答案
我有一个生成元文件 (EMF) 的应用程序。它使用引用设备(又名屏幕)来呈现这些元文件,因此元文件的 DPI 会根据代码运行的机器而变化。 假设我的代码打算创建一个 8.5 x 11 英寸的元文件。
我在同时使用 GDI 和 GDI+ 进行绘图时遇到问题。页面转换——尤其是缩放——似乎在两者之间有点偏离。除了 SetViewportExt 和 SetWindowExt 之外,GDI 上下文的哪些属
我需要从应用程序中获取一个大表(300K+ 行)并且没有导出功能。经过多次不成功的尝试后,我只剩下一个复制粘贴宏,一次一行。如果有办法在绘制时获取字符串,我可以一次获取一页(40 行)。 最佳答案 如
我曾经在我的 Win7 系统上注意到一个问题,认为这是一个 DWM 错误,因为它在重新启动后得到修复。但现在我意识到它正在其他人的系统上发生(作为默认行为),这也是 Surface Pro 上的正常行
我正在寻找一些高级教程,或者可能是用 C++ 或 .NET 编写的开源应用程序,它们可以实现复杂的基于 vector 的应用程序,例如 MS Visio 或 Autocad。我需要知道的是,当用户可以
我正在使用第三方库来绘制图表。该库需要一个 HDC (GDI)。但是我的应用程序使用的是 GDI+。 Q1:这样做安全吗? void f(Gdiplus::Graphics& graphics) {
关闭。这个问题是opinion-based .它目前不接受答案。 想改善这个问题吗?更新问题,以便可以通过 editing this post 用事实和引文回答问题. 4年前关闭。 Improve t
对不起,如果这是题外话。如果是这样的话;请随时将其移至适当的站点。 GDI/GDI+ 如何在不使用 DirectX 或 OpenGL 等较低级别的 API 与 GPU 通信的情况下渲染到显卡(在屏幕上
我正在尝试在兼容的渲染目标上使用 Gdi 和 Direct 2D 来渲染位图。我使用 D2D1_COMPATIBLE_RENDER_TARGET_OPTIONS_GDI_COMPATIBLE 选项创建
我们目前正在将一个较旧的应用程序转换为通过 GDI+ 绘制,而不是直接使用 GDI。随着我们逐步翻译系统,有时我们需要从 Gdiplus::Graphics 对象中获取 HDC,以便允许尚未翻译的代码
我正在尝试使用 GDI+ 在屏幕上(整个屏幕,在所有其他窗口的顶部)绘图。 我已将 NULL 传递给 GetDC 以将 HDC 显示到屏幕上,然后使用它创建一个 Graphics 对象,并使用 Dra
GDI+ 非常慢,几乎完全是软件,而 GDI 是高度硬件加速的。GDI+ 是 Graphics 类在 WinForms 上使用的东西,它太慢了。 有没有人制作了 .NET GDI 库以便我们可以有速度
ASP.NET 网站随机引发此 System.Drawing-error: System.Runtime.InteropServices.ExternalException:System.Drawin
我是一名优秀的程序员,十分优秀!