原理
DC(Device Contexts)是GDI内部的一个数据结构,与特定的显示设备相关联,如果我们获取该DC的handle,我们就能操作显示设备进行绘制。默认情况下(如MFC中),我们都会直接使用DC进行绘制,但是当对DC的操作非常频繁时,GDI频繁向显示设备输出,导致闪屏。
Memory DC使用中非常高效的绘图技术,使用非常广泛。Memory DC的原理是创建一个与物理显示设备适配的内存DC,所有的绘图动作都在Memory DC上完成后,再将Memory DC拷贝到物理DC上,GDI只需要向显示设备进行一次输出即可完成。由于内存访问速度比设备访问速度高得多,所以避免了闪屏现象。
使用方法(MFC下)
CClientDC dc(this);
CDC dcMem;
CBitmap bmp;
CRect rect;
this->GetClientRect(&rect);
dcMem.CreateCompatibleDC(dc);
bmp.CreateCompatibleBitmap(dc, rect.Width(), rect.Height());
dcMem.SelectObject(&bmp);
// ...
// 在这儿使用dcMem绘图
// ...
dc.BitBlt(0,0,rect.Width(),rect.Height(),&dcMem,0,0,SRCCOPY);
对于复杂的多元素界面,对元素进行分层绘制是一个很高效的方法。例如,一个对话框中需要绘制一个动态的坐标系实时显示曲线变化趋势。需要绘制的元素包括以下几种:
元素 | 重绘频率 |
---|---|
背景 | 绘制1次 |
坐标轴 | 绘制1次 |
坐标网格 | 绘制1次 |
坐标标值 | 坐标尺度变换时需要重绘 |
曲线 | 实时重绘 |
根据上表可以创建3个Memory DC
Memory DC | 功能 |
---|---|
dcBackground | 绘制背景、坐标轴、坐标网格,需要有绘制一次,以后每次拷贝到物理DC |
dcLabel | 绘制坐标标值,当进行坐标制度变换时重绘,否则拷贝到物理DC |
dcLines | 每次重绘曲线,拷贝到物理DC |
拷贝顺序如下: