• 博客园logo
  • 会员
  • 众包
  • 新闻
  • 博问
  • 闪存
  • 赞助商
  • HarmonyOS
  • Chat2DB
    • 搜索
      所有博客
    • 搜索
      当前博客
  • 写随笔 我的博客 短消息 简洁模式
    用户头像
    我的博客 我的园子 账号设置 会员中心 简洁模式 ... 退出登录
    注册 登录
james1207

博客园    首页    新随笔    联系   管理    订阅  订阅

Windows DDB和DIB技术应用(3)--图元外边矩形检测

GDI/GDI+中只有对字体的外边框的测量,而没有提供对点,线,面,曲线的外边框获取函数。下面是本人利用DIB技术编写的探测简单图元,甚至也可以探测自己定义的复杂图元的外边矩形框的函数。本人已经测试,效果很棒。

 

bool GetFeatureRange(void *object, //自己定义的图元对象
        CRect rect, // DIB屏幕大小
		CDC *pDC, //绘图设置
       CRect &retVal // 检测范围
)
	{
		CDC memDC; //临时绘图设备
		COLORREF bkcolor = RGB(255,255,255); // 背景色
		//创建临时设备
		memDC.CreateCompatibleDC(pDC);
		// 建立一个与屏幕显示相同大小的DIB位图
		BITMAPINFO info;
		memset(&info.bmiHeader,0,sizeof(BITMAPINFOHEADER));
		info.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
		info.bmiHeader.biWidth = rect.Width();
		info.bmiHeader.biHeight = rect.Height();
		info.bmiHeader.biPlanes = 1;
		info.bmiHeader.biBitCount = 32;
		info.bmiHeader.biCompression = BI_RGB;

		PVOID pBits; // 位图数据指针
		HBITMAP hbitmap = CreateDIBSection(memDC.m_hDC,&info,DIB_RGB_COLORS,
			&pBits,0,0);
		HBITMAP hOldBitmap = (HBITMAP)memDC.SelectObject(hbitmap);
		// 使用背景色清除位图
		memDC.FillSolidRect(0,0,rect.Width(), rect.Height(), bkcolor);
		
        // 绘制图元
        object->Draw(...);
        // 还原位图
		memDC.SelectObject(hOldBitmap);
        // 销毁临时绘图设备
		memDC.DeleteDC();
        // 获取位图信息
		CBitmap *pBitmap = CBitmap::FromHandle(hbitmap);
		BITMAP bmp;
		pBitmap->GetBitmap(&bmp);
		BYTE *pixels = (BYTE*)bmp.bmBits;
		// 探测范围
		bool bExist = false;
		// DIB存储方向有下至上 颜色存储形式BGR
		BYTE r,g,b;
		for(int i = 0; i < bmp.bmHeight; i++)
		{
			for(int j = 0; j < bmp.bmWidth; j++)
			{
				b = *(pixels++);
				g = *(pixels++);
				r = *(pixels++);
				pixels++; //跳过透明度 位图像素占32位字节
				if(RGB(r,g,b) != bkcolor)
				{
					if(bExist){
						retVal.top = i;
						if(retVal.left > j) retVal.left = j;
						if(retVal.right < j) retVal.right = j;
					}
					else
					{
						retVal.left = 
							retVal.right = j;
						retVal.top = 
							retVal.bottom = i;
						bExist = true;
					}
				}
			}
		}

		if(bExist) //调整与屏幕相同的坐标
		{
			retVal.top = bmp.bmHeight - retVal.top;
			retVal.bottom = bmp.bmHeight - retVal.bottom;
		}
		pBitmap->DeleteObject();
		return bExist;
	}


 

 

posted @ 2013-08-29 18:52  Class Xman  阅读(277)  评论(0)    收藏  举报
刷新页面返回顶部
博客园  ©  2004-2025
浙公网安备 33010602011771号 浙ICP备2021040463号-3