Peng Lv

毋意,毋必,毋固,毋我。 言必行,行必果。

导航

Windows编程学习笔记(四)

第三章 图形基础(中)

/*******************************************************/

 

使用画笔

1.获得现有的画笔句柄:

HPEN hPen = GetStockObject(WHITE_PEN); // get the handle of pen

SelectObject(hdc,hPen); // use this pen

函数也可以这样用 hPen = SelectObject(hdc,GetStockObject(WHITE_PEN));

2.创建新的画笔

   这种方式更加灵活,同时要求也更高,应遵循以下三条原则:

      ·最后要删除自己建立的所有的GDI对象,否则会发生内存泄露

      ·当GDI对象正在一个有效的设备内容中使用时,不要删除它

      ·不要删除现有对象。

创建画笔: hPen = CreatePen(iPenStyle,iWidth,crColor);

其中第一个参数是确定画笔的线条,常用的有以下几个 PS_SOLID实线 PS_DASH虚线 PS_DOT 点线 第二个参数是画笔的宽度 , 第三个参数是画笔的颜色,windows会将颜色转换为设备所能表示的最相近的颜色。

3.逻辑画笔

我们也可以通过建立一个形态为LOGPEN的结构,用CreatePenIndirect来建立,如果程序中使用许多能在源代码中初始化的画笔,那么这种方法会有效得多。

LOGPEN 有三个成员,lopnStyle是画笔样式 , lopnwidth画笔宽度 , lopncolor画笔颜色,使用时如下:

LOGPEN logpen = CreatePenIndirect(&logpen);这时logpen是与设备无关的,当使用SelectObject时才会相关联。

/****************************************************************/

 

删除画笔

   当使用完画笔后,一定要删除建立的画笔,可以使用DeleteObject(hPen)来删除画笔。但现在考虑如下情况:

SelectObject(hdc,CreatePen(PS_DASH,0,RGB(0,255,0));

使用完后,这时我们如果想删除建立的绿色画笔该怎么办呢? 不用着急,因为SelectObject函数是返回的上次的画笔句柄,所以我们可一选择一个现有的画笔来得到刚才创建的绿色画笔句柄:

DeleteObject(SelectObject(hdc,GetStoctObject(BLACK_PEN)));

这样是有些麻烦,所以我们还是老老实实的用如下方法吧:

HPEN hPen = CreatePen(PS_SOLID,0,RGB(0,255,0));

SelectObject(hdc,hPen);

/* use pen */

DeleteObject(hPen);

/*************************************************************/

 

绘图方式

 

设备内容中定义的绘图方式也影响显示器上所画线的外观。设想画这样一条直线,它的色彩由画笔色彩和画线区域原来的色彩共同决定。设想用同一种画笔在白色表面上画出黑线而在黑色表面上画出白线,而且不用知道表面是什么色彩。这样的功能对您有用吗?通过绘图方式的设定,这些都可以实作。

当Windows使用画笔来画线时,它实际上执行画笔图素与目标位置处原来图素之间的某种位布尔运算。图素间的位布尔运算叫做「位映像运算」,简称为「ROP」。由于画一条直线只涉及两种图素(画笔和目标),因此这种布尔运算又称为「二元位映像运算」,简记为「ROP2」。Windows定义了16种ROP2代码,表示Windows组合画笔图素和目标图素的方式。在内定设备内容中,绘图方式定义为R2_COPYPEN,这意味着Windows只是将画笔图素复制到目标图素,这也是我们通常所熟知的。此外,还有15种ROP2

16种不同的ROP2是怎样得来的呢?为了示范的需要,我们假设使用单色系统,目标色(窗口显示区域的色彩)为黑色(用0来表示)或者白色(用1来表示),画笔也可以为黑色或者白色。用黑色或者白色画笔在黑色或者白色目标上画图有四种组合:白笔与白目标、白笔与黑目标、黑笔与白目标、黑笔与黑目标。

画笔在目标上绘制后会得到什么呢?一种可能是不管画笔和目标的色彩,画出的线总是黑色的,这种绘图方式由ROP2代码R2_BLACK表示。另一种可能是只有当画笔与目标都为黑色时,画出的结果才是白色,其它情况下画出的都是黑色。尽管这似乎有些奇怪,Windows还是为这种方式起了一个名字,叫做R2_NOTMERGEPEN。Windows执行目标图素与画笔图素的位「或」运算,然后翻转所得色彩。

可以通过以下呼叫在设备内容中设定新的绘图模式:

SetROP2 (hdc, iDrawMode) ;

iDrawMode参数是表中「绘图模式」一栏中给出的值之一。您可以用函数:

iDrawMode = GetROP2 (hdc) ;

来取得目前绘图方式。设备内容中的内定设定为R2_COPYPEN,它用画笔色彩替代目标色彩。在R2_NOTCOPYPEN方式下,若画笔为黑色,则画成白色;若画笔为白色,则画成黑色。R2_BLACK方式下,不管画笔和背景色为何种色彩,总是画成黑色。与此相反,R2_WHITE方式下总是画成白色。R2_NOP方式就是「不操作」,让目标保持不变。

/**************************************************************/

 

绘制填入区域

图形以目前设备内容中选择的画刷来填入。内定情况下,使用现有对象,这意味着图形内部将画为白色。Windows定义六种现有画刷:WHITE_BRUSH、LTGRAY_BRUSH、GRAY_BRUSH、DKGRAY_BRUSH、BLACK_BRUSH和NULL_BRUSH (也叫HOLLOW_BRUSH)。您可以将任何一种现有画刷选入您的设备内容中,就和您选择一种画笔一样。Windbws将HBRUSH定义为画刷的句柄,所以可以先定义一个画刷句柄变量:

HBRUSH hBrush ;

您可以通过呼叫GetStockObject来取得GRAY_BRUSH的句柄:

hBrush = GetStockObject (GRAY_BRUSH) ;

您可以呼叫SelectObject将它选进设备内容:

SelectObject (hdc, hBrush) ;

现在,如果您要画上表中的任一个图形,则其内部将为灰色。

如果您想画一个没有边界框的图形,可以将NULL_PEN选进设备内容:

SelectObject (hdc, GetStockObject (NULL_PEN)) ;

如果您想画出图形的边界框,但不填入内部,则将NULL_BRUSH选进设备内容:

SelectObject (hdc, GetStockobject (NULL_BRUSH) ;

使用NULL_BRUSH的效果截图和使用NULL_PEN的效果截图如下:



 

posted on 2010-02-03 16:47  Lvpengms  阅读(514)  评论(0编辑  收藏  举报