我一直在学习 WebGL 图形课程,我已经到了尝试渲染点云的地步。我已经成功地渲染了其他几个对象,并且已经用动画对象做了一堆。我是 Mac 用户,我主要使用 safari,所以我一直在 safari 上使用 live-server 运行我的测试网站。当尝试将点云实现到我的代码中时,网站上的结果是一堆垃圾。渲染的内容看起来像是一堆随机大小、颜色和位置的矩形闪烁到画布中。
我尝试修改我的比例、转换、重写我的着色器以防我遗漏了什么,最后我只是在 chrome 中运行它并且它运行完美。切换回 safari,一切又乱套了,同样的问题。我所期待的是一个包含在立方体体积内的缓慢旋转的点云。 这是网站上元素的代码。
const canvas = document.querySelector('canvas');
const gl = canvas.getContext('webgl');
const mat4 = glMatrix.mat4;
if (!gl) {
throw new Error('WebGL not supported');
}
function spherePointCloud(pointCount) {
let points = [];
for (let i = 0; i < pointCount; i++) {
const r = () => Math.random() - 0.5; // -.5 < x < 0.5
const outputPoint = [r(), r(), r()];
points.push(...outputPoint);
}
return points;
}
const vertexData = spherePointCloud(1e5);
const positionBuffer = gl.createBuffer();
gl.bindBuffer(gl.ARRAY_BUFFER, positionBuffer);
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertexData), gl.STATIC_DRAW);
const vertexShader = gl.createShader(gl.VERTEX_SHADER);
gl.shaderSource(vertexShader, `
precision mediump float;
attribute vec3 position;
varying vec3 vColor;
uniform mat4 matrix;
void main() {
vColor = vec3(position.xy, 1);
gl_Position = matrix * vec4(position, 1);
}
`);
gl.compileShader(vertexShader);
const fragmentShader = gl.createShader(gl.FRAGMENT_SHADER);
gl.shaderSource(fragmentShader, `
precision mediump float;
varying vec3 vColor;
void main() {
gl_FragColor = vec4(vColor, 1);
}
`);
gl.compileShader(fragmentShader);
console.log(gl.getShaderInfoLog(fragmentShader));
const program = gl.createProgram();
gl.attachShader(program, vertexShader);
gl.attachShader(program, fragmentShader);
gl.linkProgram(program);
const positionLocation = gl.getAttribLocation(program, `position`);
gl.enableVertexAttribArray(positionLocation);
gl.bindBuffer(gl.ARRAY_BUFFER, positionBuffer);
gl.vertexAttribPointer(positionLocation, 3, gl.FLOAT, false, 0, 0);
gl.useProgram(program);
gl.enable(gl.DEPTH_TEST);
const uniformLocations = {
matrix: gl.getUniformLocation(program, `matrix`),
};
const modelMatrix = mat4.create();
const viewMatrix = mat4.create();
const projectionMatrix = mat4.create();
mat4.perspective(projectionMatrix,
75 * Math.PI/180, // vertical field-of-view (angle, radians)
canvas.width/canvas.height, // aspect W/H
1e-4, // near cull distance
1e4 // far cull distance
);
const mvMatrix = mat4.create();
const mvpMatrix = mat4.create();
mat4.translate(modelMatrix, modelMatrix, [0, 0, 0]);
mat4.translate(viewMatrix, viewMatrix, [0, 0.1, 2]);
mat4.invert(viewMatrix, viewMatrix);
function animate() {
requestAnimationFrame(animate);
mat4.rotateY(modelMatrix, modelMatrix, 0.03);
mat4.multiply(mvMatrix, viewMatrix, modelMatrix);
mat4.multiply(mvpMatrix, projectionMatrix, mvMatrix);
gl.uniformMatrix4fv(uniformLocations.matrix, false, mvpMatrix);
gl.drawArrays(gl.POINTS, 0, vertexData.length / 3);
}
animate();
这是在此代码的 safari 上呈现的图像