示例#1
0
def process_file(base_dir, f):
    current_process().daemon = False

    base_name = decode(f['base_name'])
    full_path = decode(f['full_path'])
    zip_hash = decode(f['metadata']['types']['original']['zip'])

    f_dir = full_path.replace('/', '_')
    f_dir = os.path.join(base_dir, f_dir)
    if not os.path.isdir(f_dir):
        os.mkdir(f_dir)

    orig_zip = os.path.join(f_dir, base_name + '.orig.zip')
    if not os.path.isfile(orig_zip):
        f_data = urllib2.urlopen(DOWNLOAD + '/' + zip_hash).read()
        orig_zip_file = open(orig_zip, 'wb')
        orig_zip_file.write(f_data)
        orig_zip_file.close()

    optimizations = factory.getInstance('full_optimizations')
    save = factory.getInstance('save_collada_zip')

    orig_ss = orig_zip + '.png'
    opt_zip = os.path.join(f_dir, base_name + '.opt.zip')
    opt_ss = opt_zip + '.png'

    mesh = collada.Collada(orig_zip, zip_filename=base_name)
    orig_render_info = getRenderInfo(mesh)

    if not os.path.isfile(orig_ss):
        p = Process(target=save_screenshot,
                    args=(orig_zip, orig_ss),
                    kwargs={'zip_filename': base_name})
        p.start()
        p.join()

    if not os.path.isfile(opt_zip):
        optimizations.apply(mesh)
        save.apply(mesh, opt_zip)
        mesh = None

    optmesh = collada.Collada(opt_zip)
    opt_render_info = getRenderInfo(optmesh)
    optmesh = None

    if not os.path.isfile(opt_ss):
        p = Process(target=save_screenshot, args=(opt_zip, opt_ss))
        p.start()
        p.join()

    orig_ss_copy = f_dir + '.orig.png'
    opt_ss_copy = f_dir + '.opt.png'
    if not os.path.isfile(orig_ss_copy):
        shutil.copy2(orig_ss, orig_ss_copy)
    if not os.path.isfile(opt_ss_copy):
        shutil.copy2(opt_ss, opt_ss_copy)

    orig_size = os.stat(orig_zip)[6]
    opt_size = os.stat(opt_zip)[6]
    return (f_dir, orig_size, opt_size, orig_render_info, opt_render_info)
示例#2
0
    def test_collada_duck_poly(self):
        f = os.path.join(self.datadir, "duck_polylist.dae")
        mesh = collada.Collada(f, validate_output=True)
        self.assertEqual(mesh.scene.id, 'VisualSceneNode')
        self.assertIn('LOD3spShape-lib', mesh.geometries)
        self.assertIn('directionalLightShape1-lib', mesh.lights)
        self.assertIn('cameraShape1', mesh.cameras)
        self.assertIn('file2', mesh.images)
        self.assertIn('blinn3-fx', mesh.effects)
        self.assertIn('blinn3', mesh.materials)
        self.assertEqual(len(mesh.nodes), 0)
        self.assertIn('VisualSceneNode', mesh.scenes)

        s = BytesIO()
        mesh.write(s)
        out = s.getvalue()
        t = BytesIO(out)
        mesh = collada.Collada(t, validate_output=True)

        self.assertEqual(mesh.scene.id, 'VisualSceneNode')
        self.assertIn('LOD3spShape-lib', mesh.geometries)
        self.assertIn('directionalLightShape1-lib', mesh.lights)
        self.assertIn('cameraShape1', mesh.cameras)
        self.assertIn('file2', mesh.images)
        self.assertIn('blinn3-fx', mesh.effects)
        self.assertIn('blinn3', mesh.materials)
        self.assertEqual(len(mesh.nodes), 0)
        self.assertIn('VisualSceneNode', mesh.scenes)
示例#3
0
 def read(self, f, assethandler=None, submesh=None, options=None):
     '''
     Read collada model data given the file path
     '''
     self._basepath = os.path.dirname(f)
     self._assethandler = assethandler
     try:
         d = collada.Collada(f)
     except:
         # workaround for pycollada's handling of xml comments
         xdoc = lxml.etree.parse(f)
         for c in xdoc.xpath('//comment()'):
             p = c.getparent()
             p.remove(c)
         try:
             d = collada.Collada(StringIO(lxml.etree.tostring(xdoc)))
         except:
             logging.error("error while processing %s" % f)
             raise
     for m in d.materials:
         mm = model.MaterialModel()
         mm.name = m.id
         if type(m.effect.diffuse) == collada.material.Map:
             fname = os.path.abspath(
                 os.path.join(self._basepath,
                              m.effect.diffuse.sampler.surface.image.path))
             if not os.path.exists(fname):
                 if fname.count('/meshes/') > 0:
                     fname = fname.replace('/meshes/',
                                           '/materials/textures/')
             if self._assethandler:
                 mm.texture = self._assethandler(fname)
             else:
                 mm.texture = fname
         elif m.effect.diffuse is not None:
             mm.diffuse = m.effect.diffuse
         self._materials[mm.name] = mm
     m = model.MeshTransformData()
     unitmeter = d.assetInfo.unitmeter
     if unitmeter == None:
         unitmeter = 1.0
         logging.info("unitmeter is not specified in dae and 1.0 is used.")
     m.matrix = tf.scale_matrix(unitmeter)
     m.children = []
     rootnodes = d.scene.nodes
     if submesh is not None:
         for n in d.scene.nodes:
             trans = model.TransformationModel()
             trans.matrix = numpy.identity(4)
             f = self.findchild(n, submesh, trans)
             f = self.filterchild(f, submesh)
             if f is not None:
                 rootnodes = [f]
                 break
     for n in rootnodes:
         cm = self.convertchild(n)
         if cm is not None:
             m.children.append(cm)
     return m
