Beispiel #1
0
 def get_area(self):
     pt1 = ModelData.dictVertices[self.__v[0]]
     pt2 = ModelData.dictVertices[self.__v[1]]
     pt3 = ModelData.dictVertices[self.__v[2]]
     pt1pt2 = SimpleMath.tuple_minus(pt2, pt1)
     pt1pt3 = SimpleMath.tuple_minus(pt3, pt1)
     return 0.5 * SimpleMath.vector_length_3(SimpleMath.cross_product_3(pt1pt2, pt1pt3))
Beispiel #2
0
def keep_tetrahedron(curTetId, faceIDsInCurTet):
    #use the tag of the tetrahedron
    if ModelData.dictTetrahedrons[curTetId].get_tag == ClassFace.FIX:
        return
    #set the tag
    ModelData.dictTetrahedrons[curTetId].set_tag(ClassFace.FIX)
    #deal with all the known faces
    for j in faceIDsInCurTet:
        if  ModelData.dictFaces[j].get_tag() != ClassFace.FIX:
            ModelData.dictFaces[j].set_tag(ClassFace.KEEP)
    #add the unkown faces and define them as KEEP (in order to seperate KEEP and FIX)
    if len(faceIDsInCurTet) < 4:
        vertexList = ModelData.dictTetrahedrons[curTetId].get_vids()
        faceList = []
        faceList.append((vertexList[0], vertexList[1], vertexList[2]))
        faceList.append((vertexList[0], vertexList[2], vertexList[3]))
        faceList.append((vertexList[0], vertexList[3], vertexList[1]))
        faceList.append((vertexList[1], vertexList[2], vertexList[3]))
        for f in faceList:
            isDefined = False
            for i in faceIDsInCurTet:
                if ModelData.dictFaces[i].is_equal_geometry(ClassFace.Class_face(f)):
                    isDefined = True
                    break
            if not isDefined :
                tetNormal = []
                for v in vertexList:
                    if v not in f:
                        #facing outwards
                        tetNormal = SimpleMath.tuple_minus(ModelData.dictVertices[f[0]], ModelData.dictVertices[v])
                        break
                #do not have to consider semantics at this moment
                fId = ModelDataFuncs.add_face(ClassFace.Class_face(ModelDataFuncs.create_orientated_vids(f, tetNormal), ClassFace.KEEP))
Beispiel #3
0
def constraint_5(curTetId, faceIDsInCurTet):
    bIsInterior = False
    for i in faceIDsInCurTet:
        if ModelData.dictFaces[i].get_tag() == ClassFace.FIX:
            #normal check
            vIds = ModelData.dictFaces[i].get_vids()
            vectorNormal = SimpleMath.get_face_normal([ModelData.dictVertices[vIds[0]], ModelData.dictVertices[vIds[1]], ModelData.dictVertices[vIds[2]]])
            for v in ModelData.dictTetrahedrons[curTetId].get_vids():
                if v not in vIds:
                    #test whether the tetrahedron is in the interior
                    vectorTest = SimpleMath.tuple_minus(ModelData.dictVertices[v], ModelData.dictVertices[vIds[0]]);
                    if SimpleMath.dot_product_3(vectorNormal , vectorTest) < 0:
                        #find one inside
                        return True
    return bIsInterior
