C++11 や Emscripten と
付き合って1年間の振り返り
Boost.勉強会#17@東京
2015/5/30
今日は何の話?
今日は何の話?
商用ブラウザゲームを開発した話
今日は何の話?
商用ブラウザゲームを開発した話
!
Boost.勉強会だから Flash ではなく
今日は何の話?
商用ブラウザゲームを開発した話
!
Boost.勉強会だから Flash ではなく
!
C++で!!
アジェンダ
Emscripten 概要
C++11 で開発した振り返り
Emscripten 問題と解決策
● サウンド
● フォント
● WebGL
● ファイルシステム
● デバッグ
アンケート
聞いたことある方!
!
(・ω・)ノシ
アジェンダ
Emscripten 概要
C++11 で開発した振り返り
Emscripten 問題と解決策
● サウンド
● フォント
● WebGL
● ファイルシステム
● デバッグ
C/C++ のコードを asm.js にコンパイルし
ブラウザで実行することができる
C / C++ asm.jsLLVM IR
asm.js とは
JavaScript サブセット
静的型付けのような特徴を持ち
低レベルな演算を高速実行
asm.js とは
JavaScript サブセット
静的型付けのような特徴を持ち
低レベルな演算を高速実行
!
Firefox は asm.js に最適化した
JavaScript エンジンを搭載
しているので好相性
移植性
C/C++ で書かれた
既存プロジェクトやライブラリを
修正なしで再利用できる
!
学習コストが下がって
ノウハウと社内資産を生かせる
APIs
OpenGL の API は WebGL に
変換されるのでそのまま使用可能
SDL の API も使えるため
ネイティブ版との差異を吸収する
APIs
ネイティブに近い実行速度を誇る
!
翻訳前の C/C++ コードと比べて
約1.5倍遅い程度
!
手書きのJavaScriptより断然速い!
実行速度
実行速度(現実)
asm.js なら Firefox が圧倒的かと思いきや
実行環境によってまちまち・・・
!
グラフィック処理の負担が大きいゲームでは
『このブラウザが最速』とは明言しづらい
asm.js の今後
IE, Chrome がサポートするかどうか
!
そういう噂はちらほら聞きますが
実現すれば時代の変化に繋がる?
!
http://www.infoq.com/jp/news/2015/03/ie-chrome-asmjs
http://news.mynavi.jp/news/2015/02/23/270/
ゲームエンジン
WebGL 向けエクスポート機能に
Emscripten が使用されている
Unity5.0 Unreal Engine 4.7
Emscripten
概要まとめ
Emscripten 概要まとめ
C/C++ から JavaScript へコンパイル
移植性が高く、生成されたコードも高速
!
主要ブラウザも asm.js をサポートし始め
これからの Web アプリケーションの開発に
注目されている
アジェンダ
Emscripten 概要
C++11 で開発した振り返り
Emscripten 問題と解決策
● サウンド
● フォント
● WebGL
● ファイルシステム
● デバッグ
C++11 で
開発した振り返り
内容
商用ゲームの開発で
C++11, Boost ライブラリを利用
!
得られた効果、教訓の振り返り
はじめに
対象
C++11 以降, Boost ライブラリを
(職場で)利用していない開発者
はじめに
導入したもの
C++11
Boost ライブラリ
!
得られたもの
言語機能
ライブラリの拡張
はじめに
はじめに
ここがよかった
メモリ管理
スマートポインタを利用
メモリ管理の手間が解消
 
ここがよかった
メモリ管理
スマートポインタを利用
メモリ管理の手間が解消
 
delete 呼ばれてなかった
ここで delete しちゃだめ
ここがよかった
無効値の統一
Boost.Optional により実装ごとの
無効値の違いによる手間が解消
ここがよかった
無効値の統一
Boost.Optional により実装ごとの
無効値の違いによる手間が解消
0がエラー?-1がエラー?0が正常?
実装見ないと戻り値の意味がわからん
ここがよかった
auto による型の推論
関数の戻り値などからローカル変数を
生成する場合に型の指定の手間が解消
ここがよかった
auto による型の推論
関数の戻り値などからローカル変数を
生成する場合に型の指定の手間が解消
参照型への & 忘れはよくやらかした
イテレータの型指定めんどうくさい
ここがよかった
auto による型の推論
関数の戻り値などからローカル変数を
生成する場合に型の指定の手間が解消
参照型への & 忘れはよくやらかした
イベントハンドラの実装が容易に
std::function, Boost.Signals2 を利用
!
ラムダ式との併用が強力
!
状態を保持するイベントの実装で
オブジェクトを渡す手間が解消
ここがよかった
イベントハンドラの実装が容易に
std::function, Boost.Signals2 を利用
!
ラムダ式との併用が強力
状態を保持するイベントの実装で
オブジェクトを渡す手間が解消
ここがよかった
関数ポインタでイベント実装だるい
ラムダ式が便利すぎる
関数オブジェクトの生成を簡略化
可読性が向上
!
ここがよかった
ラムダ式が便利すぎる
関数オブジェクトの生成を簡略化
可読性が向上
!
ここがよかった
関数オブジェクトつくるのかったるい
ラムダ式が便利すぎる
関数オブジェクトの生成を簡略化
可読性が向上
便利すぎて調子に乗ったら
shared_ptrのコピーキャプチャで循環参照
参照、this キャプチャでの寿命切れ
ここがよかった
さらによくなりたい
便利なラムダ式でも引数の型の指定が手間
STLとの組み合わせだと顕著
関数テンプレートみたいに使わせろ
さらによくなりたい
便利なラムダ式でも引数の型の指定が手間
STLとの組み合わせだと顕著
!
C++14 のジェネリックラムダでは
引数の型に auto を指定できる
さらによくなりたい
便利なラムダ式でも引数の型の指定が手間
STLとの組み合わせだと顕著
!
C++14 のジェネリックラムダでは
引数の型を auto で指定できる早く C++14 使いたい!!
グラフ構造
Boost.Graph を利用
グラフ(頂点と辺)でマップを実装
ここがよかった
これらにより様々な手間が解消された
開発現場の変化
これらにより様々な手間が解消された
!
コードの質が向上
開発現場の変化
これらにより様々な手間が解消された
!
コードの質が向上
↓
バグの減少
開発現場の変化
これらにより様々な手間が解消された
!
コードの質が向上
↓
バグの減少
↓
BTS が不要に
開発現場の変化
コードの質が向上
手間の解消により作業効率が向上
!
設計、デバッグ、リファクタリングに
充てる時間が増える
開発現場の変化
バグの減少
コードレビュー、自動テストの実施
技術的負債を抑える
!
発生したバグの件数が
過去の開発と比べてもっとも少ない
開発現場の変化
BTS が不要に
開発で使用したコミュニケーションツール
にバグを報告し、修正したらそこに返信
!
BTS を運用するより低コストだった
!
導入コスト、学習コストを上回る効果
開発現場の変化
振り返りまとめ
新機能により簡潔で質のよいコードを書ける
振り返りまとめ
新機能により簡潔で質のよいコードを書ける
!
開発効率の向上により開発現場に変化
振り返りまとめ
新機能により簡潔で質のよいコードを書ける
!
開発効率の向上により開発現場に変化
!
新しい技術に対する学習、関心を忘れない
振り返りまとめ
新機能により簡潔で質のよいコードを書ける
!
開発効率の向上により開発現場に変化
!
新しい技術に対する学習、関心を忘れない
!
導入コスト、学習コストも忘れずに
cpprefjp, boostjp
いつもありがとうございます
!
http://cpprefjp.github.io/
http://boostjp.github.io/
困ったら
アジェンダ
Emscripten 概要
C++11 で開発した振り返り
Emscripten 問題と解決策
● サウンド
● フォント
● WebGL
● ファイルシステム
● デバッグ
Emscripten
問題と解決策
サウンド
サウンド
SDL_mixer を使用
Emscripten は <audio> と Web Audio API を
利用する JavaScript を生成可能
Web Audio API は IE 未対応のため
今回は <audio> を利用する
(Windows10 でサポート予定。将来に期待)
http://blogs.msdn.com/b/ie/archive/2015/03/18/rendering-engine-updates-in-march-for-the-windows-10-technical-preview.aspx
● 精密なフェードはできないと考えていい
● ループは繋ぎ目の無音がはっきりわかる
● 対応ファイル形式のブラウザごとの違い
<audio> の問題
<audio> はゲームに不向き
JavaScript のみでの実装に拘らなければ
プラグインを使うのが賢明
サウンド振り返り
フォント
フォント
FreeType2 を使用
パフォーマンスはそこそこ
Emscripten は SDL_ttf もサポート
ただしユーザーがインストールしていない
フォントは使用不可
WebGL
mat4 から mat3 に変換できない
シェーダーの不具合
mat4 m4;
mat3 m3 = mat3(m4); ← エラー
最新版のIE11.0.3では修正済
https://connect.microsoft.com/IE/feedback/details/810829/glsl-mat3-
constructor-taking-a-mat4-is-not-supported
メソッドが未実装の可能性がある
コンパイル成功したが、実行しても効果がない
実装詳細を確認したら TODO になってた
例:glLightfv: function() { throw 'glLightfv:TODO' }
怪しいと思ったら実装を確認する
!
PATH:/Emscripten/emscripten/(version)/src/library_xxx.js
WebGL の動作確認に役に立つサイト
WebGL 機能毎のテストケース
https://www.khronos.org/registry/webgl/sdk/tests/
webgl-conformance-tests.html
!
WebGL バージョン確認
http://biz.turbulenz.com/sample_assets/
device_initialization.canvas.release.html
ファイルシステム
仮想ファイルシステム
Emscripten で生成した JavaScript は
仮想ファイルシステムを搭載
!
C/C++ の fopen(), std::fstream
によるファイルアクセスが可能
Preload
仮想ファイルシステムに登録したいファイルを
パッキングし JavaScript 実行時に構築する
!
コンパイルオプションで指定
--preload-file image.jpg 別ファイルに出力
--embed-file image.png JSに埋め込む
Preload は最小限
Preload ファイルの肥大化による弊害
● ダウンロード時間増
● ブラウザ展開時間増
● メモリ負担増
特にグラフィック、サウンドデータの
サーバーから非同期読み込みは必須
デバッグ
デバッグ
最適化された JavaScript は理解できず
ブレークポイントを置くのも困難
!
ブラウザのコンソールにログを出力
VisualStudioと併用しネイティブ版を作成
デバッグ情報を JS に埋め込む
コンパイルオプションで指定可能
C/C++ の関数名、変数名を
JavaScript に埋め込んで残す
Release    → 15 MB
関数名を残す → 50 MB 以上
変数名も残す → 100 MB 以上
Emscripten
振り返りまとめ
Emscripten 振り返りまとめ
ブラウザゲーム制作に Emscripten を利用
C++ コードを利用できる有用性
Web の表現力向上とゲームエンジンの対応
実行環境に対する要求スペックは低くない
Powered by
ライブラリ

C++11やemscriptenと付き合って1年間の振り返り