2017-12-09 6 views
1

vrmlファイルのテキストの一部を解析しようとしています。具体的には、座標点(フィールドポイント)とポイント間の連結性(フィールドcoordIndex)で定義される一連の三角形を表すIndexedFaceSetsに含まれる情報に興味があります。ブロック単位でファイルを解析し、Pythonで各ブロックの情報を抽出する

テキストの単一のindexedFaceSet(最初のもの)を解析する関数を作成しましたが、コードを変更する方法について頭を悩めることができませんので、各IndexedFaceSetに次のリスト[translate,verts,facets,normals]を格納できます。

My機能は次のとおり

def extractDataFromVRML(root): 
    #Lists to be populated 
    translate=[] 
    verts=[] 
    facets=[] 
    normals=[] 
    #Parsing the vrml file 
    f=open(root+'.wrl') 
    while 1:# skip through initial stuff 
     linney=str.split(f.readline()) 
    # print linney 
     if len(linney) == 4: 
     if linney[0] == 'translation': #Not shown in th vrml example 
      transx = float(linney[1]) 
      transy = float(linney[2]) 
      transz = float(linney[3]) 
      t=[transx,transy,transz] 
      translate.append(t) 
     if linney == ['point', '[']: 
     break 
    #print 'Reading vertex coordinates.' 
    while 1: 
     xyz = f.readline() 
     i = str.find(xyz,',') 
     if i < 0: # end of vertex coordinates 
     break 
     verts.append(xyz[:i]) # building a list of xyz strings 
    print ('We have',len(verts)-1,'vertices.') 
    #for v in verts: print v 
    print ('Reading triangles.') 
    while 1: 
     linney=f.readline() 
     if linney == '}\n': 
     break  # end of file 
     abc = str.split(str.replace(linney,',',' ')) # l of vertex ids 
     if len(abc) < 3: 
     continue # separation between groups of triangles 
     # look up a vertex in the list to generate a triangle tuple 
     xyz = str.split(verts[int(abc[0])]) 
     p1=[float(xyz[0]),float(xyz[1]),float(xyz[2])]  
     xyz = str.split(verts[int(abc[1])]) 
     p2=[float(xyz[0]),float(xyz[1]),float(xyz[2])]  
     xyz = str.split(verts[int(abc[2])]) 
     p3=[float(xyz[0]),float(xyz[1]),float(xyz[2])]  
     tri=[p1,p2,p3] 
     facets.append(tri) 
     #n=getNormals(p1[0],p1[1],p1[2],p2[0],p2[1],p2[2],p3[0],p3[1],p3[2]) 
     #normals.append(n) 
    print ('END') 
    return [translate,verts,facets,normals] 

VRMLでキューブの例は次のとおりです。

#VRML V2.0 utf8 

