Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
軽率にBabylon.jsの WebGPUエンジンを使って ComputeShaderに入門した / learn-about-babylonjs-webgpu-computeshader
Search
にー兄さん
September 30, 2023
Technology
0
390
軽率にBabylon.jsの WebGPUエンジンを使って ComputeShaderに入門した / learn-about-babylonjs-webgpu-computeshader
IwakenLab Shaderこんな感じ発表会#2
にー兄さん
September 30, 2023
Tweet
Share
More Decks by にー兄さん
See All by にー兄さん
Babylon.js 7注目機能を 軽率にまとめてみる/whats-new-in-babylonjs-v7
drumath2237
1
53
軽率にVFX Graphと Compute Shaderを 組み合わせるテクニック/integrate-vfxgraph-and-compute-shader
drumath2237
1
52
軽率にVue 3で リアルタイム3Dアプリを作れる ライブラリを作ってみた/vue-with-3d-app
drumath2237
3
1.5k
軽率にBabylon.jsを C#で使う技術 / using-babylonjs-with-csharp
drumath2237
1
380
今こそ軽率に理解したい WebXR Device APIとBabylon.jsの話 / understand-webxr-device-api-and-babylonjs
drumath2237
0
30
Vue・Babylon連携ライブラリ BabyuewJSについて / about-babyuewjs
drumath2237
0
78
Snapdragon Spacesを通して Unity XRプラグインフレームワーク について軽率に学ぶ / about snapdragon spaces sdk and unity xr framework
drumath2237
0
390
Babylon.jsユーザのためのCLIを軽率にnpmで公開した話 / about create babylon app CLI
drumath2237
0
530
軽率な執筆活動 / writing books roughly
drumath2237
0
34
Other Decks in Technology
See All in Technology
20240509 CloudWatch でいろいろなものを監視してみよう
masaruogura
1
120
Autonomous Database Cloud 技術詳細 / adb-s_technical_detail_jp
oracle4engineer
PRO
15
36k
【リラン】AIの光と闇?失敗しないために知っておきたいAIリスクとその対応 ①政府の動き編
tkhresk
0
140
社内での継続的な機械学習勉強会の開催のコツ
yudai00
2
390
.NET GraphQL Client のリアル
sansantech
PRO
1
460
動画配信サービスのフロントエンド実装に学ぶ設計原則
yud0uhu
1
140
大規模言語モデル (LLM)における低精度数値表現
pfn
PRO
3
860
#phpconkagawa レガシーコードにもオブザーバビリティを 〜少しずつ始めるサービス監視〜
yamato_sorariku
0
570
ワールドカフェ再び、そしてロール・ツール群の開発 / World Café Again, and Development of Suites of Roles and Tools
ks91
PRO
0
130
多言語化対応における TypeScript の型定義を通して開発のしやすさについて考えた / TSKaigi TypeScript Multilingualization
nabeliwo
2
400
CloudflareとHonoを使って飲食店のレビューができるLINEアプリを作った
shinaps
1
630
Blazor WASM × Code-first gRPC で始める C# ⼤統⼀理論
sansantech
PRO
1
910
Featured
See All Featured
Creatively Recalculating Your Daily Design Routine
revolveconf
211
11k
VelocityConf: Rendering Performance Case Studies
addyosmani
321
23k
No one is an island. Learnings from fostering a developers community.
thoeni
16
2.1k
The Psychology of Web Performance [Beyond Tellerrand 2023]
tammyeverts
15
1.6k
Become a Pro
speakerdeck
PRO
13
4.6k
Thoughts on Productivity
jonyablonski
60
3.9k
The Cult of Friendly URLs
andyhume
74
5.7k
The Art of Programming - Codeland 2020
erikaheidi
43
12k
Fashionably flexible responsive web design (full day workshop)
malarkey
398
65k
Easily Structure & Communicate Ideas using Wireframe
afnizarnur
188
16k
Building a Modern Day E-commerce SEO Strategy
aleyda
22
6.5k
What the flash - Photography Introduction
edds
64
11k
Transcript
軽率にBabylon.jsの WebGPUエンジンを使って ComputeShaderに入門した Shaderってこんな感じ発表会 #2 にー兄さん(@ninisan_drumath)
にー兄さん(@ninisan_drumath) ソフトウェアエンジニア 株式会社ホロラボ / IwakenLab Unity / ロケーションベースAR / WebAR
/ Babylon.js / Azure Kinect 最新技術を使った検証開発や デモンストレーションが好き 唐突な うちの猫たち→
本日の話: 「WebGPUのComputeShaderって こんな感じ」 Babylon.jsの
アジェンダ - WebGPUとかWGSLとかComputeShaderとか - Babylon.jsでもComputeShaderが使いたい - おわりに
WebGPUとかWGSLとか ComputeShaderとか
WebGPUとは① ブラウザ向けグラフィクスAPIの一種 従来はWebGL・WebGL2などがあり、 WebGL2が主流になろうとしている(ここの温度感あってる?) 今年の5月くらいにPC向けGoogle Chrome 113から 特殊な設定なしで利用できるように
WebGPUとは② 嬉しいところ - 低レベルなAPIを採用され、処理効率が向上 - モダングラフィクスAPIの流れを汲んでいる - コンピュートシェーダが使える これからに期待 -
2023年現在 使える環境が限られている - WebXRでは使えない、はず(要出典)
WGSL WebGPUで採用されているシェーダ言語 Rustっぽい構文 下記はCYOSで生成されたコードの比較(少し調整済み) #version 300 es precision highp float;
in vec3 position; uniform mat4 worldViewProjection; out vec4 vPosition; void main() { vec4 p = vec4(position, 1.f); vPosition = p; gl_Position = worldViewProjection * p; } #include<sceneUboDeclaration> #include<meshUboDeclaration> attribute position : vec3<f32>; varying vPosition : vec4<f32>; @vertex fn main(input: VertexInputs) -> FragmentInputs { let p = vec4<f32>(vertexInputs.position, 1.0); vertexOutputs.vPosition = p; vertexOutputs.position = scene.viewProjection * mesh.world * p; } WGSL GLSL
Compute Shader 汎用的な計算をGPUで行うための仕組み つまりGPGPU(General Purpose GPU) WebGL系ではこの仕組みが無かったので vertex/fragmentシェーダで実現していた WebGPUには標準搭載されており、WGSLで書ける
Babylon.jsでも ComputeShaderが使いたい
完成イメージ
どんなものを作るか GPUパーティクルを意識して 大量のオブジェクトの属性計算をGPGPUで処理したい (今回は90,000パーティクル) 平面上のランダムな位置にパーティクル位置を初期化 StorageBufferにPositionの配列を格納 3D Sin Waveを適用(dispatch) PointsCloudSystemにPosition配列を適用
時間によってアニメーションさせて上記処理を繰り返す
環境 - Windows 10 Home - Google Chrome 117 -
Babylon.js 6.7.0 - WebGPU Engine使用 - Vite + TypeScript - もし素でWebGPUをTSで開発する場合 @webgpu/typesに型定義があります - Babylon.jsでは不要です サンプルはGitHubで公開しています(docs整備中) https://github.com/drumath2237/babylon-compute-shader-sandbox
Babylon.jsにおけるWebGPUとComputeShader WebGPUは ほぼフルサポート 一部機能は動かないらしい 基本的にEngineをWebGPUEngineに差し替えれば 既存のWebGLアプリから移行できる const engine = new WebGPUEngine(renderCanvas,
{ antialias: true, }); await engine.initAsync(); ComputeShaderはWebGPUエンジンでのみ使用可能 > Note that in Babylon.js this is a WebGPU feature only (starting at v5.0), WebGL does not support compute shaders.
ComputeShaderを書く(3dSinWave.wgsl) struct Params { time: f32 } @group(0) @binding(0) var<uniform>
params : Params; @group(0) @binding(1) var<storage,read_write> positionBuffer : array<f32>; @compute @workgroup_size(2,1,1) fn main(@builtin(global_invocation_id) global_id: vec3<u32>) { var particleId = global_id.x * u32(300) + global_id.y; var x = positionBuffer[particleId * u32(3)]; var z = positionBuffer[particleId * u32(3) + u32(2)]; var distance = sqrt(x * x + z * z); positionBuffer[particleId * u32(3) + u32(1)] = sin(distance * 1.2 - params.time); } 拡張機能を入れれば VSCodeで普通に書ける
ComputeShaderインスタンスの作成 Compute Shaderのコードと bindingsのLayoutを定義して インスタンス化 const sinWaveComputeShader = new ComputeShader(
"3d sin wave", engine, { computeSource: computeShaderSource }, { bindingsMapping: { params: { group: 0, binding: 0 }, positionBuffer: { group: 0, binding: 1 }, }, } );
UniformBufferを作成 プリミティブな値は UniformBufferとして渡している 時間によるアニメーションのための float32を渡して更新する let time = 5; const
waveParamsUniformBuffer = new UniformBuffer( engine, undefined, undefined, "params" ); waveParamsUniformBuffer.addUniform("time", 1); waveParamsUniformBuffer.updateFloat("time", time); sinWaveComputeShader.setUniformBuffer( "params", waveParamsUniformBuffer );
Position配列の初期化とStorageBufferの作成 PointCloudSystemと Compute Shaderの相互で 参照するPosition配列(Float32Array) ComputeShaderには StorageBufferに変換して渡している const positionBuffer =
new Float32Array(PARTICLE_COUNT * 3); for (let i = 0; i < PARTICLE_COUNT; i++) { positionBuffer[i * 3] = randomNumberBetween(-10, 10); positionBuffer[i * 3 + 1] = 0; positionBuffer[i * 3 + 2] = randomNumberBetween(-10, 10); } const positionStorage = new StorageBuffer( engine, positionBuffer.byteLength ); positionStorage.update(positionBuffer); sinWaveComputeShader.setStorageBuffer( "positionBuffer", positionStorage);
繰り返しdispatch シーンのレンダリングループで 時間を更新して位置を再計算 dispatchのコスト高そうなので あまりよくない……? scene.registerBeforeRender(async () => { time
+= 0.1; waveParamsUniformBuffer.updateFloat("time", time); waveParamsUniformBuffer.update(); await sinWaveComputeShader.dispatchWhenReady( PARTICLE_ONE_SIDE, PARTICLE_ONE_SIDE ); const res = await positionStorage.read(); positionBuffer.set(new Float32Array(res.buffer)); pointCloud.setParticles(); });
完成
おわりに
まとめと感想 WebGPUのComputeShader気になっていたので 入門できてうれしい Babylon.jsだと普通に動くっぽいのでみんなでやろう
参考 WebGPUがついに利用可能に WebGL以上の高速な描画と、計算処理への可能性 https://ics.media/entry/230426/ IwakenLabShader勉強会でBabylon.jsにおけるComputeShaderでGPUパーティクルを行うデモの準備 https://zenn.dev/drumath2237/scraps/082ff30318fb2e WGSL 仕様メモ https://ikorin2.hatenablog.jp/entry/2023/04/23/213426 Compute
Shaders | Babylon.js Documentation https://doc.babylonjs.com/features/featuresDeepDive/materials/shaders/computeShader