日別アーカイブ: 2014年5月24日

Emscripten C++/OpenGL ES 2.0 (6) Chrome の速度と IE11/Safari

以前のテストで Chrome の場合だけ極端に遅かった原因が判明しました。
Chrome の WebGL getError() 呼び出しが非常に重かったためです。
getError() 無しのビルドでは 60fps を超える速度となっています。
JavaScript が遅いわけではありませんでした。

Windows 8.1 Chrome 35 (60fps)
emscripten_windows_chrome.png

InternetExplorer でも動くようになったので比較してみます。

Core i7-3615QM / Intel HD Graphics 4000
----------------------------------------------------------
Windows 8.1  Firefox 29         60fps 以上
Windows 8.1  Chrome 35          60fps 以上 (glGetError無し)
Windows 8.1  IE 11           34-60fps

いずれも fps 値が大きい方が高速です。
fps に幅があるものは、前回のテストに従い描画負荷を変更しているため。
「34-60fps」なら一番重い 1. で 34fps 前後、一番軽い 3. で 60fps 以上
出ていることを意味しています。

以下別の PC のテスト

Core i7-2720QM / RADEON HD 6750M
----------------------------------------------------------
Mac OSX 10.9  Firefox 29        60fps 以上
Mac OSX 10.9  Chrome 35         60fps 以上 (glGetError無し)
Mac OSX 10.9  Safari 7          60fps 以上

Windows 8.1   Firefox 29        60fps 以上
Windows 8.1   Chrome 35         60fps 以上 (glGetError無し)
Windows 8.1   IE 11             60fps 以上

AMD Athlon 5350 / GeForce GTX 650
----------------------------------------------------------
Windows 7     Firefox 29        60fps 以上
Windows 7     Chrome 35         60fps 以上 (glGetError無し)
Windows 7     IE 11          50-60fps

Tegra 4 Cortex-A15 / ULP GeForce 72 (Tegra Note 7)
----------------------------------------------------------
Android 4.4   Firefox 29        60fps 以上
Android 4.4   Chrome 35         60fps 以上 (glGetError無し)

↓ Chrome 向け 修正の例: Emscripten から出力された *.js の _glGetError() 内にある
return GLctx.getError() を return 0 に変更。

function _glGetError() {
      // First return any GL error generated by the emscripten library_gl.js interop layer.
      if (GL.lastError) {
        var error = GL.lastError;
        GL.lastError = 0/*GL_NO_ERROR*/;
        return error;
      } else { // If there were none, return the GL error from the browser GL context.
        //return GLctx.getError();  // ← 削除
	return	0;
      }
    }

Chrome 以外では glGetError() (WebGL の getError()) があってもなくても
速度には影響がないようです。
IE/Safari 共にかなり高速に動作しています。

これまで IE で動かなかった原因は、オプティマイザが
小さい描画の Index を BYTE Size に変換してしまっていたためでした。

また IE は WebGL Extension の対応度があまり高くないようです。
DXT, float texture はすべてのブラウザが対応していますが、
depth_texture, element_index_uint 未対応は IE だけとなっています。

上の Chrome のキャプチャ画面では depth_texture が用いられています。
↓ IE は depth_texture がないので、Tegra2/3 と同じく ShadowMap に
Color Buffer を使用しています。

Windows 8.1 Internet Explorer 11
emscripten_windows_ie

// IE11
GL_VERSION: WebGL 0.93
GL_RENDERER: Internet Explorer
GL_VENDOR: Microsoft
GL_SHADING_LANGUAGE_VERSION: OpenGL ES GLSL 1.00 (WebGL)

Extension:
GL_WEBGL_compressed_texture_s3tc
GL_OES_texture_float
GL_OES_texture_float_linear
GL_EXT_texture_filter_anisotropic
GL_OES_standard_derivatives

// Firefox 29
GL_VERSION: WebGL 1.0
GL_RENDERER: Mozilla
GL_VENDOR: Mozilla
GL_SHADING_LANGUAGE_VERSION: OpenGL ES GLSL 1.00 (WebGL)

Extension:
GL_EXT_texture_filter_anisotropic
GL_OES_element_index_uint
GL_OES_standard_derivatives
GL_OES_texture_float
GL_OES_texture_float_linear
GL_OES_texture_half_float
GL_WEBGL_compressed_texture_s3tc
GL_WEBGL_depth_texture
GL_WEBGL_lose_context
GL_MOZ_WEBGL_lose_context
GL_MOZ_WEBGL_compressed_texture_s3tc
GL_MOZ_WEBGL_depth_texture

// Chrome
GL_VERSION: WebGL 1.0 (OpenGL ES 2.0 Chromium)
GL_RENDERER: WebKit WebGL
GL_VENDOR: WebKit
GL_SHADING_LANGUAGE_VERSION: OpenGL ES GLSL 1.00 (WebGL)

Extension:
GL_ANGLE_instanced_arrays
GL_EXT_texture_filter_anisotropic
GL_WEBKIT_EXT_texture_filter_anisotropic
GL_OES_element_index_uint
GL_OES_standard_derivatives
GL_OES_texture_float
GL_OES_texture_float_linear
GL_OES_texture_half_float
GL_OES_texture_half_float_linear
GL_OES_vertex_array_object
GL_WEBGL_compressed_texture_s3tc
GL_WEBKIT_WEBGL_compressed_texture_s3tc
GL_WEBGL_depth_texture
GL_WEBKIT_WEBGL_depth_texture
GL_WEBGL_lose_context
GL_WEBKIT_WEBGL_lose_context
GL_WEBGL_debug_renderer_info

// Safari 7
GL_VERSION: WebGL 1.0 (2.1 ATI-1.22.25)
GL_RENDERER: WebKit WebGL
GL_VENDOR: WebKit
GL_SHADING_LANGUAGE_VERSION: OpenGL ES GLSL 1.00 (WebGL)

Extension:
GL_OES_texture_float
GL_OES_standard_derivatives
GL_WEBKIT_EXT_texture_filter_anisotropic
GL_OES_vertex_array_object
GL_OES_element_index_uint
GL_WEBGL_lose_context
GL_WEBKIT_WEBGL_compressed_texture_s3tc
GL_WEBKIT_WEBGL_depth_texture

HOST GPU によって多少違いがあります。
OS 毎、GPU 毎のより詳しいデータは下記に載せました。

WebGL Extensions

次回: Emscripten C++/OpenGL ES 2.0 (7) Emscripten の OpenGL API と WebGL

関連エントリ
Emscripten C++/OpenGL ES 2.0 のアプリケーションをブラウザで動かす (5)
Emscripten C++/OpenGL ES 2.0 のアプリケーションをブラウザで動かす (4)
Emscripten C++/OpenGL ES 2.0 のアプリケーションをブラウザで動かす (3)
Emscripten C++/OpenGL ES 2.0 のアプリケーションをブラウザで動かす (2)
Emscripten C++/OpenGL ES 2.0 のアプリケーションをブラウザで動かす (1)
Emscripten C++/OpenGL ES 2.0 のアプリケーションをブラウザで動かす 一覧