示例#4
0
def read(farm_boy_model_path: Path) -> Model:
    '''
    Read a collada file.

    When reading a collada file we need to extract data about two main parts of the model - the mesh and the skeleton. We can also
    extract animation data.

    The mesh data includes the vertices, texture_coords and normals. It also includes the indices.
    The skeleton data includes information about the skeleton of the model - the joints, their hierarchy, transformation matrices (local
    bind transform, inverse bind transform); also, for each vertex we have the joints that affect it and the respective weights (used for LBS).
    The animation data mainly includes the key frames.
    '''

    ext = farm_boy_model_path.suffix.lower()
    if ext != '.dae':
        print("Please use only .dae files. Exiting...")
        raise SystemExit

    model_data = collada.Collada(farm_boy_model_path.as_posix())
    data = _read_model_data(model_data)

    model = Model(faces=data["faces"],
                  vertices=data["vertices"],
                  vertex_texture_coords=data["vertex_texture_coords"],
                  vertex_normals=data["vertex_normals"],
                  root_joint=data["root_joint"],
                  vertex_joints=data["vertex_joints"],
                  vertex_joints_weights=data["vertex_joints_weights"],
                  animation=Animation(data["key_frames"]))
    return model
示例#5
0
    def __init__(self, model_path):
        ext = splitext(model_path)[1].lower()
        if ext != '.dae':
            print("Please use only .dae files. Exiting...")
            raise SystemExit

        self.model_data = collada.Collada(model_path)
        # vertices, indices, texture_coords = self.__parse_model_data()
        indices, vertices, texture_coords, vertex_joints, weights, root_joint, key_frames = self.__parse_model_data_no_texture()

        normals = np.zeros(len(vertices))
        self.indices = indices.astype('int32')
        self.vertices = vertices.astype('float32')
        self.texture_coords = texture_coords.astype('float32')
        self.normals = normals.astype('float32')
        self.vertex_joints = vertex_joints.astype('int32')
        self.weights = weights.astype('float32')
        assert self.indices.max()+1 == len(self.vertices) // 3 == len(self.texture_coords) // 2 == len(
            self.normals) // 3 == len(self.vertex_joints) // 3 == len(self.weights) // 3

        self.root_joint: Joint = root_joint
        self.key_frames = key_frames

        print(self.root_joint)
        return
示例#6
0
    def run(self):
        sys = self.getData("sys")
        cmp = Component()
        cmp = sys.addComponent(cmp, self.object)

        print self.FileName
        col = collada.Collada(
            self.FileName,
            ignore=[collada.DaeUnsupportedError, collada.DaeBrokenRefError])
        for geom in col.geometries:
            for triset in geom.primitives:
                trilist = list(triset)
                elements = len(trilist)
                for i in range(elements):
                    nl = nodevector()
                    for j in range(3):
                        node = triset.vertex[triset.vertex_index][i][j]
                        n = sys.addNode(
                            float(node[0] * self.ScaleX + self.OffsetX),
                            float(node[1] * self.ScaleY + self.OffsetY),
                            float(node[2]) * self.ScaleZ)
                        nl.append(n)
                    nl.append(nl[0])
                    f = sys.addFace(nl, self.geometry)
                    cmp.getAttribute("Geometry").setLink(
                        "Geometry", f.getUUID())
示例#7
0
def read(filename):
    global col
    col = collada.Collada(filename, ignore=[collada.DaeUnsupportedError])
    # Read the unitmeter info from dae file and compute unit to convert to mm
    unitmeter = col.assetInfo.unitmeter or 1
    unit = unitmeter / 0.001
    for geom in col.scene.objects('geometry'):
        #for geom in col.geometries:
        for prim in geom.primitives():
            #for prim in geom.primitives:
            #print prim, dir(prim)
            meshdata = []
            if hasattr(prim, "triangles"):
                tset = prim.triangles()
            elif hasattr(prim, "triangleset"):
                tset = prim.triangleset()
            for tri in tset:
                face = []
                for v in tri.vertices:
                    v = [x * unit for x in v]
                    face.append([v[0], v[1], v[2]])
                meshdata.append(face)
            #print meshdata
            newmesh = Mesh.Mesh(meshdata)
            #print newmesh
            obj = FreeCAD.ActiveDocument.addObject("Mesh::Feature", "Mesh")
            obj.Mesh = newmesh
