找回密码
 立即注册→加入我们

QQ登录

只需一步,快速开始

搜索
热搜: 下载 VB C 实现 编写
查看: 3825|回复: 0

【性能测试】经典组合,VB6+DX8,2D平面画大量旋转的椭圆,接近最优解。

[复制链接]
发表于 2017-3-26 12:38:38 | 显示全部楼层 |阅读模式

欢迎访问技术宅的结界,请注册或者登录吧。

您需要 登录 才可以下载或查看,没有账号?立即注册→加入我们

×
以下是截图:

128个圆:
128.png

256个圆:
256.png

512个圆:
512.png

1024个圆:
1024.png

2048个圆:
2048.png

4096个圆:
4096.png

8192个圆:
8192.png

16384个圆:
16384.png

32768个圆:
32768.png

其中在我的机器上(i7 6700K 四核心八线程 4 GHz,RAM是DDR4,单通道32GB,频率是2133MHz,显卡是GTX 970)绘制2048个以内的圆能跑满60Hz的帧率(每个圆的分段数将近2048*PI,也就是绘制一个直径2048的圆的时候,它每个像素依然是准确定位的,只有在直径到达4096后才会出现插值)在绘制4096个圆的时候帧率大概会降到30、40Hz,8192的时候卡顿就比较明显了。16384个圆的时候卡顿就十分明显了,而32768的时候,虽然看不到画面在动(它已经几乎全是白色了),但其它窗口的绘制也变慢了。

这里面虽然绘制的圆都是2D的,但我依然使用了Direct3DVertexBuffer8来存储圆的模型。事实上绘制2D或者3D都可以使用顶点缓冲器,它只是一种存储图元形状和属性的缓冲区而已。
我只用了一个顶点缓冲器,里面存储了一个半径为1、分段数为6433(总共6434个顶点,Int(2048*PI)=6433)的圆的二维模型。
绘制尺寸和形状不同的圆,靠的是矩阵变换。我绘制每一个圆的时候,我都要计算一次矩阵。其中我的投影矩阵是自建矩阵,自己弄的类似正交投影一样的玩意儿,它把屏幕的坐标空间由原先的x,y区间为[-1,1]变为了[0,窗口像素尺寸)这样的位置,并且坐标原点被我固定到了左上角。而观察矩阵我用的是单位矩阵。
绘制圆的时候,先用缩放矩阵来设置圆的尺寸缩放,然后用旋转矩阵来转动圆,最后用位移矩阵把圆移动到指定的位置。
在循环遍历圆的时候,每个圆我都要为它进行5次矩阵运算,可能就是这个上面消耗了一些CPU时间,所以在16384的时候它比较卡了。编译exe的时候我勾选了它的那几个优化(用了总比没用好)后,渲染16384个圆的时候比IDE里面运行的看起来快了许多。。

其实DX8是可以用Instancing的,但这需要你在一个顶点缓冲器里存储多个模型,并且用一个可以区分它的实例ID的方式来区分开(比如用纹理坐标或者漫反射颜色中给你提供的那几个域),然后在顶点着色起里面通过读取这个ID来区分它使用的矩阵。但关键是你需要把模型的数据从“线条”D3DPT_LINESTRIP换成“线表”D3DPT_LINELIST,这个过程会降低显卡的一部分性能,其实得不偿失(不过对于3D的图形而言,尤其是原先模型就是三角形表的数据的情况下,这种Instancing方式还是有一定收益的。)

DX9原生支持的Instancing就十分好用了,因为模型的实例化是由显卡负责处理完成的,不需要CPU插手,而且也不需要给模型附加额外的数据。它也能支持不同的模型存储顺序,包括三角形带、三角形扇、三角形表、线条、线表、点表。只不过这玩意儿依然依赖顶点着色器。

后面我测试了一下如果我把圆的分段从2048 * PI 改成 256 * PI后,就算16384个圆它也能跑满60Hz。在处理顶点数据的时候,显卡也是需要一定的流式处理,所以这个时候并行性能并不能十分体现得出来。真正能体现显卡的并行性能的地方其实是对每个像素进行颜色计算的时候,显卡的着色器指令同步运行带来的收益是最大的。

circles.png

源码: Circles.7z (16.01 KB, 下载次数: 21)
源码里面有一套简单的DX资源管理器,能够把设备丢失和重置的操作给包了。相当于写了个保姆。

回复

使用道具 举报

本版积分规则

QQ|Archiver|小黑屋|技术宅的结界 ( 滇ICP备16008837号 )|网站地图

GMT+8, 2024-12-22 10:18 , Processed in 0.035343 second(s), 27 queries , Gzip On.

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表