- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我正在尝试在 webgl 中渲染一个球体,我正在使用来自 webglfundamentals 的方法但不知何故,在我的程序中,球体只渲染到 20%。在 chrome 中我得到这个错误:L ERROR :GL_INVALID_OPERATION : glDrawArrays: attempt to access out of range vertices in attribute 1
var canvas;
var gl;
var index = 0;
var pointsArray = [];
var normalsArray = [];
var indexArray = [];
var colorArray = [];
var near = -10;
var far = 10;
var radius = 1.5;
var theta = 0.0;
var phi = 0.0;
var dr = 5.0 * Math.PI/180.0;
var left = -3.0;
var right = 3.0;
var ytop =3.0;
var bottom = -3.0;
var va = vec4(0.0, 0.0, -1.0,1);
var vb = vec4(0.0, 0.942809, 0.333333, 1);
var vc = vec4(-0.816497, -0.471405, 0.333333, 1);
var vd = vec4(0.816497, -0.471405, 0.333333,1);
var lightPosition = vec4(0.0, 1.0, 1.0, 0.0 );
var lightAmbient = vec4(0.2, 0.2, 0.2, 1.0 );
var lightDiffuse = vec4( 1.0, 1.0, 1.0, 1.0 );
var lightSpecular = vec4( 1.0, 1.0, 1.0, 1.0 );
var materialAmbient = vec4( 1.0, 0.0, 1.0, 1.0 );
var materialDiffuse = vec4( 1.0, 0.0, 0.0, 1.0 );
var materialSpecular = vec4( 1.0, 0.8, 0.0, 1.0 );
var materialShininess = 100.0;
var ctm;
var ambientColor, diffuseColor, specularColor;
var texture;
var modelViewMatrix, projectionMatrix;
var modelViewMatrixLoc, projectionMatrixLoc;
var eye;
var at = vec3(0.0, 0.0, 0.0);
var up = vec3(0.0, 1.0, 0.0);
var iBuffer;
function createSphereVertices(
radius,
subdivisionsAxis,
subdivisionsHeight,
opt_startLatitudeInRadians,
opt_endLatitudeInRadians,
opt_startLongitudeInRadians,
opt_endLongitudeInRadians) {
if (subdivisionsAxis <= 0 || subdivisionsHeight <= 0) {
throw Error('subdivisionAxis and subdivisionHeight must be > 0');
}
opt_startLatitudeInRadians = opt_startLatitudeInRadians || 0;
opt_endLatitudeInRadians = opt_endLatitudeInRadians || Math.PI;
opt_startLongitudeInRadians = opt_startLongitudeInRadians || 0;
opt_endLongitudeInRadians = opt_endLongitudeInRadians || (Math.PI * 2);
var latRange = opt_endLatitudeInRadians - opt_startLatitudeInRadians;
var longRange = opt_endLongitudeInRadians - opt_startLongitudeInRadians;
// We are going to generate our sphere by iterating through its
// spherical coordinates and generating 2 triangles for each quad on a
// ring of the sphere.
// var numVertices = (subdivisionsAxis + 1) * (subdivisionsHeight + 1);
var positions = [];
// var normals = webglUtils.createAugmentedTypedArray(3, numVertices);
// var texCoords = webglUtils.createAugmentedTypedArray(2 , numVertices);
// Generate the individual vertices in our vertex buffer.
for (var y = 0; y <= subdivisionsHeight; y++) {
for (var x = 0; x <= subdivisionsAxis; x++) {
// Generate a vertex based on its spherical coordinates
var u = x / subdivisionsAxis;
var v = y / subdivisionsHeight;
var theta = longRange * u;
var phi = latRange * v;
var sinTheta = Math.sin(theta);
var cosTheta = Math.cos(theta);
var sinPhi = Math.sin(phi);
var cosPhi = Math.cos(phi);
var ux = cosTheta * sinPhi;
var uy = cosPhi;
var uz = sinTheta * sinPhi;
positions.push(vec4(radius * ux, radius * uy, radius * uz,1.0));
normalsArray.push(vec4(ux, uy, uz,1.0));
// texCoords.push(1 - u, v);
}
}
var numVertsAround = subdivisionsAxis + 1;
// var indices = webglUtils.createAugmentedTypedArray(3, subdivisionsAxis * subdivisionsHeight * 2, Uint16Array);
for (var x = 0; x < subdivisionsAxis; x++) {
for (var y = 0; y < subdivisionsHeight; y++) {
// Make triangle 1 of quad.
pointsArray.push(positions[(y + 0) * numVertsAround + x]);
pointsArray.push(positions[(y + 0) * numVertsAround + x + 1]);
pointsArray.push(positions[(y + 1) * numVertsAround + x]);
// Make triangle 2 of quad.
pointsArray.push(positions[(y + 1) * numVertsAround + x]);
pointsArray.push(positions[(y + 0) * numVertsAround + x + 1]);
pointsArray.push(positions[(y + 1) * numVertsAround + x + 1]);
index +=6;
}
}
}
window.onload = function init() {
canvas = document.getElementById( "gl-canvas" );
gl = WebGLUtils.setupWebGL( canvas );
if ( !gl ) { alert( "WebGL isn't available" ); }
gl.viewport( 0, 0, canvas.width, canvas.height );
gl.clearColor( 0.0, 0.0, 0.0, 1.0 );
gl.enable(gl.DEPTH_TEST);
//
// Load shaders and initialize attribute buffers
//
var program = initShaders( gl, "vertex-shader", "fragment-shader" );
gl.useProgram( program );
createSphereVertices(1,12,12);
ambientProduct = mult(lightAmbient, materialAmbient);
diffuseProduct = mult(lightDiffuse, materialDiffuse);
specularProduct = mult(lightSpecular, materialSpecular);
var nBuffer = gl.createBuffer();
gl.bindBuffer( gl.ARRAY_BUFFER, nBuffer);
gl.bufferData( gl.ARRAY_BUFFER, flatten(normalsArray), gl.STATIC_DRAW );
var vNormal = gl.getAttribLocation( program, "vNormal" );
gl.vertexAttribPointer( vNormal, 4, gl.FLOAT, false, 0, 0 );
gl.enableVertexAttribArray( vNormal);
var vBuffer = gl.createBuffer();
gl.bindBuffer(gl.ARRAY_BUFFER, vBuffer);
gl.bufferData(gl.ARRAY_BUFFER, flatten(pointsArray), gl.STATIC_DRAW);
var vPosition = gl.getAttribLocation( program, "vPosition");
gl.vertexAttribPointer(vPosition, 4, gl.FLOAT, false, 0, 0);
gl.enableVertexAttribArray(vPosition);
modelViewMatrixLoc = gl.getUniformLocation( program, "modelViewMatrix" );
projectionMatrixLoc = gl.getUniformLocation( program, "projectionMatrix" );
gl.uniform4fv( gl.getUniformLocation(program,
"ambientProduct"),flatten(ambientProduct) );
gl.uniform4fv( gl.getUniformLocation(program,
"diffuseProduct"),flatten(diffuseProduct) );
gl.uniform4fv( gl.getUniformLocation(program,
"specularProduct"),flatten(specularProduct) );
gl.uniform4fv( gl.getUniformLocation(program,
"lightPosition"),flatten(lightPosition) );
gl.uniform1f( gl.getUniformLocation(program,
"shininess"),materialShininess );
render();
}
function render() {
gl.clear( gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
eye = vec3(radius*Math.sin(theta)*Math.cos(phi),
radius*Math.sin(theta)*Math.sin(phi), radius*Math.cos(theta));
modelViewMatrix = lookAt(eye, at , up);
projectionMatrix = ortho(left, right, bottom, ytop, near, far);
gl.uniformMatrix4fv(modelViewMatrixLoc, false, flatten(modelViewMatrix) );
gl.uniformMatrix4fv(projectionMatrixLoc, false, flatten(projectionMatrix) );
for( var i=0; i<index; i+=3)
gl.drawArrays( gl.TRIANGLES, i, 3);
window.requestAnimFrame(render);
}
project1.html
<!DOCTYPE html>
<html>
<script id="vertex-shader" type="x-shader/x-vertex">
attribute vec4 vPosition;
attribute vec4 vNormal;
varying vec3 N, L, E;
uniform mat4 modelViewMatrix;
uniform mat4 projectionMatrix;
uniform vec4 lightPosition;
void main()
{
vec3 pos = -(modelViewMatrix * vPosition).xyz;
vec3 light = lightPosition.xyz;
L = normalize( light - pos );
E = -pos;
N = normalize( (modelViewMatrix*vNormal).xyz);
gl_Position = projectionMatrix * modelViewMatrix * vPosition;
}
</script>
<script id="fragment-shader" type="x-shader/x-fragment">
precision mediump float;
uniform vec4 ambientProduct;
uniform vec4 diffuseProduct;
uniform vec4 specularProduct;
uniform float shininess;
varying vec3 N, L, E;
void main()
{
vec4 fColor;
vec3 H = normalize( L + E );
vec4 ambient = ambientProduct;
float Kd = max( dot(L, N), 0.0 );
vec4 diffuse = Kd*diffuseProduct;
float Ks = pow( max(dot(N, H), 0.0), shininess );
vec4 specular = Ks * specularProduct;
if( dot(L, N) < 0.0 ) specular = vec4(0.0, 0.0, 0.0, 1.0);
fColor = ambient + diffuse +specular;
fColor.a = 1.0;
gl_FragColor = fColor;
}
</script>
<script type="text/javascript" src="./Common/webgl-utils.js"></script>
<script type="text/javascript" src="./Common/initShaders.js"></script>
<script type="text/javascript" src="./Common/MV.js"></script>
<script type="text/javascript" src="project1.js"></script>
<body>
<canvas id="gl-canvas" width="512" height="512">
Oops ... your browser doesn't support the HTML5 canvas element
</canvas>
</body>
</html>
最佳答案
我不知道这是实际的正确答案,因为我没有通过运行代码来检查它。但是,我只是猜测为什么会发生此错误。
“属性变量超出范围”的主要原因
基本上,当您传递的缓冲区没有足够的长度时,就会发生这种情况。因此,您需要检查您创建的缓冲区源的数量。
您的错误是 ":GL_INVALID_OPERATION : glDrawArrays: attempt to access out of range vertices in attribute 1"
。在这种情况下,错误消息中的 attribute 1
表示 GLSL 代码中的“vNormal”属性。因为它是 GLSL 代码中的第二个属性变量。(如果错误码是attribute 0
,这个问题应该是vPosition造成的)
只要我看到你的代码,我认为与普通缓冲区和位置缓冲区的长度不匹配。
分割高度 * 分割轴 * 2
分割高度 * 分割轴 *6
Subdivision Height * Subdivision Axis * 4
我想这就是问题的原因。在这种情况下,每个顶点都必须有位置和法线,因此您的法线元素数必须为 Subdivision Height * Subdivision Axis * 6
gl.vertexAttribPointer 中的第二个参数
我认为您对 gl.vertexAttribPointer 中的第二个参数有误。这是计数,表示每个顶点需要传递多少个浮点元素。
在这种情况下,您为每个顶点推送了 3 个 float 元素。因此,即使您在 GLSL 代码中使用了 vec4
,也需要指定 3 作为 vPosition 的参数。通过这个参数,GPU 可以为每个顶点拆分这些缓冲区,并将它们并行地传递给顶点着色器。
向量中的第 4 个元素
这与您的问题没有密切关系。但我发现代码可能是错误的原因。
positions.push(vec4(radius * ux, radius * uy, radius * uz,1.0));
normalsArray.push(vec4(ux, uy, uz,1.0));
你需要理解vec4中第4个元素的含义。当这个向量表示坐标时,第4个元素必须为1。但是当这个向量表示方向时,第4个元素必须为0。
因为,如果这意味着方向,则方向不会受到平移变换的影响。 (我建议你学习仿射变换来理解这一点)
因此,您需要像这样重写该代码。
positions.push(vec4(radius * ux, radius * uy, radius * uz,1.0));
normalsArray.push(vec4(ux, uy, uz,0));
希望这个回答能帮到你...
关于javascript - 为什么我的球体渲染不完整?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34617490/
在我的 OpenGL 程序中,我按顺序执行以下操作: // Drawing filled polyhedrons // Drawing points using GL_POINTS // Displa
我想传递一个包含原始页面的局部变量,这个变量只包含一个带有值的符号。 当我使用此代码时,它运行良好,可以在部分中访问 origin 变量: render :partial => "products",
为什么这个 HTML/脚本(来自“JavaScript Ninja 的 secret ”)不渲染? http://jsfiddle.net/BCL54/
我想在阅读完 View 后返回到特定的网页位置(跳转到页内 anchor )。换句话说,在 views.py 中,我想做类似的事情: context={'form':my_form} return r
我有一个包含单条折线的 PathGeometry,并以固定的间隔向该线添加一个新点(以绘制波形)。使用 Perforator 工具时,我可以看到每次向直线添加一个点时,WPF 都会将整个 PathGe
尝试了解如何消除或最小化网站上不同 JavaScript 库的渲染延迟。 例如,如果我想加载来自许多社交网络的“即时”关注按钮,它们似乎会相互阻止渲染,并且您会收到令人不快的弹出窗口。 (func
我有以 xyz 点格式表示 3D 表面(即地震断层平面)的数据。我想创建这些表面的 3D 表示。我使用 rgl 和 akima 取得了一些成功,但是它无法真正处理可能会自行折叠或在同一 x,y 点具有
我正在用 Libgdx 编写一个小游戏。 我有一个 Render[OpenGL] 线程,它不断对所有对象调用 render() 和一个更新线程不断对所有对象调用 update(double delta
我有一个 .Rmd 文件包含: ```{r, echo=FALSE, message=FALSE, results='asis'} library(xtable) print(xtable(group
关闭。这个问题是opinion-based .它目前不接受答案。 想要改进这个问题? 更新问题,以便 editing this post 可以用事实和引用来回答它. 关闭 9 年前。 Improve
请不要评判我,我只是在学习 Swift。 最近我安装了 MetalPetal 框架,并按照说明操作: https://github.com/MetalPetal/MetalPetal#example-
如果您尝试渲染 Canvas 宽度和高度之外的图像,计算机是否仍会尝试渲染它并使用资源来尝试渲染它?我只是想找出在尝试渲染图像之前检查图像是否在 Canvas 内是否更好。 最佳答案 我相信它仍然在无
我在 safari 中渲染时遇到问题。 在 firefox、chrome 和 IE 上。如下图所示: input.searchbox{-webkit-border-radius:10px;-moz-b
我正在尝试通过远程桌面在 Windows7 下运行我在 RHEL7 服务器中制作的 java 程序。 服务器中的所有java程序都无法通过远程桌面呈现。如果我在服务器位置访问服务器本身,它们看起来没问
我正处于一个新项目的设计阶段,该项目将采用数据集并将其加载到文档中,然后围绕模板呈现文档。呈现的文件可以是 CSV 数据集、PDF 营销信函、电子邮件……很多东西。数据不会是数学方程式,我只是在寻找一
有没有办法在不同的 div 下渲染 React 组件的子组件? ... ... ... ... ...
使用以下代码: import numpy as np from plotly.offline import iplot, init_notebook_mode import plotly.graph_
截至最近, meteor 的所有文档都指出 onRendered是一种在模板完成渲染时获取回调的新方法。和 rendered只是为了向后兼容。 但是,这似乎对我不起作用。 onRendered永远不会
所以在我的基本模板中,我有:{% render "EcsCrmBundle:Module:checkClock" %} 然后我创建了 ModuleController.php ... getDoctr
我正在使用 vue-mathjax 来编译我的 vue 项目中的数学方程。它正在编译第一个括号 () 之间的文本。我想防止编译括号内的字符串。在文档中我发现,对于$符号,如果我们想逃避编译,我们需要使
我是一名优秀的程序员,十分优秀!