近日用VC写一个GDI相关的程序时,一不小心栽了跟头,害得我浪费了整整一天的时间来debug!!
跟头1:COLORREF的high-order byte
我在处理图片的透明色是,用到了如下代码:
COLORREF color1 = ....;
COLORREF color2 = ....;
if (color1 = = color2)
{
......
}
可是很奇怪的是,两种颜色明明是一样的,可if的判断条件就是不满足!!!最后发现是COLORREF的high-order byte 的问题. 我们知道RGB三色共占用了3个字节,剩余的1个字节对颜色来说是无效的,但对 "==" 比较来说就有效了!!原来我的color1和color2的high-order byte不相同!!其实,按照MSDN的说法,这个Byte必须为0的,不过好像不为0也不影响GDI的绘图,就是比较时出问题.
于是我写了一个宏,NO_HIGH_BYTE_COLOR
#define NO_HIGH_BYTE_COLOR(clr) ((clr)&0x00FFFFFF) //取出没有high-order byte 的COLORREF值(置high-order byte为0)
然后把判断处该为:
if (NO_HIGH_BYTE_COLOR(color1) = = NO_HIGH_BYTE_COLOR(color2))
{
......
}
以防万一. :)
跟头2:{}和局部变量
这个就比较弱智了.呵呵,纯粹是自己粗心
我写的一个画字符串的函数(DrawText API的扩展,可以指定字体,背景颜色等,但是测试发现有连续运行几百次后出现字体错误和花屏(win98下如此.但奇怪的是GID资源泄漏在XP下似乎没有影响,容错性好???......),根据经验,很明显就是资源泄漏了.经过排除,最后锁定了下面这个成员函数,但怎么看都看不出问题,最后还是同事"一语惊醒梦中人",帮我找出了错误.呵呵,错在哪里?自己看代码吧.注意红色部分......
class CCanvas : public CDC
......
int CCanvas::DrawString(const CString &str, LPRECT lpRect, UINT uFormat, HFONT hFont, COLORREF clrText, BOOL blTrans, COLORREF clrBk)
{
int nOldBk = SetBkMode(blTrans ? TRANSPARENT : OPAQUE);
int nOldBkColor = SetBkColor(clrBk);
COLORREF clrOldTextColor = SetTextColor(clrText);
HFONT hOldFont = NULL;
if (hFont)
{
HFONT hOldFont = (HFONT)SelectObject(hFont);
}
int nResult = DrawText(str,lpRect, uFormat);
//Set Back
if (hFont)
{
SelectObject(hOldFont);
}
SetTextColor(clrOldTextColor);
SetBkColor(nOldBkColor);
SetBkMode(nOldBk);
return nResult;
}
函数中任何地方都可以声明变量是C++的一个特性,确实很方便,但有时也会带来隐患,当然,前提是你足够粗心:)我个人认为,这样的情况(内层作用域的变量和外层作用域的变量重名)编译器是应该来个warning的,不知道这个是不是违背了"C的精神"所以才没有做....呵呵,不仅怀念起Pascal的var了......
刚栽了两个跟头,大家吸取教训啊......
最新推荐文章于 2019-03-14 16:08:10 发布