learning webglで学ぶwebgl入門

82
Learning WebGL学ぶWebGL入門 nakamura001

Upload: nakamura001

Post on 28-May-2015

11.690 views

Category:

Technology


0 download

DESCRIPTION

WebGL勉強会 第5回(http://atnd.org/events/11693)で発表をした時のスライドに少し、加筆したもの。WebGLをこれから勉強する方のとっかかりに成る様に意識して作成したので、発表向けというより授業向けに近い内容と成っています。

TRANSCRIPT

Page 1: Learning WebGLで学ぶWebGL入門

Learning WebGLで学ぶWebGL入門

nakamura001

Page 2: Learning WebGLで学ぶWebGL入門

今回はLesson 1の内容を解説

Page 3: Learning WebGLで学ぶWebGL入門

http://learningwebgl.com/blog/?p=28

Lesson 1のURLはこちら

Page 4: Learning WebGLで学ぶWebGL入門

https://github.com/gpjt/webgl-lessons

サンプルコードはこちら

Page 6: Learning WebGLで学ぶWebGL入門

サンプルの内容を確認

Page 7: Learning WebGLで学ぶWebGL入門

プログラム構造の概要解説

Page 8: Learning WebGLで学ぶWebGL入門

<body onload="webGLStart();"> <a href="http://learningwebgl.com/blog/?p=28">&lt;&lt; Back to Lesson 1</a><br />

<canvas id="lesson01-canvas" style="border: none;" width="500" height="500"></canvas>

<br/> <a href="http://learningwebgl.com/blog/?p=28">&lt;&lt; Back to Lesson 1</a><br /></body>

HTML

Page 9: Learning WebGLで学ぶWebGL入門

<body onload="webGLStart();"> <a href="http://learningwebgl.com/blog/?p=28">&lt;&lt; Back to Lesson 1</a><br />

<canvas id="lesson01-canvas" style="border: none;" width="500" height="500"></canvas>

<br/> <a href="http://learningwebgl.com/blog/?p=28">&lt;&lt; Back to Lesson 1</a><br /></body>

HTML

Page 10: Learning WebGLで学ぶWebGL入門

<body onload="webGLStart();"> <a href="http://learningwebgl.com/blog/?p=28">&lt;&lt; Back to Lesson 1</a><br />

<canvas id="lesson01-canvas" style="border: none;" width="500" height="500"></canvas>

<br/> <a href="http://learningwebgl.com/blog/?p=28">&lt;&lt; Back to Lesson 1</a><br /></body>

HTML

Page 11: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

JavaScript

Page 12: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

学習のアドバイス

Page 13: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

学習のアドバイス

Page 14: Learning WebGLで学ぶWebGL入門

先頭が gl. に成っているものはほどんどがOpenGL ESのコマンドをWebGLに

移植したもの(※Learning WebGLの場合)

Page 15: Learning WebGLで学ぶWebGL入門

先頭が gl. に成っているものはほどんどがOpenGL ESのコマンドをWebGLに

移植したもの(※Learning WebGLの場合)

gl.clearColor()↓

glClearColor()

Page 16: Learning WebGLで学ぶWebGL入門

先頭が gl. に成っているものはほどんどがOpenGL ESのコマンドをWebGLに

移植したもの(※Learning WebGLの場合)

gl.clearColor()↓

glClearColor() このワードで検索

Page 17: Learning WebGLで学ぶWebGL入門

注意点glTranslate()

void glTranslated(GLdouble x, GLdouble y, GLdouble z)void glTranslatef(GLfloat x, GLfloat y, GLfloat z)

glTranslated()

glTranslatef()

Page 18: Learning WebGLで学ぶWebGL入門

OpenGLのリファレンス

http://d.hatena.ne.jp/nakamura001/20080918/1221738923

ここでOpenGLやOpenGL ESのリファレンスの一覧を紹介しています

Page 19: Learning WebGLで学ぶWebGL入門

順番に細かく説明

Page 20: Learning WebGLで学ぶWebGL入門

initGL()

Page 21: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 22: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 23: Learning WebGLで学ぶWebGL入門

var gl; function initGL(canvas) { try { gl = canvas.getContext("experimental-webgl"); gl.viewportWidth = canvas.width; gl.viewportHeight = canvas.height; } catch(e) { } if (!gl) { alert("Could not initialise WebGL, sorry :-("); } }

Page 24: Learning WebGLで学ぶWebGL入門

initBuffers()

Page 25: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 26: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 27: Learning WebGLで学ぶWebGL入門

var triangleVertexPositionBuffer; var squareVertexPositionBuffer; function initBuffers() { triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ];

Page 28: Learning WebGLで学ぶWebGL入門

頂点

(X,Y,Z)の3つの情報で指定

Page 29: Learning WebGLで学ぶWebGL入門

右手座標系

XZ

Y主にOpenGLで使われる

Page 30: Learning WebGLで学ぶWebGL入門

右手座標系

XZ

Y主にOpenGLで使われる

Page 31: Learning WebGLで学ぶWebGL入門

左手座標系

X

Y

Z

主にDirectXで使われる

Page 32: Learning WebGLで学ぶWebGL入門

ディスプレイとの対応

XZ

Y

Page 33: Learning WebGLで学ぶWebGL入門

右手座標系

XZ

Y

WebGLはもちろん、OpenGLと同じ右手座標系

Page 34: Learning WebGLで学ぶWebGL入門

右手座標系

XZ

Y

WebGLはもちろん、OpenGLと同じ右手座標系

Page 35: Learning WebGLで学ぶWebGL入門

var triangleVertexPositionBuffer; var squareVertexPositionBuffer; function initBuffers() { triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ];

XZ

Y

Page 36: Learning WebGLで学ぶWebGL入門

var triangleVertexPositionBuffer; var squareVertexPositionBuffer; function initBuffers() { triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ];

XZ

Y

X

Y

Page 37: Learning WebGLで学ぶWebGL入門

var triangleVertexPositionBuffer; var squareVertexPositionBuffer; function initBuffers() { triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ];

XZ

Y

X

Y

Page 38: Learning WebGLで学ぶWebGL入門

var triangleVertexPositionBuffer; var squareVertexPositionBuffer; function initBuffers() { triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ];

XZ

Y

X

Y

Page 39: Learning WebGLで学ぶWebGL入門

var triangleVertexPositionBuffer; var squareVertexPositionBuffer; function initBuffers() { triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ]; gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW); triangleVertexPositionBuffer.itemSize = 3; triangleVertexPositionBuffer.numItems = 3;

