admin管理员组

文章数量:1122832

I want to detect group sub object bounds from obj file content. In blender for example create obj with sub group CUBE.COLLIDER. In js loader i want center or bounds of CUBE.COLLIDER for later (For physics body). I need simple and pragmatic solution.For example to create exstra data holder for CUBE.COLLIDER group vertices...

What is the l case? It is unsed flag in my program at the moment.

For now i see g.

...
l 5 19
l 6 20
g Cube.ME.COLLIDER_Mesh
v -0.515941 -3.226738 -4.906731
v -0.515941 2.340278 -4.906731
...

Any suggestion ?

Most important code lines:

 
export class constructMesh {
    constructor(objectData, inputArg) {
        this.inputArg = inputArg;
        this.objectData = objectData;
        this.create(objectData, inputArg);
        this.setScale = (s) => {
            this.inputArg.scale = s;
            initMeshBuffers(world.GL.gl, this.create(this.objectData, this.inputArg));
        };
        this.updateBuffers = () => {
            this.inputArg.scale = 1;
            initMeshBuffers(world.GL.gl, this.create(this.objectData, this.inputArg));
        };
    }

    create = (objectData, inputArg, callback) => {
        if(typeof callback === 'undefined') callback = function() {};
        let initOrientation = [0, 1, 2];
        /*
            To solve the issue of duplicate Vertices (the `(vertex, [texture], normal)`
            groups), while iterating through the face lines, when a group is encountered
            the whole group string ('16/92/11') is checked to see if it exists in the
            packed.hashindices object, and if it doesn't, the indices it specifies
            are used to look up each attribute in the corresponding attribute arrays
            already created. The values are then copied to the corresponding unpacked
            array (flattened to play nice with WebGL's ELEMENT_ARRAY_BUFFER indexing),
            the group string is added to the hashindices set and the current unpacked
            index is used as this hashindices value so that the group of elements can
            be reused. The unpacked index is incremented. If the group string already
            exists in the hashindices object, its corresponding value is the index of
            that group and is appended to the unpacked indices array.
            */
        var verts = [],
            vertNormals = [],
            textures = [],
            unpacked = {};
        // unpacking stuff
        unpacked.verts = [];
        unpacked.norms = [];
        unpacked.textures = [];
        unpacked.hashindices = {};
        unpacked.indices = [];
        unpacked.index = 0;
        // array of lines separated by the newline
        var lines = objectData.split('\n');
        // update swap orientation
        if(inputArg.swap[0] !== null) {
            swap(inputArg.swap[0], inputArg.swap[1], initOrientation);
        }

        var VERTEX_RE = /^v\s/;
        var NORMAL_RE = /^vn\s/;
        var TEXTURE_RE = /^vt\s/;
        var FACE_RE = /^f\s/;
        var WHITESPACE_RE = /\s+/;

        for(var i = 0;i < lines.length;i++) {
            var line = lines[i].trim();
            var elements = line.split(WHITESPACE_RE);
            elements.shift();

            if(VERTEX_RE.test(line)) {
                // if this is a vertex
                verts.push.apply(verts, elements);
            } else if(NORMAL_RE.test(line)) {
                // if this is a vertex normal
                vertNormals.push.apply(vertNormals, elements);
            } else if(TEXTURE_RE.test(line)) {
                // if this is a texture
                textures.push.apply(textures, elements);
            } else if(FACE_RE.test(line)) {
                // if this is a face
                /*
                    split this face into an array of vertex groups
                    for example:
                        f 16/92/11 14/101/22 1/69/1
                    becomes:
                        ['16/92/11', '14/101/22', '1/69/1'];
                    */
                var quad = false;
                for(var j = 0, eleLen = elements.length;j < eleLen;j++) {
                    // Triangulating quads
                    // quad: 'f v0/t0/vn0 v1/t1/vn1 v2/t2/vn2 v3/t3/vn3/'
                    // corresponding triangles:
                    //      'f v0/t0/vn0 v1/t1/vn1 v2/t2/vn2'
                    //      'f v2/t2/vn2 v3/t3/vn3 v0/t0/vn0'
                    if(j === 3 && !quad) {
                        // add v2/t2/vn2 in again before continuing to 3
                        j = 2;
                        quad = true;
                    }
                    if(elements[j] in unpacked.hashindices) {
                        unpacked.indices.push(unpacked.hashindices[elements[j]]);
                    } else {
 
                        var vertex = elements[j].split('/');
 
                        // vertex position
                        unpacked.verts.push(+verts[(vertex[0] - 1) * 3 + initOrientation[0]] * inputArg.scale);
                        unpacked.verts.push(+verts[(vertex[0] - 1) * 3 + initOrientation[1]] * inputArg.scale);
                        unpacked.verts.push(+verts[(vertex[0] - 1) * 3 + initOrientation[2]] * inputArg.scale);

                        // vertex textures
                        if(textures.length) {
                            unpacked.textures.push(+textures[(vertex[1] - 1) * 2 + 0]);
                            unpacked.textures.push(+textures[(vertex[1] - 1) * 2 + 1]);
                        }
                        // vertex normals
                        unpacked.norms.push(+vertNormals[(vertex[2] - 1) * 3 + 0]);
                        unpacked.norms.push(+vertNormals[(vertex[2] - 1) * 3 + 1]);
                        unpacked.norms.push(+vertNormals[(vertex[2] - 1) * 3 + 2]);
                        // add the newly created vertex to the list of indices
                        unpacked.hashindices[elements[j]] = unpacked.index;
                        unpacked.indices.push(unpacked.index);
                        // increment the counter
                        unpacked.index += 1;
                    }
                    if(j === 3 && quad) {
                        // add v0/t0/vn0 onto the second triangle
                        unpacked.indices.push(unpacked.hashindices[elements[0]]);
                    }
                }
            } else {
                console.log(':::::::obj loader:::::::::::', line)
                  }
        }
        this.vertices = unpacked.verts;
        this.vertexNormals = unpacked.norms;
        this.textures = unpacked.textures;
        this.indices = unpacked.indices;
        callback();
        return this;
    };

}
 