WorldInfo { 
    info [ "File created using CATIA" ] 
} 
NavigationInfo { 
    type [ "EXAMINE" , "WALK" , "FLY" ] 
} 
Background { 
    skyColor [ 1 1 1 ] 
} 
Viewpoint { 
    position  0.411502 0.183945 0.216403 
    orientation 0.326678 0.502925 0.800218 2.185925 
    fieldOfView 0.471225 
    description "Main Viewpoint" 
} 
Viewpoint { 
    position  0.288675 0.288675 0.288675 
    orientation 0.187053 0.451587 0.872399 2.448076 
    fieldOfView 0.471225 
    description "Iso View" 
} 
Viewpoint { 
    position  0.500000 0.000000 0.000000 
    orientation 0.577350 0.577350 0.577350 2.094395 
    fieldOfView 0.471225 
    description "Front View" 
} 
Viewpoint { 
    position  -0.500000 0.000000 0.000000 
    orientation 0.577350 -0.577350 -0.577350 2.094395 
    fieldOfView 0.471225 
    description "Back View" 
} 
Viewpoint { 
    position  0.000000 -0.500000 0.000000 
    orientation 1.000000 -0.000173 0.000173 1.570796 
    fieldOfView 0.471225 
    description "Left View" 
} 
Viewpoint { 
    position  0.000000 0.500000 0.000000 
    orientation -0.000122 -0.707107 -0.707107 3.141348 
    fieldOfView 0.471225 
    description "Right View" 
} 
Viewpoint { 
    position  0.000000 0.000000 0.500000 
    orientation 0.000000 0.000000 1.000000 1.570796 
    fieldOfView 0.471225 
    description "Top View" 
} 
Viewpoint { 
    position  0.000000 0.000000 -0.500000 
    orientation 0.707107 0.707107 0.000000 3.141593 
    fieldOfView 0.471225 
    description "Bottom View" 
} 
Transform { 
    scale   0.001 0.001 0.001 
    children [ 
Group { 
    children [ 
Group { 
    children [ 
DEF _000000002346A9A0 Group { 
    children [ 
    ] 
} 
    ] 
} 
Group { 
    children [ 
DEF _0000000023470B20 Group { 
    children [ 
    ] 
} 
    ] 
} 
Group { 
    children [ 
DEF _00000000234700D0 Group { 
    children [ 
    ] 
} 
    ] 
} 
Group { 
    children [ 
Group { 
    children [ 
DEF _0000000020D0F390 Group { 
    children [ 
Shape { 
appearance Appearance { 
    material DEF _material0 Material { 
     diffuseColor 0.823529 0.823529 1 
    } 
} 
geometry IndexedFaceSet { 
solid FALSE 
coord Coordinate { 
    point [ 
     0 50 50, 
     50 50 50, 
     50 0 50, 
     0 0 50, 
     ] 
    } 
coordIndex [ 
3,2,0,-1, 
2,1,0,-1, 
] 

} 
} 
Shape { 
appearance Appearance { 
material USE _material0 
} 
geometry IndexedFaceSet { 
solid FALSE 
coord Coordinate { 
    point [ 
     0 50 0, 
     50 50 0, 
     50 0 0, 
     0 0 0, 
     ] 
    } 
coordIndex [ 
3,0,2,-1, 
0,1,2,-1, 
] 

} 
} 
Shape { 
appearance Appearance { 
material USE _material0 
} 
geometry IndexedFaceSet { 
solid FALSE 
coord Coordinate { 
    point [ 
     0 0 50, 
     0 0 0, 
     0 50 0, 
     0 50 50, 
     ] 
    } 
coordIndex [ 
2,1,3,-1, 
1,0,3,-1, 
] 

} 
} 
Shape { 
appearance Appearance { 
material USE _material0 
} 
geometry IndexedFaceSet { 
solid FALSE 
coord Coordinate { 
    point [ 
     0 50 50, 
     0 50 0, 
     50 50 0, 
     50 50 50, 
     ] 
    } 
coordIndex [ 
2,1,3,-1, 
1,0,3,-1, 
] 

} 
} 
Shape { 
appearance Appearance { 
material USE _material0 
} 
geometry IndexedFaceSet { 
solid FALSE 
coord Coordinate { 
    point [ 
     50 50 50, 
     50 50 0, 
     50 0 0, 
     50 0 50, 
     ] 
    } 
coordIndex [ 
2,1,3,-1, 
1,0,3,-1, 
] 

} 
} 
Shape { 
appearance Appearance { 
material USE _material0 
} 
geometry IndexedFaceSet { 
solid FALSE 
coord Coordinate { 
    point [ 
     50 0 50, 
     50 0 0, 
     0 0 0, 
     0 0 50, 
     ] 
    } 
coordIndex [ 
2,1,3,-1, 
1,0,3,-1, 
] 

} 
} 
    ] 
} 
    ] 
} 
    ] 
} 
    ] 
} 
    ] 
} 
+0