頂点数

要素の数

Page 40: Learning WebGLで学ぶWebGL入門

triangleVertexPositionBuffer.itemSize = 3; triangleVertexPositionBuffer.numItems = 3;

ちなみにここで出てきた .itemSize と .numItems はこのサンプルで独自に追加されたプロパティ(メンバ変数)です。※OpenGL ES由来のプロパティでは有りません。

ここで指定した値は実際には他のメソッドの引数として使用されます。※具体的には gl.vertexAttribPointer() と gl.drawArrays() 。

注意!

Page 41: Learning WebGLで学ぶWebGL入門

squareVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, squareVertexPositionBuffer); vertices = [ 1.0, 1.0, 0.0, -1.0, 1.0, 0.0, 1.0, -1.0, 0.0, -1.0, -1.0, 0.0 ]; gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW); squareVertexPositionBuffer.itemSize = 3; squareVertexPositionBuffer.numItems = 4;

四角形

Page 42: Learning WebGLで学ぶWebGL入門

drawScene()

Page 43: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 44: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 45: Learning WebGLで学ぶWebGL入門

function drawScene() { gl.viewport(0, 0, gl.viewportWidth, gl.viewportHeight); gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);

Page 46: Learning WebGLで学ぶWebGL入門

デプスバッファ有り正しい前後関係となる

