javascript - 如何为 WebGL 正确解析 collada 文件? (包括示例)

标签 javascript xml parsing webgl collada

这是我目前的结果:

incorrect collada model parsing

如您所见,这些模型中存在很多漏洞。我的猜测,为什么会发生这种情况,我需要以某种方式包括 <vcount> <polylist> 中的数据元素,它应该确定每个平面的顶点数(?)。由于 WebGL 只能绘制 3 边的多边形,这似乎行不通。如果到目前为止我的假设是正确的,我需要将所有四边形分别切成两个三 Angular 形。

我已经对使用 WebGL 进行的 collada 解析进行了大量研究,但几乎每个站点都将我重定向到几个已经实现了此类功能的 WebGL 库(所以请不要这样做)。我总是从自己编写所有核心功能开始,以便更好地了解内部工作原理。

这是我的解析函数:

function load_collada(gl, program, path) {
    var request = new XMLHttpRequest(),

        buffers = {
            vbo: gl.createBuffer(),
            nbo: gl.createBuffer(),
            ibo: gl.createBuffer(),

            aVertex: gl.getAttribLocation(program, "aVertex"),
            aNormal: gl.getAttribLocation(program, "aNormal")
        },

        mesh,
        vertices,
        indicesList,
        normals = [],
        indices = [];

    request.open("GET", path, false);
    request.overrideMimeType("text/xml");
    request.send();

    mesh = request.responseXML.querySelector("mesh");

    vertices = mesh.querySelectorAll("float_array")[0].textContent.split(" ");
    normals = mesh.querySelectorAll("float_array")[1].textContent.split(" ");
    indicesList = mesh.querySelectorAll("polylist p")[0].textContent.split(" ");

    for (i=0 ; i < indicesList.length; i+=2) { indices.push(indicesList[i]); }

    buffers.vbo.count = parseInt(mesh.querySelectorAll("float_array")[0].getAttribute("count"), 10); 
    buffers.nbo.count = normals.length;
    buffers.ibo.count = indices.length;

    gl.bindBuffer(gl.ARRAY_BUFFER, buffers.vbo);
    gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertices), gl.STATIC_DRAW);
    gl.vertexAttribPointer(buffers.aVertex, 3, gl.FLOAT, true, 0, 0);
    gl.enableVertexAttribArray(buffers.aVertex);

    gl.bindBuffer(gl.ARRAY_BUFFER, buffers.nbo);
    gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(normals), gl.STATIC_DRAW);
    gl.vertexAttribPointer(buffers.aNormal, 3, gl.FLOAT, true, 0, 0);
    gl.enableVertexAttribArray(buffers.aNormal);

    gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, buffers.ibo);
    gl.bufferData(gl.ELEMENT_ARRAY_BUFFER, new Uint16Array(indices), gl.STATIC_DRAW);

    return buffers;
}

我也不太清楚为什么法线也有索引,但我忽略了它们,只添加了 indicesList 中的每一秒值| .

我的绘图程序很简单 gl.drawElements(gl.TRIANGLE_STRIP, program.models[i].ibo.count, gl.UNSIGNED_SHORT, 0); .

如果有任何关于此问题的解决方案或建议,我将不胜感激。


更新:再次尝试使用此解析器后,我注意到上面的解析函数(即使使用正确导出的模型)也不会正确显示法线。您必须更改数据,以便每个面而不是每个唯一位置定义顶点。

最佳答案

找到了一个潜在的解决方案。在 blender 中导出模型之前,您需要添加一个 decimate 修饰符。选中 triangulate 并将 ratio 设置为 0.9900(单击左箭头)。

编辑:实际上有一个triangulate修饰符,所以改用这个。

所以最后你的球体网格看起来像这样:

enter image description here

关于javascript - 如何为 WebGL 正确解析 collada 文件? (包括示例),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14882366/

相关文章:

c# - 在 C# 中动态创建和公开 SOAP 服务及其 WSDL(使用自定义 TCP 监听器!)

javascript - Jquery使用on事件监听器获取选择器的值

javascript - JS用什么技巧显示/计算 float

xml - 使用 log4j.xml 配置 Spark 日志记录

xml - 如何使用 Delphi 检查 XML 文件是否格式正确?

javascript - 语法错误: Unexpected identifier while Parsin XML Data Using Google App Script

regex - 插入式、可移植的解析

javascript - 尝试在React Native Stack Navigator v5中访问route.params

javascript - 如何检查 javascript 对象键中的等效项

java - 构建XML服务解析库