// t_transparent_memory_dc.cpp : Defines the entry point for the application.
//
#include "framework.h"
#include "t_transparent_memory_dc.h"
#include <atlconv.h>
#include <gdiplus.h>
#include <vector>
#pragma comment(lib, "gdiplus.lib")
#define MAX_LOADSTRING 100
#define IMAGE_PATH L"test.wmf"
#define ORIG_W 175
#define ORIG_H 188
#define RADIO 1
#define IMAGE_W (int)(ORIG_W * RADIO)
#define IMAGE_H (int)(ORIG_H * RADIO)
// Global Variables:
HINSTANCE hInst; // current instance
WCHAR szTitle[MAX_LOADSTRING]; // The title bar text
WCHAR szWindowClass[MAX_LOADSTRING]; // the main window class name
Gdiplus::GdiplusStartupInput g_gsi;
ULONG_PTR g_token;
#pragma pack(1)
typedef struct tagWIN16RECT {
WORD left;
WORD top;
WORD right;
WORD bottom;
} WIN16RECT;
typedef struct tagPLACEABLEMETAHEADER {
DWORD key;
WORD hmf;
WIN16RECT bbox;
WORD inch;
DWORD reserved;
WORD checksum;
} PLACEABLEMETAHEADER;
#pragma pack()
HENHMETAFILE WINAPI convert_wmf_to_emf(IN LPCWSTR meta_file) {
HANDLE hfile = CreateFileW(meta_file, GENERIC_READ, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if (!hfile || INVALID_HANDLE_VALUE == hfile) {
return NULL;
}
DWORD dwsize = GetFileSize(hfile, NULL);
std::vector<BYTE> data(dwsize);
DWORD dwread = -1;
BOOL bret = ReadFile(hfile, &data[0], dwsize, &dwread, NULL);
CloseHandle(hfile);
HENHMETAFILE hemf = NULL;
if (bret) {
PLACEABLEMETAHEADER* pmh = (PLACEABLEMETAHEADER*)&data[0];
int offset = -1;
if (pmh->key != 0x9AC6CDD7)
offset = 0;
else
offset = sizeof(PLACEABLEMETAHEADER);
hemf = SetWinMetaFileBits((UINT)data.size(), &data[offset], NULL, NULL);
}
return hemf;
}
void DrawTransparentBitmap(HDC hdc, HBITMAP hBitmap, short xStart, short yStart, COLORREF cTransparentColor)
{
BITMAP bm;
COLORREF cColor;
HBITMAP bmAndBack, bmAndObject, bmAndMem, bmSave;
HBITMAP bmBackOld, bmObjectOld, bmMemOld, bmSaveOld;
HDC hdcMem, hdcBack, hdcObject, hdcTemp, hdcSave;
POINT ptSize;
hdcTemp = CreateCompatibleDC(hdc);
SelectObject(hdcTemp, hBitmap); // Select the bitmap
GetObject(hBitmap, sizeof(BITMAP), (LPSTR)&bm);
ptSize.x = bm.bmWidth; // Get width of bitmap
ptSize.y = bm.bmHeight; // Get height of bitmap
DPtoLP(hdcTemp, &ptSize, 1); // Convert from device
// Create some DCs to hold temporary data.
hdcBack = CreateCompatibleDC(hdc);
hdcObject = CreateCompatibleDC(hdc);
hdcMem = CreateCompatibleDC(hdc);
hdcSave = CreateCompatibleDC(hdc);
// Create a bitmap for each DC. DCs are required for a number of
// GDI functions.
// Monochrome DC
bmAndBack = CreateBitmap(ptSize.x, ptSize.y, 1, 1, NULL);
// Monochrome DC
bmAndObject = CreateBitmap(ptSize.x, ptSize.y, 1, 1, NULL);
bmAndMem = CreateCompatibleBitmap(hdc, ptSize.x, ptSize.y);
bmSave = CreateCompatibleBitmap(hdc, ptSize.x, ptSize.y);
// Each DC must select a bitmap object to store pixel data.
bmBackOld = (HBITMAP)SelectObject(hdcBack, bmAndBack);
bmObjectOld = (HBITMAP)SelectObject(hdcObject, bmAndObject);
bmMemOld = (HBITMAP)SelectObject(hdcMem, bmAndMem);
bmSaveOld = (HBITMAP)SelectObject(hdcSave, bmSave);
// Set proper mapping mode.
SetMapMode(hdcTemp, GetMapMode(hdc));
// Save the bitmap sent here, because it will be overwritten.
BitBlt(hdcSave, 0, 0, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCCOPY);
// Set the background color of the source DC to the color.
// contained in the parts of the bitmap that should be transparent
cColor = SetBkColor(hdcTemp, cTransparentColor);
// Create the object mask for the bitmap by performing a BitBlt
// from the source bitmap to a monochrome bitmap.
BitBlt(hdcObject, 0, 0, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCCOPY);
BitBlt(hdc, ptSize.x * 1, ptSize.y * 1, ptSize.x, ptSize.y, hdcObject, 0, 0, SRCCOPY);
// Set the background color of the source DC back to the original color.
SetBkColor(hdcTemp, cColor);
// Create the inverse of the object mask.
BitBlt(hdcBack, 0, 0, ptSize.x, ptSize.y, hdcObject, 0, 0, NOTSRCCOPY);
BitBlt(hdc, ptSize.x * 2, ptSize.y * 1, ptSize.x, ptSize.y, hdcBack, 0, 0, SRCCOPY);
// Copy the background of the main DC to the destination.
BitBlt(hdcMem, 0, 0, ptSize.x, ptSize.y, hdc, xStart, yStart, SRCCOPY);
BitBlt(hdc, ptSize.x * 3, ptSize.y * 1, ptSize.x, ptSize.y, hdcMem, 0, 0, SRCCOPY);
// Mask out the places where the bitmap will be placed.
BitBlt(hdcMem, 0, 0, ptSize.x, ptSize.y, hdcObject, 0, 0, SRCAND);
BitBlt(hdc, ptSize.x * 4, ptSize.y * 1, ptSize.x, ptSize.y, hdcMem, 0, 0, SRCCOPY);
// Mask out the transparent colored pixels on the bitmap.
BitBlt(hdcTemp, 0, 0, ptSize.x, ptSize.y, hdcBack, 0, 0, SRCAND);
BitBlt(hdc, ptSize.x * 5, ptSize.y * 1, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCCOPY);
// XOR the bitmap with the background on the destination DC.
BitBlt(hdcMem, 0, 0, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCPAINT);
BitBlt(hdc, ptSize.x * 6, ptSize.y * 1, ptSize.x, ptSize.y, hdcMem, 0, 0, SRCCOPY);
// Copy the destination to the screen.
BitBlt(hdc, xStart, yStart, ptSize.x, ptSize.y, hdcMem, 0, 0, SRCCOPY);
// Place the original bitmap back into the bitmap sent here.
BitBlt(hdcTemp, 0, 0, ptSize.x, ptSize.y, hdcSave, 0, 0, SRCCOPY);
// Delete the memory bitmaps.
DeleteObject(SelectObject(hdcBack, bmBackOld));
DeleteObject(SelectObject(hdcObject, bmObjectOld));
DeleteObject(SelectObject(hdcMem, bmMemOld));
DeleteObject(SelectObject(hdcSave, bmSaveOld));
// Delete the memory DCs.
DeleteDC(hdcMem);
DeleteDC(hdcBack);
DeleteDC(hdcObject);
DeleteDC(hdcSave);
DeleteDC(hdcTemp);
}
void t_gdi_paint_hbitmap(HDC hdc, HBITMAP hbitmap) {
HDC mem_dc = CreateCompatibleDC(hdc);
HGDIOBJ old = SelectObject(mem_dc, hbitmap);
if (!old)
MessageBox(0, L"SelectObject return NULL", 0, 0);
BITMAP bmpinfo;
GetObject(hbitmap, sizeof(bmpinfo), &bmpinfo);
BitBlt(hdc, 0, 0, bmpinfo.bmWidth, bmpinfo.bmHeight, mem_dc, 0, 0, SRCCOPY);
}
void t_gdiplus_paint_hbitmap(HDC hdc, HBITMAP hbitmap) {
BITMAP bmpinfo;
GetObject(hbitmap, sizeof(bmpinfo), &bmpinfo);
Gdiplus::Bitmap bitmap(hbitmap, NULL);
Gdiplus::Graphics g(hdc);
g.DrawImage(&bitmap, bitmap.GetWidth(), 0, bitmap.GetWidth(), bitmap.GetHeight());
}
void t_transparent_memory_dc(HDC hdc) {
HBITMAP mem_bmp = NULL;
BITMAPINFOHEADER bih = { 0 };
bih.biSize = sizeof(BITMAPINFOHEADER);
bih.biWidth = IMAGE_W;
bih.biHeight = -IMAGE_H;
bih.biPlanes = 1;
bih.biBitCount = 32;
bih.biCompression = BI_RGB;
bih.biSizeImage = 0;
bih.biXPelsPerMeter = 0;
bih.biYPelsPerMeter = 0;
bih.biClrUsed = 0;
bih.biClrImportant = 0;
BITMAPINFO bi = { 0 };
bi.bmiHeader = bih;
int len = IMAGE_W * IMAGE_H;
PBYTE pbits = new BYTE[len * 4];
memset(pbits, 0, len * 4);
HDC dc = CreateDC(L"DISPLAY", NULL, NULL, NULL);
mem_bmp = CreateDIBitmap(dc, &bih, CBM_INIT, pbits, &bi, DIB_RGB_COLORS);
DeleteDC(dc);
HDC mem_dc = CreateCompatibleDC(NULL);
HGDIOBJ old_gdi = SelectObject(mem_dc, mem_bmp);
RECT rc{ 0, 0, IMAGE_W, IMAGE_H };
HBRUSH hbrush = CreateSolidBrush(RGB(255, 255, 255));
FillRect(mem_dc, &rc, hbrush);
HENHMETAFILE hemf = convert_wmf_to_emf(IMAGE_PATH);
if (hemf) {
PlayEnhMetaFile(hdc, hemf, &rc);
PlayEnhMetaFile(mem_dc, hemf, &rc);
// BitBlt(hdc, 0, 0, IMAGE_W, IMAGE_H, mem_dc, 0, 0, SRCCOPY);
DeleteEnhMetaFile(hemf);
}
SelectObject(mem_dc, old_gdi);
// t_gdi_paint_hbitmap(hdc, mem_bmp);
// t_gdiplus_paint_hbitmap(hdc, mem_bmp);
DrawTransparentBitmap(hdc, mem_bmp, 0, IMAGE_H, RGB(255, 255, 255));
DeleteObject(mem_bmp);
DeleteDC(mem_dc);
}
void desc(HDC hdc) {
没有合适的资源?快使用搜索试试~ 我知道了~
t-transparent-memory-dc.zip
共13个文件
h:4个
ico:2个
wmf:1个
需积分: 1 0 下载量 97 浏览量
2024-01-16
17:09:55
上传
评论
收藏 24KB ZIP 举报
温馨提示
双缓冲,绘制透明位图,使用图片掩码
资源推荐
资源详情
资源评论
收起资源包目录
t_transparent_memory_dc.zip (13个子文件)
t_transparent_memory_dc
t_transparent_memory_dc.h 39B
t_transparent_memory_dc.sln 1KB
framework.h 395B
t_transparent_memory_dc.ico 45KB
t_transparent_memory_dc.vcxproj.filters 2KB
small.ico 45KB
Resource.h 786B
t_transparent_memory_dc.vcxproj.user 168B
t_transparent_memory_dc.cpp 13KB
t_transparent_memory_dc.rc 7KB
targetver.h 313B
t_transparent_memory_dc.vcxproj 7KB
test.wmf 4KB
共 13 条
- 1
资源评论
遍地是牛
- 粉丝: 781
- 资源: 3
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功