WebGL-翻訳

これまで、WebGLを使用してさまざまな形状を描画し、それらに色を適用する方法について説明してきました。ここで、この章では、三角形を平行移動する方法を示す例を取り上げます。

翻訳

翻訳はの1つです affine transformationsWebGLによって提供されます。平行移動を使用して、xyz平面上で三角形(任意のオブジェクト)を移動できます。三角形[a、b、c]があり、正のX軸に向かって5単位、正のY軸に向かって3単位の位置に三角形を移動するとします。その場合、新しい頂点は[a + 5、b + 3、c +0]になります。つまり、三角形を平行移動するには、各頂点に平行移動距離(tx、ty、tzなど)を追加する必要があります。

なので per-vertex operation, 頂点シェーダープログラムで実行できます。

頂点シェーダーでは、属性とともに、 coordinates(頂点位置を保持する)、並進距離(x、y、z)を保持する一様変数を定義します。後で、この一様変数を座標変数に追加し、結果をに割り当てます。gl_Position 変数。

Note −頂点シェーダーは各頂点で実行されるため、三角形のすべての頂点が変換されます。

三角形を平行移動する手順

三角形を描画して新しい位置に変換するWebGLアプリケーションを作成するには、次の手順が必要です。

Step 1 − Prepare the Canvas and Get the WebGL Rendering Context

このステップでは、を使用してWebGLレンダリングコンテキストオブジェクトを取得します。 getContext()

Step 2 − Define the Geometry and Store it in the Buffer Objects

三角形を描画しているので、三角形の3つの頂点を渡し、それらをバッファに格納する必要があります。

var vertices = [ -0.5,0.5,0.0, -0.5,-0.5,0.0, 0.5,-0.5,0.0, ];

Step 3 − Create and Compile the Shader Programs

このステップでは、頂点シェーダープログラムとフラグメントシェーダープログラムを作成してコンパイルし、これら2つのプログラムをリンクして結合プログラムを作成する必要があります。

  • Vertex Shader−プログラムの頂点シェーダーで、3D座標を格納するためのベクトル属性を定義します。それに加えて、並進距離を格納するための一様変数を定義し、最後に、これら2つの値を加算してに割り当てます。gl_position これは、頂点の最終的な位置を保持します。

var vertCode =
   'attribute vec4 coordinates;' +
   'uniform vec4 translation;'+
   'void main(void) {' +
      ' gl_Position = coordinates + translation;' +
   '}';
  • Fragment Shader −フラグメントシェーダーでは、フラグメントの色を変数gl_FragColorに割り当てるだけです。

var fragCode = 'void main(void) {' +' gl_FragColor = vec4(1, 0.5, 0.0, 1);' +'}';

Step 4 − Associate the Shader Programs to the Buffer Objects

このステップでは、バッファオブジェクトをシェーダープログラムに関連付けます。

Step 5 − Drawing the Required Object

インデックスを使用して三角形を描画しているので、この方法を使用します drawArrays()。このメソッドには、考慮される頂点/要素の数を渡す必要があります。三角形を描いているので、パラメータとして3を渡します。

gl.drawArrays(gl.TRIANGLES, 0, 3);

例–三角形を平行移動する

次の例は、xyz平面上の三角形を平行移動する方法を示しています。

<!doctype html>
<html>
   <body>
      <canvas width = "300" height = "300" id = "my_Canvas"></canvas>
         
      <script>
         /*=================Creating a canvas=========================*/
         var canvas = document.getElementById('my_Canvas');
         gl = canvas.getContext('experimental-webgl'); 
 
         /*===========Defining and storing the geometry==============*/
         var vertices = [
            -0.5,0.5,0.0, 	
            -0.5,-0.5,0.0, 	
            0.5,-0.5,0.0,   
         ];
            
         //Create an empty buffer object and store vertex data            
         var vertex_buffer = gl.createBuffer(); 
			
         //Create a new buffer
         gl.bindBuffer(gl.ARRAY_BUFFER, vertex_buffer);   
			
         //bind it to the current buffer			
         gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW); 
			
         // Pass the buffer data
         gl.bindBuffer(gl.ARRAY_BUFFER, null);  
            
         /*========================Shaders============================*/
            
         //vertex shader source code 
         var vertCode =
            'attribute vec4 coordinates;' + 
            'uniform vec4 translation;'+
            'void main(void) {' +
               '  gl_Position = coordinates + translation;' +
            '}';
            
         //Create a vertex shader program object and compile it              
         var vertShader = gl.createShader(gl.VERTEX_SHADER);
         gl.shaderSource(vertShader, vertCode);
         gl.compileShader(vertShader);
            
   
         //fragment shader source code
         var fragCode =
            'void main(void) {' +
               '   gl_FragColor = vec4(0.0, 0.0, 0.0, 0.1);' +
            '}';

         //Create a fragment shader program object and compile it            
         var fragShader = gl.createShader(gl.FRAGMENT_SHADER);
         gl.shaderSource(fragShader, fragCode);
         gl.compileShader(fragShader);
            
         //Create and use combiened shader program
         var shaderProgram = gl.createProgram();
         gl.attachShader(shaderProgram, vertShader);
         gl.attachShader(shaderProgram, fragShader);
         gl.linkProgram(shaderProgram);
   
         gl.useProgram(shaderProgram);
   
         /* ===========Associating shaders to buffer objects============*/
      
         gl.bindBuffer(gl.ARRAY_BUFFER, vertex_buffer);    
         var coordinatesVar = gl.getAttribLocation(shaderProgram, "coordinates");
         gl.vertexAttribPointer(coordinatesVar, 3, gl.FLOAT, false, 0, 0);   
         gl.enableVertexAttribArray(coordinatesVar); 
   
         /* ==========translation======================================*/
         var Tx = 0.5, Ty = 0.5, Tz = 0.0;
         var translation = gl.getUniformLocation(shaderProgram, 'translation');
         gl.uniform4f(translation, Tx, Ty, Tz, 0.0);
 
         /*=================Drawing the riangle and transforming it========================*/ 

         gl.clearColor(0.5, 0.5, 0.5, 0.9);
         gl.enable(gl.DEPTH_TEST);
   
         gl.clear(gl.COLOR_BUFFER_BIT);
         gl.viewport(0,0,canvas.width,canvas.height);
         gl.drawArrays(gl.TRIANGLES, 0, 3);
      </script>
    </body>
 </html>

この例を実行すると、次の出力が生成されます-