Beispiel #4
0
def reader_obj(FILEPATH):
    try:
        f_obj = file(FILEPATH, "r")
    except:
        print ("Invalide file: " + MIDFILEPATH)
        return False
    # read vertics and ModelData.dictFaces
    statFace = 0
    for line in f_obj:
        if line.startswith("v") and line[1] == " ":
            line = line[1:-1].strip()
            vertList = map(float, line.split(" "))
            add_vertexEx([vertList[0], vertList[1], vertList[2]])
        elif line.startswith("f") and line[1] == " ":
            indexList = []
            # to filter out the /
            for index in line[1:-1].strip().split(" "):
                indexList.append(index.split("/")[0])
            statFace = statFace + 1
            if len(indexList) > 2:
                # index - 1
                indexList = [int(i) - 1 for i in indexList]
                add_face(Class_face((indexList[0], indexList[1], indexList[2]), ClassFace.FIX))
    # check the content
    if len(ModelData.dictFaces) == 0 or len(ModelData.dictVertices) == 0:
        print "Invalid Obj file!\n"
        return False
    else:
        print ("Remove " + str(statFace - len(ModelData.dictFaces)) + " invalid ModelData.dictFaces")
        print (
            "Read "
            + str(len(ModelData.dictFaces))
            + " ModelData.dictFaces and "
            + str(len(ModelData.dictVertices))
            + " ModelData.dictVertices"
        )

    f_obj.close()

    # optimise the coordinates by translate and scale
    for key in ModelData.dictVertices:
        ModelData.centerVertex = SimpleMath.tuple_plus(ModelData.centerVertex, ModelData.dictVertices[key])
    ModelData.centerVertex = SimpleMath.tuple_numproduct(1.0 / len(ModelData.dictVertices), ModelData.centerVertex)
    # maxpt = [-9999999999.0, -9999999999.0, -9999999999.0]
    # minpt = [9999999999.0, 9999999999.0, 9999999999.0]
    for key in ModelData.dictVertices:
        ModelData.dictVertices[key] = SimpleMath.tuple_minus(ModelData.dictVertices[key], ModelData.centerVertex)
        # if ModelData.dictVertices[key][0] > maxpt[0]:
        #    maxpt[0] = ModelData.dictVertices[key][0]
        # if ModelData.dictVertices[key][1] > maxpt[1]:
        #    maxpt[1] = ModelData.dictVertices[key][1]
        # if ModelData.dictVertices[key][2] > maxpt[2]:
        #    maxpt[2] = ModelData.dictVertices[key][2]

        # if ModelData.dictVertices[key][0] < minpt[0]:
        #    minpt[0] = ModelData.dictVertices[key][0]
        # if ModelData.dictVertices[key][1] < minpt[1]:
        #    minpt[1] = ModelData.dictVertices[key][1]
        # if ModelData.dictVertices[key][2] < minpt[2]:
        #    minpt[2] = ModelData.dictVertices[key][2]
    # ModelData.scaleVertex = ModelData.scaleVertex / SimpleMath.vector_length_3(SimpleMath.tuple_minus(maxpt, minpt))
    # for key in ModelData.dictVertices:
    #    ModelData.dictVertices[key] = SimpleMath.tuple_numproduct(ModelData.scaleVertex, ModelData.dictVertices[key])
    if ModelData.global_DO_TRUNCATE:
        truncate_verts(ModelData.global_TOL_TRUNCATE)
    print (">>>>>>Eliminate degeneracies...")
    clean_duplicated_vertices()
    print ("{} illshaped ModelData.dictFaces are removed").format(discard_illshaped_faces())
    print (
        "After cleaning redundant ModelData.dictVertices there are "
        + str(len(ModelData.dictFaces))
        + " ModelData.dictFaces and "
        + str(len(ModelData.dictVertices))
        + " ModelData.dictVertices"
    )
    return True
Beispiel #5
0
def optimise_illshaped_shellfaces():
    iCount = 0
    for key in ModelData.listShellFaceIDs:
        if key not in ModelData.dictFaces:
            continue
        if (
            ModelData.global_OPTIMAL_SHP
            and ModelData.dictFaces[key].get_tag() != ClassFace.FLIP
            and ModelData.dictFaces[key].get_area() < ModelData.global_TOL_AREA_DISCARD
        ):
            print key
            vert0 = ModelData.dictVertices[ModelData.dictFaces[key].get_vids()[0]]
            vert1 = ModelData.dictVertices[ModelData.dictFaces[key].get_vids()[1]]
            vert2 = ModelData.dictVertices[ModelData.dictFaces[key].get_vids()[2]]
            # face collapse or flip
            # calculate vectors
            vector01 = SimpleMath.tuple_minus(vert0, vert1)
            length01 = SimpleMath.vector_length_3(vector01)
            if length01 > SimpleMath.Tol:
                vector01 = SimpleMath.tuple_numproduct(1.0 / length01, vector01)
            else:
                iCount += 1
                collapse_edge(ModelData.dictFaces[key].get_vids()[0], ModelData.dictFaces[key].get_vids()[1])
                continue

            vector21 = SimpleMath.tuple_minus(vert2, vert1)
            length21 = SimpleMath.vector_length_3(vector21)
            if length21 > SimpleMath.Tol:
                vector21 = SimpleMath.tuple_numproduct(1.0 / length21, vector21)
            else:
                iCount += 1
                collapse_edge(ModelData.dictFaces[key].get_vids()[2], ModelData.dictFaces[key].get_vids()[1])
                continue

            vector02 = SimpleMath.tuple_minus(vert0, vert2)
            length02 = SimpleMath.vector_length_3(vector02)
            if length02 > SimpleMath.Tol:
                vector02 = SimpleMath.tuple_numproduct(1.0 / length02, vector02)
            else:
                iCount += 1
                collapse_edge(ModelData.dictFaces[key].get_vids()[0], ModelData.dictFaces[key].get_vids()[2])
                continue

            # calculate angles
            Ang012 = SimpleMath.dot_product_3(vector01, vector21)
            Ang102 = SimpleMath.dot_product_3(vector01, vector02)
            vector12 = SimpleMath.tuple_numproduct(-1, vector21)
            Ang021 = SimpleMath.dot_product_3(vector02, vector12)
            # cos value
            if Ang012 < ModelData.global_TOL_LARGEST_ANGLE:
                # flip 20
                iCount += 1
                flip_edge(ModelData.dictFaces[key].get_vids()[2], ModelData.dictFaces[key].get_vids()[0])
            elif Ang102 < ModelData.global_TOL_LARGEST_ANGLE:
                # flip 12
                iCount += 1
                flip_edge(ModelData.dictFaces[key].get_vids()[1], ModelData.dictFaces[key].get_vids()[2])
            elif Ang021 < ModelData.global_TOL_LARGEST_ANGLE:
                # flip 01
                iCount += 1
                flip_edge(ModelData.dictFaces[key].get_vids()[0], ModelData.dictFaces[key].get_vids()[1])
    #
    # clean_unreferenced_vertices()
    print ("{} illshaped ModelData.dictFaces are optimized").format(iCount)
    if iCount > 0:
        return True
    else:
        return False
