Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
WebGL / WebVR for FrontEnd Engineer
Search
Sponsored
·
Ship Features Fearlessly
Turn features on and off without deploys. Used by thousands of Ruby developers.
→
yomotsu
February 25, 2017
Technology
4.9k
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
1k
PBR in three.js
yomotsu
1
1.5k
dialog要素でつくるモーダルダイアログ
yomotsu
0
1.1k
IE to Edge
yomotsu
1
410
A Camera Control Library for three.js
yomotsu
1
1.6k
Let’s try AR on mobile Web with <model-viewer>
yomotsu
0
610
WebXR: Beyond WebGL
yomotsu
2
2k
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
You Have Agency(サンキュー、Ruby)
snoozer05
PRO
5
640
Vue で書く 空間コンピューティング、TresJS と WebXR を使ったXR デバイスのフロントエンド開発
hiranuma
0
150
Consistency for mere mortals - A gentle guide to consistency
ufried
0
120
デザインレビューは自動化できるのか?─ Flutter × Figma で UI 品質保証を考える
techiro
2
720
[General] 개발자로 해외 기업에서 일하기
skydoves
1
250
AIコーディングエージェント開発_全体像
happysamurai294
0
150
AIがGISを代替する日:〜すべてをAIが創る時代に、私たちがFOSS4Gに関わる意味〜
lehupa
0
190
Flutter Widget Previewerで始めるUIプレビューとVRTの自動化
sakusaku3939
0
190
Content Mapper APIの応用例~CSS Modules、言語ファイル~
uhyo
2
490
仕様駆動開発の、その先へ。決める力と確かめる仕組み
inariku
1
160
Systems Manager AgentがインストールされたPCを紛失した時の対策を考えてみた
amarelo_n24
1
110
渡米前の準備を制す!re:Invent 2026徹底準備術 / The Ultimate Preparation Guide for re:Invent 2026
yuj1osm
1
490
Featured
See All Featured
Bridging the Design Gap: How Collaborative Modelling removes blockers to flow between stakeholders and teams @FastFlow conf
baasie
0
750
Designing Dashboards & Data Visualisations in Web Apps
destraynor
232
55k
How to build a perfect <img>
jonoalderson
1
6.2k
Impact Scores and Hybrid Strategies: The future of link building
tamaranovitovic
0
480
What Being in a Rock Band Can Teach Us About Real World SEO
427marketing
0
1.1k
Visual Storytelling: How to be a Superhuman Communicator
reverentgeek
2
740
The Spectacular Lies of Maps
axbom
PRO
1
1.1k
Stop Working from a Prison Cell
hatefulcrawdad
274
21k
Lightning talk: Run Django tests with GitHub Actions
sabderemane
0
310
First, design no harm
axbom
PRO
2
1.4k
Agile that works and the tools we love
rasmusluckow
331
22k
Ten Tips & Tricks for a 🌱 transition
stuffmc
1
280
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