在Win7 x64上使用DrawText表现不佳

Ash*_*ain 8 c++ windows performance mfc

我注意到在MFC应用程序中我正在开发的同时拖动滚动条以平滑地向下滚动文档,当屏幕上包含大约一段文本的块时,帧速率会下降到不连续的水平,但是当它在屏幕外时会变得柔滑.在调查表现时,我发现CDC::DrawText对该段文本负责的单一调用.这是一个优化的发布版本.

QueryPerformanceCounter以前得到DrawText调用的高分辨率测量,如下所示:

QueryPerformanceCounter(...);
pDC->DrawText(some_cstring, some_crect, DT_WORDBREAK);
QueryPerformanceCounter(...);
Run Code Online (Sandbox Code Playgroud)

文本是unicode,lorem-ipsum样式填充,长度为865个字符,并且在给定矩形和字体(Segoe UI,lfHeight= -12,标准正文文本大小)的情况下包裹7位和1位线.根据我的测量结果,单独调用平均需要7.5 ms,奇数峰值需要21 ms.(注意为了跟上60Hz的监视器,你需要大约16ms来渲染每次更新.)

我尝试进行一些更改以提高性能:

  • 删除DT_WORDBREAK性能提高到大约1毫秒(大约快7倍),但只有一行文字进入屏幕,并且只有超过7行断字,这似乎告诉我瓶颈在其他地方.
  • 我是以透明模式(SetBkMode(TRANSPARENT))绘制文本.所以我尝试了带有实心背景填充的不透明模式.没有得到改善.
  • 我认为ClearType渲染可能是罪魁祸首.我改变了字体lfQualityCLEARTYPE_QUALITYNONANTIALIASED_QUALITY.它看起来像带有锋利边缘的垃圾,而且没有任何改进.
  • 根据评论建议,我使用的是CMemDC,但我摆脱了它并直接绘图.它像疯了一样闪烁,没有任何进步.

这是在配备英特尔酷睿2双核P8400 @ 2.26 GHz和4 GB RAM的Windows 7 64位笔记本电脑上运行 - 我不认为它是一个慢速系统.

我每次绘制时都会调用DrawText(),这显然会使用如此慢的函数来破坏性能,特别是如果这些文本块中的几个一次可见的话.这足以让体验变得迟钝.但是,Firefox可以使用更多文本在ClearType中呈现这样的页面,并且似乎可以很好地应对.我究竟做错了什么?如何解决实际DrawText调用的糟糕表现?

Che*_*Alf 7

每次刷新时绘制文本都是浪费.使用双缓冲,即在屏幕外位图中绘制并将其blit到屏幕上.然后,对于滚动,只需根据需要向上或向下或横向复制大部分位图,然后仅绘制无效区域(在将结果blit到屏幕之前).

即使结果太慢,也要将绘制的文本保留在屏幕外的位图中,然后使用blit而不是绘制.

干杯&hth.,