C++实现双缓冲
首先声明下,这篇资料也是整理别人的资料的基础上,总结来的。
在图形图像处理过程中,双缓冲技术是一种比较常见的技术。窗体在响应WM_PAINT消息时,需要对图像进行绘制处理。如果图像绘制次数过多,重绘过于频繁时,或者当要绘制的对象太复杂,尤其是含有位图时,一般计算机便力不从心了。显示器上就会因为刷新过频或者过慢而闪烁。双缓冲就是解决这种问题的技术。
窗体在刷新前,会首先擦除(OnEraseBkgnd)之前的内容,然后利用背景色填充,再调用绘制代码进行绘制。一擦一填一写,就会形成颜色的反差,当反差过于明显且频繁时,闪烁就来了。擦除绘制需要时间去处理。如果不在窗体上直接绘制,而是在“别的地方”绘制好,然后再直接搬过来,就不会有这种问题了。这就是双缓冲的基本原理。
双缓冲技术中,内存就充当了“别的地方”。双缓冲技术分为五步:
1、在内存中申请缓冲区,创建兼容内存;
2、创建位图,并将位图与缓冲区内存相关联起来;
3、在兼容内存里绘制;
4、将绘制好的位图拷贝到当前设备;
5、释放兼容内存。
具体代码实现如下(这是一个绘制同心圆的例子):
CPoint ptCenter;
CRect rect,ellipseRect;
GetClientRect(&rect);
ptCenter = rect.CenterPoint();
CDC dcMem; //用于缓冲作图的内存DC
CBitmap cbBmp; //内存中承载临时图象的位图
dcMem.CreateCompatibleDC(pDC); //申请缓冲区,依附窗口DC创建兼容内存DC
cbBmp.CreateCompatibleBitmap(pDC,rect.Width(),rect.Height());//创建兼容位图
dcMem.SelectObject(&cbBmp); //将位图选择进内存DC
//按原来背景填充客户区,不然会是黑色
dcMem.FillSolidRect(rect,pDC->GetBkColor());
for(int i=;i>;i--) //在内存DC上做同样的同心圆图象
{
ellipseRect.SetRect(ptCenter,ptCenter);
ellipseRect.InflateRect(i*,i*);
dcMem.Ellipse(ellipseRect);
}
/*
//提供下绘制方框、画线等方法
dcMem.FillSolidRect(0,0,nWidth,nHeight,RGB(255,255,255));
//绘图
dcMem.MoveTo(……);
dcMem.LineTo(……);
*/
pDC->BitBlt(,,rect.Width(),rect.Height(), &dcMem,,,SRCCOPY);//将内存DC上的图象拷贝到前台
dcMem.DeleteDC(); //删除DC
该段代码中已经提供了填充客户区的方法,为了提高绘制效率,可以继承OnEraseBkgnd,然后直接返回true就行。
BOOL Test::OnEraseBkgnd(CDC* pDC)
{
//调用父类的OnEraseBkgnd函数,我们屏蔽此调用
//return CView::OnEraseBkgnd(pDC);
return TRUE;
}
C++实现双缓冲的更多相关文章
- C++双缓冲多线程分析大文件词频
实习生活告一段落,我正式从一名.NET程序员转入Java阵营,不得不说刚开始用Java的东西是多么的不习惯,但是经过三个月的使用与开发,我也发现了Java的优势:不在于语言,而在于开源.这意味着有更多 ...
- (转载)GDI+双缓冲
双缓冲在GDI+里可以有效的提高描画效率.改善显示的质量. 下面的代码是一个最简单的双缓冲的模板.可以根据需要,做简单的修改即可. Bitmap CacheImage( [Width], [Heigh ...
- OpenGL中实现双缓冲技术
在OpenGL中实现双缓冲技术的一种简单方法: 1.在调用glutInitDisplayMode函数时, 开启GLUT_DOUBLE,即glutInitDisplayMode(GLUT_RGB | G ...
- MFC双缓冲绘图(2015.09.24)
问题引入: 最近在尝试编写贪吃蛇游戏时遇到这么一个问题:当系统以较快频率向窗口发送WM_PAINT消息时,调用OnPaint()函数在窗口中绘制图形就会发生闪烁现象. 问题分析: 当我们把绘图过程放在 ...
- winform上控件太多,绘制时会逐个出现,通常说双缓冲能解决但实际不能解决的问题的解决方法。
protected override CreateParams CreateParams { get { CreateParams cp = base.CreateParams; cp.ExStyle ...
- Winform打砖块游戏制作step by step第6节---双缓冲应用
一 引子 为了让更多的编程初学者,轻松愉快地掌握面向对象的思考方法,对象继承和多态的妙用,故推出此系列随笔,还望大家多多支持. 二 本节内容---双缓冲应用 1. 主界面截图如下: 2. 什么是双 ...
- OpenGL的消隐与双缓冲
首先是大家可能已经发现,在我们之前提到的所有例子中,在图形的旋转过程中整个图形都有一定程度的闪烁现象,显得图形的过渡极不平滑,这当然不是我们所要的效果,幸好opengl 支 持一个称为双缓存的技术,可 ...
- win32下的双缓冲绘图技术
一:双缓冲原理 为了解决窗口刷新频率过快所带来的闪烁问题,利用双缓冲技术进行绘图.所谓双缓冲技术,就是将资源加载到内存,然后复制内存数据到设备DC(这个比较快),避免了直接在设备DC上绘图(这个比较慢 ...
- VC++绘图时,利用双缓冲解决屏幕闪烁 转载
最近做中国象棋,绘制界面时遇到些问题,绘图过程中屏幕闪烁,估计都会想到利用双缓冲来解决问题,但查了下网上双缓冲的资料,发现基本是MFC的,转化为VC++后,大概代码如下: void DrawBmp(H ...
随机推荐
- 注册Com组件..
开发一些第三方的接口或者功能时..有时会需要接入对方提供Com组件..是一个dll文件.. 这个文件会在你的程序中引用.. 比如一个CMBChina.dll文件..这是招商银行的支付开发时必备的.. ...
- Python开发【第十一篇】:JavaScript
JavaScript是一门编程语言,浏览器内置了JavaScript语言的解释器,所以在浏览器上按照JavaScript语言的规则编写相应代码之,浏览器可以解释并做出相应的处理. 一.如何编写 1.J ...
- Devexpress-1 DataGrid控件
参考资料: 使用XtraGrid自定义列计算 DEV GridControl小结 实现对两列求和后作为新的列
- IOS表情存入MYSQL数据库失败
从 MySQL 5.5.3 开始,MySQL 支持一种 utf8mb4 的字符集,这个字符集能够支持 4 字节的 UTF8 编码的字符. utf8mb4 字符集能够完美地向下兼容 utf8 字符串.在 ...
- 移动端 css实现自适应正圆 ( 宽高随着手机屏幕宽度自适应 )
序言:应朋友要求随手写了一下移动端 css实现自适应正圆 ( 宽高随着手机屏幕宽度自适应 ) ,以备后用 LESS代码: .adaptive-circle { margin: 50px auto 0; ...
- PHP CLI下接受参数的几种方法
PHP CLI(命令行模式下)接受参数有多种方法: (1)使用$argv接受参数 <?php //变量仅在 register_argc_argv 打开时可用. print_r($argc); / ...
- 此请求的查询字符串的长度超过配置的 maxQueryStringLength 值 --不仅wen.fonfig一个地方需要设置
提示已经很明确了... 搜出来的都是: <system.webServer> <security> <requestFiltering> <requestLi ...
- assign与weak区别(面试)
weak 比 assign 多了一个功能就是当属性所指向的对象消失的时候(也就是内存引用计数为0)会自动赋值为 nil ,这样再向 weak 修饰的属性发送消息就不会导致野指针操作crash. 可能不 ...
- SQL Server数据库邮件配置
一.数据库邮件介绍 数据库邮件是从SQL Server数据库引擎中发送电子邮件的企业解决方案,通过使用数据库邮件,数据库应用程序可以向用户发送电子邮件.邮件中可以包含查询结果,还可以包含来自网络中任何 ...
- 在PHP中$_SESSION的使用方法
使用PHP应用session时,将session中的数据存储在服务器上,然后通过客户端传来的sessionID识别客户端的信息,并提取信息. php中的session的常用操作:session的写入. ...