Beispiel #6
0
def reader_poly_with_semantics(str_filepath):
    fin = file(str_filepath, "r")
    # read the first line and try to extract semantics
    strFirstLine = fin.readline().split()
    if strFirstLine[0] == "#":
        # read the building id
        ModelData.strModelID = strFirstLine[1]
        # whether the geometry is a solid:1 or a multisurface:0
        ModelData.isSolid = fin.readline().split()[1]
        # the point information
        strFirstLine = int(fin.readline().split()[0])
    else:
        # no semanics
        ModelData.strModelID = "-1"
        # we assume it is a solid
        ModelData.isSolid = "1"
        # the point information
        strFirstLine = int(strFirstLine[0])
    # read all the points
    for i in range(strFirstLine):
        vertList = map(float, fin.readline().split()[1:4])
        add_vertexEx((vertList[0], vertList[1], vertList[2]))
    # read each face
    nof = int(fin.readline().split()[0])
    strPolygonid = ""
    strPolygontype = ""
    for i in range(nof):
        strPolygoninfo = fin.readline().split()
        numRings = int(strPolygoninfo[0])
        if numRings != 1:
            print ("The input has not been tesselated")
            return False
        if len(strPolygoninfo) >= 4:
            strPolygonid = strPolygoninfo[3]
        if len(strPolygoninfo) >= 6:
            strPolygontype = strPolygoninfo[5]
        oring = map(int, fin.readline().split())
        if len(oring) > 4:
            print ("The input has not been tesselated")
            return False
        oring.pop(0)
        if len(oring) == 3:
            add_face(Class_face((oring[0], oring[1], oring[2]), ClassFace.FIX, strPolygonid, strPolygontype))

    # check the content
    if len(ModelData.dictFaces) == 0 or len(ModelData.dictVertices) == 0:
        print "Invalid Poly file!\n"
        return False
    else:
        print ("Remove " + str(nof - len(ModelData.dictFaces)) + " invalid Faces")
        print ("Read " + str(len(ModelData.dictFaces)) + " Faces and " + str(len(ModelData.dictVertices)) + " Vertices")
    fin.close()

    # optimise the coordinates by translate and scale
    for key in ModelData.dictVertices:
        ModelData.centerVertex = SimpleMath.tuple_plus(ModelData.centerVertex, ModelData.dictVertices[key])
    ModelData.centerVertex = SimpleMath.tuple_numproduct(1.0 / len(ModelData.dictVertices), ModelData.centerVertex)
    for key in ModelData.dictVertices:
        ModelData.dictVertices[key] = SimpleMath.tuple_minus(ModelData.dictVertices[key], ModelData.centerVertex)
    if ModelData.global_DO_TRUNCATE:
        truncate_verts(ModelData.global_TOL_TRUNCATE)
    print ("--Eliminate degeneracies")
    clean_duplicated_vertices()
    print ("{} illshaped ModelData.dictFaces are removed").format(discard_illshaped_faces())
    print (
        "After cleaning redundant ModelData.dictVertices there are "
        + str(len(ModelData.dictFaces))
        + " Faces and "
        + str(len(ModelData.dictVertices))
        + " Vertices"
    )
    return True