示例#8
0
    def test_collada_attribute_replace(self):
        mesh = collada.Collada(validate_output=True)
        self.assertIsInstance(mesh.geometries, collada.util.IndexedList)
        self.assertIsInstance(mesh.controllers, collada.util.IndexedList)
        self.assertIsInstance(mesh.animations, collada.util.IndexedList)
        self.assertIsInstance(mesh.lights, collada.util.IndexedList)
        self.assertIsInstance(mesh.cameras, collada.util.IndexedList)
        self.assertIsInstance(mesh.images, collada.util.IndexedList)
        self.assertIsInstance(mesh.effects, collada.util.IndexedList)
        self.assertIsInstance(mesh.materials, collada.util.IndexedList)
        self.assertIsInstance(mesh.nodes, collada.util.IndexedList)
        self.assertIsInstance(mesh.scenes, collada.util.IndexedList)

        mesh.geometries = []
        mesh.controllers = []
        mesh.animations = []
        mesh.lights = []
        mesh.cameras = []
        mesh.images = []
        mesh.effects = []
        mesh.materials = []
        mesh.nodes = []
        mesh.scenes = []

        self.assertIsInstance(mesh.geometries, collada.util.IndexedList)
        self.assertIsInstance(mesh.controllers, collada.util.IndexedList)
        self.assertIsInstance(mesh.animations, collada.util.IndexedList)
        self.assertIsInstance(mesh.lights, collada.util.IndexedList)
        self.assertIsInstance(mesh.cameras, collada.util.IndexedList)
        self.assertIsInstance(mesh.images, collada.util.IndexedList)
        self.assertIsInstance(mesh.effects, collada.util.IndexedList)
        self.assertIsInstance(mesh.materials, collada.util.IndexedList)
        self.assertIsInstance(mesh.nodes, collada.util.IndexedList)
        self.assertIsInstance(mesh.scenes, collada.util.IndexedList)
示例#9
0
    def _shape(self):
        shapes = []

        c = collada.Collada(self.path)

        for g in c.geometries:
            for p in g.primitives:
                if not isinstance(p, collada.lineset.LineSet):
                    fields = {}
                    fields['geometry'] = self._indexed_face_set(p)

                    if p.material:
                        material = c.materials[p.material]
                        if material and material.effect:
                            appearance = self._appearance(material.effect)
                            fields['appearance'] = appearance

                    shapes.append(Node('Shape', fields))
        
        if len(shapes) == 1:
            return shapes[0]
        
        return Node('Group', {
            'children': shapes
        })
示例#10
0
def export_mesh(vertices, triangles, filename, mesh_name="mcubes_mesh"):
    """
    Exports a mesh in the COLLADA (.dae) format.
    
    Needs PyCollada (https://github.com/pycollada/pycollada).
    """

    import collada

    mesh = collada.Collada()

    vert_src = collada.source.FloatSource("verts-array", vertices,
                                          ('X', 'Y', 'Z'))
    geom = collada.geometry.Geometry(mesh, "geometry0", mesh_name, [vert_src])

    input_list = collada.source.InputList()
    input_list.addInput(0, 'VERTEX', "#verts-array")

    triset = geom.createTriangleSet(np.copy(triangles), input_list, "")
    geom.primitives.append(triset)
    mesh.geometries.append(geom)

    geomnode = collada.scene.GeometryNode(geom, [])
    node = collada.scene.Node(mesh_name, children=[geomnode])

    myscene = collada.scene.Scene("mcubes_scene", [node])
    mesh.scenes.append(myscene)
    mesh.scene = myscene

    mesh.write(filename)
示例#11
0
    def __init__(self, inFileName):
        # 	inputFilename = sys.argv[1]
        col = collada.Collada(
            inFileName,
            ignore=[collada.DaeUnsupportedError, collada.DaeBrokenRefError])
        if col.scene is not None:
            for geom in col.scene.objects('geometry'):
                for prim in geom.primitives():
                    # use primitive-specific ways to get triangles
                    prim_type = type(prim).__name__
                    if prim_type == 'BoundTriangleSet':
                        triangles = prim
                    elif prim_type == 'BoundPolylist':
                        triangles = prim.triangleset()
                    else:
                        print 'Unsupported mesh used:', prim_type
                        triangles = None
                    if triangles is not None:

                        # # triangles.generateNormals()
                        vertices = triangles.vertex  #.flatten().tolist()
                        vertex_indices = triangles.vertex_index  #.flatten().tolist()
                        VERTICES = vertices[vertex_indices]

                        normals = triangles.normal
                        normal_indices = triangles.normal_index  # .flatten().tolist()
                        NORMALS = normals[normal_indices]

                        uv = triangles.texcoordset[0]
                        uv_indices = triangles.texcoord_indexset[0]
                        UV = uv[uv_indices]

                        x1 = VERTICES[:, 1, 0] - VERTICES[:, 0, 0]
                        x2 = VERTICES[:, 2, 0] - VERTICES[:, 0, 0]
                        y1 = VERTICES[:, 1, 1] - VERTICES[:, 0, 1]
                        y2 = VERTICES[:, 2, 1] - VERTICES[:, 0, 1]
                        z1 = VERTICES[:, 1, 2] - VERTICES[:, 0, 2]
                        z2 = VERTICES[:, 2, 2] - VERTICES[:, 0, 2]

                        s1 = UV[:, 1, 0] - UV[:, 0, 0]
                        s2 = UV[:, 2, 0] - UV[:, 0, 0]
                        t1 = UV[:, 1, 1] - UV[:, 0, 1]
                        t2 = UV[:, 2, 1] - UV[:, 0, 1]

                        f = 1.0 / (s1 * t2 - s2 * t1)
                        tanX = (x1 * t2 - x2 * t1) * f
                        tanY = (y1 * t2 - y2 * t1) * f
                        tanZ = (z1 * t2 - z2 * t1) * f

                        tangent = numpy.vstack((tanX, tanY, tanZ)).T
                        TANGENTS = normalize_v3(
                            tangent)  # one tangent   for triangle face
                        BINORMALS = numpy.cross(
                            NORMALS,
                            tangent)  # one BINORMALS for triangle face
                        self.VERTICES = VERTICES
                        self.NORMALS = NORMALS
                        self.UV = UV
                        self.TANGENTS = TANGENTS
                        self.BINORMALS = BINORMALS
