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
WebGL / WebVR for FrontEnd Engineer
Search
yomotsu
February 25, 2017
Technology
4.8k
4
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
WebGL / WebVR for FrontEnd Engineer
yomotsu
February 25, 2017
More Decks by yomotsu
See All by yomotsu
three.jsとRapierでレースゲームが3日でできた話
yomotsu
0
900
PBR in three.js
yomotsu
1
1.4k
dialog要素でつくるモーダルダイアログ
yomotsu
0
1.1k
IE to Edge
yomotsu
1
410
A Camera Control Library for three.js
yomotsu
1
1.5k
Let’s try AR on mobile Web with <model-viewer>
yomotsu
0
600
WebXR: Beyond WebGL
yomotsu
2
1.9k
Non-DOM components with WebGL in Vue.js
yomotsu
5
13k
WebGL Libs for WebApp Frameworks
yomotsu
4
7.9k
Other Decks in Technology
See All in Technology
モダンフロントエンド 開発研修
recruitengineers
PRO
3
560
MIRU 2026 チュートリアル
keisuke198619
0
870
『三匹の子ぶた』から学ぶネットワークセキュリティの昔と今 / Network Security: Then and Now Through the Lens of The Three Little Pigs
nttcom
1
1.8k
Master Dataグループ紹介資料
sansan33
PRO
1
4.8k
ボトムアップ文化が強い組織で セキュリティをどう根付かせていくかの現在進行形の話 / Making Security Stick in a Bottom-Up Organization
yamaguchitk333
0
210
【5分でわかる】セーフィー エンジニア向け会社紹介
safie_recruit
0
53k
【CEDEC2026】『ウマ娘 プリティーダービー』 英語版のキャラクターの方言や口調をローカライズするための創造的アプローチ
cygames
PRO
1
200
新しい SLO が良い感じにハマっている話
z63d
5
2.1k
Forza Horizon 6 のテレメトリ機能で 自動運転に使えそうな学習データを集める話
henjin0
0
150
JavaScript 研修 (2026)
recruitengineers
PRO
1
460
事業価値と Engineering 2026年度版
recruitengineers
PRO
44
22k
toio・myCobotでフィジカルAIっぽいことを行うための検討(とりあえず調査) / フィジカルAI LT(IoTLTによる開催)
you
PRO
0
300
Featured
See All Featured
How to Get Subject Matter Experts Bought In and Actively Contributing to SEO & PR Initiatives.
livdayseo
0
170
Max Prin - Stacking Signals: How International SEO Comes Together (And Falls Apart)
techseoconnect
PRO
0
360
Technical Leadership for Architectural Decision Making
baasie
3
470
Code Review Best Practice
trishagee
74
20k
Odyssey Design
rkendrick25
PRO
2
750
Leveraging LLMs for student feedback in introductory data science courses - posit::conf(2025)
minecr
1
340
The Cost Of JavaScript in 2023
addyosmani
55
10k
Prompt Engineering for Job Search
mfonobong
0
400
How People are Using Generative and Agentic AI to Supercharge Their Products, Projects, Services and Value Streams Today
helenjbeal
1
260
Ten Tips & Tricks for a 🌱 transition
stuffmc
0
160
Design and Strategy: How to Deal with People Who Don’t "Get" Design
morganepeng
133
19k
Designing for Timeless Needs
cassininazir
1
430
Transcript
WebGL / WebVR for FrontEnd Engineer Presented by Akihiro Oyamada
(@yomotsu) Feb 25, 2017
Frontend Engineer at PixelGrid, Inc. Akihiro Oyamada @yomotsu
I don’t talk about WebVR much… Disclaimer...
None
http://yomotsu.net/blog/assets/2016-12-25-xmas/ http://www.welcometofillory.com/ https://plus360degrees.com/uxcars/ http://www.playkeepout.com/
Almost native app looks! Cuz it works on top of
native graphic APIs
None
Sounds difficult? There are libraries!
None
Pros • Strong and large community • Docs and examples
• JS friendly easy APIs • Low level WebGL access Cons • Doesn't follow semver, Breaking changes sometime • Tricky garbage collection
None
None
None
var scene = new THREE.Scene(); var camera = new THREE.PerspectiveCamera(
60, width / height, 1, 1000 ); camera.position.set( 0, 0, 5 ); var renderer = new THREE.WebGLRenderer(); renderer.setSize( width, height ); document.body.appendChild( renderer.domElement ); var light = new THREE.HemisphereLight( 0x443333, 0x332222, 2 ); scene.add( light ); var geometry = new THREE.SphereGeometry( 2, 2, 2 ); var material = new THREE.MeshPhongMaterial( { color: 0xff0000 } ); var mesh = new THREE.Mesh( geometry, material ); scene.add( mesh ); renderer.render( scene, camera );
let’s move onto the main topics for today
• Avoid unnecessary rendering • Reduce drawcalls • Avoid frequent
texture uploading • Consider to use GPU • Compress 3D assets
Avoid unnecessary rendering
Continuously re-rendering Better
demo 19 http://localhost:8000/1_re-rendering/bad.html http://localhost:8000/1_re-rendering/better.html
( function anim () { requestAnimationFrame( anim ); renderer.render( scene,
camera ); } )(); Re-rendering may unnecessary
window.addEventListener( 'resize', function () { const width = window.innerWidth; const
height = window.innerHeight; camera.aspect = width / height; camera.updateProjectionMatrix(); renderer.setSize( width, height ); renderer.render( scene, camera ); // <- don't do this! } ); Re-rendering may unnecessary
( function anim () { requestAnimationFrame( anim ); if (
!myApp.needsUpdate ) { return; } renderer.render( scene, camera ); } )(); Pass re-rendering if unnecessary
var prevPosition = new THREE.Vector3(); var checkCameraPosition = function ()
{ if ( !approximatelyEqual( camera.position, prevPosition ) ) { myApp.needsUpdate = true; } prevPosition.copy( camera.position ); }; Checking “needsUpdate”
window.addEventListener( 'resize', function () { const width = window.innerWidth; const
height = window.innerHeight; camera.aspect = width / height; camera.updateProjectionMatrix(); renderer.setSize( width, height ); myApp.needsUpdate = true; // for next rAF } ); Checking “needsUpdate”
Reduce drawcalls
Continuously repainting Better 8 drawcalls 1 drawcall
demo 27 http://localhost:8000/2_texture-atlas/1_house1.html http://localhost:8000/2_texture-atlas/2_house2.html
.FSHFNBUFSJBMT
3 drawcalls for 3 objects 1 drawcall 3 objects
demo 30 http://localhost:8000/2_texture-atlas/3_house-multi1.html http://localhost:8000/2_texture-atlas/4_house-multi2.html http://localhost:8000/2_texture-atlas/5_house-multi3.html
var houseGeometry = ...; var houseGeometry2 = ...; houseGeometry2.applyMatrix( new
THREE.Matrix4().makeTranslation( -10, 0, 0 ) ); houseGeometry.merge( houseGeometry2 ); Merge geometries
Avoid frequent texture uploading
None
demo 34 http://localhost:8000/3_spriteAnim/bad.html http://localhost:8000/3_spriteAnim/better.html
None
None
$16BOE(16 BSFQIZTJDBMMZTFQBSBUFE
( function anim () { var elapsed = clock.getElapsedTime(); requestAnimationFrame(
anim ); texture.image = images[ frame ]; texture.needsUpdate = true; renderer.render( scene, camera ); frame = ( elapsed * 20 % images.length ) | 0; } )(); Bad: Replacing image
( function anim () { var elapsed = clock.getElapsedTime(); requestAnimationFrame(
anim ); texture.offset.set( frame % frameCol / frameCol, ( frameRow - 1 ) / frameRow - ( ( frame / frameCol ) | 0 ) / frameRow ); renderer.render( scene, camera ); frame = ( elapsed * 20 % frameLength ) | 0; } )(); Better: Use UV offset
None
var rtt = new THREE.WebGLRenderTarget( 512, 512, { minFilter: THREE.LinearFilter,
magFilter: THREE.NearestFilter, format: THREE.RGBFormat } ); renderer.render( sceneRTT, cameraRTT, rtt, true ); RTT
GPU may be utilised
None
demo 44 http://localhost:8000/4_particle/bad.html http://localhost:8000/4_particle/better.html
requestAnimationFrame( anim ); for ( var i = 0, l
= particleLength; i < l; i ++ ) { if ( geometry.attributes.position.array[ i * 3 + 1 ] > - boxHeight * 0.5 ) { geometry.attributes.position.array[ i * 3 + 1 ] -= delta; } else { geometry.attributes.position.array[ i * 3 + 1 ] = boxHeight * 0.5; } }; geometry.attributes.position.needsUpdate = true; Calc in CPU
uniform float time; uniform float height; uniform float scale; void
main () { vec3 pos = vec3( position.x, position.y - time * 1.0, position.z ); pos.y = mod( pos.y, height ) - ( height * 0.5 ); vec4 mvPosition = modelViewMatrix * vec4( pos, 1.0 ); gl_Position = projectionMatrix * mvPosition; gl_PointSize = 1.0; } Calc in GPU (Shader)
Compress 3D assets
3D Model file consists of mostly numbers
3D scanned(ish) Model file
http://localhost:8000/5_compress/bad.html
None
Save 70% of size!
None
zip is an archive format
Multiple files in one zip file
• Contains multi files • Compressed One file • Arrows
you to make a progressive bar • UnZip JS libs are available on GitHub
None
None
https://opensource.googleblog.com/2017/01/introducing-draco-compression-for-3d.html As of Jan 13, 2017
• Compressing lib for 3D assets • Developed by Google
• Decompressor is available in JS (but 800kb emscripten) Might be still early…?
Conclusion
WebGL is… • Click, then it will open • No
installing, but loading • Devices/Browsers are unspecified
• Write your code efficiently • CPU and GPU are
separated • Compress 3D assets Conclusion
WebVR?
https://www.youtube.com/watch?v=cBvCS78ZC1c
https://w3c.github.io/webvr/
Navigator.getVRDisplays() params and states
Navigator.getVRDisplays() params and states •d[ i ].VREyeParameters •FOV •offset (eye
transition) •d[ i ].getPose() •position •orientation (quaternion) and etc…
WebVR is a small API!
None
None
One more thing
None
... mounted () { const scene = this.getScene(); scene.add( this.mesh
); }, beforeDestroy () { const scene = this.getScene(); // optional // this.mesh.material.map.dispose(); // this.mesh.geometry.dispose(); // this.mesh.material.dispose(); scene.remove( this.mesh ); },
WebGL can be used with WebApp frameworks!
for FrontEnd Engineer Presented by Akihiro Oyamada (@yomotsu) Feb
25, 2017 WebGL / WebVR
three.js for FrontEnd Engineer Presented by Akihiro Oyamada (@yomotsu) Feb
25, 2017
gl.finish(); @yomotsu
Ξϯέʔτʹ ͝ڠྗ͍ͩ͘͞ http://bit.ly/2meQNnL gl.finish(); @yomotsu