3D回転変換ツール
2025-11-10
はじめに
3D回転の表現方法は複数ありますね。クォータニオン、オイラー角、回転行列、軸角表現、MRP(Modified Rodrigues Parameters)...。それぞれに長所と短所があり、アプリケーションによって最適な表現が異なったりします。
ゲーム開発でUnityを使っているときはクォータニオン、航空宇宙のシミュレーションではオイラー角やクォータニオン、論文ではMRPが出提案されていたりする。 異なる表現の間を行き来する必要があるとき、マニュアルでの計算は面倒であり、ミスも起きやすい。
そこで、ブラウザ上でインタラクティブに回転表現を変換できるツール「Attitude Converter」を作りました。
デモ: https://attitude-converter.tompython.com/
ソースコード: GitHub
機能
対応する回転表現
- Quaternion(クォータニオン): 4次元の単位ベクトル。ジンバルロックがなく、補間が容易
- Euler Angles(オイラー角): 3つの角度で表現。直感的だがジンバルロックの問題あり
- MRP(Modified Rodrigues Parameters): 3次元で表現。特異点を避けるシャドウセットが存在
- Axis-Angle(軸角表現): 回転軸と回転角で表現
- Rotation Matrix(回転行列): 3×3の直交行列
12種類のオイラー角順序
航空宇宙でよく使われるZYX(Yaw-Pitch-Roll)から、古典力学のZXZ(歳差運動)まで、12種類すべてのオイラー角順序に対応しています。
- Tait-Bryan角: XYZ, XZY, YXZ, YZX, ZXY, ZYX
- 固有オイラー角: XYX, XZX, YXY, YZY, ZXZ, ZYZ
ジンバルロック検出
オイラー角の宿命であるジンバルロック。第2角が±90°(Tait-Bryan角の場合)に近づくと、自動的に警告を表示します。
MRPシャドウセット
MRPは$|\sigma|^2 > 1$になると数値的に不安定になります。Auto Shadowモードでは、自動的にシャドウセット($\sigma' = -\sigma /|\sigma|^2$)に切り替えて、常に$|\sigma|^2 \leq 1$を保証します。
インタラクティブ3Dビュー
React Three Fiberを使った3Dビューで、回転を視覚的に確認できます。リングをドラッグして直接回転を操作することも可能です。
技術スタック
なぜRust + WebAssembly?
回転の計算は浮動小数点演算が中心です。JavaScriptでも十分な性能が出ますが、以下の理由からRust + WASMを選択しました:
- 型安全性: 回転計算は符号やインデックスのミスが致命的。Rustの型システムで多くのバグを防げる(た)
- 将来の拡張性: 姿勢推定やカルマンフィルタなど、より重い計算を追加する可能性
- 学習目的: Rust + WASMの実践的なプロジェクトとして
フロントエンド
- Next.js 14: App Router、Static Export
- React Three Fiber: 3D可視化
- TypeScript: 型安全なUI開発
コア計算
- Rust: 回転計算ロジック
- wasm-bindgen: RustとJavaScriptのブリッジ
- serde_json: データのシリアライズ
実装のポイント
wasm-optとexternref問題
開発中、wasm-optによる最適化後にWASMが動作しなくなる問題に遭遇しました。原因はexternref(Reference Types)機能との互換性問題。解決策としてwasm-optを無効化しました:
[package.metadata.wasm-pack.profile.release]
wasm-opt = false
性能への影響は、このアプリケーションでは無視できるレベルです。
Next.jsでのWASM読み込み
Next.jsのWebpack設定とWASMの相性は難しい部分があります。最終的に、public/ディレクトリにWASMファイルを配置し、動的インポートで読み込む方式に落ち着きました:
const wasm = await import(/* webpackIgnore: true */ '/wasm/attitude_wasm.js');
await wasm.default(wasmBuffer);
おわりに
回転表現の変換は、3Dグラフィックス、ロボティクス、航空宇宙など様々な分野で必要になります。このツールが、そうした場面での作業効率化に役立てば幸いです。
機能要望やバグ報告は、GitHubのIssueでお待ちしています。
Attitude Converter