from: http://jacksondunstan.com/articles/1617
Stage3D Upload Speed Tester
Since Flash Player 11′s new Stage3D
allows us to utilize hardware-acceleration for 3D graphics, that entails a whole new set of performance we need to consider. Today’s article discusses the performance of uploading data from system memory (RAM) to video memory (VRAM), such as when you upload textures, vertex buffers, and index buffers. Is it faster to upload to one type rather than another? Is it faster to upload from a Vector
, a ByteArray
, or a BitmapData
? Is there a significant speedup when using software rendering so that VRAM is the same as RAM? Find out the answers to all of these questions below.
The below performance test checks the upload speeds in both hardware and software mode of all of these types:
-
Texture
from…- BitmapData
- Vector
- ByteArray
-
VertexBuffer3D
from…- Vector
- ByteArray
-
IndexBuffer3D
from…- Vector
- ByteArray
Check it out:
package { import flash.display3D.*; import flash.display3D.textures.*; import flash.external.*; import flash.display.*; import flash.sampler.*; import flash.system.*; import flash.events.*; import flash.utils.*; import flash.text.*; import flash.geom.*; import com.adobe.utils.*; public class Stage3DUploadTester extends Sprite { private var __stage3D:Stage3D; private var __logger:TextField = new TextField(); private var __context:Context3D; private var __driverInfo:String; private var __texture:Texture; private var __bmdNoAlpha:BitmapData; private var __bmdAlpha:BitmapData; private var __texBytes:ByteArray; private var __vertexBuffer:VertexBuffer3D; private var __vbVector:Vector.<Number>; private var __vbBytes:ByteArray; private var __indexBuffer:IndexBuffer3D; private var __ibVector:Vector.<uint>; private var __ibBytes:ByteArray; public function Stage3DUploadTester() { __stage3D = stage.stage3Ds[0]; __logger.autoSize = TextFieldAutoSize.LEFT; addChild(__logger); // Allocate texture data __bmdNoAlpha = new BitmapData(2048, 2048, false, 0xffffffff); __bmdAlpha = new BitmapData(2048, 2048, true, 0xffffffff); __texBytes = new ByteArray(); var size:int = __texBytes.length = 2048*2048*4; for (var i:int; i < size; ++i) { __texBytes[i] = 0xffffffff; } // Allocate vertex buffer data size = 65535*64; __vbVector = new Vector.<Number>(size); for (i = 0; i < size; ++i) { __vbVector[i] = 1.0; } __vbBytes = new ByteArray(); __vbBytes.length = size*4; for (i = 0; i < size; ++i) { __vbBytes.writeFloat(1.0); } __vbBytes.position = 0; // Allocate index buffer data size = 524287; __ibVector = new Vector.<uint>(size); for (i = 0; i < size; ++i) { __ibVector[i] = 1.0; } __ibBytes = new ByteArray(); __ibBytes.length = size*4; for (i = 0; i < size; ++i) { __ibBytes.writeFloat(1.0); } __ibBytes.position = 0; setupContext(Context3DRenderMode.AUTO); } private function setupContext(renderMode:String): void { __stage3D.addEventListener(Event.CONTEXT3D_CREATE, onContextCreated); __stage3D.requestContext3D(renderMode); } private function onContextCreated(ev:Event): void { __stage3D.removeEventListener(Event.CONTEXT3D_CREATE, onContextCreated); var first:Boolean = __logger.text.length == 0; if (first) { __logger.appendText("Driver,Test,Time,Bytes/Sec\n"); } const width:int = stage.stageWidth; const height:int = stage.stageHeight; __context = __stage3D.context3D; __context.configureBackBuffer(width, height, 0, true); __driverInfo = __context.driverInfo; __texture = __context.createTexture( 2048, 2048, Context3DTextureFormat.BGRA, false ); __vertexBuffer = __context.createVertexBuffer(65535, 64); __indexBuffer = __context.createIndexBuffer(524287); runTests(); if (first) { __context.dispose(); setupContext(Context3DRenderMode.SOFTWARE); } } private function runTests(): void { var beforeTime:int; var afterTime:int; var time:int; beforeTime = getTimer(); __texture.uploadFromBitmapData(__bmdNoAlpha); afterTime = getTimer(); time = afterTime - beforeTime; row("Texture from BitmapData w/o alpha", time, 2048*2048*4); beforeTime = getTimer(); __texture.uploadFromBitmapData(__bmdAlpha); afterTime = getTimer(); time = afterTime - beforeTime; row("Texture from BitmapData w/ alpha", time, 2048*2048*4); beforeTime = getTimer(); __texture.uploadFromByteArray(__texBytes, 0); afterTime = getTimer(); time = afterTime - beforeTime; row("Texture from ByteArray", time, 2048*2048*4); beforeTime = getTimer(); __vertexBuffer.uploadFromVector(__vbVector, 0, 65535); afterTime = getTimer(); time = afterTime - beforeTime; row("VertexBuffer from Vector", time, 65535*64*4); beforeTime = getTimer(); __vertexBuffer.uploadFromByteArray(__vbBytes, 0, 0, 65535); afterTime = getTimer(); time = afterTime - beforeTime; row("VertexBuffer from ByteArray", time, 65535*64*4); beforeTime = getTimer(); __indexBuffer.uploadFromVector(__ibVector, 0, 524287); afterTime = getTimer(); time = afterTime - beforeTime; row("IndexBuffer from Vector", time, 524287*4); beforeTime = getTimer(); __indexBuffer.uploadFromByteArray(__ibBytes, 0, 0, 524287); afterTime = getTimer(); time = afterTime - beforeTime; row("IndexBuffer from ByteArray", time, 524287*4); } private function row(name:String, time:int, bytes:int): void { __logger.appendText( __driverInfo + "," + name + "," + time + "," + (bytes/time).toFixed(2) + "\n" ); } } }
I ran this performance test with the following environment:
- Flex SDK (MXMLC) 4.5.1.21328, compiling in release mode (no debugging or verbose stack traces)
- Release version of Flash Player 11.0.1.152
- 2.4 Ghz Intel Core i5
- Mac OS X 10.7.2
And got these results
OpenGL (Direct blitting) | Texture from BitmapData w/o alpha | 22 | 762600.73 |
OpenGL (Direct blitting) | Texture from BitmapData w/ alpha | 18 | 932067.56 |
OpenGL (Direct blitting) | Texture from ByteArray | 18 | 932067.56 |
OpenGL (Direct blitting) | VertexBuffer from Vector | 42 | 399451.43 |
OpenGL (Direct blitting) | VertexBuffer from ByteArray | 5 | 3355392.00 |
OpenGL (Direct blitting) | IndexBuffer from Vector | 3 | 699049.33 |
OpenGL (Direct blitting) | IndexBuffer from ByteArray | 1 | 2097148.00 |
Software (Direct blitting) | Texture from BitmapData w/o alpha | 12 | 1398101.33 |
Software (Direct blitting) | Texture from BitmapData w/ alpha | 5 | 3355443.20 |
Software (Direct blitting) | Texture from ByteArray | 5 | 3355443.20 |
Software (Direct blitting) | VertexBuffer from Vector | 15 | 1118464.00 |
Software (Direct blitting) | VertexBuffer from ByteArray | 5 | 3355392.00 |
Software (Direct blitting) | IndexBuffer from Vector | 3 | 699049.33 |
Software (Direct blitting) | IndexBuffer from ByteArray | 2 | 1048574.00 |
There is a clear order of speed in all tests, regardless of hardware or software or type of GPU resource being uploaded to:
-
ByteArray
(fastest) Vector
-
BitmapData
(slowest)
Only the magnitude of the advantage changes with this. In particular, if you can manage to upload a vertex or index buffer from a ByteArray
, you’re assured a huge performance win.
Uploading texture data seems much faster in software compared to hardware: a 3x improvement. As for vertex and index buffers, it’s more of a mixed bag. Software is faster when uploading vertex buffers from a Vector
, hardware is faster when uploading index buffers from a ByteArray
, and the rest are a tie. Vertex buffers are curiously quicker to upload than index buffers. The difference is more dramatic with software rendering (3x faster) than hardware rendering (50% faster).
More so than ever before in my performance articles is it important to keep in mind that the performance results posted above are valid only for the test environment that produced them. These numbers may change on Windows, which uses DirectX instead of OpenGL, or any of a number of mobile handsets using OpenGL ES.
相关推荐
网页速度测试工具Page Speed Tester v1.1是一款轻量级的应用程序,专为网页开发者设计,用于检测和优化网站的加载性能。它无需安装且不修改注册表,确保了使用的便捷性和系统的安全性。这款工具的核心功能是分析网页...
这个特定的实现,名为"Typing-speed-tester",是基于JavaScript构建的,这是一种广泛使用的客户端脚本语言,允许在用户的浏览器上运行代码,为用户提供动态、交互式的网页体验。通过结合HTML(超文本标记语言)和CSS...
TCP Tester和TCP_TESTER是两种可能的网络诊断工具,主要用于测试TCP/IP协议栈的功能和性能。TCP(传输控制协议)是互联网协议栈中最核心的部分之一,它负责在两台计算机之间建立可靠的数据传输连接。而TCP Tester则...
SNMP测试工具,如Paessler SNMP Tester,是网络管理员进行故障排查、性能优化和配置验证的重要工具。 Paessler SNMP Tester是一款功能强大的SNMP协议测试软件,它提供了多种测试和诊断功能,帮助用户检查SNMP代理的...
**Modbus TCP Client Tester** 是一个专为PLC(可编程逻辑控制器)设计的通信测试工具,它支持Modbus TCP协议,这是一种广泛应用于工业自动化领域的通信协议。该工具提供了客户端和服务器端两种测试模式,使得用户...
PageSpeedTester一个无须安装,不写注册表的免费小程序。专门用来检查网页的载入速度,特别适应用于网站开发者进行页面加载速度测试。使用非常简单,输入目标网址,设定载入次数即可,如果是多次测试,它会自动给出...
这就是Forex Tester 1.0 登场的原因,它是一款专为外汇交易者设计的模拟测试软件,允许用户在无需实际资金投入的情况下,通过历史数据进行交易实践。本文将深入探讨这款软件的功能、特点以及如何利用其注册码来获取...
《XBox 360手柄测试工具:XBox Tester V1.1详解》 XBox Tester是一款专为XBox 360游戏手柄设计的测试软件,它集成了耳机支持,允许用户全面检查手柄的各项功能是否正常运行。在V1.1版本中,该工具提供了一种直观且...
**Chrome插件-Talend API Tester** Talend API Tester是一款专为后端开发人员设计的Chrome浏览器插件,它提供了强大的接口测试功能,类似于知名的Postman工具。这个插件使得开发者可以在浏览器环境下便捷地测试、...
Paessler SNMP Tester 是一款实用工具,专为网络管理员设计,用于测试和诊断SNMP协议的功能。这款工具的中文版为中国的用户提供了更友好的界面,方便他们进行SNMP相关的测试工作。通过这个工具,用户可以: 1. **...
【Visual Tester】是一款专业的自动化测试工具,主要用于对各种软件、应用程序和系统进行视觉测试。它以其直观易用的界面和高效的功能,使得测试过程既快速又准确,极大地提高了IT行业的测试效率。 在软件开发过程...
网页测速工具PageSpeed Tester是IT领域中一种实用的软件,尤其对于网络维护人员来说,它可以帮助用户实时监测和分析网页加载速度,从而优化网络性能。这款名为"PageSpeedTester_1.0_XiaZaiBa.zip"的压缩包包含了Page...
**IE Tester浏览器测试工具** IE Tester是一款非常实用的软件,专为开发者和网站管理员设计,用于测试网页在不同版本的Internet Explorer(IE)浏览器中的兼容性。它支持从IE5.5到IE11的各个版本,对于那些需要确保...
Rational Performance Tester是一款由IBM公司推出的强大性能测试工具,它专为软件应用系统提供负载和压力测试,确保在高并发、大数据量等复杂环境下的稳定性和性能。在本篇文章中,我们将详细介绍Rational ...
IBM Rational Performance Tester
"ConnTester-2.0.1f1_raknet_unity3d_ConnTester_connect_Tester_"是一个专为Unity3D设计的源代码项目,它利用了RakNet库进行网络连接测试,帮助开发者验证和优化网络连接性能。接下来,我们将深入探讨这个项目的...
`Paessler SNMP Tester` 是一款实用工具,专为测试SNMP通信而设计,能够帮助用户读取SNMP设备的各种OID(Object Identifier,对象标识符)信息,以确保网络设备的SNMP功能正常运行。 SNMP由一系列标准组成,主要...
Snmp_Tester测试软件 压缩包内有"crack.exe"或者"破解补丁.exe"文件
"RegEX Tester"是一款实用的工具,它能帮助用户方便地测试和验证正则表达式的效果,确保它们能够按照预期工作。 在使用RegEX Tester时,首先需要了解的是正则表达式的语法。正则表达式由一系列特殊字符和普通字符...
### Rational Functional Tester for Terminal Application #### 一、概述与背景 在软件开发过程中,回归测试是确保代码修改后不会导致意外结果的关键环节。然而,在许多实际应用中,尤其是在那些依赖于终端应用...