示例#12
0
 def get_collada_data(self):
     if self._cached_collada_data is not None:
         collada_data = self._cached_collada_data
     else:
         collada_data = collada.Collada(self.filesystem_path)
         self._cached_collada_data = collada_data
     return collada_data
示例#13
0
def main():
    mesh = collada.Collada(f'{name}.dae')

    geom = mesh.geometries[0]
    triset = geom.primitives[0]

    # TODO: Read pycollada docs, this is probably tremendously inefficient
    pos_set = triset.sources['VERTEX'][0][4]
    normal_set = triset.sources['NORMAL'][0][4]
    tex_set = triset.sources['TEXCOORD'][0][4]
    color_set = triset.sources['COLOR'][0][4]

    vert_dict = {}
    for t in triset.indices:
        for v in t:
            vert_dict[v[0]] = (v[1], v[2], v[3])

    #print(f'Pos: {pos_set[0]}')
    #print(f'Normal: {normal_set[vert_dict[0][0]]}')
    #print(f'Tex: {tex_set[vert_dict[0][1]]}')
    #print(f'Color: {color_set[vert_dict[0][2]]}')

    # Write vertices to file
    with open(f'{name}-out.bin', 'wb') as f:
        for i in range(0, len(pos_set)):
            x = pos_set[i][0]
            y = pos_set[i][1]
            z = pos_set[i][2]

            a = normal_set[vert_dict[i][0]][0]
            b = normal_set[vert_dict[i][0]][1]
            c = normal_set[vert_dict[i][0]][2]
            f.write(struct.pack('<6f', x, y, z, a, b, c))

            if vert_mode == 36:
                r = int(color_set[vert_dict[0][2]][0] * 255)
                g = int(color_set[vert_dict[0][2]][1] * 255)
                b = int(color_set[vert_dict[0][2]][2] * 255)
                f.write(struct.pack('<BBBB', r, g, b, 255))

            u = tex_set[vert_dict[i][1]][0]
            v = 1.0 - tex_set[vert_dict[i][1]][1]
            f.write(struct.pack('<2f', u, v))

    # Stripify and write index buffer to file
    trilist = []
    for face in triset.indices:
        #INVERTED WINDING ORDER
        trilist.append((int(face[2][0]), int(face[1][0]), int(face[0][0])))
    stripped = tristrip.stripify(trilist, True)[0]
    print(len(stripped))

    with open(f'{name}-ibuf.txt', 'w') as f:
        f.write('1\n')
        f.write('1\n')
        f.write(f'{len(stripped)}\n')
        for i in stripped:
            f.write(f'{i} ')
        f.write('\n')
示例#14
0
 def _build_graph(self):
     col = collada.Collada(self._graph_collada_fname)
     geom = col.geometries[0]
     lineset = geom.primitives[0]
     self._graph = defaultdict(set)
     for node1, node2 in lineset.vertex_index:
         self._graph[node1].add(node2)
     self._points = lineset.vertex
示例#15
0
def check_large(files):
    dae = collada.Collada(files)
    alltriangles = np.vstack([
        i.vertex[i.vertex_index] for j in dae.scene.objects('geometry')
        for i in j.primitives()
        if isinstance(i, collada.triangleset.BoundTriangleSet)
    ])
    print(files, alltriangles.shape)
示例#16
0
 def apply(self, filename):
     if not os.path.isfile(filename):
         raise FilterException("argument is not a valid file")
     try:
         col = collada.Collada(filename)
     except collada.DaeError, e:
         print e
         raise FilterException("errors while loading file")
示例#17
0
    def test_should_find_commented_objects_in_mesh(self):
        #file = open('./test_resources/3wall.dae')
        file = open('./test_resources/blue_house.dae')
        collada_data = collada.Collada(file)

        for item in collada_data.scene.nodes:
            for child in item.children:
                self.assertEqual('ID2', child.id)