あなたの予想される出力は何を?簡素化するitertools.takewhile()itertools.dropwhile()機能を使用loggingライブラリ

  • から作成されたロガーオブジェクトを使用しますか –

  • +0

    期待される出力は理想的には、 'IndexedFaceSet 1,2,3 ...'というキーと対応するデータ、すなわち各面に関連付けられた[translate、verts、facets、normals]キーを持つ辞書です(現在の関数の出力、現時点で最初のIndexedFaceSetの場合)。 – user3641829

    答えて

    1

    これは非自明な解析の問題です。あなたが解析するためのいくつかのPythonパッケージを見つけることができれば、それが最適でしょう。私のアプローチは次のとおりです:行単位でファイルをスキャンします。私が理解していることが分かったら、残りの行をそのブロックのパーサーに渡してください。たとえば、 "geometry IndexedFaceSet"という行で始まるブロックを解析するパーサーがあります。開発中に

    import itertools 
    import json 
    import logging 
    from pprint import pprint 
    import os 
    
    # For the next line, use logging.WARN to turn off debug print, use 
    # logging.DEBUG to turn on 
    logging.basicConfig(level=os.getenv('LOGLEVEL', logging.WARN)) 
    logger = logging.getLogger(__name__) 
    
    
    def skip_pass(marker, lines): 
        """ 
        Skip until reach the line which contains the marker, then also skip 
        the marker line 
        """ 
        result = itertools.dropwhile(
         lambda line: marker not in line, # Condition 
         lines)       # The lines 
        next(result)       # skip pass the marker 
        return result 
    
    def take(marker, lines): 
        """ 
        Take and return those lines which contains a marker 
        """ 
        result = itertools.takewhile(
         lambda line: marker in line,  # Condition 
         lines)       # The lines 
        return result 
    
    def parse_indexed_face_set(translate, lines): 
        """ 
        Parse one block of 'geometry IndexedFaceSet' 
        """ 
        # lines = skip_pass('geometry IndexedFaceSet', lines) 
    
        # Parse the "point" structure 
        lines = skip_pass('point', lines) 
        point_lines = take(',', lines) 
        verts = [[float(token) for token in line.strip(',\n').split()] for line in point_lines] 
        logger.debug('verts: %r', verts) 
    
        # parse the coordIndex structure 
        lines = skip_pass('coordIndex', lines) 
        coor_lines = take(',', lines) 
        coord_index = [tuple(int(token) for token in line.strip(',\n').split(',')) for line in coor_lines] 
        logger.debug('coord_index: %r', coord_index) 
    
        facets = [[verts[i] for i in indices[:3]] for indices in coord_index] 
        logger.debug('facets: %r', facets) 
    
        return dict(vert=verts, facets=facets, translate=translate, normals=[]) 
    
    def parse_translate(line): 
        """ 
        Given a line such as: "translate 5 6 7", return [5.0, 6.0, 7.0] 
        """ 
        translate = [float(x) for x in line.split()[1:4]] 
        return translate 
    
    def extractDataFromVRML(root): 
        indexed_face_sets = [] 
        translate = [] 
        with open(root + '.wrl') as infile: 
         for line in infile: 
          if 'geometry IndexedFaceSet' in line: 
           a_set = parse_indexed_face_set(translate=translate, lines=infile) 
           indexed_face_sets.append(a_set) 
          elif 'translation' in line and line.split()[0] == 'translation': 
           translate = parse_translate(line) 
    
        return indexed_face_sets 
    
    
    # main 
    indexed_face_sets = extractDataFromVRML('root') 
    for a_set in indexed_face_sets: 
        print('vert:', a_set['vert']) 
        print('facets:', a_set['facets']) 
        print('---') 
    

    出力

    vert: [[0.0, 50.0, 50.0], [50.0, 50.0, 50.0], [50.0, 0.0, 50.0], [0.0, 0.0, 50.0]] 
    facets: [[[0.0, 0.0, 50.0], [50.0, 0.0, 50.0], [0.0, 50.0, 50.0]], [[50.0, 0.0, 50.0], [50.0, 50.0, 50.0], [0.0, 50.0, 50.0]]] 
    --- 
    vert: [[0.0, 50.0, 0.0], [50.0, 50.0, 0.0], [50.0, 0.0, 0.0], [0.0, 0.0, 0.0]] 
    facets: [[[0.0, 0.0, 0.0], [0.0, 50.0, 0.0], [50.0, 0.0, 0.0]], [[0.0, 50.0, 0.0], [50.0, 50.0, 0.0], [50.0, 0.0, 0.0]]] 
    --- 
    vert: [[0.0, 0.0, 50.0], [0.0, 0.0, 0.0], [0.0, 50.0, 0.0], [0.0, 50.0, 50.0]] 
    facets: [[[0.0, 50.0, 0.0], [0.0, 0.0, 0.0], [0.0, 50.0, 50.0]], [[0.0, 0.0, 0.0], [0.0, 0.0, 50.0], [0.0, 50.0, 50.0]]] 
    --- 
    vert: [[0.0, 50.0, 50.0], [0.0, 50.0, 0.0], [50.0, 50.0, 0.0], [50.0, 50.0, 50.0]] 
    facets: [[[50.0, 50.0, 0.0], [0.0, 50.0, 0.0], [50.0, 50.0, 50.0]], [[0.0, 50.0, 0.0], [0.0, 50.0, 50.0], [50.0, 50.0, 50.0]]] 
    --- 
    vert: [[50.0, 50.0, 50.0], [50.0, 50.0, 0.0], [50.0, 0.0, 0.0], [50.0, 0.0, 50.0]] 
    facets: [[[50.0, 0.0, 0.0], [50.0, 50.0, 0.0], [50.0, 0.0, 50.0]], [[50.0, 50.0, 0.0], [50.0, 50.0, 50.0], [50.0, 0.0, 50.0]]] 
    --- 
    vert: [[50.0, 0.0, 50.0], [50.0, 0.0, 0.0], [0.0, 0.0, 0.0], [0.0, 0.0, 50.0]] 
    facets: [[[0.0, 0.0, 0.0], [50.0, 0.0, 0.0], [0.0, 0.0, 50.0]], [[50.0, 0.0, 0.0], [50.0, 0.0, 50.0], [0.0, 0.0, 50.0]]] 
    --- 
    

    ノート

    • は、私はよく目的をデバッグするためのいくつかの値を印刷する必要があります。そのために、私はいくつかのタスク
    +0

    Hai Vu、これは素晴らしいコードです。問題に取り組む前の試みよりはるかにクリーンな方法です!ありがとうございました! – user3641829

    関連する問題