• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            eryar

            PipeCAD - Plant Piping Design Software.
            RvmTranslator - Translate AVEVA RVM to OBJ, glTF, etc.
            posts - 603, comments - 590, trackbacks - 0, articles - 0

            OpenCASCADE BRepTools

            Posted on 2015-03-14 20:18 eryar 閱讀(5257) 評(píng)論(0)  編輯 收藏 引用 所屬分類: 2.OpenCASCADE

            OpenCASCADE BRepTools

            eryar@163.com

            Abstract. OpenCASCADE BRepTools provides utilities for BRep data structure. OuterWire method to find the outer wire of a face. Dump method to dump a BRep object. It also can be used as the data exchange for OpenCASCADE native shapes. 

            Key Words. OpenCASCADE, BRepTools, BRep, Topology

            1. Introduction

            OpenCASCADE提供了一個(gè)類BRepTools,其中有許多static函數(shù),主要用來對(duì)BRep表示的拓樸形狀的數(shù)據(jù)進(jìn)行讀寫,也提供了查找一個(gè)面中外環(huán)(Outer Wire)的函數(shù)。因?yàn)镺penCASCADE中的邊界表示法BRep的數(shù)據(jù)結(jié)構(gòu)如下圖1.1所示:

            wps_clip_image-4070

            Figure 1.1 BRep Data Structure of OpenCASCADE

            因?yàn)镺penCASCADE中拓樸結(jié)構(gòu)采用了包含關(guān)系,當(dāng)需要將TopoDS_Shape數(shù)據(jù)保存到文件時(shí),如何保持TopoDS_Shape中的關(guān)系,以便于從文件讀取這些數(shù)據(jù)時(shí),可以重構(gòu)出TopoDS_Shape中的各種關(guān)系?

            參考o(jì)pennurbs中的BRep表示時(shí)數(shù)據(jù)的存儲(chǔ)方式,可知直接在BRep中保存拓樸及幾何數(shù)據(jù)的索引,這樣對(duì)數(shù)據(jù)的存儲(chǔ)及讀取時(shí)重構(gòu)拓樸結(jié)構(gòu)還是很方便的。而在OpenCASCADE中拓樸數(shù)據(jù)是以Handle來保存的,且為組合關(guān)系,即一個(gè)父結(jié)構(gòu)中有一個(gè)列表(TopoDS_ListOfShape)給包含了子結(jié)構(gòu)數(shù)據(jù)。對(duì)于沒有索引的OpenCASCADE的拓樸結(jié)構(gòu),如何進(jìn)行讀寫操作呢?

            本文結(jié)合類BRepTools中的函數(shù),對(duì)OpenCASCADE中TopoDS_Shape數(shù)據(jù)的保存和讀取功能的代碼進(jìn)行分析,從而對(duì)ModelingData中的BRep數(shù)據(jù)做進(jìn)一步的理解。

            2.Topology Shape Serialization

            OpenCASCADE的類BRepTools中提供了如下函數(shù),可以TopoDS_Shape中的數(shù)據(jù)進(jìn)行導(dǎo)入導(dǎo)出:

            v BRepTools::Dump();

            v BRepTools::Read();

            v BRepTools::Write();

            這幾個(gè)函數(shù)比較常用,因?yàn)榭梢苑奖愕貙opoDS_Shape導(dǎo)出,或?qū)氲絆penCASCADE的Draw Test Harness中,來對(duì)程序一些算法進(jìn)行驗(yàn)證。對(duì)于使用了組合關(guān)系的TopoDS_Shape如何確保數(shù)據(jù)的保存及讀取后,能夠維持這些關(guān)系?帶著這個(gè)問題去看BRep文件讀寫的功能,應(yīng)該更為清晰。

            還是看看代碼,如下所示為輸出TopoDS_Shape的函數(shù),在程序Debug時(shí)比較常用:

            //=======================================================================
            //function : Dump
            //purpose  : 
            //=======================================================================
            void  BRepTools::Dump(const TopoDS_Shape& Sh, Standard_OStream& S)
            {
              BRepTools_ShapeSet SS;
              SS.Add(Sh);
              SS.Dump(Sh,S);
              SS.Dump(S);
            }

            其中使用了類BRepTools_ShapeSet,這里的Set的意思我理解為集合的意思,其Add函數(shù)如下:


            //=======================================================================
            //function : Add
            //purpose  : 
            //=======================================================================
            Standard_Integer  TopTools_ShapeSet::Add(const TopoDS_Shape& S)
            {
              
            if (S.IsNull()) return 0;
              myLocations.Add(S.Location());
              TopoDS_Shape S2 
            = S;
              S2.Location(TopLoc_Location());
              Standard_Integer index 
            = myShapes.FindIndex(S2);
              
            if (index == 0) {
                AddGeometry(S2);

                
            for (TopoDS_Iterator its(S2,Standard_False,Standard_False);
                     its.More(); its.Next())
                  Add(its.Value());
                index 
            = myShapes.Add(S2);
              }
              
            return index;
            }

            這是一個(gè)遞歸函數(shù),通過AddGeometry函數(shù),將TopoDS_Shape中的幾何信息都保存到相應(yīng)的集合Set中,Set中使用了Map,即給每個(gè)幾何信息一個(gè)唯一的編號(hào)與之對(duì)應(yīng)。


            //=======================================================================
            //function : AddGeometry
            //purpose  : 
            //=======================================================================

            void BRepTools_ShapeSet::AddGeometry(const TopoDS_Shape& S)
            {
              
            // Add the geometry
              
              
            if (S.ShapeType() == TopAbs_VERTEX) {
                
                Handle(BRep_TVertex) TV 
            = Handle(BRep_TVertex)::DownCast(S.TShape());
                BRep_ListIteratorOfListOfPointRepresentation itrp(TV
            ->Points());
                
                
            while (itrp.More()) {
                  
            const Handle(BRep_PointRepresentation)& PR = itrp.Value();

                  
            if (PR->IsPointOnCurve()) {
                    myCurves.Add(PR
            ->Curve());
                  }

                  
            else if (PR->IsPointOnCurveOnSurface()) {
                    myCurves2d.Add(PR
            ->PCurve());
                    mySurfaces.Add(PR
            ->Surface());
                  }

                  
            else if (PR->IsPointOnSurface()) {
                    mySurfaces.Add(PR
            ->Surface());
                  }

                  ChangeLocations().Add(PR
            ->Location());
                  itrp.Next();
                }

              }
              
            else if (S.ShapeType() == TopAbs_EDGE) {

                
            // Add the curve geometry
                Handle(BRep_TEdge) TE = Handle(BRep_TEdge)::DownCast(S.TShape());
                BRep_ListIteratorOfListOfCurveRepresentation itrc(TE
            ->Curves());

                
            while (itrc.More()) {
                  
            const Handle(BRep_CurveRepresentation)& CR = itrc.Value();
                  
            if (CR->IsCurve3D()) {
                    
            if (!CR->Curve3D().IsNull()) {
                      myCurves.Add(CR
            ->Curve3D());
                      ChangeLocations().Add(CR
            ->Location());
                    }
                  }
                  
            else if (CR->IsCurveOnSurface()) {
                    mySurfaces.Add(CR
            ->Surface());
                    myCurves2d.Add(CR
            ->PCurve());
                    ChangeLocations().Add(CR
            ->Location());
                    
            if (CR->IsCurveOnClosedSurface())
                      myCurves2d.Add(CR
            ->PCurve2());
                  }
                  
            else if (CR->IsRegularity()) {
                    mySurfaces.Add(CR
            ->Surface());
                    ChangeLocations().Add(CR
            ->Location());
                    mySurfaces.Add(CR
            ->Surface2());
                    ChangeLocations().Add(CR
            ->Location2());
                  }
                  
            else if (myWithTriangles) { // for XML Persistence
                    if (CR->IsPolygon3D()) {
                      
            if (!CR->Polygon3D().IsNull()) {
                        myPolygons3D.Add(CR
            ->Polygon3D());
                        ChangeLocations().Add(CR
            ->Location());
                      }
                    }
                    
            else if (CR->IsPolygonOnTriangulation()) {
                      myTriangulations.Add(CR
            ->Triangulation());
                      myNodes.Add(CR
            ->PolygonOnTriangulation());
                      ChangeLocations().Add(CR
            ->Location());
                      
            if (CR->IsPolygonOnClosedTriangulation())
                        myNodes.Add(CR
            ->PolygonOnTriangulation2());
                    }
                    
            else if (CR->IsPolygonOnSurface()) {
                      mySurfaces.Add(CR
            ->Surface());
                      myPolygons2D.Add(CR
            ->Polygon());
                      ChangeLocations().Add(CR
            ->Location());
                      
            if (CR->IsPolygonOnClosedSurface())
                      myPolygons2D.Add(CR
            ->Polygon2());
                    }
                  }
                  itrc.Next();
                }
              }

              
            else if (S.ShapeType() == TopAbs_FACE) {

                
            // Add the surface geometry
                Handle(BRep_TFace) TF = Handle(BRep_TFace)::DownCast(S.TShape());
                
            if (!TF->Surface().IsNull())  mySurfaces.Add(TF->Surface());

                
            if (myWithTriangles) { // for XML Persistence
                  Handle(Poly_Triangulation) Tr = TF->Triangulation();
                  
            if (!Tr.IsNull()) myTriangulations.Add(Tr);
                }

                ChangeLocations().Add(TF
            ->Location());
              }
            }

            由上述代碼可知,Edge中的幾何信息較多,F(xiàn)ace中的幾何信息最少,只是幾何曲面或其用于顯示的網(wǎng)格數(shù)據(jù)。在將拓樸數(shù)據(jù)輸出時(shí),拓樸面、邊及頂點(diǎn)中包含的幾何信息都是前面幾何數(shù)據(jù)的編號(hào),即相當(dāng)于索引號(hào)的形式輸出,代碼如下所示:


            //=======================================================================
            //function : WriteGeometry
            //purpose  : 
            //=======================================================================

            void  BRepTools_ShapeSet::WriteGeometry(const TopoDS_Shape& S, 
                                                    Standard_OStream
            &   OS)const 
            {
              
            // Write the geometry
              
              
            if (S.ShapeType() == TopAbs_VERTEX) {

                
            // Write the point geometry
                TopoDS_Vertex V = TopoDS::Vertex(S);
                OS 
            << BRep_Tool::Tolerance(V) << "\n";
                gp_Pnt p 
            = BRep_Tool::Pnt(V);
                OS
            <<p.X()<<" "<<p.Y()<<" "<<p.Z()<<"\n";

                Handle(BRep_TVertex) TV 
            = Handle(BRep_TVertex)::DownCast(S.TShape());
                BRep_ListIteratorOfListOfPointRepresentation itrp(TV
            ->Points());
                
                
            while (itrp.More()) {
                  
            const Handle(BRep_PointRepresentation)& PR = itrp.Value();

                  OS 
            << PR->Parameter();
                  
            if (PR->IsPointOnCurve()) {
                    OS 
            << " 1 " << myCurves.Index(PR->Curve());
                  }

                  
            else if (PR->IsPointOnCurveOnSurface()) {
                    OS 
            << " 2 " <<  myCurves2d.Index(PR->PCurve());
                    OS 
            << " " << mySurfaces.Index(PR->Surface());
                  }

                  
            else if (PR->IsPointOnSurface()) {
                    OS 
            << " 3 " << PR->Parameter2() << " ";
                    OS 
            << mySurfaces.Index(PR->Surface());
                  }

                  OS 
            << " " << Locations().Index(PR->Location());
                  OS 
            << "\n";
                  
                  itrp.Next();
                }
                
                OS 
            << "0 0\n"// end representations

              }

              
            else if (S.ShapeType() == TopAbs_EDGE) {

                
            // Write the curve geometry 

                Handle(BRep_TEdge) TE 
            = Handle(BRep_TEdge)::DownCast(S.TShape());

                OS 
            << " " << TE->Tolerance() << " ";
                OS 
            << ((TE->SameParameter()) ? 1 : 0<< " ";
                OS 
            << ((TE->SameRange())     ? 1 : 0<< " ";
                OS 
            << ((TE->Degenerated())   ? 1 : 0<< "\n";
                
                Standard_Real first, last;
                BRep_ListIteratorOfListOfCurveRepresentation itrc 
            = TE->Curves();
                
            while (itrc.More()) {
                  
            const Handle(BRep_CurveRepresentation)& CR = itrc.Value();
                  
            if (CR->IsCurve3D()) {
                    
            if (!CR->Curve3D().IsNull()) {
                      Handle(BRep_GCurve) GC 
            = Handle(BRep_GCurve)::DownCast(itrc.Value());
                      GC
            ->Range(first, last);
                      OS 
            << "";                               // -1- Curve 3D
                      OS << " "<<myCurves.Index(CR->Curve3D());
                      OS 
            << " "<<Locations().Index(CR->Location());
                      OS 
            << " "<<first<<" "<<last;
                      OS 
            << "\n";
                    }
                  }
                  
            else if (CR->IsCurveOnSurface()) {
                    Handle(BRep_GCurve) GC 
            = Handle(BRep_GCurve)::DownCast(itrc.Value());
                    GC
            ->Range(first, last);
                    
            if (!CR->IsCurveOnClosedSurface())
                      OS 
            << "";                             // -2- Curve on surf
                    else
                      OS 
            << "";                             // -3- Curve on closed surf
                    OS <<" "<<myCurves2d.Index(CR->PCurve());
                    
            if (CR->IsCurveOnClosedSurface()) {
                      OS 
            <<" " << myCurves2d.Index(CR->PCurve2());
                      PrintRegularity(CR
            ->Continuity(),OS);
                    }
                    OS 
            << " " << mySurfaces.Index(CR->Surface());
                    OS 
            << " " << Locations().Index(CR->Location());
                    OS 
            << " "<<first<<" "<<last;
                    OS 
            << "\n";

                    
            // Write UV Points // for XML Persistence higher performance
                    if (FormatNb() == 2)
                    {
                      gp_Pnt2d Pf,Pl;
                      
            if (CR->IsCurveOnClosedSurface()) {
                        Handle(BRep_CurveOnClosedSurface) COCS 
            = 
                          Handle(BRep_CurveOnClosedSurface)::DownCast(CR);
                        COCS
            ->UVPoints2(Pf,Pl);
                      }
                      
            else {
                        Handle(BRep_CurveOnSurface) COS 
            = 
                          Handle(BRep_CurveOnSurface)::DownCast(CR);
                        COS
            ->UVPoints(Pf,Pl);
                      }
                      OS 
            << Pf.X() << " " << Pf.Y() << " " << Pl.X() << " " << Pl.Y() << "\n";
                    }
                  }
                  
            else if (CR->IsRegularity()) {
                    OS 
            << "";                              // -4- Regularity
                    PrintRegularity(CR->Continuity(),OS);
                    OS 
            << " "<<mySurfaces.Index(CR->Surface());
                    OS 
            << " "<<Locations().Index(CR->Location());
                    OS 
            << " "<<mySurfaces.Index(CR->Surface2());
                    OS 
            << " "<<Locations().Index(CR->Location2());
                    OS 
            << "\n";
                  }

                  
            else if (myWithTriangles) { // for XML Persistence
                    if (CR->IsPolygon3D()) {
                      Handle(BRep_Polygon3D) GC 
            = Handle(BRep_Polygon3D)::DownCast(itrc.Value());
                      
            if (!GC->Polygon3D().IsNull()) {
                        OS 
            << "";                            // -5- Polygon3D
                        OS << " "<<myPolygons3D.FindIndex(CR->Polygon3D());
                        OS 
            << " "<<Locations().Index(CR->Location());
                        OS 
            << "\n";
                      }
                    }
                    
            else if (CR->IsPolygonOnTriangulation()) {
                      Handle(BRep_PolygonOnTriangulation) PT 
            = 
                        Handle(BRep_PolygonOnTriangulation)::DownCast(itrc.Value());
                      
            if (!CR->IsPolygonOnClosedTriangulation())
                        OS 
            << "";                            // -6- Polygon on triangulation
                      else
                        OS 
            << "";                            // -7- Polygon on closed triangulation
                      OS << " " <<  myNodes.FindIndex(PT->PolygonOnTriangulation());
                      
            if (CR->IsPolygonOnClosedTriangulation()) {
                        OS 
            << " " << myNodes.FindIndex(PT->PolygonOnTriangulation2());
                      }
                      OS 
            << " " << myTriangulations.FindIndex(PT->Triangulation());
                      OS 
            << " "<<Locations().Index(CR->Location());
                      OS 
            << "\n";
                    }
                  }
                  
                  itrc.Next();
                }
                OS 
            << "0\n"// end of the list of representations
              }
              
              
            else if (S.ShapeType() == TopAbs_FACE) {

                Handle(BRep_TFace) TF 
            = Handle(BRep_TFace)::DownCast(S.TShape());
                
            const TopoDS_Face& F = TopoDS::Face(S);

                
            if (!(TF->Surface()).IsNull()) {
                  OS 
            << ((BRep_Tool::NaturalRestriction(F)) ? 1 : 0);
                  OS 
            << " ";
                  
            // Write the surface geometry
                  OS << " " <<TF->Tolerance();
                  OS 
            << " " <<mySurfaces.Index(TF->Surface());
                  OS 
            << " " <<Locations().Index(TF->Location());
                  OS 
            << "\n";
                }
                
            else //For correct reading of null face
                  {
                OS 
            << 0;
                OS 
            << " ";
                OS 
            << " " <<TF->Tolerance();
                OS 
            << " " << 0;
                OS 
            << " " << 0;
                OS 
            << "\n";
                  }
                
            if (myWithTriangles) { // for XML Persistence
                  if (!(TF->Triangulation()).IsNull()) {
                    OS 
            << 2;
                    OS 
            << " ";
                    
            // Write the triangulation
                    OS << " " <<myTriangulations.FindIndex(TF->Triangulation());
                  }
                }
              }
              
            }

            通過先將幾何數(shù)據(jù)收集到相應(yīng)的集合(映射)中,再在拓樸結(jié)構(gòu)對(duì)應(yīng)的地方以索引號(hào)的方式輸出,這樣就便于從文件讀取數(shù)據(jù)時(shí),以類似的方式來重構(gòu)BRep邊界表示的拓樸Shape的結(jié)構(gòu)。即讀取文件重構(gòu)拓樸結(jié)構(gòu)數(shù)據(jù)是輸出的逆過程。

            在實(shí)現(xiàn)從文件讀取BRep表示的數(shù)據(jù)時(shí),先將幾何信息讀取到對(duì)應(yīng)的集合中,再讀取拓樸結(jié)構(gòu)數(shù)據(jù)時(shí),若拓樸結(jié)構(gòu)中包含幾何信息,則以索引的方式,找到對(duì)應(yīng)的幾何數(shù)據(jù)即可。詳細(xì)實(shí)現(xiàn)可參考源程序。

            3. For Debugging

            由于BRepTools為Toolkit TKBRep中的類,所以依賴的動(dòng)態(tài)庫(kù)較少,所以在編程時(shí),若要驗(yàn)證一些算法的正確性時(shí),經(jīng)常需要將TopoDS_Shape的數(shù)據(jù)導(dǎo)出,甚至可以直接先在Draw Test Harness中使用相關(guān)命令來將導(dǎo)出的數(shù)據(jù)導(dǎo)入來查看結(jié)果。

            4. Conclusion

            通過BRepTools中對(duì)TopoDS_Shape數(shù)據(jù)的輸出及導(dǎo)入的代碼分析可知,對(duì)于只有組合關(guān)系的數(shù)據(jù),若想維持這種關(guān)系,就需要引入集合映射的類來產(chǎn)生索引,進(jìn)而在讀取數(shù)據(jù)時(shí),可以根據(jù)索引來重構(gòu)拓樸關(guān)系。由于opennurbs中的BRep在內(nèi)存中本來就是索引的方式,所以在數(shù)據(jù)存取時(shí),實(shí)現(xiàn)要簡(jiǎn)單很多。

            5. References

            1. OpenCASCADE Team. BRep Format. 2014.12

            2. Shing Liu. Topology and Geometry in OpenCascade-Topology. 

            http://m.shnenglu.com/eryar/archive/2013/09/21/203338.html

            3. Shing Liu. Topology and Geometry in OpenCascade-Vertex

            http://m.shnenglu.com/eryar/archive/2013/08/20/202678.html

            4. Shing Liu. Topology and Geometry in OpenCascade-Edge

            http://m.shnenglu.com/eryar/archive/2013/08/24/202739.html

            5. Shing Liu. Topology and Geometry in OpenCascade-Face

            http://m.shnenglu.com/eryar/archive/2013/09/12/203199.html

            亚洲精品无码久久不卡| 国产精品嫩草影院久久| 久久人人爽人人爽AV片| 久久综合久久综合亚洲| 精品欧美一区二区三区久久久| a高清免费毛片久久| 秋霞久久国产精品电影院| 久久久99精品一区二区| 亚洲中文久久精品无码| 国产精品一区二区久久精品无码| 国产69精品久久久久99尤物| 久久久久高潮综合影院| 久久精品人人做人人爽电影| 中文精品久久久久人妻| 久久精品水蜜桃av综合天堂| 久久996热精品xxxx| 欧美喷潮久久久XXXXx| 99久久婷婷国产综合精品草原| 亚洲欧美一级久久精品| 麻豆精品久久精品色综合| 欧美精品丝袜久久久中文字幕| 国产亚洲美女精品久久久2020| 国产99精品久久| 一本色道久久综合狠狠躁| 久久乐国产综合亚洲精品| 日本三级久久网| 潮喷大喷水系列无码久久精品| 精品无码久久久久国产动漫3d| 久久最新精品国产| 精品久久一区二区| 久久国产精品国产自线拍免费| 亚洲人成电影网站久久| 精品99久久aaa一级毛片| 久久www免费人成看片| 一级a性色生活片久久无| 午夜精品久久久久9999高清| 精品免费久久久久国产一区| 色综合久久精品中文字幕首页| 狠色狠色狠狠色综合久久| 久久亚洲国产成人影院| 久久久久亚洲AV成人网人人软件|