示例#18
0
def export(exportList,filename,tessellation=1):
    "called when freecad exports a file"
    if not checkCollada(): return
    p = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Mod/Arch")
    scale = p.GetFloat("ColladaScalingFactor",1.0)
    colmesh = collada.Collada()
    colmesh.assetInfo.upaxis = collada.asset.UP_AXIS.Z_UP
    effect = collada.material.Effect("effect0", [], "phong", diffuse=(.7,.7,.7), specular=(1,1,1))
    mat = collada.material.Material("material0", "mymaterial", effect)
    colmesh.effects.append(effect)
    colmesh.materials.append(mat)
    objind = 0
    scenenodes = []
    objectslist = Draft.getGroupContents(exportList,walls=True,addgroups=True)
    objectslist = Arch.pruneIncluded(objectslist)
    for obj in objectslist:
        vindex = []
        nindex = []
        findex = []
        m = None
        if obj.isDerivedFrom("Part::Feature"):
            print "exporting object ",obj.Name, obj.Shape
            m = Mesh.Mesh(triangulate(obj.Shape))
        elif obj.isDerivedFrom("Mesh::Feature"):
            print "exporting object ",obj.Name, obj.Mesh
            m = obj.Mesh
        if m:
            # vertex indices
            for v in m.Topology[0]:
                vindex.extend([v.x*scale,v.y*scale,v.z*scale])
            # normals
            for f in m.Facets:
                n = f.Normal
                nindex.extend([n.x,n.y,n.z])
            # face indices
            for i in range(len(m.Topology[1])):
                f = m.Topology[1][i]
                findex.extend([f[0],i,f[1],i,f[2],i])
        print len(vindex), " vert indices, ", len(nindex), " norm indices, ", len(findex), " face indices."
        vert_src = collada.source.FloatSource("cubeverts-array"+str(objind), numpy.array(vindex), ('X', 'Y', 'Z'))
        normal_src = collada.source.FloatSource("cubenormals-array"+str(objind), numpy.array(nindex), ('X', 'Y', 'Z'))
        geom = collada.geometry.Geometry(colmesh, "geometry"+str(objind), obj.Name, [vert_src, normal_src])
        input_list = collada.source.InputList()
        input_list.addInput(0, 'VERTEX', "#cubeverts-array"+str(objind))
        input_list.addInput(1, 'NORMAL', "#cubenormals-array"+str(objind))
        triset = geom.createTriangleSet(numpy.array(findex), input_list, "materialref")
        geom.primitives.append(triset)
        colmesh.geometries.append(geom)
        matnode = collada.scene.MaterialNode("materialref", mat, inputs=[])
        geomnode = collada.scene.GeometryNode(geom, [matnode])
        node = collada.scene.Node("node"+str(objind), children=[geomnode])
        scenenodes.append(node)
        objind += 1
    myscene = collada.scene.Scene("myscene", scenenodes)
    colmesh.scenes.append(myscene)
    colmesh.scene = myscene
    colmesh.write(filename)
    FreeCAD.Console.PrintMessage(translate("Arch","file %s successfully created.") % filename)
示例#19
0
def merge_dae_files(list_fpath_inputs, fpath_output, scene_name="myscene"):
    list_dae_objects = []

    for fpath_input in list_fpath_inputs:
        list_dae_objects.append(dae.Collada(fpath_input))

    merged_dae_object = merge_dae_objects(list_dae_objects,
                                          scene_name="myscene")
    merged_dae_object.write(fpath_output)
