WebGL - Zeichnen eines Quad

Im vorherigen Kapitel haben wir die verschiedenen Zeichenmodi von WebGL erläutert. Wir können auch Indizes verwenden, um Primitive in einem dieser Modi zu zeichnen. Um Modelle in WebGL zu zeichnen, müssen wir eines dieser Grundelemente auswählen und das erforderliche Netz zeichnen (dh ein Modell, das mit einem oder mehreren Grundelementen erstellt wurde).

In diesem Kapitel zeigen wir anhand eines Beispiels, wie mit WebGL ein Viereck gezeichnet wird.

Schritte zum Zeichnen eines Vierecks

Die folgenden Schritte sind erforderlich, um eine WebGL-Anwendung zum Zeichnen eines Vierecks zu erstellen.

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

In diesem Schritt erhalten wir das WebGL-Rendering-Kontextobjekt mit getContext().

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

Ein Quadrat kann mit zwei Dreiecken gezeichnet werden. In diesem Beispiel stellen wir die Eckpunkte für zwei Dreiecke (mit einer gemeinsamen Kante) und Indizes bereit.

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

indices = [3,2,1,3,1,0];

Step 3 − Create and Compile the Shader Programs

In diesem Schritt müssen Sie die Programme Vertex Shader und Fragment Shader schreiben, kompilieren und ein kombiniertes Programm erstellen, indem Sie diese beiden Programme verknüpfen.

  • Vertex Shader - Im Vertex-Shader des Programms definieren wir das Vektorattribut, um 3D-Koordinaten zu speichern und zuzuweisen gl_position.

var vertCode =
   'attribute vec3 coordinates;' +
   'void main(void) {' +
      ' gl_Position = vec4(coordinates, 1.0);' +
   '}';
  • Fragment Shader - Im Fragment-Shader weisen wir dem einfach die Fragmentfarbe zu gl_FragColor Variable.

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

Step 4 − Associate the Shader Programs to Buffer Objects

In diesem Schritt ordnen wir die Pufferobjekte dem Shader-Programm zu.

Step 5 − Drawing the Required Object

Da wir zwei Dreiecke zeichnen, um mithilfe von Indizes ein Quad zu bilden, verwenden wir die Methode drawElements(). An diese Methode müssen wir die Anzahl der Indizes übergeben. Der Wert vonindices.length gibt die Anzahl der Indizes an.

gl.drawElements(gl.TRIANGLES, indices.length, gl.UNSIGNED_SHORT,0);

Beispiel - Zeichnen Sie ein Viereck

Das folgende Programm zeigt, wie Sie eine WebGL-Anwendung zum Zeichnen eines Vierecks erstellen.

<!doctype html>
<html>
   <body>
      <canvas width = "570" height = "570" 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,
            0.5,0.5,0.0 
         ];

         indices = [3,2,1,3,1,0];

         // Create an empty buffer object to store vertex buffer
         var vertex_buffer = gl.createBuffer();

         // Bind appropriate array buffer to it
         gl.bindBuffer(gl.ARRAY_BUFFER, vertex_buffer);

         // Pass the vertex data to the buffer
         gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW);

         // Unbind the buffer
         gl.bindBuffer(gl.ARRAY_BUFFER, null);

         // Create an empty buffer object to store Index buffer
         var Index_Buffer = gl.createBuffer();

         // Bind appropriate array buffer to it
         gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, Index_Buffer);

         // Pass the vertex data to the buffer
         gl.bufferData(gl.ELEMENT_ARRAY_BUFFER, new Uint16Array(indices), gl.STATIC_DRAW);

         // Unbind the buffer
         gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, null);

         /*====================== Shaders =======================*/

         // Vertex shader source code
         var vertCode =
            'attribute vec3 coordinates;' +
            'void main(void) {' +
               ' gl_Position = vec4(coordinates, 1.0);' +
            '}';

         // Create a vertex shader object
         var vertShader = gl.createShader(gl.VERTEX_SHADER);

         // Attach vertex shader source code
         gl.shaderSource(vertShader, vertCode);

         // Compile the vertex shader
         gl.compileShader(vertShader);

         // Fragment shader source code
         var fragCode =
            'void main(void) {' +
               ' gl_FragColor = vec4(0.0, 0.0, 0.0, 0.1);' +
            '}';

         // Create fragment shader object 
         var fragShader = gl.createShader(gl.FRAGMENT_SHADER);

         // Attach fragment shader source code
         gl.shaderSource(fragShader, fragCode);

         // Compile the fragmentt shader
         gl.compileShader(fragShader);

         // Create a shader program object to
         // store the combined shader program
         var shaderProgram = gl.createProgram();

         // Attach a vertex shader
         gl.attachShader(shaderProgram, vertShader);

         // Attach a fragment shader
         gl.attachShader(shaderProgram, fragShader);

         // Link both the programs
         gl.linkProgram(shaderProgram);

         // Use the combined shader program object
         gl.useProgram(shaderProgram);

         /* ======= Associating shaders to buffer objects =======*/

         // Bind vertex buffer object
         gl.bindBuffer(gl.ARRAY_BUFFER, vertex_buffer);

         // Bind index buffer object
         gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, Index_Buffer); 

         // Get the attribute location
         var coord = gl.getAttribLocation(shaderProgram, "coordinates");

         // Point an attribute to the currently bound VBO
         gl.vertexAttribPointer(coord, 3, gl.FLOAT, false, 0, 0);

         // Enable the attribute
         gl.enableVertexAttribArray(coord);

         /*============= Drawing the Quad ================*/

         // Clear the canvas
         gl.clearColor(0.5, 0.5, 0.5, 0.9);

         // Enable the depth test
         gl.enable(gl.DEPTH_TEST);

         // Clear the color buffer bit
         gl.clear(gl.COLOR_BUFFER_BIT);

         // Set the view port
         gl.viewport(0,0,canvas.width,canvas.height);

         // Draw the triangle
         gl.drawElements(gl.TRIANGLES, indices.length, gl.UNSIGNED_SHORT,0);
      </script>
   </body>
</html>

Wenn Sie dieses Beispiel ausführen, wird die folgende Ausgabe erzeugt: