WebGL绘制三角形

WebGL绘制三角形

1. 初始化WebGL context

/**
 * Initialize the context of WebGL
 */
function initWebgl() {
  const canvas = document.querySelector('#glcanvas');
  const gl = canvas.getContext('webgl');

  // If we don't have WebGL, print tip
  if (!gl) {
    console.log('%c%s', 'color: red', 'Unable to initialize WebGL, your browser or machine may not support it.');
    return;
  }

  // Set the viewport of context
  gl.viewport(0, 0, canvas.clientWidth, canvas.clientHeight);

  return gl;
}

2. 初始化WebGLShader着色器对象

/**
 * Initialize the shader
 */
function initShader(gl, type, source) {
  // Create the shader
  const shader = gl.createShader(type);

  // Send the source to shader
  gl.shaderSource(shader, source);

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

  // If compiling shader failed, print tip
  if (!gl.getShaderParameter(shader, gl.COMPILE_STATUS)) {
    console.log('%c%s', 'color: red', 'An error occurred compiling shaders: ' + gl.getShaderInfoLog(shader));
    return null;
  }

  return shader;
}

3. 初始化WebGLProgram对象

/**
 * Initialize the shader program
 */
function initShaderProgram(gl, vsShader, fsShader) {
  // Create the program
  const program = gl.createProgram();

  // Attach the shaders to shader program
  gl.attachShader(program, vsShader);
  gl.attachShader(program, fsShader);

  // Tell WebGL the shader program we'll use to draw
  gl.linkProgram(program);

  // See if link shader program failed, print tip
  if (!gl.getProgramParameter(program, gl.LINK_STATUS)) {
    console.log('%c%s', 'color: red', 'Unable to initialize the shader program: ' + gl.getProgramInfoLog(program));
    return null;
  }

  gl.useProgram(program);

  return program;
}

4. 初始化保存顶点数据的WebGLBuffer对象

/**
 * Initialize the buffer
 */
function initBuffer(gl, shaderProgram) {
  // Positions of vertice 
  const verticePositions = [
    0.0, 1.0, 0.0,
    -1.0, -1.0, 0.0,
    1.0, -1.0, 0.0
  ];

  // Create the buffer
  const buffer = gl.createBuffer();

  // Tell WebGL the buffer we'll use to draw
  gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
  gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(verticePositions), gl.STATIC_DRAW);

  // Bind attribute vertexPosition
  let positionBound;
  gl.bindAttribLocation(shaderProgram, positionBound, 'vertexPosition');

  return { buffer, positionBound };
}

5. 绘制图元

/**
 * Draw scene
 */
function drawScene(gl, position, buffer) {
  // Clear to black, fully opaque
  gl.clearColor(0.0, 0.0, 0.0, 1.0);
  gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);

  // Enable to use vertex attribute array
  gl.enableVertexAttribArray(position);

  // Set the pointer of vertex attribute
  gl.vertexAttribPointer(position, 3, gl.FLOAT, false, 12, 0);

  // Draw
  gl.drawArrays(gl.TRIANGLES, 0, 3);
}

6. 汇总以上方法至入口函数中,并调用

/**
 * Entry
 */
function entry() {
  // Get WebGL's context
  const gl = initWebgl();

  // Vertex source
  const vsSource = `
    attribute vec4 vertexPosition;

    void main(void) {
      gl_Position = vertexPosition;
    }
  `;

  // Fragment source
  const fsSource = `
    void main(void) {
      gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0);
    }
  `;

  // Get vertex shader
  const vertexShader = initShader(gl, gl.VERTEX_SHADER, vsSource);
  
  // Get fragment shader
  const fragmentShader = initShader(gl, gl.FRAGMENT_SHADER, fsSource);

  // Get shader program
  const shaderProgram = initShaderProgram(gl, vertexShader, fragmentShader);

  // Get buffer and the reference of vertexPosition
  const { buffer, positionBound } = initBuffer(gl, shaderProgram);

  // Draw the scene
  drawScene(gl, positionBound, buffer);
}

// Call entry method
entry();

7. 总结

WebGL的api很多,要多手打demo(最好注释也写全面,加深记忆),不能偷懒...

posted @   刘狗蛋Alison  阅读(65)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 一个费力不讨好的项目,让我损失了近一半的绩效!
· 清华大学推出第四讲使用 DeepSeek + DeepResearch 让科研像聊天一样简单!
· 实操Deepseek接入个人知识库
· 易语言 —— 开山篇
· CSnakes vs Python.NET:高效嵌入与灵活互通的跨语言方案对比
点击右上角即可分享
微信分享提示