示例#20
0
def get_stlstr(binary=1, _self=cmd):
    '''
DESCRIPTION

    STL geometry export
    '''
    import collada
    import io
    import struct

    _self.set('cartoon_loop_cap', 2)
    _self.set('stick_round_nub', 2)
    _self.set('collada_geometry_mode', 1)

    daestring = _self.get_collada()
    daestream = io.BytesIO(daestring.encode('utf-8'))

    mesh = collada.Collada(daestream, [
        collada.common.DaeUnsupportedError,
        collada.common.DaeBrokenRefError,
    ])

    if binary:
        bout = [b' ' * 80, None]
    else:
        aout = ['solid x']

    for geom in mesh.geometries:
        for prim in geom.primitives:
            for t in prim:
                N = len(t.vertices)
                for i0 in range(0, N - 1, 2):
                    triangle = [t.vertices[i % N] for i in range(i0, i0 + 3)]
                    if binary:
                        bout.append(struct.pack('<fff', *t.normals[i0]))
                        for vertex in triangle:
                            bout.append(struct.pack('<fff', *vertex))
                        bout.append(struct.pack('<H',
                                                0))  # Attribute byte count
                    else:
                        aout.append('facet normal %f %f %f' %
                                    tuple(t.normals[i0]))
                        aout.append('outer loop')
                        for vertex in triangle:
                            aout.append('vertex %f %f %f' % tuple(vertex))
                        aout.append('endloop')
                        aout.append('endfacet')

    if binary:
        bout[1] = struct.pack('<I', (len(bout) - 2) // 5)

        return b''.join(bout)

    aout.append('endsolid x')
    aout.append('')

    return '\n'.join(aout)
示例#21
0
    def write(self, m, f, options=None):
        '''
        Write simulation model in collada format
        '''
        # we use pycollada to generate the dae file
        self._mesh = collada.Collada()

        # create effect and material
        if m.data.material:
            if m.data.material.texture:
                image = collada.material.CImage("material0-image",
                                                m.data.material.texture)
                surface = collada.material.Surface("material0-image-surface",
                                                   image)
                sampler2d = collada.material.Sampler2D(
                    "material0-image-sampler", surface)
                map1 = collada.material.Map(sampler2d, "UVSET0")
                effect = collada.material.Effect("effect0",
                                                 [surface, sampler2d],
                                                 "lambert",
                                                 emission=(0.0, 0.0, 0.0, 1),
                                                 ambient=(0.0, 0.0, 0.0, 1),
                                                 diffuse=map1,
                                                 transparency=0.0,
                                                 double_sided=True)
                self._mesh.images.append(image)
            else:
                effect = collada.material.Effect(
                    "effect0", [],
                    "phong",
                    double_sided=True,
                    diffuse=m.data.material.diffuse,
                    specular=m.data.material.specular,
                    index_of_refraction=1.0)
        else:
            effect = collada.material.Effect("effect0", [],
                                             "phong",
                                             double_sided=True,
                                             diffuse=(0.8, 0.8, 0.8),
                                             specular=(1, 1, 1),
                                             index_of_refraction=1.0)
        mat = collada.material.Material("material0", "mymaterial", effect)
        self._mesh.effects.append(effect)
        self._mesh.materials.append(mat)
        self._matnode = collada.scene.MaterialNode("materialref",
                                                   mat,
                                                   inputs=[])

        # convert shapes recursively
        node = collada.scene.Node("root", children=[self.convertchild(m.data)])

        # create scene graph
        myscene = collada.scene.Scene("myscene", [node])
        self._mesh.scenes.append(myscene)
        self._mesh.scene = myscene
        self._mesh.write(f)
示例#22
0
def read(filename):

    "reads a DAE file"

    global col
    col = collada.Collada(filename, ignore=[collada.DaeUnsupportedError])
    # Read the unitmeter info from dae file and compute unit to convert to mm
    unitmeter = col.assetInfo.unitmeter or 1
    unit = unitmeter / 0.001
    #for geom in col.geometries:
    #for geom in col.scene.objects('geometry'):
    for node in col.scene.nodes:
        if list(node.objects("geometry")):
            color = None
            # retrieving material
            if "}" in node.xmlnode.tag:
                bt = node.xmlnode.tag.split("}")[0] + "}"
                gnode = node.xmlnode.find(bt + "instance_geometry")
                if gnode is not None:
                    bnode = gnode.find(bt + "bind_material")
                    if bnode is not None:
                        tnode = bnode.find(bt + "technique_common")
                        if tnode is not None:
                            mnode = tnode.find(bt + "instance_material")
                            if mnode is not None:
                                if "target" in mnode.keys():
                                    mname = mnode.get("target").strip("#")
                                    for m in col.materials:
                                        if m.id == mname:
                                            e = m.effect
                                            if isinstance(e.diffuse, tuple):
                                                color = e.diffuse
            for geom in node.objects("geometry"):
                for prim in geom.primitives():
                    #print(prim, dir(prim))
                    meshdata = []
                    if hasattr(prim, "triangles"):
                        tset = prim.triangles()
                    elif hasattr(prim, "triangleset"):
                        tset = prim.triangleset()
                    else:
                        tset = []
                    for tri in tset:
                        face = []
                        for v in tri.vertices:
                            v = [x * unit for x in v]
                            face.append([v[0], v[1], v[2]])
                        meshdata.append(face)
                    #print(meshdata)
                    newmesh = Mesh.Mesh(meshdata)
                    #print(newmesh)
                    obj = FreeCAD.ActiveDocument.addObject(
                        "Mesh::Feature", "Mesh")
                    obj.Mesh = newmesh
                    if color and FreeCAD.GuiUp:
                        obj.ViewObject.ShapeColor = color
示例#23
0
def write_collada(vertices, normals, triangle_indices, fname):
    vertices = np.array(vertices)
    normals = np.array(normals)
    triangle_indices = np.array(triangle_indices, dtype=np.int32)

    for i in xrange(triangle_indices.shape[0]):
        k1, k2, k3 = triangle_indices[i, :]
        x, y, z = vertices[k1], vertices[k2], vertices[k3]
        nx = normals[k1]
        if np.dot(np.cross(y - x, x - z), nx) < 0:
            triangle_indices[i, :] = np.array([k3, k2, k1], dtype=np.int32)

    assert len(vertices.shape) == 2 and vertices.shape[1] == 3
    assert vertices.shape == normals.shape
    assert len(triangle_indices.shape) == 2 and triangle_indices.shape[1] == 3

    mesh = collada.Collada()
    effect = collada.material.Effect("effect0", [],
                                     "phong",
                                     diffuse=(1, 0, 0),
                                     specular=(0, 1, 0))
    mat = collada.material.Material("material0", "mymaterial", effect)
    mesh.effects.append(effect)
    mesh.materials.append(mat)

    vert_floats = vertices.flatten()
    normal_floats = normals.flatten()

    vert_src = collada.source.FloatSource("cubeverts-array",
                                          np.array(vert_floats),
                                          ('X', 'Y', 'Z'))
    normal_src = collada.source.FloatSource("cubenormals-array",
                                            np.array(normal_floats),
                                            ('X', 'Y', 'Z'))

    geom = collada.geometry.Geometry(mesh, "geometry0", "mycube",
                                     [vert_src, normal_src])

    input_list = collada.source.InputList()
    input_list.addInput(0, 'VERTEX', "#cubeverts-array")
    input_list.addInput(1, 'NORMAL', "#cubenormals-array")

    indices = np.hstack([triangle_indices, triangle_indices]).flatten()

    triset = geom.createTriangleSet(indices, input_list, "materialref")
    geom.primitives.append(triset)
    mesh.geometries.append(geom)

    matnode = collada.scene.MaterialNode("materialref", mat, inputs=[])
    geomnode = collada.scene.GeometryNode(geom, [matnode])
    node = collada.scene.Node("node0", children=[geomnode])

    myscene = collada.scene.Scene("myscene", [node])
    mesh.scenes.append(myscene)
    mesh.scene = myscene
    mesh.write(fname)
示例#24
0
    def setUp(self):
        self.dummy = collada.Collada(aux_file_loader = self.image_dummy_loader,
                validate_output=True)

        self.dummy_cimage = collada.material.CImage("yourcimage", "./whatever.tga", self.dummy)
        self.cimage = collada.material.CImage("mycimage", "./whatever.tga", self.dummy)
        self.dummy.images.append(self.dummy_cimage)
        self.dummy.images.append(self.cimage)
        self.othereffect = collada.material.Effect("othereffect", [], "phong")
        self.dummy.effects.append(self.othereffect)
示例#25
0
def generate_ground_plane():
    mesh = collada.Collada()
    geom, id = generate_geometry(mesh, [100, 100, .1], [0, 0, .05, 0, 0, 0])
    mesh.geometries.append(geom)
    geomnode = collada.scene.GeometryNode(geom)
    node = collada.scene.Node('node' + id, children=[geomnode])
    scene = collada.scene.Scene('scene' + id, [node])
    mesh.scenes.append(scene)
    mesh.scene = scene
    return [mesh]
示例#26
0
    def test_triangle_iterator_vert_normals(self):
        mesh = collada.Collada(validate_output=True)

        vert_floats = [-50, 50, 50, 50, 50, 50, -50, -50, 50, 50, -50,
                       50, -50, 50, -50, 50, 50, -50, -50, -50, -50, 50, -50, -50]
        normal_floats = [0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, -1, 0, 0, -1, 0, 0, -1, 0, 0, -1, 0, -1, 0, 0,
                         -1, 0, 0, -1, 0, 0, -1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, -1, 0, 0, -1, 0, 0, -1, 0, 0, -1]
        vert_src = collada.source.FloatSource(
            "cubeverts-array", numpy.array(vert_floats), ('X', 'Y', 'Z'))
        normal_src = collada.source.FloatSource(
            "cubenormals-array", numpy.array(normal_floats), ('X', 'Y', 'Z'))
        geometry = collada.geometry.Geometry(
            mesh, "geometry0", "mycube", [
                vert_src, normal_src], [])

        input_list = collada.source.InputList()
        input_list.addInput(0, 'VERTEX', "#cubeverts-array")
        input_list.addInput(1, 'NORMAL', "#cubenormals-array")

        indices = numpy.array([0, 0, 2, 1, 3, 2, 0, 0, 3, 2, 1, 3, 0, 4, 1, 5, 5, 6, 0, 4, 5, 6, 4, 7, 6, 8, 7, 9, 3, 10, 6, 8, 3, 10, 2, 11, 0, 12,
                               4, 13, 6, 14, 0, 12, 6, 14, 2, 15, 3, 16, 7, 17, 5, 18, 3, 16, 5, 18, 1, 19, 5, 20, 7, 21, 6, 22, 5, 20, 6, 22, 4, 23])
        triangleset = geometry.createTriangleSet(
            indices, input_list, "cubematerial")
        geometry.primitives.append(triangleset)
        mesh.geometries.append(geometry)

        geomnode = collada.scene.GeometryNode(geometry, [])
        mynode = collada.scene.Node(
            'mynode6', children=[geomnode], transforms=[])
        scene = collada.scene.Scene('myscene', [mynode])
        mesh.scenes.append(scene)
        mesh.scene = scene

        mesh.save()

        geoms = list(mesh.scene.objects('geometry'))
        self.assertEqual(len(geoms), 1)

        prims = list(geoms[0].primitives())
        self.assertEqual(len(prims), 1)

        tris = list(prims[0])
        self.assertEqual(len(tris), 12)

        self.assertEqual(list(tris[0].vertices[0]), [-50.0, 50.0, 50.0])
        self.assertEqual(list(tris[0].vertices[1]), [-50.0, -50.0, 50.0])
        self.assertEqual(list(tris[0].vertices[2]), [50.0, -50.0, 50.0])
        self.assertEqual(list(tris[0].normals[0]), [0.0, 0.0, 1.0])
        self.assertEqual(list(tris[0].normals[1]), [0.0, 0.0, 1.0])
        self.assertEqual(list(tris[0].normals[2]), [0.0, 0.0, 1.0])
        self.assertEqual(tris[0].texcoords, [])
        self.assertEqual(tris[0].material, None)
        self.assertEqual(list(tris[0].indices), [0, 2, 3])
        self.assertEqual(list(tris[0].normal_indices), [0, 1, 2])
        self.assertEqual(tris[0].texcoord_indices, [])
示例#27
0
def fv_scalar_to_collada(verts, faces, scalars):
    # color = color_func(scalars)
    a = (scalars - np.min(scalars)) / (np.max(scalars) - np.min(scalars)) * 256
    color = cm.jet(a.astype(int))
    color = np.delete(color, 3, 1)

    #create collada obj
    mesh = collada.Collada()

    #add shading
    effect = collada.material.Effect("effect0",\
      [], #TEXTURES GO HERE
      "phong", diffuse=(1,1,1), specular=(1,1,1),
      double_sided=True)
    mat = collada.material.Material("material0", "mymaterial", effect)
    mesh.effects.append(effect)
    mesh.materials.append(mat)

    vert_src = collada.source.FloatSource("verts-array", verts,
                                          ('X', 'Y', 'Z'))
    color_src = collada.source.FloatSource("colors-array", np.array(color),
                                           ('R', 'G', 'B'))

    geom = collada.geometry.Geometry(mesh, "geometry0", "fsave_test",\
      [vert_src,color_src])

    #creates list of inputs for collada DOM obj...so many decorators
    input_list = collada.source.InputList()

    input_list.addInput(0, 'VERTEX', "#verts-array")
    input_list.addInput(1, 'COLOR', "#colors-array")

    #creates faces
    triset = geom.createTriangleSet(
      np.concatenate([faces,faces],axis=1),\
      input_list, "materialref")

    triset.generateNormals()

    geom.primitives.append(triset)
    mesh.geometries.append(geom)

    #creates scene node, which causes display
    matnode = collada.scene.MaterialNode("materialref", mat, inputs=[])
    geomnode = collada.scene.GeometryNode(geom, [matnode])
    node = collada.scene.Node("node0", children=[geomnode])

    #create scene
    myscene = collada.scene.Scene("fs_base_scene", [node])
    mesh.scenes.append(myscene)
    mesh.scene = myscene

    buf = io.BytesIO()
    mesh.write(buf)
    return buf
示例#28
0
def getInertia(geometry, m, s):
    print("\033[97m Link name: \033[0m" + link_name)
    print("\033[93m Mass: \033[0m" + str(m))
    print("\033[95m Scale: \033[0m" + str(s))
    xx = yy = zz = 0.0
    if type(geometry) == Mesh:
        print("\033[94m Mesh: \033[0m" + geometry.filename)
        print("---\nCalculating inertia...\n---")
        ROS_VERSION = os.getenv("ROS_VERSION")
        get_pkg_fn = None
        if not ROS_VERSION:
            print("Could not find the ROS_VERSION environment variable, thus, can't determine your ros version. Assuming ROS2!")
            ROS_VERSION = "2"
        if ROS_VERSION == "1":
            import rospkg
            get_pkg_fn = rospkg.RosPack().get_path
        else:
            import ament_index_python
            get_pkg_fn = ament_index_python.get_package_share_path
        pkg_tag = "package://"
        file_tag = "file://"
        mesh_file = ""
        if geometry.filename.startswith(pkg_tag):
            package, mesh_file = geometry.filename.split(pkg_tag)[1].split(os.sep, 1)
            print(get_pkg_fn(package))
            mesh_file = str(get_pkg_fn(package))+os.sep+mesh_file
        elif geometry.filename.startswith(file_tag):
            mesh_file = geometry.filename.replace(file_tag, "")
        x = y = z = 0
        if mesh_file.endswith(".stl"):
            model = mesh.Mesh.from_file(mesh_file)
            x,y,z = getSTLDimensions(model)
        # Assuming .dae
        else:
            model = collada.Collada(mesh_file)
            x,y,z = getColladaDimensions(model)
        xx,yy,zz = getBoxInertia(x, y, z, m, s)
    elif type(geometry) == Box:
        print("\033[94m Box: \033[0m" + str(geometry.size))
        print("---\nCalculating inertia...\n---")
        x,y,z = geometry.size
        xx,yy,zz = getBoxInertia(x, y, z, m, s)
    elif type(geometry) == Sphere:
        print("\033[94m Sphere Radius: \033[0m" + str(geometry.radius))
        print("---\nCalculating inertia...\n---")
        xx,yy,zz = getSphereInertia(geometry.radius, m)
    elif type(geometry) == Cylinder:
        print("\033[94m Cylinder Radius and Length: \033[0m" + str(geometry.radius) + "," + str(geometry.length))
        print("---\nCalculating inertia...\n---")
        xx,yy,zz = getCylinderInertia(geometry.radius, geometry.length, m)

    print("\033[92m")
    print("<inertia  ixx=\"%s\" ixy=\"0\" ixz=\"0\" iyy=\"%s\" iyz=\"0\" izz=\"%s\" />" % (xx,yy,zz))
    print("\033[0m")
示例#29
0
    def __init__(self, model_part, collada_filename, import_normals=False):
        self.model_part = model_part
        self.collada_filename = str(collada_filename)
        self.import_normals = import_normals

        #open and import the collada collada_file
        print("attempting to open ", self.collada_filename)
        f = open(self.collada_filename, 'rb')

        self.collada_mesh = collada.Collada(f)
        f.close()
示例#30
0
    def export_collada(self):
        # not yet working
        import collada
        mesh = collada.Collada()

        effect = collada.material.Effect("effect0", [],
                                         "phong",
                                         diffuse=(1, 0, 0),
                                         specular=(0, 1, 0))
        mat = collada.material.Material("material0", "mymaterial", effect)
        mesh.effects.append(effect)
        mesh.materials.append(mat)