Page 47: Learning WebGLで学ぶWebGL入門

デプスバッファ無し描画した順番の表示となる

Page 48: Learning WebGLで学ぶWebGL入門

デプスバッファ

•デプスバッファを使うと複雑な前後関係を持ったモデルでも正しい順番で描画される

•デプスバッファ(深度バッファ)はDirectXではZバッファと呼ばれるもの

Page 49: Learning WebGLで学ぶWebGL入門

perspective(45, gl.viewportWidth / gl.viewportHeight, 0.1, 100.0);

詳しくは gluPerspective で検索

Page 50: Learning WebGLで学ぶWebGL入門

loadIdentity();

mvTranslate([-1.5, 0.0, -7.0]);

XZ

Y

Page 51: Learning WebGLで学ぶWebGL入門

loadIdentity();

mvTranslate([-1.5, 0.0, -7.0]);

XZ

Y

詳しくはglTranslateで検索

Page 52: Learning WebGLで学ぶWebGL入門

実際に描画する命令

Page 53: Learning WebGLで学ぶWebGL入門

gl.drawArrays(gl.TRIANGLES, 0, triangleVertexPositionBuffer.numItems);

三角形の描画

Page 54: Learning WebGLで学ぶWebGL入門

gl.drawArrays(gl.TRIANGLES, 0, triangleVertexPositionBuffer.numItems);

三角形の描画

三角形の頂点を個別に指定※複数三角形を描画可能ですが今回は1つしか指定してないので描画される三角形は1つのみです。

Page 55: Learning WebGLで学ぶWebGL入門

gl.drawArrays(gl.TRIANGLE_STRIP, 0, squareVertexPositionBuffer.numItems);

四角形の描画

Page 56: Learning WebGLで学ぶWebGL入門

gl.drawArrays(gl.TRIANGLE_STRIP, 0, squareVertexPositionBuffer.numItems);

四角形の描画

前に指定した「2頂点+新規1頂点」で三角形の頂点を指定

Page 57: Learning WebGLで学ぶWebGL入門

gl.drawArrays(gl.TRIANGLE_STRIP, 0, squareVertexPositionBuffer.numItems);

四角形の描画

前に指定した「2頂点+新規1頂点」で三角形の頂点を指定

http://d.hatena.ne.jp/nakamura001/20081231/1230719279

詳しくはこちらの「GL_TRIANGLE_STRIP」の解説を参照

Page 58: Learning WebGLで学ぶWebGL入門

initShaders()

Page 59: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 60: Learning WebGLで学ぶWebGL入門

function webGLStart() { var canvas = document.getElementById("lesson01-canvas"); initGL(canvas); initShaders(); initBuffers();

gl.clearColor(0.0, 0.0, 0.0, 1.0);

gl.clearDepth(1.0);

gl.enable(gl.DEPTH_TEST); gl.depthFunc(gl.LEQUAL);

setInterval(drawScene, 15); }

Page 61: Learning WebGLで学ぶWebGL入門

var shaderProgram; function initShaders() { var fragmentShader = getShader(gl, "shader-fs"); var vertexShader = getShader(gl, "shader-vs");

shaderProgram = gl.createProgram();

Page 62: Learning WebGLで学ぶWebGL入門

シェーダ

CPUでは無く、GPUで実行される3D処理関連のプログラム

頂点やピクセルを操作する処理を記述

Page 63: Learning WebGLで学ぶWebGL入門

シェーダ

Vertex Shader(頂点シェーダ)

Page 64: Learning WebGLで学ぶWebGL入門

シェーダ

Vertex Shader(頂点シェーダ)

頂点情報を操作

Page 65: Learning WebGLで学ぶWebGL入門

シェーダ

Vertex Shader(頂点シェーダ)

頂点情報を操作

http://www.nvidia.co.jp/object/IO_20011001_6613.html分り易いVertex Shaderの解説ページ(NVIDIAのサイト)

Page 66: Learning WebGLで学ぶWebGL入門

シェーダ

Fragment Shader(フラグメント・シェーダ)

Page 67: Learning WebGLで学ぶWebGL入門

シェーダ

ピクセル情報を操作

Fragment Shader(フラグメント・シェーダ)

Page 68: Learning WebGLで学ぶWebGL入門

GLSL(OpenGL Shading Language)で検索

http://d.hatena.ne.jp/nakamura001/20090927/1254058173

参考書籍などは以前こちらで紹介しましたので宜しければ参照下さい。

Page 69: Learning WebGLで学ぶWebGL入門

より、理解する為に自分で変更してみよう

Page 70: Learning WebGLで学ぶWebGL入門

色を変えてみる<script id="shader-fs" type="x-shader/x-fragment"> #ifdef GL_ES precision highp float; #endif

void main(void) { gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0); }</script>

Page 71: Learning WebGLで学ぶWebGL入門

色を変えてみる<script id="shader-fs" type="x-shader/x-fragment"> #ifdef GL_ES precision highp float; #endif

void main(void) { gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0); }</script>

Page 72: Learning WebGLで学ぶWebGL入門

頂点を変更してみる triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ]; gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW); triangleVertexPositionBuffer.itemSize = 3; triangleVertexPositionBuffer.numItems = 3;

※四角形の方 (gl.TRIANGLE_STRIP) はちょっと頂点の指定方法が直感的で無いので最初は三角形の方の頂点を変更してみるのが良いと思います。

Page 73: Learning WebGLで学ぶWebGL入門

頂点を変更してみる triangleVertexPositionBuffer = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, triangleVertexPositionBuffer); var vertices = [ 0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0 ]; gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW); triangleVertexPositionBuffer.itemSize = 3; triangleVertexPositionBuffer.numItems = 3;

※四角形の方 (gl.TRIANGLE_STRIP) はちょっと頂点の指定方法が直感的で無いので最初は三角形の方の頂点を変更してみるのが良いと思います。

Page 74: Learning WebGLで学ぶWebGL入門

注意点

•描画される三角形は表裏、両面ではなく表面のみ描画される

•法線の向きが表を表す

Page 75: Learning WebGLで学ぶWebGL入門

法線

※これはイメージです。実際にはポリゴンを描画した時に法線が描画される事は有りません。

Page 76: Learning WebGLで学ぶWebGL入門

法線• 面と垂直な線

※これはイメージです。実際にはポリゴンを描画した時に法線が描画される事は有りません。

Page 77: Learning WebGLで学ぶWebGL入門

法線• 面と垂直な線 • 面の向きを表す。法線の向きが面の表

※これはイメージです。実際にはポリゴンを描画した時に法線が描画される事は有りません。

Page 78: Learning WebGLで学ぶWebGL入門

法線• 面と垂直な線 • 面の向きを表す。法線の向きが面の表• 主にライティングの計算時に利用される

※これはイメージです。実際にはポリゴンを描画した時に法線が描画される事は有りません。

Page 79: Learning WebGLで学ぶWebGL入門

法線• 面と垂直な線

これが法線

• 面の向きを表す。法線の向きが面の表• 主にライティングの計算時に利用される

※これはイメージです。実際にはポリゴンを描画した時に法線が描画される事は有りません。

Page 80: Learning WebGLで学ぶWebGL入門

右手座標系の場合はこの様に手で法線を握ったときの親指以外が指している向き(反時計回り)の順番で頂点を指定する必要が有ります。もし、逆順(時計回り)に指定すると面の向きが逆になります。

Page 81: Learning WebGLで学ぶWebGL入門

使用しているライブラリを見てみよう

Page 82: Learning WebGLで学ぶWebGL入門

使用ライブラリ

<script type="text/javascript" src="sylvester.js"></script><script type="text/javascript" src="glUtils.js"></script>

http://sylvester.jcoglan.com/Sylvesterのサイト

※sylvester.src.js が無圧縮状態のコード