export var downloadMeshes = function(nameAndURLs, completionCallback, inputArg) {
    // the total number of meshes. this is used to implement "blocking"
    var semaphore = Object.keys(nameAndURLs).length;
    // if error is true, an alert will given
    var error = false;
    // this is used to check if all meshes have been downloaded
    // if meshes is supplied, then it will be populated, otherwise
    // a new object is created. this will be passed into the completionCallback
    if(typeof inputArg === 'undefined') {
        var inputArg = {
            scale: 1,
            swap: [null]
        };
    }
    if(typeof inputArg.scale === 'undefined') inputArg.scale = 1;
    if(typeof inputArg.swap === 'undefined') inputArg.swap = [null];

    var meshes = {};

    // loop over the mesh_name,url key,value pairs
    for(var mesh_name in nameAndURLs) {
        if(nameAndURLs.hasOwnProperty(mesh_name)) {
            new Ajax().get(
                nameAndURLs[mesh_name],
                (function(name) {
                    return function(data, status) {
                        if(status === 200) {
                            meshes[name] = new constructMesh(data, inputArg);
                        } else {
                            error = true;
                            console.error('An error has occurred and the mesh "' + name + '" could not be downloaded.');
                        }
                        // the request has finished, decrement the counter
                        semaphore--;
                        if(semaphore === 0) {
                            if(error) {
                                // if an error has occurred, the user is notified here and the
                                // callback is not called
                                console.error('An error has occurred and one or meshes has not been ' + 'downloaded. The execution of the script has terminated.');
                                throw '';
                            }
                            // there haven't been any errors in retrieving the meshes
                            // call the callback
                            completionCallback(meshes);
                        }
                    };
                })(mesh_name)
            );
        }
    }
};

var _buildBuffer = function(gl, type, data, itemSize) {
    var buffer = gl.createBuffer();
    var arrayView = type === gl.ARRAY_BUFFER ? Float32Array : Uint16Array;
    gl.bindBuffer(type, buffer);
    gl.bufferData(type, new arrayView(data), gl.STATIC_DRAW);
    buffer.itemSize = itemSize;
    buffer.numItems = data.length / itemSize;
    return buffer;
};

export var initMeshBuffers = function(gl, mesh) {
    mesh.normalBuffer = _buildBuffer(gl, gl.ARRAY_BUFFER, mesh.vertexNormals, 3);
    mesh.textureBuffer = _buildBuffer(gl, gl.ARRAY_BUFFER, mesh.textures, 2);
    mesh.vertexBuffer = _buildBuffer(gl, gl.ARRAY_BUFFER, mesh.vertices, 3);
    mesh.indexBuffer = _buildBuffer(gl, gl.ELEMENT_ARRAY_BUFFER, mesh.indices, 1);
};

OUTPUT FOR ELSE : (console.log(':::::::obj loader:::::::::::', line))

:::::::obj loader::::::::::: # Blender 4.1.1
app.js:1976 :::::::obj loader::::::::::: # www.blender
app.js:1976 :::::::obj loader::::::::::: mtllib door1.mtl
app.js:1976 :::::::obj loader::::::::::: g Cube_Mesh
app.js:1976 :::::::obj loader::::::::::: s 0
app.js:1976 :::::::obj loader::::::::::: usemtl Material
app.js:1976 :::::::obj loader::::::::::: l 1 17
app.js:1976 :::::::obj loader::::::::::: l 2 18
app.js:1976 :::::::obj loader::::::::::: l 5 19
app.js:1976 :::::::obj loader::::::::::: l 6 20
app.js:1976 :::::::obj loader::::::::::: g Cube.ME.COLLIDER_Mesh
app.js:1976 :::::::obj loader::::::::::: s 0
app.js:1976 :::::::obj loader::::::::::: g Cube.ME.COLLIDER2_Mesh
app.js:1976 :::::::obj loader::::::::::: s 0
app.js:1976 :::::::obj loader::::::::::: 

本文标签: webglDeterminate groups in parsing obj 3d model in javascriptStack Overflow