From 05a257d4f4e64a05ba8bb953efd5a2f1846e3fe1 Mon Sep 17 00:00:00 2001 From: eap Date: Thu, 12 Oct 2017 19:52:03 +0300 Subject: [PATCH] Add "Deflection 2D" quality control for GPUSPHGUI project --- doc/salome/examples/quality_controls_defl.py | 45 ++ doc/salome/examples/tests.set | 1 + doc/salome/gui/SMESH/images/deflection_2d.png | Bin 0 -> 12975 bytes doc/salome/gui/SMESH/input/about_filters.doc | 19 +- .../SMESH/input/about_quality_controls.doc | 1 + doc/salome/gui/SMESH/input/deflection_2d.doc | 25 + .../SMESH/input/selection_filter_library.doc | 13 +- .../gui/SMESH/input/tui_quality_controls.doc | 3 + idl/SMESH_Filter.idl | 3 + resources/CMakeLists.txt | 1 + resources/mesh_deflection.png | Bin 0 -> 827 bytes src/Controls/SMESH_Controls.cxx | 537 ++++++++++-------- src/Controls/SMESH_ControlsDef.hxx | 20 +- src/OBJECT/SMESH_Actor.cxx | 10 +- src/OBJECT/SMESH_Actor.h | 2 +- src/SMDS/SMDS_Mesh.hxx | 2 +- src/SMDS/SMDS_SetIterator.hxx | 5 + src/SMESHGUI/SMESHGUI.cxx | 15 +- src/SMESHGUI/SMESHGUI_FilterDlg.cxx | 13 +- src/SMESHGUI/SMESHGUI_MeshInfo.cxx | 27 +- src/SMESHGUI/SMESHGUI_MeshInfo.h | 4 +- src/SMESHGUI/SMESHGUI_Operations.h | 1 + src/SMESHGUI/SMESHGUI_Selection.cxx | 9 +- src/SMESHGUI/SMESH_images.ts | 4 + src/SMESHGUI/SMESH_msg_en.ts | 28 + src/SMESH_I/SMESH_2smeshpy.cxx | 3 + src/SMESH_I/SMESH_DumpPython.cxx | 1 + src/SMESH_I/SMESH_Filter_i.cxx | 33 +- src/SMESH_I/SMESH_Filter_i.hxx | 17 +- src/SMESH_I/SMESH_MeshPartDS.hxx | 14 + src/SMESH_I/SMESH_Mesh_i.cxx | 16 + src/SMESH_SWIG/smeshBuilder.py | 43 +- src/StdMeshersGUI/StdMeshers_msg_en.ts | 2 +- 33 files changed, 647 insertions(+), 270 deletions(-) create mode 100644 doc/salome/examples/quality_controls_defl.py create mode 100644 doc/salome/gui/SMESH/images/deflection_2d.png create mode 100644 doc/salome/gui/SMESH/input/deflection_2d.doc create mode 100644 resources/mesh_deflection.png diff --git a/doc/salome/examples/quality_controls_defl.py b/doc/salome/examples/quality_controls_defl.py new file mode 100644 index 000000000..9105fee6a --- /dev/null +++ b/doc/salome/examples/quality_controls_defl.py @@ -0,0 +1,45 @@ +# Deflection 2D + + +import salome +salome.salome_init() +from salome.geom import geomBuilder +geompy = geomBuilder.New(salome.myStudy) + +import SMESH +from salome.smesh import smeshBuilder +smesh = smeshBuilder.New(salome.myStudy) + +# fuse a box and a sphere +Sphere_1 = geompy.MakeSphereR(100) +Box_1 = geompy.MakeBoxDXDYDZ(200, 200, 200) +Fuse = geompy.MakeFuse( Sphere_1, Box_1, theName="box + sphere" ) + +# create a mesh +mesh = smesh.Mesh( Fuse, "Deflection_2D") +algo = mesh.Segment() +algo.LocalLength(35) +algo = mesh.Triangle() +mesh.Compute() + +# get min and max deflection +minMax = mesh.GetMinMax( SMESH.FT_Deflection2D ) +print "min and max deflection: ", minMax + +# get deflection of a certain face +faceID = mesh.NbEdges() + mesh.NbFaces() +defl = mesh.FunctorValue( SMESH.FT_Deflection2D, faceID ) +print "deflection of face %s = %s" % ( faceID, defl ) + +margin = minMax[1] / 2 + +# get all faces with deflection LESS than the margin +aFilter = smesh.GetFilter(SMESH.FACE, SMESH.FT_Deflection2D, '<', margin, mesh=mesh) +anIds = aFilter.GetIDs() +print "%s faces have deflection less than %s" %( len(anIds), margin ) + +# create a group of faces with deflection MORE than the margin +aGroup = mesh.MakeGroup("Deflection > " + `margin`, SMESH.FACE, SMESH.FT_Deflection2D,'>',margin) +print "%s faces have deflection more than %s: %s ..." %( aGroup.Size(), margin, aGroup.GetIDs()[:10] ) + +salome.sg.updateObjBrowser(True) diff --git a/doc/salome/examples/tests.set b/doc/salome/examples/tests.set index 3319c3208..2cf9698d1 100644 --- a/doc/salome/examples/tests.set +++ b/doc/salome/examples/tests.set @@ -156,6 +156,7 @@ SET(GOOD_TESTS quality_controls_ex17.py quality_controls_ex18.py quality_controls_ex19.py + quality_controls_defl.py transforming_meshes_ex01.py transforming_meshes_ex02.py transforming_meshes_ex03.py diff --git a/doc/salome/gui/SMESH/images/deflection_2d.png b/doc/salome/gui/SMESH/images/deflection_2d.png new file mode 100644 index 0000000000000000000000000000000000000000..f8159622fb0c06c6ac29ee02e30544115a3b0239 GIT binary patch literal 12975 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\subpage bare_border_faces_page "Bare border faces"
  • \subpage over_constrained_faces_page "Over-constrained faces"
  • \subpage length_2d_page "Length 2D"
  • +
  • \subpage deflection_2d_page "Deflection 2D"
  • \subpage borders_at_multi_connection_2d_page "Borders at multi-connection 2D"
  • \subpage area_page "Area"
  • \subpage taper_page "Taper"
  • diff --git a/doc/salome/gui/SMESH/input/deflection_2d.doc b/doc/salome/gui/SMESH/input/deflection_2d.doc new file mode 100644 index 000000000..a9d38cde3 --- /dev/null +++ b/doc/salome/gui/SMESH/input/deflection_2d.doc @@ -0,0 +1,25 @@ +/*! + +\page deflection_2d_page Deflection 2D + +\n This quality control criterion consists of calculation of distance +between a mesh face gravity corner and the surface the face discretizes. + +To apply the Deflection 2D quality criterion to your mesh: +
      +
    1. Display your mesh in the viewer.
    2. + +
    3. Choose Controls > Face Controls > Deflection 2D or click +"Deflection 2D" button in the toolbar. + +Your mesh will be displayed in the viewer with faces colored according +to the applied mesh quality control criterion: + +\image html deflection_2d.png +
    4. +
    + +
    See Also a sample TUI Script of a +\ref tui_deflection_2d "Deflection 2D quality control" operation. + +*/ diff --git a/doc/salome/gui/SMESH/input/selection_filter_library.doc b/doc/salome/gui/SMESH/input/selection_filter_library.doc index 03438c490..97d63ec02 100644 --- a/doc/salome/gui/SMESH/input/selection_filter_library.doc +++ b/doc/salome/gui/SMESH/input/selection_filter_library.doc @@ -2,6 +2,10 @@ \page selection_filter_library_page Selection filter library +\tableofcontents + +\section selection_filter_library Filter library + \n Selection filter library allows creating and storing in files the filters that can be later reused for operations on meshes. You can access it from the Main Menu via Tools / Selection filter library. @@ -18,8 +22,7 @@ the current study. You can \b Add or \b Delete filters. \n In Filter name box you can specify the name for your filter. By default it is prefixed with the corresponding entity type. -\anchor filtering_elements -

    Filter Dialog

    +\section filtering_elements Filter Dialog When we use filters during group creation or another operation (by clicking Set Filter button in the corresponding dialog), the @@ -64,6 +67,8 @@ in the Library. is no selected mesh in the Object Browser and the filter can not be created. You have to select the mesh and the button will be enabled. +\section filtering_criteria Filtering Criteria + Some criteria are applicable to all Entity types:
    • Belong to Geom selects entities whose all nodes lie on the @@ -231,6 +236,10 @@ normal to the neighboring face and the normal to the selected face is less then angular tolerance (defined in degrees). Selection continues among all neighbor faces of already selected ones.
    • +Deflection 2D selects 2D mesh elements having distance between their gravity +centers and underlying surfaces, which is more, less or equal (within a given Tolerance) to the predefined Threshold Value. See also a +\ref deflection_2d_page "Deflection 2D quality control". +
    • Element Diameter 2D selects triangles and quadrangles composed of the edges and diagonals with a value of length, which is more, less or equal (within a given Tolerance) to the predefined Threshold Value. See also a diff --git a/doc/salome/gui/SMESH/input/tui_quality_controls.doc b/doc/salome/gui/SMESH/input/tui_quality_controls.doc index 1434c9b07..cb1632c1e 100644 --- a/doc/salome/gui/SMESH/input/tui_quality_controls.doc +++ b/doc/salome/gui/SMESH/input/tui_quality_controls.doc @@ -37,6 +37,9 @@ \section tui_length_2d Length 2D \tui_script{quality_controls_ex11.py} +\section tui_deflection_2d Deflection 2D +\tui_script{quality_controls_defl.py} + \section tui_borders_at_multiconnection_2d Borders at Multiconnection 2D \tui_script{quality_controls_ex12.py} diff --git a/idl/SMESH_Filter.idl b/idl/SMESH_Filter.idl index c354e064d..283aa1b29 100644 --- a/idl/SMESH_Filter.idl +++ b/idl/SMESH_Filter.idl @@ -61,6 +61,7 @@ module SMESH FT_MultiConnection2D, FT_Length, FT_Length2D, + FT_Deflection2D, FT_NodeConnectivityNumber, FT_BelongToMeshGroup, FT_BelongToGeom, @@ -150,6 +151,7 @@ module SMESH typedef sequence Values; Values GetValues(); }; + interface Deflection2D : NumericalFunctor{}; interface MultiConnection : NumericalFunctor{}; interface MultiConnection2D : NumericalFunctor { @@ -585,6 +587,7 @@ module SMESH MaxElementLength3D CreateMaxElementLength3D(); Length CreateLength(); Length2D CreateLength2D(); + Deflection2D CreateDeflection2D(); MultiConnection CreateMultiConnection(); MultiConnection2D CreateMultiConnection2D(); BallDiameter CreateBallDiameter(); diff --git a/resources/CMakeLists.txt b/resources/CMakeLists.txt index d2801c905..6db2127eb 100755 --- a/resources/CMakeLists.txt +++ b/resources/CMakeLists.txt @@ -228,6 +228,7 @@ SET(SMESH_RESOURCES_FILES mesh_quality.png mesh_show.png mesh_hide.png + mesh_deflection.png ) INSTALL(FILES ${SMESH_RESOURCES_FILES} DESTINATION ${SALOME_SMESH_INSTALL_RES_DATA}) diff --git a/resources/mesh_deflection.png b/resources/mesh_deflection.png new file mode 100644 index 0000000000000000000000000000000000000000..f9d8542dc4c09468cfcfe064ad0f374d7f892684 GIT binary patch literal 827 zcmV-B1H}A^P)MFDX7fByTB$lB$P+1g_2q6?v_CXd=kwlx! zvKG<8MMZ_0%pxjiQDA{lSqMQNwh6K?6~}qwym_a^*z?Wwv_G81<=peX|9j8>TvV0J zXliPrq@)B9Ss)@25g80ONAzOktEyuXRP#5o$V4(5!!Q^a7+4MT0#AV@Ufy&dnVpIN zWM`6LI<&T0%Yi$<*22QVC;k2X=~bqawm+C~GHF?s1>6N1&Ub!(;=0Q9BkKaycxrv5 zSpg><0Q!oHi|?bL3cJod^a>2a2qq1@atif8^_J#NlCI*a;_6f~FE0)B^xh;#P`NxBN88gr_4 zA+CO+y>VHf(oEaT1Aab#)31j%glOp*8Kulk- z^F(Bl@CN|V;UUI`zj5R6TH^6I<>loh5()6nriiQ(k=}7dPu%{3Iws?a?rwR6f0j4x zyY`P=)~ufFx~h7lA~H)veu+q4Q^#i-+h3(}j_DBwd9Qwt5!_|lwiCc(pf(mAWqkA( zTTkAi`ruV&Lb%rFN$=~KQduk_UqvK$Tl2lCqG=R+sfPQWbt;5ZHy6%~|~mBoPd zzyjczh^+LU=r57!{QraP>FMz=M?|Cw*a2Mr=X0F~e*hmoa~eQU{gD6w002ovPDHLk FV1mBVc~1ZU literal 0 HcmV?d00001 diff --git a/src/Controls/SMESH_Controls.cxx b/src/Controls/SMESH_Controls.cxx index 9333e7023..aa1eb5eaa 100644 --- a/src/Controls/SMESH_Controls.cxx +++ b/src/Controls/SMESH_Controls.cxx @@ -23,6 +23,7 @@ #include "SMESH_ControlsDef.hxx" #include "SMDS_BallElement.hxx" +#include "SMDS_FacePosition.hxx" #include "SMDS_Iterator.hxx" #include "SMDS_Mesh.hxx" #include "SMDS_MeshElement.hxx" @@ -41,6 +42,7 @@ #include #include #include +#include #include #include #include @@ -48,6 +50,7 @@ #include #include #include +#include #include #include #include @@ -261,13 +264,10 @@ bool NumericalFunctor::GetPoints(const SMDS_MeshElement* anElem, } if ( anIter ) { - double xyz[3]; + SMESH_NodeXYZ p; while( anIter->more() ) { - if ( const SMDS_MeshNode* aNode = static_cast( anIter->next() )) - { - aNode->GetXYZ( xyz ); - theRes.push_back( gp_XYZ( xyz[0], xyz[1], xyz[2] )); - } + if ( p.Set( anIter->next() )) + theRes.push_back( p ); } } @@ -1553,247 +1553,240 @@ SMDSAbs_ElementType Length::GetType() const */ //================================================================================ -double Length2D::GetValue( long theElementId ) +double Length2D::GetValue( const TSequenceOfXYZ& P ) { - TSequenceOfXYZ P; - - if ( GetPoints( theElementId, P )) - { - double aVal = 0; - int len = P.size(); - SMDSAbs_EntityType aType = P.getElementEntity(); + double aVal = 0; + int len = P.size(); + SMDSAbs_EntityType aType = P.getElementEntity(); - switch (aType) { - case SMDSEntity_Edge: - if (len == 2) - aVal = getDistance( P( 1 ), P( 2 ) ); - break; - case SMDSEntity_Quad_Edge: - if (len == 3) // quadratic edge - aVal = getDistance(P( 1 ),P( 3 )) + getDistance(P( 3 ),P( 2 )); - break; - case SMDSEntity_Triangle: - if (len == 3){ // triangles - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 1 )); - aVal = Min(L1,Min(L2,L3)); - } - break; - case SMDSEntity_Quadrangle: - if (len == 4){ // quadrangles - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 4 )); - double L4 = getDistance(P( 4 ),P( 1 )); - aVal = Min(Min(L1,L2),Min(L3,L4)); - } - break; - case SMDSEntity_Quad_Triangle: - case SMDSEntity_BiQuad_Triangle: - if (len >= 6){ // quadratic triangles - double L1 = getDistance(P( 1 ),P( 2 )) + getDistance(P( 2 ),P( 3 )); - double L2 = getDistance(P( 3 ),P( 4 )) + getDistance(P( 4 ),P( 5 )); - double L3 = getDistance(P( 5 ),P( 6 )) + getDistance(P( 6 ),P( 1 )); - aVal = Min(L1,Min(L2,L3)); - } - break; - case SMDSEntity_Quad_Quadrangle: - case SMDSEntity_BiQuad_Quadrangle: - if (len >= 8){ // quadratic quadrangles - double L1 = getDistance(P( 1 ),P( 2 )) + getDistance(P( 2 ),P( 3 )); - double L2 = getDistance(P( 3 ),P( 4 )) + getDistance(P( 4 ),P( 5 )); - double L3 = getDistance(P( 5 ),P( 6 )) + getDistance(P( 6 ),P( 7 )); - double L4 = getDistance(P( 7 ),P( 8 )) + getDistance(P( 8 ),P( 1 )); - aVal = Min(Min(L1,L2),Min(L3,L4)); - } - break; - case SMDSEntity_Tetra: - if (len == 4){ // tetrahedra - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 1 )); - double L4 = getDistance(P( 1 ),P( 4 )); - double L5 = getDistance(P( 2 ),P( 4 )); - double L6 = getDistance(P( 3 ),P( 4 )); - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - } - break; - case SMDSEntity_Pyramid: - if (len == 5){ // pyramid - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 4 )); - double L4 = getDistance(P( 4 ),P( 1 )); - double L5 = getDistance(P( 1 ),P( 5 )); - double L6 = getDistance(P( 2 ),P( 5 )); - double L7 = getDistance(P( 3 ),P( 5 )); - double L8 = getDistance(P( 4 ),P( 5 )); - - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal,Min(L7,L8)); - } - break; - case SMDSEntity_Penta: - if (len == 6) { // pentahedron - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 1 )); - double L4 = getDistance(P( 4 ),P( 5 )); - double L5 = getDistance(P( 5 ),P( 6 )); - double L6 = getDistance(P( 6 ),P( 4 )); - double L7 = getDistance(P( 1 ),P( 4 )); - double L8 = getDistance(P( 2 ),P( 5 )); - double L9 = getDistance(P( 3 ),P( 6 )); - - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal,Min(Min(L7,L8),L9)); - } - break; - case SMDSEntity_Hexa: - if (len == 8){ // hexahedron - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 4 )); - double L4 = getDistance(P( 4 ),P( 1 )); - double L5 = getDistance(P( 5 ),P( 6 )); - double L6 = getDistance(P( 6 ),P( 7 )); - double L7 = getDistance(P( 7 ),P( 8 )); - double L8 = getDistance(P( 8 ),P( 5 )); - double L9 = getDistance(P( 1 ),P( 5 )); - double L10= getDistance(P( 2 ),P( 6 )); - double L11= getDistance(P( 3 ),P( 7 )); - double L12= getDistance(P( 4 ),P( 8 )); - - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal,Min(Min(L7,L8),Min(L9,L10))); - aVal = Min(aVal,Min(L11,L12)); - } - break; - case SMDSEntity_Quad_Tetra: - if (len == 10){ // quadratic tetrahedron - double L1 = getDistance(P( 1 ),P( 5 )) + getDistance(P( 5 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 6 )) + getDistance(P( 6 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 7 )) + getDistance(P( 7 ),P( 1 )); - double L4 = getDistance(P( 1 ),P( 8 )) + getDistance(P( 8 ),P( 4 )); - double L5 = getDistance(P( 2 ),P( 9 )) + getDistance(P( 9 ),P( 4 )); - double L6 = getDistance(P( 3 ),P( 10 )) + getDistance(P( 10 ),P( 4 )); - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - } - break; - case SMDSEntity_Quad_Pyramid: - if (len == 13){ // quadratic pyramid - double L1 = getDistance(P( 1 ),P( 6 )) + getDistance(P( 6 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 7 )) + getDistance(P( 7 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 8 )) + getDistance(P( 8 ),P( 4 )); - double L4 = getDistance(P( 4 ),P( 9 )) + getDistance(P( 9 ),P( 1 )); - double L5 = getDistance(P( 1 ),P( 10 )) + getDistance(P( 10 ),P( 5 )); - double L6 = getDistance(P( 2 ),P( 11 )) + getDistance(P( 11 ),P( 5 )); - double L7 = getDistance(P( 3 ),P( 12 )) + getDistance(P( 12 ),P( 5 )); - double L8 = getDistance(P( 4 ),P( 13 )) + getDistance(P( 13 ),P( 5 )); - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal,Min(L7,L8)); - } - break; - case SMDSEntity_Quad_Penta: - case SMDSEntity_BiQuad_Penta: - if (len >= 15){ // quadratic pentahedron - double L1 = getDistance(P( 1 ),P( 7 )) + getDistance(P( 7 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 8 )) + getDistance(P( 8 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 9 )) + getDistance(P( 9 ),P( 1 )); - double L4 = getDistance(P( 4 ),P( 10 )) + getDistance(P( 10 ),P( 5 )); - double L5 = getDistance(P( 5 ),P( 11 )) + getDistance(P( 11 ),P( 6 )); - double L6 = getDistance(P( 6 ),P( 12 )) + getDistance(P( 12 ),P( 4 )); - double L7 = getDistance(P( 1 ),P( 13 )) + getDistance(P( 13 ),P( 4 )); - double L8 = getDistance(P( 2 ),P( 14 )) + getDistance(P( 14 ),P( 5 )); - double L9 = getDistance(P( 3 ),P( 15 )) + getDistance(P( 15 ),P( 6 )); - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal,Min(Min(L7,L8),L9)); - } - break; - case SMDSEntity_Quad_Hexa: - case SMDSEntity_TriQuad_Hexa: - if (len >= 20) { // quadratic hexahedron - double L1 = getDistance(P( 1 ),P( 9 )) + getDistance(P( 9 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 10 )) + getDistance(P( 10 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 11 )) + getDistance(P( 11 ),P( 4 )); - double L4 = getDistance(P( 4 ),P( 12 )) + getDistance(P( 12 ),P( 1 )); - double L5 = getDistance(P( 5 ),P( 13 )) + getDistance(P( 13 ),P( 6 )); - double L6 = getDistance(P( 6 ),P( 14 )) + getDistance(P( 14 ),P( 7 )); - double L7 = getDistance(P( 7 ),P( 15 )) + getDistance(P( 15 ),P( 8 )); - double L8 = getDistance(P( 8 ),P( 16 )) + getDistance(P( 16 ),P( 5 )); - double L9 = getDistance(P( 1 ),P( 17 )) + getDistance(P( 17 ),P( 5 )); - double L10= getDistance(P( 2 ),P( 18 )) + getDistance(P( 18 ),P( 6 )); - double L11= getDistance(P( 3 ),P( 19 )) + getDistance(P( 19 ),P( 7 )); - double L12= getDistance(P( 4 ),P( 20 )) + getDistance(P( 20 ),P( 8 )); - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal,Min(Min(L7,L8),Min(L9,L10))); - aVal = Min(aVal,Min(L11,L12)); - } - break; - case SMDSEntity_Polygon: - if ( len > 1 ) { - aVal = getDistance( P(1), P( P.size() )); - for ( size_t i = 1; i < P.size(); ++i ) - aVal = Min( aVal, getDistance( P( i ), P( i+1 ))); - } - break; - case SMDSEntity_Quad_Polygon: - if ( len > 2 ) { - aVal = getDistance( P(1), P( P.size() )) + getDistance( P(P.size()), P( P.size()-1 )); - for ( size_t i = 1; i < P.size()-1; i += 2 ) - aVal = Min( aVal, getDistance( P( i ), P( i+1 )) + getDistance( P( i+1 ), P( i+2 ))); - } - break; - case SMDSEntity_Hexagonal_Prism: - if (len == 12) { // hexagonal prism - double L1 = getDistance(P( 1 ),P( 2 )); - double L2 = getDistance(P( 2 ),P( 3 )); - double L3 = getDistance(P( 3 ),P( 4 )); - double L4 = getDistance(P( 4 ),P( 5 )); - double L5 = getDistance(P( 5 ),P( 6 )); - double L6 = getDistance(P( 6 ),P( 1 )); - - double L7 = getDistance(P( 7 ), P( 8 )); - double L8 = getDistance(P( 8 ), P( 9 )); - double L9 = getDistance(P( 9 ), P( 10 )); - double L10= getDistance(P( 10 ),P( 11 )); - double L11= getDistance(P( 11 ),P( 12 )); - double L12= getDistance(P( 12 ),P( 7 )); - - double L13 = getDistance(P( 1 ),P( 7 )); - double L14 = getDistance(P( 2 ),P( 8 )); - double L15 = getDistance(P( 3 ),P( 9 )); - double L16 = getDistance(P( 4 ),P( 10 )); - double L17 = getDistance(P( 5 ),P( 11 )); - double L18 = getDistance(P( 6 ),P( 12 )); - aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); - aVal = Min(aVal, Min(Min(Min(L7,L8),Min(L9,L10)),Min(L11,L12))); - aVal = Min(aVal, Min(Min(Min(L13,L14),Min(L15,L16)),Min(L17,L18))); - } - break; - case SMDSEntity_Polyhedra: - { + switch (aType) { + case SMDSEntity_Edge: + if (len == 2) + aVal = getDistance( P( 1 ), P( 2 ) ); + break; + case SMDSEntity_Quad_Edge: + if (len == 3) // quadratic edge + aVal = getDistance(P( 1 ),P( 3 )) + getDistance(P( 3 ),P( 2 )); + break; + case SMDSEntity_Triangle: + if (len == 3){ // triangles + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 1 )); + aVal = Min(L1,Min(L2,L3)); } break; - default: - return 0; + case SMDSEntity_Quadrangle: + if (len == 4){ // quadrangles + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 4 )); + double L4 = getDistance(P( 4 ),P( 1 )); + aVal = Min(Min(L1,L2),Min(L3,L4)); + } + break; + case SMDSEntity_Quad_Triangle: + case SMDSEntity_BiQuad_Triangle: + if (len >= 6){ // quadratic triangles + double L1 = getDistance(P( 1 ),P( 2 )) + getDistance(P( 2 ),P( 3 )); + double L2 = getDistance(P( 3 ),P( 4 )) + getDistance(P( 4 ),P( 5 )); + double L3 = getDistance(P( 5 ),P( 6 )) + getDistance(P( 6 ),P( 1 )); + aVal = Min(L1,Min(L2,L3)); + } + break; + case SMDSEntity_Quad_Quadrangle: + case SMDSEntity_BiQuad_Quadrangle: + if (len >= 8){ // quadratic quadrangles + double L1 = getDistance(P( 1 ),P( 2 )) + getDistance(P( 2 ),P( 3 )); + double L2 = getDistance(P( 3 ),P( 4 )) + getDistance(P( 4 ),P( 5 )); + double L3 = getDistance(P( 5 ),P( 6 )) + getDistance(P( 6 ),P( 7 )); + double L4 = getDistance(P( 7 ),P( 8 )) + getDistance(P( 8 ),P( 1 )); + aVal = Min(Min(L1,L2),Min(L3,L4)); + } + break; + case SMDSEntity_Tetra: + if (len == 4){ // tetrahedra + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 1 )); + double L4 = getDistance(P( 1 ),P( 4 )); + double L5 = getDistance(P( 2 ),P( 4 )); + double L6 = getDistance(P( 3 ),P( 4 )); + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); } + break; + case SMDSEntity_Pyramid: + if (len == 5){ // pyramid + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 4 )); + double L4 = getDistance(P( 4 ),P( 1 )); + double L5 = getDistance(P( 1 ),P( 5 )); + double L6 = getDistance(P( 2 ),P( 5 )); + double L7 = getDistance(P( 3 ),P( 5 )); + double L8 = getDistance(P( 4 ),P( 5 )); - if (aVal < 0 ) { - return 0.; + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal,Min(L7,L8)); } + break; + case SMDSEntity_Penta: + if (len == 6) { // pentahedron + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 1 )); + double L4 = getDistance(P( 4 ),P( 5 )); + double L5 = getDistance(P( 5 ),P( 6 )); + double L6 = getDistance(P( 6 ),P( 4 )); + double L7 = getDistance(P( 1 ),P( 4 )); + double L8 = getDistance(P( 2 ),P( 5 )); + double L9 = getDistance(P( 3 ),P( 6 )); - if ( myPrecision >= 0 ) - { - double prec = pow( 10., (double)( myPrecision ) ); - aVal = floor( aVal * prec + 0.5 ) / prec; + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal,Min(Min(L7,L8),L9)); + } + break; + case SMDSEntity_Hexa: + if (len == 8){ // hexahedron + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 4 )); + double L4 = getDistance(P( 4 ),P( 1 )); + double L5 = getDistance(P( 5 ),P( 6 )); + double L6 = getDistance(P( 6 ),P( 7 )); + double L7 = getDistance(P( 7 ),P( 8 )); + double L8 = getDistance(P( 8 ),P( 5 )); + double L9 = getDistance(P( 1 ),P( 5 )); + double L10= getDistance(P( 2 ),P( 6 )); + double L11= getDistance(P( 3 ),P( 7 )); + double L12= getDistance(P( 4 ),P( 8 )); + + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal,Min(Min(L7,L8),Min(L9,L10))); + aVal = Min(aVal,Min(L11,L12)); + } + break; + case SMDSEntity_Quad_Tetra: + if (len == 10){ // quadratic tetrahedron + double L1 = getDistance(P( 1 ),P( 5 )) + getDistance(P( 5 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 6 )) + getDistance(P( 6 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 7 )) + getDistance(P( 7 ),P( 1 )); + double L4 = getDistance(P( 1 ),P( 8 )) + getDistance(P( 8 ),P( 4 )); + double L5 = getDistance(P( 2 ),P( 9 )) + getDistance(P( 9 ),P( 4 )); + double L6 = getDistance(P( 3 ),P( 10 )) + getDistance(P( 10 ),P( 4 )); + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + } + break; + case SMDSEntity_Quad_Pyramid: + if (len == 13){ // quadratic pyramid + double L1 = getDistance(P( 1 ),P( 6 )) + getDistance(P( 6 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 7 )) + getDistance(P( 7 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 8 )) + getDistance(P( 8 ),P( 4 )); + double L4 = getDistance(P( 4 ),P( 9 )) + getDistance(P( 9 ),P( 1 )); + double L5 = getDistance(P( 1 ),P( 10 )) + getDistance(P( 10 ),P( 5 )); + double L6 = getDistance(P( 2 ),P( 11 )) + getDistance(P( 11 ),P( 5 )); + double L7 = getDistance(P( 3 ),P( 12 )) + getDistance(P( 12 ),P( 5 )); + double L8 = getDistance(P( 4 ),P( 13 )) + getDistance(P( 13 ),P( 5 )); + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal,Min(L7,L8)); + } + break; + case SMDSEntity_Quad_Penta: + case SMDSEntity_BiQuad_Penta: + if (len >= 15){ // quadratic pentahedron + double L1 = getDistance(P( 1 ),P( 7 )) + getDistance(P( 7 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 8 )) + getDistance(P( 8 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 9 )) + getDistance(P( 9 ),P( 1 )); + double L4 = getDistance(P( 4 ),P( 10 )) + getDistance(P( 10 ),P( 5 )); + double L5 = getDistance(P( 5 ),P( 11 )) + getDistance(P( 11 ),P( 6 )); + double L6 = getDistance(P( 6 ),P( 12 )) + getDistance(P( 12 ),P( 4 )); + double L7 = getDistance(P( 1 ),P( 13 )) + getDistance(P( 13 ),P( 4 )); + double L8 = getDistance(P( 2 ),P( 14 )) + getDistance(P( 14 ),P( 5 )); + double L9 = getDistance(P( 3 ),P( 15 )) + getDistance(P( 15 ),P( 6 )); + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal,Min(Min(L7,L8),L9)); + } + break; + case SMDSEntity_Quad_Hexa: + case SMDSEntity_TriQuad_Hexa: + if (len >= 20) { // quadratic hexahedron + double L1 = getDistance(P( 1 ),P( 9 )) + getDistance(P( 9 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 10 )) + getDistance(P( 10 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 11 )) + getDistance(P( 11 ),P( 4 )); + double L4 = getDistance(P( 4 ),P( 12 )) + getDistance(P( 12 ),P( 1 )); + double L5 = getDistance(P( 5 ),P( 13 )) + getDistance(P( 13 ),P( 6 )); + double L6 = getDistance(P( 6 ),P( 14 )) + getDistance(P( 14 ),P( 7 )); + double L7 = getDistance(P( 7 ),P( 15 )) + getDistance(P( 15 ),P( 8 )); + double L8 = getDistance(P( 8 ),P( 16 )) + getDistance(P( 16 ),P( 5 )); + double L9 = getDistance(P( 1 ),P( 17 )) + getDistance(P( 17 ),P( 5 )); + double L10= getDistance(P( 2 ),P( 18 )) + getDistance(P( 18 ),P( 6 )); + double L11= getDistance(P( 3 ),P( 19 )) + getDistance(P( 19 ),P( 7 )); + double L12= getDistance(P( 4 ),P( 20 )) + getDistance(P( 20 ),P( 8 )); + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal,Min(Min(L7,L8),Min(L9,L10))); + aVal = Min(aVal,Min(L11,L12)); + } + break; + case SMDSEntity_Polygon: + if ( len > 1 ) { + aVal = getDistance( P(1), P( P.size() )); + for ( size_t i = 1; i < P.size(); ++i ) + aVal = Min( aVal, getDistance( P( i ), P( i+1 ))); + } + break; + case SMDSEntity_Quad_Polygon: + if ( len > 2 ) { + aVal = getDistance( P(1), P( P.size() )) + getDistance( P(P.size()), P( P.size()-1 )); + for ( size_t i = 1; i < P.size()-1; i += 2 ) + aVal = Min( aVal, getDistance( P( i ), P( i+1 )) + getDistance( P( i+1 ), P( i+2 ))); + } + break; + case SMDSEntity_Hexagonal_Prism: + if (len == 12) { // hexagonal prism + double L1 = getDistance(P( 1 ),P( 2 )); + double L2 = getDistance(P( 2 ),P( 3 )); + double L3 = getDistance(P( 3 ),P( 4 )); + double L4 = getDistance(P( 4 ),P( 5 )); + double L5 = getDistance(P( 5 ),P( 6 )); + double L6 = getDistance(P( 6 ),P( 1 )); + + double L7 = getDistance(P( 7 ), P( 8 )); + double L8 = getDistance(P( 8 ), P( 9 )); + double L9 = getDistance(P( 9 ), P( 10 )); + double L10= getDistance(P( 10 ),P( 11 )); + double L11= getDistance(P( 11 ),P( 12 )); + double L12= getDistance(P( 12 ),P( 7 )); + + double L13 = getDistance(P( 1 ),P( 7 )); + double L14 = getDistance(P( 2 ),P( 8 )); + double L15 = getDistance(P( 3 ),P( 9 )); + double L16 = getDistance(P( 4 ),P( 10 )); + double L17 = getDistance(P( 5 ),P( 11 )); + double L18 = getDistance(P( 6 ),P( 12 )); + aVal = Min(Min(Min(L1,L2),Min(L3,L4)),Min(L5,L6)); + aVal = Min(aVal, Min(Min(Min(L7,L8),Min(L9,L10)),Min(L11,L12))); + aVal = Min(aVal, Min(Min(Min(L13,L14),Min(L15,L16)),Min(L17,L18))); } + break; + case SMDSEntity_Polyhedra: + { + } + break; + default: + return 0; + } - return aVal; + if (aVal < 0 ) { + return 0.; + } + if ( myPrecision >= 0 ) + { + double prec = pow( 10., (double)( myPrecision ) ); + aVal = floor( aVal * prec + 0.5 ) / prec; } - return 0.; + + return aVal; } double Length2D::GetBadRate( double Value, int /*nbNodes*/ ) const @@ -1908,6 +1901,80 @@ void Length2D::GetValues(TValues& theValues) } } +//================================================================================ +/* + Class : Deflection2D + Description : Functor for calculating number of faces conneted to the edge +*/ +//================================================================================ + +double Deflection2D::GetValue( const TSequenceOfXYZ& P ) +{ + if ( myMesh && P.getElement() ) + { + // get underlying surface + if ( myShapeIndex != P.getElement()->getshapeId() ) + { + mySurface.Nullify(); + myShapeIndex = P.getElement()->getshapeId(); + const TopoDS_Shape& S = + static_cast< const SMESHDS_Mesh* >( myMesh )->IndexToShape( myShapeIndex ); + if ( !S.IsNull() && S.ShapeType() == TopAbs_FACE ) + { + mySurface = new ShapeAnalysis_Surface( BRep_Tool::Surface( TopoDS::Face( S ))); + } + } + // project gravity center to the surface + if ( !mySurface.IsNull() ) + { + gp_XYZ gc(0,0,0); + gp_XY uv(0,0); + int nbUV = 0; + for ( size_t i = 0; i < P.size(); ++i ) + { + gc += P(i+1); + + if ( const SMDS_FacePosition* fPos = dynamic_cast + ( P.getElement()->GetNode( i )->GetPosition() )) + { + uv.ChangeCoord(1) += fPos->GetUParameter(); + uv.ChangeCoord(2) += fPos->GetVParameter(); + ++nbUV; + } + } + gc /= P.size(); + if ( nbUV ) uv /= nbUV; + + double maxLen = MaxElementLength2D().GetValue( P ); + double tol = 1e-3 * maxLen; + if ( uv.X() != 0 && uv.Y() != 0 ) // faster way + mySurface->NextValueOfUV( uv, gc, tol, 0.5 * maxLen ); + else + mySurface->ValueOfUV( gc, tol ); + + return Round( mySurface->Gap() ); + } + } + return 0; +} + +void Deflection2D::SetMesh( const SMDS_Mesh* theMesh ) +{ + NumericalFunctor::SetMesh( dynamic_cast( theMesh )); + myShapeIndex = -100; +} + +SMDSAbs_ElementType Deflection2D::GetType() const +{ + return SMDSAbs_Face; +} + +double Deflection2D::GetBadRate( double Value, int /*nbNodes*/ ) const +{ + // meaningless as it is not quality control functor + return Value; +} + //================================================================================ /* Class : MultiConnection diff --git a/src/Controls/SMESH_ControlsDef.hxx b/src/Controls/SMESH_ControlsDef.hxx index 74a4a263d..048b10d0b 100644 --- a/src/Controls/SMESH_ControlsDef.hxx +++ b/src/Controls/SMESH_ControlsDef.hxx @@ -27,7 +27,6 @@ #include "SMESH_TypeDefs.hxx" -#include #include #include #include @@ -55,6 +54,8 @@ class SMESHDS_SubMesh; class SMESHDS_GroupBase; class gp_Pnt; +class BRepClass3d_SolidClassifier; +class ShapeAnalysis_Surface; namespace SMESH{ namespace Controls{ @@ -293,7 +294,7 @@ namespace SMESH{ */ class SMESHCONTROLS_EXPORT Length2D: public virtual NumericalFunctor{ public: - virtual double GetValue( long theElementId ); + virtual double GetValue( const TSequenceOfXYZ& thePoints ); virtual double GetBadRate( double Value, int nbNodes ) const; virtual SMDSAbs_ElementType GetType() const; struct Value{ @@ -307,6 +308,21 @@ namespace SMESH{ }; typedef boost::shared_ptr Length2DPtr; + /* + Class : Deflection2D + Description : Functor for calculating distance between a face and geometry + */ + class SMESHCONTROLS_EXPORT Deflection2D: public virtual NumericalFunctor{ + public: + virtual void SetMesh( const SMDS_Mesh* theMesh ); + virtual double GetValue( const TSequenceOfXYZ& thePoints ); + virtual double GetBadRate( double Value, int nbNodes ) const; + virtual SMDSAbs_ElementType GetType() const; + private: + Handle(ShapeAnalysis_Surface) mySurface; + int myShapeIndex; + }; + /* Class : MultiConnection Description : Functor for calculating number of faces connected to the edge diff --git a/src/OBJECT/SMESH_Actor.cxx b/src/OBJECT/SMESH_Actor.cxx index 48ad71c59..cf9c45312 100644 --- a/src/OBJECT/SMESH_Actor.cxx +++ b/src/OBJECT/SMESH_Actor.cxx @@ -844,11 +844,9 @@ void SMESH_ActorDef::SetControlMode( eControl theMode, bool theCheckEntityMode ) break; } case eLength2D: - { myFunctor.reset(new SMESH::Controls::Length2D()); myControlActor = my2DActor; break; - } case eFreeBorders: myFunctor.reset(new SMESH::Controls::FreeBorders()); myControlActor = my1DActor; @@ -958,6 +956,14 @@ void SMESH_ActorDef::SetControlMode( eControl theMode, bool theCheckEntityMode ) myControlActor = my3DActor; break; } + case eDeflection2D: + { + SMESH::Controls::Deflection2D* aControl = new SMESH::Controls::Deflection2D(); + aControl->SetPrecision( myControlsPrecision ); + myFunctor.reset( aControl ); + myControlActor = my2DActor; + break; + } case eBareBorderVolume: { myFunctor.reset(new SMESH::Controls::BareBorderVolume()); diff --git a/src/OBJECT/SMESH_Actor.h b/src/OBJECT/SMESH_Actor.h index f49d55cbb..e8818e4d5 100644 --- a/src/OBJECT/SMESH_Actor.h +++ b/src/OBJECT/SMESH_Actor.h @@ -141,7 +141,7 @@ class SMESHOBJECT_EXPORT SMESH_Actor: public SALOME_Actor virtual void SetFacesOrientation3DVectors(bool theState) = 0; virtual bool GetFacesOrientation3DVectors() = 0; - enum eControl{eNone, eLength, eLength2D, eFreeBorders, eFreeEdges, eFreeNodes, + enum eControl{eNone, eLength, eLength2D, eDeflection2D, eFreeBorders, eFreeEdges, eFreeNodes, eFreeFaces, eMultiConnection, eArea, eTaper, eAspectRatio, eMinimumAngle, eWarping, eSkew, eAspectRatio3D, eMultiConnection2D, eVolume3D, eMaxElementLength2D, eMaxElementLength3D, eBareBorderFace, eBareBorderVolume, diff --git a/src/SMDS/SMDS_Mesh.hxx b/src/SMDS/SMDS_Mesh.hxx index c1fea287f..5adcd6d62 100644 --- a/src/SMDS/SMDS_Mesh.hxx +++ b/src/SMDS/SMDS_Mesh.hxx @@ -701,7 +701,7 @@ public: int idnode4, int idnode5, int idnode6) const; const SMDS_MeshFace *FindFace(int idnode1, int idnode2, int idnode3, int idnode4, int idnode5, int idnode6, int idnode7, int idnode8) const; - const SMDS_MeshElement *FindElement(int IDelem) const; + virtual const SMDS_MeshElement * FindElement(int IDelem) const; static const SMDS_Mesh0DElement* Find0DElement(const SMDS_MeshNode * n); static const SMDS_BallElement* FindBall(const SMDS_MeshNode * n); static const SMDS_MeshEdge* FindEdge(const SMDS_MeshNode * n1, diff --git a/src/SMDS/SMDS_SetIterator.hxx b/src/SMDS/SMDS_SetIterator.hxx index e0b3c8b08..3402cbf6a 100644 --- a/src/SMDS/SMDS_SetIterator.hxx +++ b/src/SMDS/SMDS_SetIterator.hxx @@ -51,6 +51,11 @@ namespace SMDS { static VALUE value(VALUE_SET_ITERATOR it) { return (VALUE) it->second; } }; + template + struct PointerAccessor { + static VALUE value(VALUE_SET_ITERATOR it) { return (VALUE) &(*it); } + }; + /////////////////////////////////////////////////////////////////////////////// /// Filters of value pointed by iterator /////////////////////////////////////////////////////////////////////////////// diff --git a/src/SMESHGUI/SMESHGUI.cxx b/src/SMESHGUI/SMESHGUI.cxx index 527386e74..0061006d9 100644 --- a/src/SMESHGUI/SMESHGUI.cxx +++ b/src/SMESHGUI/SMESHGUI.cxx @@ -627,7 +627,7 @@ namespace "SMESH_TETRAHEDRA","SMESH_QUADRATIC_TETRAHEDRONS","SMESH_PYRAMIDS", "SMESH_QUADRATIC_PYRAMIDS","SMESH_HEXAHEDRA","SMESH_QUADRATIC_HEXAHEDRONS", "SMESH_TRIQUADRATIC_HEXAHEDRONS","SMESH_PENTAHEDRA","SMESH_QUADRATIC_PENTAHEDRONS", - "SMESH_BIQUADRATIC_PENTAHEDRONS", + "SMESH_BIQUADRATIC_PENTAHEDRONS", "SMESH_OCTAHEDRA","SMESH_POLYEDRONS","SMESH_QUADRATIC_POLYEDRONS","SMESH_BALLS" }; // is typeMsg complete? (compilation failure mains that enum SMDSAbs_EntityType changed) @@ -1138,6 +1138,8 @@ namespace type = QObject::tr( "LENGTH_EDGES" ); else if ( dynamic_cast< SMESH::Controls::Length2D* >( f.get() ) ) type = QObject::tr( "LENGTH2D_EDGES" ); + else if ( dynamic_cast< SMESH::Controls::Deflection2D* >( f.get() ) ) + type = QObject::tr( "DEFLECTION2D_FACES" ); else if ( dynamic_cast< SMESH::Controls::MultiConnection* >( f.get() ) ) type = QObject::tr( "MULTI_BORDERS" ); else if ( dynamic_cast< SMESH::Controls::MultiConnection2D* >( f.get() ) ) @@ -1673,6 +1675,7 @@ namespace ActionControl.Bind( SMESHOp::OpBareBorderFace, SMESH_Actor::eBareBorderFace ); ActionControl.Bind( SMESHOp::OpOverConstrainedFace, SMESH_Actor::eOverConstrainedFace ); ActionControl.Bind( SMESHOp::OpLength2D, SMESH_Actor::eLength2D ); + ActionControl.Bind( SMESHOp::OpDeflection2D, SMESH_Actor::eDeflection2D ); ActionControl.Bind( SMESHOp::OpConnection2D, SMESH_Actor::eMultiConnection2D ); ActionControl.Bind( SMESHOp::OpArea, SMESH_Actor::eArea ); ActionControl.Bind( SMESHOp::OpTaper, SMESH_Actor::eTaper ); @@ -3617,6 +3620,7 @@ bool SMESHGUI::OnGUIEvent( int theCommandID ) case SMESHOp::OpBareBorderFace: case SMESHOp::OpOverConstrainedFace: case SMESHOp::OpLength2D: + case SMESHOp::OpDeflection2D: case SMESHOp::OpConnection2D: case SMESHOp::OpArea: case SMESHOp::OpTaper: @@ -3918,6 +3922,7 @@ void SMESHGUI::initialize( CAM_Application* app ) createSMESHAction( SMESHOp::OpBareBorderFace, "BARE_BORDER_FACE", "ICON_BARE_BORDER_FACE", 0, true ); createSMESHAction( SMESHOp::OpOverConstrainedFace, "OVER_CONSTRAINED_FACE", "ICON_OVER_CONSTRAINED_FACE", 0, true ); createSMESHAction( SMESHOp::OpLength2D, "LENGTH_2D", "ICON_LENGTH_2D", 0, true ); + createSMESHAction( SMESHOp::OpDeflection2D, "DEFLECTION_2D", "ICON_DEFLECTION_2D", 0, true ); createSMESHAction( SMESHOp::OpConnection2D, "CONNECTION_2D", "ICON_CONNECTION_2D", 0, true ); createSMESHAction( SMESHOp::OpArea, "AREA", "ICON_AREA", 0, true ); createSMESHAction( SMESHOp::OpTaper, "TAPER", "ICON_TAPER", 0, true ); @@ -4047,6 +4052,7 @@ void SMESHGUI::initialize( CAM_Application* app ) << SMESHOp::OpNodeConnectivityNb // node controls << SMESHOp::OpFreeEdge << SMESHOp::OpFreeBorder << SMESHOp::OpLength << SMESHOp::OpConnection << SMESHOp::OpEqualEdge // edge controls + << SMESHOp::OpDeflection2D << SMESHOp::OpFreeFace << SMESHOp::OpLength2D << SMESHOp::OpConnection2D << SMESHOp::OpArea << SMESHOp::OpTaper << SMESHOp::OpAspectRatio << SMESHOp::OpMinimumAngle << SMESHOp::OpWarpingAngle << SMESHOp::OpSkew @@ -4160,6 +4166,7 @@ void SMESHGUI::initialize( CAM_Application* app ) createMenu( SMESHOp::OpSkew, faceId, -1 ); createMenu( SMESHOp::OpMaxElementLength2D, faceId, -1 ); createMenu( SMESHOp::OpEqualFace, faceId, -1 ); + createMenu( SMESHOp::OpDeflection2D, faceId, -1 ); createMenu( SMESHOp::OpAspectRatio3D, volumeId, -1 ); createMenu( SMESHOp::OpVolume, volumeId, -1 ); createMenu( SMESHOp::OpMaxElementLength3D, volumeId, -1 ); @@ -4309,6 +4316,7 @@ void SMESHGUI::initialize( CAM_Application* app ) createTool( SMESHOp::OpSkew, ctrl2dTb ); createTool( SMESHOp::OpMaxElementLength2D, ctrl2dTb ); createTool( SMESHOp::OpEqualFace, ctrl2dTb ); + createTool( SMESHOp::OpDeflection2D, ctrl2dTb ); createTool( SMESHOp::OpAspectRatio3D, ctrl3dTb ); createTool( SMESHOp::OpVolume, ctrl3dTb ); @@ -4720,10 +4728,15 @@ void SMESHGUI::initialize( CAM_Application* app ) popupMgr()->insert ( action( SMESHOp::OpOverConstrainedFace ), aSubId, -1 ); popupMgr()->setRule( action( SMESHOp::OpOverConstrainedFace ), aMeshInVtkHasFaces, QtxPopupMgr::VisibleRule ); popupMgr()->setRule( action( SMESHOp::OpOverConstrainedFace ), "controlMode = 'eOverConstrainedFace'", QtxPopupMgr::ToggleRule ); + popupMgr()->insert ( action( SMESHOp::OpEqualFace ), aSubId, -1 ); popupMgr()->setRule( action( SMESHOp::OpEqualFace ), aMeshInVtkHasFaces, QtxPopupMgr::VisibleRule ); popupMgr()->setRule( action( SMESHOp::OpEqualFace ), "controlMode = 'eCoincidentElems2D'", QtxPopupMgr::ToggleRule ); + popupMgr()->insert ( action( SMESHOp::OpDeflection2D ), aSubId, -1 ); + popupMgr()->setRule( action( SMESHOp::OpDeflection2D ), aMeshInVtkHasFaces + " && hasGeomReference", QtxPopupMgr::VisibleRule ); + popupMgr()->setRule( action( SMESHOp::OpDeflection2D ), "controlMode = 'eDeflection2D'", QtxPopupMgr::ToggleRule ); + aSubId = popupMgr()->insert( tr( "MEN_VOLUME_CTRL" ), anId, -1 ); // VOLUME CONTROLS popupMgr()->insert ( action( SMESHOp::OpAspectRatio3D ), aSubId, -1 ); diff --git a/src/SMESHGUI/SMESHGUI_FilterDlg.cxx b/src/SMESHGUI/SMESHGUI_FilterDlg.cxx index 6c6987c39..325413b0c 100755 --- a/src/SMESHGUI/SMESHGUI_FilterDlg.cxx +++ b/src/SMESHGUI/SMESHGUI_FilterDlg.cxx @@ -1572,6 +1572,7 @@ void SMESHGUI_FilterTable::updateAdditionalWidget() aCriterion == SMESH::FT_MaxElementLength3D || aCriterion == SMESH::FT_Length || aCriterion == SMESH::FT_Length2D || + aCriterion == SMESH::FT_Deflection2D || aCriterion == SMESH::FT_BallDiameter ); bool toEnable = (( isDbl && ((ComboItem*)aTable->item(aRow, 1))->value() == SMESH::FT_EqualTo) || @@ -1618,6 +1619,7 @@ const char* SMESHGUI_FilterTable::getPrecision( const int aType ) retval = "len_tol_precision"; break; case SMESH::FT_Length: case SMESH::FT_Length2D: + case SMESH::FT_Deflection2D: case SMESH::FT_MaxElementLength2D: case SMESH::FT_MaxElementLength3D: case SMESH::FT_BallDiameter: @@ -1793,13 +1795,13 @@ void SMESHGUI_FilterTable::onCriterionChanged (const int row, const int col, con } // find out a type of item required by a new criterion and other table features - int aCriterionType = GetCriterionType(row); + int aCriterionType = GetCriterionType(row); bool anIsDoubleCriterion = false; bool anIsIntCriterion = false; bool anIsComboCriterion = false; // other features: QList comboIDs; // values to show in a combo item - int nbCompareSigns = 0; // possible values are 0,1,3 + int nbCompareSigns = 0; // possible values are 0,1,3 bool isThresholdEditable = false; // actual for "simple" item types switch ( aCriterionType ) { @@ -1812,8 +1814,7 @@ void SMESHGUI_FilterTable::onCriterionChanged (const int row, const int col, con case SMESH::FT_Area: case SMESH::FT_Volume3D: case SMESH::FT_MaxElementLength2D: - case SMESH::FT_MaxElementLength3D: - anIsDoubleCriterion = true; break; + case SMESH::FT_MaxElementLength3D: anIsDoubleCriterion = true; break; case SMESH::FT_FreeBorders: case SMESH::FT_FreeEdges: @@ -1829,7 +1830,8 @@ void SMESHGUI_FilterTable::onCriterionChanged (const int row, const int col, con case SMESH::FT_MultiConnection2D: anIsIntCriterion = true; nbCompareSigns = 3; break; case SMESH::FT_Length: - case SMESH::FT_Length2D: anIsDoubleCriterion = true; break; + case SMESH::FT_Length2D: + case SMESH::FT_Deflection2D: anIsDoubleCriterion = true; break; case SMESH::FT_BelongToMeshGroup: break; @@ -2241,6 +2243,7 @@ const QMap& SMESHGUI_FilterTable::getCriteria (const int theType) aCriteria[ SMESH::FT_BelongToGenSurface ] = tr("BELONG_TO_GENSURFACE"); aCriteria[ SMESH::FT_LyingOnGeom ] = tr("LYING_ON_GEOM"); aCriteria[ SMESH::FT_Length2D ] = tr("LENGTH2D"); + aCriteria[ SMESH::FT_Deflection2D ] = tr("DEFLECTION2D"); aCriteria[ SMESH::FT_MultiConnection2D ] = tr("MULTI2D_BORDERS"); aCriteria[ SMESH::FT_FreeFaces ] = tr("FREE_FACES"); aCriteria[ SMESH::FT_BareBorderFace ] = tr("BARE_BORDER_FACE"); diff --git a/src/SMESHGUI/SMESHGUI_MeshInfo.cxx b/src/SMESHGUI/SMESHGUI_MeshInfo.cxx index a05414b8c..020dff359 100644 --- a/src/SMESHGUI/SMESHGUI_MeshInfo.cxx +++ b/src/SMESHGUI/SMESHGUI_MeshInfo.cxx @@ -966,11 +966,13 @@ SMESHGUI_ElemInfo::~SMESHGUI_ElemInfo() \brief Set mesh data source (actor) \param actor mesh object actor */ -void SMESHGUI_ElemInfo::setSource( SMESH_Actor* actor ) +void SMESHGUI_ElemInfo::setSource( SMESH_Actor* actor, SMESH::SMESH_IDSource_var obj ) { if ( myActor != actor ) { myActor = actor; myIsElement = -1; + SMESH::SMESH_Mesh_var mesh = obj->GetMesh(); + myMeshHasShape = ( !mesh->_is_nil() && mesh->HasShapeToMesh() ); clear(); } } @@ -1479,7 +1481,12 @@ void SMESHGUI_SimpleElemInfo::information( const QList& ids ) //ElemDiam2D afunctor.reset( new SMESH::Controls::MaxElementLength2D() ); afunctor->SetMesh( actor()->GetObject()->GetMesh() ); + afunctor->SetPrecision( cprecision ); myInfo->append( QString( "- %1: %2" ).arg( tr( "MAX_ELEMENT_LENGTH_2D" )).arg( afunctor->GetValue( id )) ); + //min edge length + afunctor.reset( new SMESH::Controls::Length2D() ); + afunctor->SetMesh( actor()->GetObject()->GetMesh() ); + myInfo->append( QString( "- %1: %2" ).arg( tr( "MIN_ELEM_EDGE" )).arg( afunctor->GetValue( id )) ); } if( e->GetType() == SMDSAbs_Volume ) { //AspectRatio3D @@ -2026,6 +2033,15 @@ void SMESHGUI_TreeElemInfo::information( const QList& ids ) skewItem->setText( 0, tr( "SKEW_ELEMENTS" )); skewItem->setText( 1, QString( "%1" ).arg( afunctor->GetValue( id )) ); } + //Deflection + if ( hasShapeToMesh() ) + { + afunctor.reset( new SMESH::Controls::Deflection2D() ); + afunctor->SetMesh( actor()->GetObject()->GetMesh() ); + QTreeWidgetItem* deflItem = createItem( cntrItem, Bold ); + deflItem->setText( 0, tr( "DEFLECTION_2D" )); + deflItem->setText( 1, QString( "%1" ).arg( afunctor->GetValue( id )) ); + } //ElemDiam2D if ( !e->IsPoly() ) { @@ -2060,6 +2076,13 @@ void SMESHGUI_TreeElemInfo::information( const QList& ids ) diam3Item->setText( 1, QString( "%1" ).arg( afunctor->GetValue( id )) ); } + //min edge length + afunctor.reset( new SMESH::Controls::Length2D() ); + afunctor->SetMesh( actor()->GetObject()->GetMesh() ); + QTreeWidgetItem* minEdgeItem = createItem( cntrItem, Bold ); + minEdgeItem->setText( 0, tr( "MIN_ELEM_EDGE" )); + minEdgeItem->setText( 1, QString( "%1" ).arg( afunctor->GetValue( id )) ); + // gravity center XYZ gc = gravityCenter( e ); QTreeWidgetItem* gcItem = createItem( elemItem, Bold ); @@ -2990,7 +3013,7 @@ void SMESHGUI_MeshInfoDlg::showInfo( const Handle(SALOME_InteractiveObject)& IO SMESH::GetNameOfSelectedElements( selector, IO, ID ) : SMESH::GetNameOfSelectedNodes( selector, IO, ID ); } - myElemInfo->setSource( myActor ) ; + myElemInfo->setSource( myActor, obj ) ; if ( nb > 0 ) { myID->setText( ID.trimmed() ); QSet ids; diff --git a/src/SMESHGUI/SMESHGUI_MeshInfo.h b/src/SMESHGUI/SMESHGUI_MeshInfo.h index 4b43e1aa4..85edb6001 100644 --- a/src/SMESHGUI/SMESHGUI_MeshInfo.h +++ b/src/SMESHGUI/SMESHGUI_MeshInfo.h @@ -153,7 +153,7 @@ public: SMESHGUI_ElemInfo( QWidget* = 0 ); ~SMESHGUI_ElemInfo(); - void setSource( SMESH_Actor* ); + void setSource( SMESH_Actor*, SMESH::SMESH_IDSource_var ); void showInfo( long, bool ); void showInfo( QSet, bool ); void clear(); @@ -179,6 +179,7 @@ protected: QWidget* frame() const; SMESH_Actor* actor() const; bool isElements() const; + bool hasShapeToMesh() const { return myMeshHasShape; } virtual void information( const QList& ) = 0; virtual void clearInternal(); @@ -204,6 +205,7 @@ private: QWidget* myFrame; ExtraWidget* myExtra; int myIndex; + bool myMeshHasShape; }; class SMESHGUI_EXPORT SMESHGUI_SimpleElemInfo : public SMESHGUI_ElemInfo diff --git a/src/SMESHGUI/SMESHGUI_Operations.h b/src/SMESHGUI/SMESHGUI_Operations.h index 63c9885cd..06163d911 100644 --- a/src/SMESHGUI/SMESHGUI_Operations.h +++ b/src/SMESHGUI/SMESHGUI_Operations.h @@ -116,6 +116,7 @@ namespace SMESHOp { OpSkew = 3210, // MENU CONTROLS - SKEW OpMaxElementLength2D = 3211, // MENU CONTROLS - ELEMENT DIAMETER 2D OpEqualFace = 3212, // MENU CONTROLS - DOUBLE FACES + OpDeflection2D = 3213, // MENU CONTROLS - DEFLECTION 2D OpAspectRatio3D = 3300, // MENU CONTROLS - ASPECT RATIO 3D OpVolume = 3301, // MENU CONTROLS - VOLUME OpMaxElementLength3D = 3302, // MENU CONTROLS - ELEMENT DIAMETER 3D diff --git a/src/SMESHGUI/SMESHGUI_Selection.cxx b/src/SMESHGUI/SMESHGUI_Selection.cxx index b6976df86..5eb6dba66 100644 --- a/src/SMESHGUI/SMESHGUI_Selection.cxx +++ b/src/SMESHGUI/SMESHGUI_Selection.cxx @@ -364,6 +364,7 @@ QString SMESHGUI_Selection::controlMode( int ind ) const switch( actor->GetControlMode() ) { case SMESH_Actor::eLength: mode = "eLength"; break; case SMESH_Actor::eLength2D: mode = "eLength2D"; break; + case SMESH_Actor::eDeflection2D: mode = "eDeflection2D"; break; case SMESH_Actor::eFreeEdges: mode = "eFreeEdges"; break; case SMESH_Actor::eFreeNodes: mode = "eFreeNodes"; break; case SMESH_Actor::eFreeBorders: mode = "eFreeBorders"; break; @@ -411,6 +412,11 @@ QString SMESHGUI_Selection::controlMode() const return "eNone"; } +//======================================================================= +//function : isNumFunctor +//purpose : return true if a given actor is shown using a numeric functor +//======================================================================= + bool SMESHGUI_Selection::isNumFunctor( int ind ) const { bool result = false; @@ -419,6 +425,7 @@ bool SMESHGUI_Selection::isNumFunctor( int ind ) const switch( actor->GetControlMode() ) { case SMESH_Actor::eLength: case SMESH_Actor::eLength2D: + case SMESH_Actor::eDeflection2D: case SMESH_Actor::eMultiConnection: case SMESH_Actor::eMultiConnection2D: case SMESH_Actor::eArea: @@ -442,7 +449,7 @@ bool SMESHGUI_Selection::isNumFunctor( int ind ) const //======================================================================= //function : facesOrientationMode -//purpose : +//purpose : //======================================================================= QString SMESHGUI_Selection::facesOrientationMode( int ind ) const diff --git a/src/SMESHGUI/SMESH_images.ts b/src/SMESHGUI/SMESH_images.ts index 3ccd58cba..27ce2523f 100644 --- a/src/SMESHGUI/SMESH_images.ts +++ b/src/SMESHGUI/SMESH_images.ts @@ -347,6 +347,10 @@ ICON_LENGTH_2D mesh_length_2d.png + + ICON_DEFLECTION_2D + mesh_deflection.png + ICON_MAP mesh_pattern.png diff --git a/src/SMESHGUI/SMESH_msg_en.ts b/src/SMESHGUI/SMESH_msg_en.ts index 31d955416..3e6896d59 100644 --- a/src/SMESHGUI/SMESH_msg_en.ts +++ b/src/SMESHGUI/SMESH_msg_en.ts @@ -103,6 +103,10 @@ MIN_DIAG_ELEMENTS Minimum diagonal + + MIN_ELEM_EDGE + Minimum Edge Length + ASPECTRATIO_3D_ELEMENTS Aspect Ratio 3D @@ -224,6 +228,10 @@ LENGTH2D_EDGES Length 2D + + DEFLECTION2D_FACES + Deflection 2D + LENGTH_EDGES Length @@ -240,6 +248,10 @@ MAX_ELEMENT_LENGTH_3D Element Diameter 3D + + DEFLECTION_2D + Deflection 2D + MEN_ADD Add @@ -692,6 +704,10 @@ MEN_LENGTH_2D Length 2D + + MEN_DEFLECTION_2D + Deflection 2D + MEN_MAP Pattern Mapping @@ -3278,6 +3294,10 @@ Use Display Entity menu command to show them. STB_LENGTH_2D Length 2D + + STB_DEFLECTION_2D + Deflection 2D + STB_MAP Pattern mapping @@ -3958,6 +3978,10 @@ Use Display Entity menu command to show them. TOP_LENGTH_2D Length 2D + + TOP_DEFLECTION_2D + Deflection 2D + TOP_MAP Pattern mapping @@ -5869,6 +5893,10 @@ Please enter correct value and try again LENGTH2D Length 2D + + DEFLECTION2D + Deflection 2D + LESS_THAN Less than diff --git a/src/SMESH_I/SMESH_2smeshpy.cxx b/src/SMESH_I/SMESH_2smeshpy.cxx index 876365b0c..5a9e2e519 100644 --- a/src/SMESH_I/SMESH_2smeshpy.cxx +++ b/src/SMESH_I/SMESH_2smeshpy.cxx @@ -294,6 +294,8 @@ namespace { // - FT_BelongToMeshGroup = 22 // v 8.1.0: FT_Undefined == 48, new items: // - FT_NodeConnectivityNumber= 22 + // v 8.5.0: FT_Undefined == 49, new items: + // - FT_Deflection2D = 22 // // It's necessary to continue recording this history and to fill // undef2newItems (see below) accordingly. @@ -316,6 +318,7 @@ namespace { undef2newItems[ 46 ].push_back( 39 ); undef2newItems[ 47 ].push_back( 22 ); undef2newItems[ 48 ].push_back( 22 ); + undef2newItems[ 49 ].push_back( 22 ); ASSERT( undef2newItems.rbegin()->first == SMESH::FT_Undefined ); } diff --git a/src/SMESH_I/SMESH_DumpPython.cxx b/src/SMESH_I/SMESH_DumpPython.cxx index 6298cb099..878b152f4 100644 --- a/src/SMESH_I/SMESH_DumpPython.cxx +++ b/src/SMESH_I/SMESH_DumpPython.cxx @@ -431,6 +431,7 @@ namespace SMESH case FT_MultiConnection2D: myStream<< "aMultiConnection2D"; break; case FT_Length: myStream<< "aLength"; break; case FT_Length2D: myStream<< "aLength2D"; break; + case FT_Deflection2D: myStream<< "aDeflection2D"; break; case FT_NodeConnectivityNumber:myStream<< "aNodeConnectivityNumber";break; case FT_BelongToMeshGroup: myStream<< "aBelongToMeshGroup"; break; case FT_BelongToGeom: myStream<< "aBelongToGeom"; break; diff --git a/src/SMESH_I/SMESH_Filter_i.cxx b/src/SMESH_I/SMESH_Filter_i.cxx index 9432b9117..3ae548024 100644 --- a/src/SMESH_I/SMESH_Filter_i.cxx +++ b/src/SMESH_I/SMESH_Filter_i.cxx @@ -534,6 +534,21 @@ SMESH::Length2D::Values* Length2D_i::GetValues() return aResult._retn(); } +/* + Class : Deflection2D_i + Description : Functor for calculating distance between a face and geometry +*/ +Deflection2D_i::Deflection2D_i() +{ + myNumericalFunctorPtr.reset( new Controls::Deflection2D() ); + myFunctorPtr = myNumericalFunctorPtr; +} + +FunctorType Deflection2D_i::GetFunctorType() +{ + return SMESH::FT_Deflection2D; +} + /* Class : MultiConnection_i Description : Functor for calculating number of faces conneted to the edge @@ -2113,6 +2128,14 @@ Length2D_ptr FilterManager_i::CreateLength2D() return anObj._retn(); } +Deflection2D_ptr FilterManager_i::CreateDeflection2D() +{ + SMESH::Deflection2D_i* aServant = new SMESH::Deflection2D_i(); + SMESH::Deflection2D_var anObj = aServant->_this(); + TPythonDump()<CreateLength2D(); break; + case SMESH::FT_Deflection2D: + aFunctor = aFilterMgr->CreateDeflection2D(); + break; case SMESH::FT_AspectRatio: aFunctor = aFilterMgr->CreateAspectRatio(); break; @@ -3451,9 +3477,10 @@ static inline LDOMString toString( CORBA::Long theType ) case FT_EqualFaces : return "Equal faces"; case FT_EqualVolumes : return "Equal volumes"; case FT_MultiConnection : return "Borders at multi-connections"; - case FT_MultiConnection2D :return "Borders at multi-connections 2D"; + case FT_MultiConnection2D : return "Borders at multi-connections 2D"; case FT_Length : return "Length"; case FT_Length2D : return "Length 2D"; + case FT_Deflection2D : return "Deflection 2D"; case FT_LessThan : return "Less than"; case FT_MoreThan : return "More than"; case FT_EqualTo : return "Equal to"; @@ -3502,6 +3529,7 @@ static inline SMESH::FunctorType toFunctorType( const LDOMString& theStr ) // else if ( theStr.equals( "Borders at multi-connections 2D" ) ) return FT_MultiConnection2D; else if ( theStr.equals( "Length" ) ) return FT_Length; // else if ( theStr.equals( "Length2D" ) ) return FT_Length2D; + else if ( theStr.equals( "Deflection" ) ) return FT_Deflection2D; else if ( theStr.equals( "Range of IDs" ) ) return FT_RangeOfIds; else if ( theStr.equals( "Bad Oriented Volume" ) ) return FT_BadOrientedVolume; else if ( theStr.equals( "Volumes with bare border" ) ) return FT_BareBorderVolume; @@ -4078,6 +4106,7 @@ static const char** getFunctNames() "FT_MultiConnection2D", "FT_Length", "FT_Length2D", + "FT_Deflection2D", "FT_NodeConnectivityNumber", "FT_BelongToMeshGroup", "FT_BelongToGeom", @@ -4094,7 +4123,7 @@ static const char** getFunctNames() "FT_LinearOrQuadratic", "FT_GroupColor", "FT_ElemGeomType", - "FT_EntityType", + "FT_EntityType", "FT_CoplanarFaces", "FT_BallDiameter", "FT_ConnectedElements", diff --git a/src/SMESH_I/SMESH_Filter_i.hxx b/src/SMESH_I/SMESH_Filter_i.hxx index 9baf0f3bf..5555a69b5 100644 --- a/src/SMESH_I/SMESH_Filter_i.hxx +++ b/src/SMESH_I/SMESH_Filter_i.hxx @@ -266,11 +266,23 @@ namespace SMESH Length2D_i(); SMESH::Length2D::Values* GetValues(); FunctorType GetFunctorType(); - + protected: Controls::Length2DPtr myLength2DPtr; }; - + + /* + Class : Deflection2D_i + Description : Functor for calculating distance between a face and geometry + */ + class SMESH_I_EXPORT Deflection2D_i: public virtual POA_SMESH::Deflection2D, + public virtual NumericalFunctor_i + { + public: + Deflection2D_i(); + FunctorType GetFunctorType(); + }; + /* Class : MultiConnection_i Description : Functor for calculating number of faces conneted to the edge @@ -1087,6 +1099,7 @@ namespace SMESH MaxElementLength3D_ptr CreateMaxElementLength3D(); Length_ptr CreateLength(); Length2D_ptr CreateLength2D(); + Deflection2D_ptr CreateDeflection2D(); NodeConnectivityNumber_ptr CreateNodeConnectivityNumber(); MultiConnection_ptr CreateMultiConnection(); MultiConnection2D_ptr CreateMultiConnection2D(); diff --git a/src/SMESH_I/SMESH_MeshPartDS.hxx b/src/SMESH_I/SMESH_MeshPartDS.hxx index 423dfb067..986ee3c06 100644 --- a/src/SMESH_I/SMESH_MeshPartDS.hxx +++ b/src/SMESH_I/SMESH_MeshPartDS.hxx @@ -27,6 +27,7 @@ #define __SMESH_MeshPartDS_HXX__ #include "SMESHDS_Mesh.hxx" +#include "SMESH_TypeDefs.hxx" #include #include CORBA_SERVER_HEADER(SMESH_Mesh) @@ -55,6 +56,8 @@ public: virtual SMDS_ElemIteratorPtr elementGeomIterator(SMDSAbs_GeometryType type) const; virtual SMDS_ElemIteratorPtr elementEntityIterator(SMDSAbs_EntityType type) const; + virtual const SMDS_MeshElement *FindElement(int IDelem) const; + private: TIDSortedElemSet _elements[ SMDSAbs_NbElementTypes ]; SMESHDS_Mesh* _meshDS; @@ -65,6 +68,17 @@ private: { void Add(const SMDS_MeshElement* e) { SMDS_MeshInfo::addWithPoly( e ); } }; + /*! + * \brief Element holing its ID only + */ + struct TElemID : public SMDS_MeshElement + { + TElemID(int ID) : SMDS_MeshElement( ID ) {} + virtual SMDSAbs_ElementType GetType() const { return SMDSAbs_All; } + virtual SMDSAbs_EntityType GetEntityType() const { return SMDSEntity_Last; } + virtual SMDSAbs_GeometryType GetGeomType() const { return SMDSGeom_NONE; } + virtual vtkIdType GetVtkType() const { return -1; } + }; }; #endif diff --git a/src/SMESH_I/SMESH_Mesh_i.cxx b/src/SMESH_I/SMESH_Mesh_i.cxx index 163446233..b16d38f26 100644 --- a/src/SMESH_I/SMESH_Mesh_i.cxx +++ b/src/SMESH_I/SMESH_Mesh_i.cxx @@ -6119,6 +6119,7 @@ SMESH_MeshPartDS::SMESH_MeshPartDS(SMESH::SMESH_IDSource_ptr meshPart): SMESH::SMESH_Mesh_var mesh = meshPart->GetMesh(); SMESH_Mesh_i* mesh_i = SMESH::DownCast( mesh ); + mesh_i->Load(); _meshDS = mesh_i->GetImpl().GetMeshDS(); SetPersistentId( _meshDS->GetPersistentId() ); @@ -6188,6 +6189,21 @@ SMESH_MeshPartDS::SMESH_MeshPartDS(const std::list< const SMDS_MeshElement* > & myInfo = tmpInfo; } // ------------------------------------------------------------------------------------- +const SMDS_MeshElement * SMESH_MeshPartDS::FindElement(int IDelem) const +{ + if ( _meshDS ) return _meshDS->FindElement( IDelem ); + + TElemID elem( IDelem ); + for ( int iType = SMDSAbs_Edge; iType < SMDSAbs_NbElementTypes; ++iType ) + if ( !_elements[ iType ].empty() ) + { + TIDSortedElemSet::const_iterator it = _elements[ iType ].find( &elem ); + if ( it != _elements[ iType ].end() ) + return *it; + } + return 0; +} +// ------------------------------------------------------------------------------------- SMDS_ElemIteratorPtr SMESH_MeshPartDS::elementGeomIterator(SMDSAbs_GeometryType geomType) const { if ( _meshDS ) return _meshDS->elementGeomIterator( geomType ); diff --git a/src/SMESH_SWIG/smeshBuilder.py b/src/SMESH_SWIG/smeshBuilder.py index 11ba7dcf7..4b88a8050 100644 --- a/src/SMESH_SWIG/smeshBuilder.py +++ b/src/SMESH_SWIG/smeshBuilder.py @@ -966,6 +966,8 @@ class smeshBuilder(object, SMESH._objref_SMESH_Gen): functor = aFilterMgr.CreateLength() elif theCriterion == FT_Length2D: functor = aFilterMgr.CreateLength2D() + elif theCriterion == FT_Deflection2D: + functor = aFilterMgr.CreateDeflection2D() elif theCriterion == FT_NodeConnectivityNumber: functor = aFilterMgr.CreateNodeConnectivityNumber() elif theCriterion == FT_BallDiameter: @@ -3117,6 +3119,16 @@ class Mesh: def GetPointState(self, x, y, z): return self.editor.GetPointState(x, y, z) + ## Check if a 2D mesh is manifold + # @ingroup l1_controls + def IsManifold(self): + return self.editor.IsManifold() + + ## Check if orientation of 2D elements is coherent + # @ingroup l1_controls + def IsCoherentOrientation2D(self): + return self.editor.IsCoherentOrientation2D() + ## Find the node closest to a point and moves it to a point location # @param x the X coordinate of a point # @param y the Y coordinate of a point @@ -4619,6 +4631,24 @@ class Mesh: def MergeEqualElements(self): self.editor.MergeEqualElements() + ## Returns all or only closed free borders + # @return list of SMESH.FreeBorder's + # @ingroup l2_modif_trsf + def FindFreeBorders(self, ClosedOnly=True): + return self.editor.FindFreeBorders( ClosedOnly ) + + ## Fill with 2D elements a hole defined by a SMESH.FreeBorder. + # @param FreeBorder either a SMESH.FreeBorder or a list on node IDs. These nodes + # must describe all sequential nodes of the hole border. The first and the last + # nodes must be the same. Use FindFreeBorders() to get nodes of holes. + # @ingroup l2_modif_trsf + def FillHole(self, holeNodes): + if holeNodes and isinstance( holeNodes, list ) and isinstance( holeNodes[0], int ): + holeNodes = SMESH.FreeBorder(nodeIDs=holeNodes) + if not isinstance( holeNodes, SMESH.FreeBorder ): + raise TypeError, "holeNodes must be either SMESH.FreeBorder or list of integer and not %s" % holeNodes + self.editor.FillHole( holeNodes ) + ## Return groups of FreeBorder's coincident within the given tolerance. # @param tolerance the tolerance. If the tolerance <= 0.0 then one tenth of an average # size of elements adjacent to free borders being compared is used. @@ -4934,7 +4964,14 @@ class Mesh: def CreateHoleSkin(self, radius, theShape, groupName, theNodesCoords): return self.editor.CreateHoleSkin( radius, theShape, groupName, theNodesCoords ) - def _getFunctor(self, funcType ): + ## Return a cached numerical functor by its type. + # @param theCriterion functor type - an item of SMESH.FunctorType enumeration. + # Type SMESH.FunctorType._items in the Python Console to see all items. + # Note that not all items correspond to numerical functors. + # @return SMESH_NumericalFunctor. The functor is already initialized + # with a mesh + # @ingroup l1_measurements + def GetFunctor(self, funcType ): fn = self.functors[ funcType._v ] if not fn: fn = self.smeshpyD.GetFunctor(funcType) @@ -4950,7 +4987,7 @@ class Mesh: # @return the functor value or zero in case of invalid arguments # @ingroup l1_measurements def FunctorValue(self, funcType, elemId, isElem=True): - fn = self._getFunctor( funcType ) + fn = self.GetFunctor( funcType ) if fn.GetElementType() == self.GetElementType(elemId, isElem): val = fn.GetValue(elemId) else: @@ -5056,7 +5093,7 @@ class Mesh: unRegister.set( meshPart ) if isinstance( meshPart, Mesh ): meshPart = meshPart.mesh - fun = self._getFunctor( funType ) + fun = self.GetFunctor( funType ) if fun: if meshPart: if hasattr( meshPart, "SetMesh" ): diff --git a/src/StdMeshersGUI/StdMeshers_msg_en.ts b/src/StdMeshersGUI/StdMeshers_msg_en.ts index 5b6fe40c3..91a1b3ca6 100644 --- a/src/StdMeshersGUI/StdMeshers_msg_en.ts +++ b/src/StdMeshersGUI/StdMeshers_msg_en.ts @@ -136,7 +136,7 @@ this one for this mesh/sub-mesh. SMESH_DISTR_EXPR - Distribution with analitic density + Distribution with analytic density SMESH_DISTR_REGULAR -- 2.30.2