基于WTL 双缓冲(double buffer)绘图的分析详解

2016-02-19 09:01 5 1 收藏

下面图老师小编要向大家介绍下基于WTL 双缓冲(double buffer)绘图的分析详解,看起来复杂实则是简单的,掌握好技巧就OK,喜欢就赶紧收藏起来吧!

【 tulaoshi.com - 编程语言 】

WTL中有两个Mix-in类: CDoubleBufferImpl和CDoubleBufferWindowImpl,用于创建双缓冲绘图窗口,用法非常简单。
下面创建了一个普通的WTL窗口类,在窗口的客户区中有大量的绘图工作,使用CDoubleBufferImpl类来消除绘图时的闪烁现象:
代码如下:

const COLORREF WHITE_COLOR = RGB(255,255,255);
const COLORREF BLUE_COLOR = RGB(0,0,255);
class CMainWindow :
 public CWindowImplCMainWindow,CWindow,CSimpleWinTraits,
 public CDoubleBufferImplCMainWindow
{
public:
 typedef CMainWindow _thisClass;
 typedef CDoubleBufferImpl_thisClass _baseDblBufImpl;
 BEGIN_MSG_MAP(CMainWindow)
  MSG_WM_CREATE(OnCreate)
  MSG_WM_DESTROY(OnDestroy)
  CHAIN_MSG_MAP(_baseDblBufImpl)
 END_MSG_MAP()
 int OnCreate(LPCREATESTRUCT lpCreateStruct)
 {
  m_RectPen.CreatePen(PS_SOLID,1,BLUE_COLOR);
  return 0;
 }
 void OnDestroy()
 {
  PostQuitMessage(0);
 }

 void OnPaint(CDCHandle)
 {
  CPaintDC dc(m_hWnd);
  DoPaint(dc.m_hDC);
 }
 void DoPaint(CDCHandle dc)
 {
  CRect rc;
  GetClientRect(&rc);
  dc.FillRect(&rc,WHITE_COLOR);
  HPEN hOldPen = dc.SelectPen(m_RectPen);
  const int width = 5;
  int x = 0;
  int count = rc.Width()/width;
  int height = 0;
  for (int i=0; icount; i++)
  {
   height = (int)((double)rand()*rc.Height())/RAND_MAX;
   dc.Rectangle(x,rc.Height(),x+width,rc.Height()-height);
   x += width;
  }
  dc.SelectPen(hOldPen);
 }
 /*
 void DoPaint(CDCHandle dc)
 {
  CRect rc;
  GetClientRect(&rc);
  int width = rc.Width(), height = rc.Height();
  //use GDI+ to draw in the client area
  Graphics g(dc.m_hDC);
  SolidBrush whiteBrush(Color(255,255,255));
  g.FillRectangle(&whiteBrush,0,0,width,height);
  Pen bluePen(Color(0,0,255));
  const int dx = 5;
  int count = width/dx;
  int x = 0, y = 0, h = 0;
  for (int i=0;icount;i++)
  {
   h = ((double)rand()*height)/RAND_MAX;
   g.DrawRectangle(&bluePen,x,y,dx,h);
   x += dx;
  }
 }
 */
private:
 CPen m_RectPen;
};

值得一提的是,Windows Vista操作系统增加了对Double buffered paint的内建支持,这里有一篇文章介绍如何在Win32程序中使用这些API:
Using Windows Vista Built-In Double Buffering
在WTL中使用Vista提供的这一功能非常容易,最新的WTL库中提供了CBufferedPaintImpl和CBufferedPaintWindowImpl两个类,这两个类的用法和前面提到的两个WTL自带的双缓冲类几乎一样。区别仅仅是所重载的DoPaint()函数的参数稍有不同。
对于CBufferedPaintImpl类,所需重载的DoPaint()函数的样子如下所示:
代码如下:

void DoPaint(CDCHandle dc, RECT& rect)
{
 CRect rc(rect);
 dc.FillSolidRect(&rc,WHITE_COLOR);
 HPEN hOldPen = dc.SelectPen(m_RectPen);
 const int width = 5;
 int x = 0;
 int count = rc.Width()/width;
 int height = 0;
 for (int i=0; icount; i++)
 {
  height = (int)((double)rand()*rc.Height())/RAND_MAX;
  dc.Rectangle(x,rc.Height(),x+width,rc.Height()-height);
  x += width;
 }
 dc.SelectPen(hOldPen);
}

来源:http://www.tulaoshi.com/n/20160219/1589182.html

延伸阅读
1,什么是字符编码?     字符(Character)是文字与符号的总称,包括文字、图形符号、数学符号等。一组抽象字符的集合就是字符集(Charset)。字符集的出现是为了信息进行传播储存提供方便。目前常用到字符集有:ASCII,ISO 8859-1,Unicode,GB2312 2,各种编码集有哪些特点? ASCII:     ASCII(Ameri...
有人在Quake III的源代码里面发现这么一段用来求平方根的代码: /*================SquareRootFloat================*/ float SquareRootFloat(float number) {     long i;     float x, y;     const float f = 1.5F;     x = number * 0.5F;     y  = nu...
结构指针变量:结构指针变量的说明和使用一个指针变量用来指向一个结构变量时 结构指针变量中的值是所指向的结构变量的首地址。通过结构指针即可访问该结构变量,这与数组元素的指针和函数指针的情况是相同的。 结构指针变量说明的一般形式为: struct 结构名 * 结构指针变量名 例如: struct stu *pstu;  其访问的一般形式为: (*结...
标签: Web开发
引言 大家都知道可以通过post或者get获得form表单的数据,那么我们如何实现不刷新的提交直接获得页面上的数据呢?这就要借助xmlhttp协议了。xmlhttp是xmldom技术的一部分。   下面的代码就是一个很简单的例子,我们利用xmlhttp技术实现简单的用户登陆。 开始 1.简单的登录页面 login.jsp ...
算法步骤简述: 1.计算图G加入新结点后的图G',加入的新结点0到所有原结点之间距离为0,同时形成新的边集E'; 2.使用Bellman-Ford算法处理G',并形成0结点到各结点的最小距离d。 3.如果Bellman-Ford算法检测出有负权回路则提示FALSE并退出,否则继续。 4.对所有G'中的顶点v,根据0结点到v的最小距离,将h(v)设置为这个值。 5.对所有的边w...

经验教程

635

收藏

85
微博分享 QQ分享 QQ空间 手机页面 收藏网站 回到头部