Merge remote-tracking branch 'origin/master'

This commit is contained in:
Paul RASCLE 2018-03-06 11:35:08 +01:00
commit 776a610c84
42 changed files with 554 additions and 488 deletions

View File

@ -206,7 +206,7 @@ module SMESH
{
HYP_OK,
HYP_MISSING, // algo misses a hypothesis
HYP_CONCURENT, // several applicable hypotheses
HYP_CONCURRENT, // several applicable hypotheses
HYP_BAD_PARAMETER,// hypothesis has a bad parameter value
HYP_HIDDEN_ALGO, // an algo is hidden by an upper dim algo generating all-dim elements
HYP_HIDING_ALGO, // an algo hides lower dim algos by generating all-dim elements

View File

@ -1029,7 +1029,7 @@ static int ScaKwdTab(GmfMshSct *msh)
if(isalpha(str[0]))
{
/* Search which kwd code this string is associated with,
then get its header and save the curent position in file (just before the data) */
then get its header and save the current position in file (just before the data) */
for(KwdCod=1; KwdCod<= GmfMaxKwd; KwdCod++)
if(!strcmp(str, GmfKwdFmt[ KwdCod ][0]))

View File

@ -675,7 +675,7 @@ static bool checkConformIgnoredAlgos(SMESH_Mesh& aMesh,
checkConform = false; // no more check conformity
INFOS( "ERROR: Local <" << algo->GetName() <<
"> would produce not conform mesh: "
"<Not Conform Mesh Allowed> hypotesis is missing");
"<Not Conform Mesh Allowed> hypothesis is missing");
theErrors.push_back( SMESH_Gen::TAlgoStateError() );
theErrors.back().Set( SMESH_Hypothesis::HYP_NOTCONFORM, algo, false );
}

View File

@ -77,7 +77,7 @@ int SMESH_HypoFilter::DimPredicate::Value( const SMESH_Hypothesis* aHyp ) const
bool SMESH_HypoFilter::ApplicablePredicate::IsOk(const SMESH_Hypothesis* aHyp,
const TopoDS_Shape& /*aShape*/) const
{
return SMESH_subMesh::IsApplicableHypotesis( aHyp, (TopAbs_ShapeEnum)_shapeType );
return SMESH_subMesh::IsApplicableHypothesis( aHyp, (TopAbs_ShapeEnum)_shapeType );
};
//=======================================================================

View File

@ -51,7 +51,7 @@ public:
{
HYP_OK = 0,
HYP_MISSING, // algo misses a hypothesis
HYP_CONCURENT, // several applicable hypotheses assigned to father shapes
HYP_CONCURRENT, // several applicable hypotheses assigned to father shapes
HYP_BAD_PARAMETER,// hypothesis has a bad parameter value
HYP_HIDDEN_ALGO, // an algo is hidden by an upper dim algo generating all-dim elements
HYP_HIDING_ALGO, // an algo hides lower dim algos by generating all-dim elements

View File

@ -661,7 +661,7 @@ SMESH_Mesh::AddHypothesis(const TopoDS_Shape & aSubShape,
string hypName = anHyp->GetName();
if ( hypName == "NotConformAllowed" )
{
if(MYDEBUG) MESSAGE( "Hypotesis <NotConformAllowed> can be only global" );
if(MYDEBUG) MESSAGE( "Hypothesis <NotConformAllowed> can be only global" );
return SMESH_Hypothesis::HYP_INCOMPATIBLE;
}
}
@ -698,13 +698,13 @@ SMESH_Mesh::AddHypothesis(const TopoDS_Shape & aSubShape,
}
// check concurrent hypotheses on ancestors
if (ret < SMESH_Hypothesis::HYP_CONCURENT && !isGlobalHyp )
if (ret < SMESH_Hypothesis::HYP_CONCURRENT && !isGlobalHyp )
{
SMESH_subMeshIteratorPtr smIt = subMesh->getDependsOnIterator(false,false);
while ( smIt->more() ) {
SMESH_subMesh* sm = smIt->next();
if ( sm->IsApplicableHypotesis( anHyp )) {
ret2 = sm->CheckConcurentHypothesis( anHyp->GetType() );
if ( sm->IsApplicableHypothesis( anHyp )) {
ret2 = sm->CheckConcurrentHypothesis( anHyp->GetType() );
if (ret2 > ret) {
ret = ret2;
break;
@ -751,10 +751,10 @@ SMESH_Mesh::RemoveHypothesis(const TopoDS_Shape & aSubShape,
SMESH_Hypothesis::Hypothesis_Status ret = subMesh->AlgoStateEngine(event, anHyp);
// there may appear concurrent hyps that were covered by the removed hyp
if (ret < SMESH_Hypothesis::HYP_CONCURENT &&
subMesh->IsApplicableHypotesis( anHyp ) &&
subMesh->CheckConcurentHypothesis( anHyp->GetType() ) != SMESH_Hypothesis::HYP_OK)
ret = SMESH_Hypothesis::HYP_CONCURENT;
if (ret < SMESH_Hypothesis::HYP_CONCURRENT &&
subMesh->IsApplicableHypothesis( anHyp ) &&
subMesh->CheckConcurrentHypothesis( anHyp->GetType() ) != SMESH_Hypothesis::HYP_OK)
ret = SMESH_Hypothesis::HYP_CONCURRENT;
// sub-shapes
if (!SMESH_Hypothesis::IsStatusFatal(ret) &&
@ -768,13 +768,13 @@ SMESH_Mesh::RemoveHypothesis(const TopoDS_Shape & aSubShape,
ret = ret2;
// check concurrent hypotheses on ancestors
if (ret < SMESH_Hypothesis::HYP_CONCURENT && !IsMainShape( aSubShape ) )
if (ret < SMESH_Hypothesis::HYP_CONCURRENT && !IsMainShape( aSubShape ) )
{
SMESH_subMeshIteratorPtr smIt = subMesh->getDependsOnIterator(false,false);
while ( smIt->more() ) {
SMESH_subMesh* sm = smIt->next();
if ( sm->IsApplicableHypotesis( anHyp )) {
ret2 = sm->CheckConcurentHypothesis( anHyp->GetType() );
if ( sm->IsApplicableHypothesis( anHyp )) {
ret2 = sm->CheckConcurrentHypothesis( anHyp->GetType() );
if (ret2 > ret) {
ret = ret2;
break;
@ -1169,7 +1169,7 @@ bool SMESH_Mesh::IsUsedHypothesis(SMESHDS_Hypothesis * anHyp,
SMESH_Hypothesis* hyp = static_cast<SMESH_Hypothesis*>(anHyp);
// check if anHyp can be used to mesh aSubMesh
if ( !aSubMesh || !aSubMesh->IsApplicableHypotesis( hyp ))
if ( !aSubMesh || !aSubMesh->IsApplicableHypothesis( hyp ))
return false;
SMESH_Algo *algo = aSubMesh->GetAlgo();
@ -1232,7 +1232,7 @@ void SMESH_Mesh::NotifySubMeshesHypothesisModification(const SMESH_Hypothesis* h
{
const TopoDS_Shape & aSubShape = aSubMesh->GetSubShape();
if (( aSubMesh->IsApplicableHypotesis( hyp )) &&
if (( aSubMesh->IsApplicableHypothesis( hyp )) &&
( algo = aSubMesh->GetAlgo() ) &&
( compatibleHypoKind = algo->GetCompatibleHypoFilter( !hyp->IsAuxiliary() )) &&
( compatibleHypoKind->IsOk( hyp, aSubShape )))

View File

@ -512,25 +512,25 @@ bool SMESH_subMesh::CanAddHypothesis(const SMESH_Hypothesis* theHypothesis) cons
}
//=======================================================================
//function : IsApplicableHypotesis
//function : IsApplicableHypothesis
//purpose : check if this sub-mesh can be computed using a hypothesis
//=======================================================================
bool SMESH_subMesh::IsApplicableHypotesis(const SMESH_Hypothesis* theHypothesis) const
bool SMESH_subMesh::IsApplicableHypothesis(const SMESH_Hypothesis* theHypothesis) const
{
if ( !_father->HasShapeToMesh() && _subShape.ShapeType() == TopAbs_SOLID )
return true; // true for the PseudoShape
return IsApplicableHypotesis( theHypothesis, _subShape.ShapeType() );
return IsApplicableHypothesis( theHypothesis, _subShape.ShapeType() );
}
//=======================================================================
//function : IsApplicableHypotesis
//function : IsApplicableHypothesis
//purpose : compare shape type and hypothesis type
//=======================================================================
bool SMESH_subMesh::IsApplicableHypotesis(const SMESH_Hypothesis* theHypothesis,
const TopAbs_ShapeEnum theShapeType)
bool SMESH_subMesh::IsApplicableHypothesis(const SMESH_Hypothesis* theHypothesis,
const TopAbs_ShapeEnum theShapeType)
{
if ( theHypothesis->GetType() > SMESHDS_Hypothesis::PARAM_ALGO)
{
@ -622,7 +622,7 @@ SMESH_Hypothesis::Hypothesis_Status
bool modifiedHyp = (event == MODIF_HYP); // if set to true, force event MODIF_ALGO_STATE
SMESH_Algo* algoRequiringCleaning = 0;
bool isApplicableHyp = IsApplicableHypotesis( anHyp );
bool isApplicableHyp = IsApplicableHypothesis( anHyp );
if (event == ADD_ALGO || event == ADD_FATHER_ALGO)
{
@ -1072,7 +1072,7 @@ bool SMESH_subMesh::IsConform(const SMESH_Algo* theAlgo)
if ( !theAlgo ) return false;
// Suppose that theAlgo is applicable to _subShape, do not check it here
//if ( !IsApplicableHypotesis( theAlgo )) return false;
//if ( !IsApplicableHypothesis( theAlgo )) return false;
// check only algo that doesn't NeedDiscreteBoundary(): because mesh made
// on a sub-shape will be ignored by theAlgo
@ -2207,13 +2207,13 @@ const SMESH_Hypothesis* SMESH_subMesh::getSimilarAttached(const TopoDS_Shape&
}
//=======================================================================
//function : CheckConcurentHypothesis
//function : CheckConcurrentHypothesis
//purpose : check if there are several applicable hypothesis attached to
// ancestors
//=======================================================================
SMESH_Hypothesis::Hypothesis_Status
SMESH_subMesh::CheckConcurentHypothesis (const int theHypType)
SMESH_subMesh::CheckConcurrentHypothesis (const int theHypType)
{
// is there local hypothesis on me?
if ( getSimilarAttached( _subShape, 0, theHypType ) )
@ -2235,7 +2235,7 @@ SMESH_Hypothesis::Hypothesis_Status
aPrevHyp = hyp;
}
else if ( aPrevWithHyp.ShapeType() == ancestor.ShapeType() && aPrevHyp != hyp )
return SMESH_Hypothesis::HYP_CONCURENT;
return SMESH_Hypothesis::HYP_CONCURRENT;
else
return SMESH_Hypothesis::HYP_OK;
}

View File

@ -238,14 +238,14 @@ public:
// return true if theHypothesis can be attached to me:
// its dimension is checked
static bool IsApplicableHypotesis(const SMESH_Hypothesis* theHypothesis,
static bool IsApplicableHypothesis(const SMESH_Hypothesis* theHypothesis,
const TopAbs_ShapeEnum theShapeType);
bool IsApplicableHypotesis(const SMESH_Hypothesis* theHypothesis) const;
bool IsApplicableHypothesis(const SMESH_Hypothesis* theHypothesis) const;
// return true if theHypothesis can be used to mesh me:
// its shape type is checked
SMESH_Hypothesis::Hypothesis_Status CheckConcurentHypothesis (const int theHypType);
SMESH_Hypothesis::Hypothesis_Status CheckConcurrentHypothesis (const int theHypType);
// check if there are several applicable hypothesis on fathers
/*!

View File

@ -1994,7 +1994,7 @@ void SMESHGUI_PrecomputeOp::onPreview()
{
computeFailed = false;
myPreviewDisplayer->SetData( previewRes );
// append shape indeces with computed mesh entities
// append shape indices with computed mesh entities
for ( int i = 0, n = aShapesId->length(); i < n; i++ )
myMapShapeId[ aShapesId[ i ] ] = 0;
}

View File

@ -622,7 +622,7 @@ void SMESHGUI_CreatePatternDlg::onSelectionDone()
//=======================================================================
// function : onDeactivate()
// purpose : SLOT called when dialog must be deativated
// purpose : SLOT called when dialog must be deactivated
//=======================================================================
void SMESHGUI_CreatePatternDlg::onDeactivate()
{

View File

@ -315,7 +315,7 @@ void SMESHGUI_DeleteGroupDlg::onSelectionDone()
//=================================================================================
// function : onDeactivate()
// purpose : SLOT called when dialog must be deativated
// purpose : SLOT called when dialog must be deactivated
//=================================================================================
void SMESHGUI_DeleteGroupDlg::onDeactivate()
{

View File

@ -688,7 +688,7 @@ bool SMESHGUI_DuplicateNodesDlg::isValid()
}
/*!
\brief SLOT called when dialog shoud be deativated.
\brief SLOT called when dialog should be deactivated.
*/
void SMESHGUI_DuplicateNodesDlg::onDeactivate()
{

View File

@ -3073,7 +3073,7 @@ void SMESHGUI_FilterDlg::onHelp()
//=======================================================================
// name : SMESHGUI_FilterDlg::onDeactivate
// Purpose : SLOT called when dialog must be deativated
// Purpose : SLOT called when dialog must be deactivated
//=======================================================================
void SMESHGUI_FilterDlg::onDeactivate()
{

View File

@ -517,7 +517,7 @@ void SMESHGUI_FilterLibraryDlg::onHelp()
//=======================================================================
// name : SMESHGUI_FilterLibraryDlg::onDeactivate
// Purpose : SLOT called when dialog must be deativated
// Purpose : SLOT called when dialog must be deactivated
//=======================================================================
void SMESHGUI_FilterLibraryDlg::onDeactivate()
{
@ -602,7 +602,7 @@ QStringList SMESHGUI_FilterLibraryDlg::prepareFilters() const
//================================================================
// Function : onBrowse
// Purpose : SLOT. Display "Open file" dialog for chosing library name
// Purpose : SLOT. Display "Open file" dialog for choosing library name
//================================================================
void SMESHGUI_FilterLibraryDlg::onBrowse()
{

View File

@ -1197,7 +1197,7 @@ bool SMESHGUI_GroupDlg::onApply()
anActor->SetSufaceColor( aColor.R, aColor.G, aColor.B, delta ); break;
break;
}
// update a visible group accoding to a changed contents
// update a visible group according to a changed contents
if ( !isConversion && anActor->GetVisibility() )
{
SMESH::Update( anIO, true );
@ -2310,7 +2310,7 @@ void SMESHGUI_GroupDlg::onHelp()
//=================================================================================
// function : SMESHGUI_GroupDlg::onDeactivate
// purpose : SLOT called when dialog must be deativated
// purpose : SLOT called when dialog must be deactivated
//=================================================================================
void SMESHGUI_GroupDlg::onDeactivate()
{

View File

@ -134,7 +134,7 @@ SMESHGUI_GroupOnShapeDlg::~SMESHGUI_GroupOnShapeDlg()
//================================================================================
/*!
* \brief slot to enable/diable [Apply]
* \brief slot to enable/disable [Apply]
*/
//================================================================================
@ -505,6 +505,6 @@ void SMESHGUI_GroupOnShapeOp::selectionDone()
myNodeGeoIDs = goodIds;
}
// enable/diable Apply, which can change at selection
// enable/disable Apply, which can change at selection
myDlg->updateButtons();
}

View File

@ -482,7 +482,7 @@ void SMESHGUI_GroupOpDlg::setVisible( bool visible )
}
/*!
\brief SLOT called when dialog must be deativated
\brief SLOT called when dialog must be deactivated
*/
void SMESHGUI_GroupOpDlg::onDeactivate()
{

View File

@ -692,7 +692,7 @@ void SMESHGUI_MeshDlg::reset()
//================================================================================
/*!
* \brief Sets curent tab
* \brief Sets current tab
*/
//================================================================================
void SMESHGUI_MeshDlg::setCurrentTab( const int theId )

View File

@ -122,7 +122,7 @@ static void addMeshItem( QListWidget* theList,
// =========================================================================================
/*!
* \brief Clear submesh names and indeces
* \brief Clear submesh names and indices
*/
// =========================================================================================
@ -134,7 +134,7 @@ void SMESHGUI_MeshOrderBox::Clear()
// =========================================================================================
/*!
* \brief Set submesh names and indeces
* \brief Set submesh names and indices
*/
// =========================================================================================
@ -159,7 +159,7 @@ void SMESHGUI_MeshOrderBox::SetMeshes(const ListListName& theMeshNames,
// =========================================================================================
/*!
* \brief cehck that item exists and not a separator
* \brief check that item exists and not a separator
*/
// =========================================================================================
@ -191,7 +191,7 @@ ListListId SMESHGUI_MeshOrderBox::GetMeshIds() const
// =========================================================================================
/*!
* \brief Returns result (ordered by user) mesh indeces
* \brief Returns result (ordered by user) mesh indices
*/
// =========================================================================================

View File

@ -57,7 +57,7 @@ class SMESHGUI_EXPORT SMESHGUI_MeshOrderBox : public QGroupBox
//! Clear mesh box
void Clear();
//! Set mesh (submesh) names and indeces
//! Set mesh (submesh) names and indices
void SetMeshes(const ListListName& theMeshNames,
const ListListId& theMeshIds);
@ -66,7 +66,7 @@ class SMESHGUI_EXPORT SMESHGUI_MeshOrderBox : public QGroupBox
//! Returns result (ordered by user) mesh names
ListListId GetMeshIds() const;
//! Returns result (ordered by user) mesh indeces
//! Returns result (ordered by user) mesh indices
ListListName GetMeshNames() const;
private slots:

View File

@ -120,7 +120,7 @@ void SMESHGUI_MeshOrderOp::initDialog()
if ( !myMgr->GetMeshOrder() ) {
SUIT_MessageBox::information(desktop(),
tr("SMESH_INFORMATION"),
tr("SMESH_NO_CONCURENT_MESH"));
tr("SMESH_NO_CONCURRENT_MESH"));
onCancel();
return;
@ -199,7 +199,7 @@ void SMESHGUI_MeshOrderMgr::SetMesh(SMESH::SMESH_Mesh_var& theMesh)
//================================================================================
/*!
* \brief Check for concurents between submesh objects
* \brief Check for concurrents between submesh objects
*/
//================================================================================
@ -211,7 +211,7 @@ bool SMESHGUI_MeshOrderMgr::GetMeshOrder()
//================================================================================
/*!
* \brief Check for concurents between submesh objects
* \brief Check for concurrents between submesh objects
*/
//================================================================================
@ -300,8 +300,8 @@ bool SMESHGUI_MeshOrderMgr::SetMeshOrder( const ListListId& theListListIds )
}
}
// is it enought to set modifid attribute on root mesh objects only?
// it is seems that modifaction flag will be set on child submeshes
// is it enough to set modified attribute on root mesh objects only?
// it is seems that modifcation flag will be set on child submeshes
// automatically (see SMESH::ModifiedMesh for details)
SMESH::ModifiedMesh( aMeshSObj, false, false );

View File

@ -45,9 +45,9 @@ public:
virtual ~SMESHGUI_MeshOrderMgr();
//! Set root mesh object
void SetMesh( SMESH::SMESH_Mesh_var& theMesh );
//! Check for concurents between submesh objects
//! Check for concurrents between submesh objects
bool GetMeshOrder();
//! Check for concurents between submesh objects
//! Check for concurrents between submesh objects
bool GetMeshOrder( ListListId& theIds );
//! Store submesh priority order
bool SetMeshOrder();

View File

@ -723,7 +723,7 @@ void SMESHGUI_MeshPatternDlg::resetSelInput()
//=======================================================================
// name : SMESHGUI_MeshPatternDlg::onDeactivate
// Purpose : SLOT called when dialog must be deativated
// Purpose : SLOT called when dialog must be deactivated
//=======================================================================
void SMESHGUI_MeshPatternDlg::onDeactivate()
{

View File

@ -600,7 +600,7 @@ void SMESHGUI_MultiEditDlg::onSelectionDone()
//=======================================================================
// name : SMESHGUI_MultiEditDlg::onDeactivate
// Purpose : SLOT called when dialog must be deativated
// Purpose : SLOT called when dialog must be deactivated
//=======================================================================
void SMESHGUI_MultiEditDlg::onDeactivate()
{
@ -1628,7 +1628,7 @@ SMESHGUI_SplitVolumesDlg::SMESHGUI_SplitVolumesDlg(SMESHGUI* theModule)
gb->setTitle( tr("TARGET_ELEM_TYPE"));
}
myToAllChk->setChecked( true ); //aplly to the whole mesh by default
myToAllChk->setChecked( true ); //apply to the whole mesh by default
bool hasHexa = true;//myMesh->_is_nil() ? false : myMesh->NbHexas();
if ( hasHexa )

View File

@ -538,7 +538,7 @@ void SMESHGUI_OffsetDlg::onTextChange (const QString& theNewText)
buttonOk->setEnabled(false);
buttonApply->setEnabled(false);
// hilight entered elements
// highlight entered elements
SMDS_Mesh* aMesh = 0;
if (myActor)
aMesh = myActor->GetObject()->GetMesh();

View File

@ -20,7 +20,7 @@
// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
//
// SMESH SMDS : implementaion of Salome mesh data structure
// SMESH SMDS : implementation of Salome mesh data structure
// File : SMESHGUI_Operation.h
// Author : Sergey LITONIN, Open CASCADE S.A.S.
//

View File

@ -247,15 +247,13 @@ void SMESHGUI_RemoveElementsDlg::ClickOnApply()
} catch (const SALOME::SALOME_Exception& S_ex) {
SalomeApp_Tools::QtCatchCorbaException(S_ex);
myEditCurrentArgument->clear();
} catch (...){
myEditCurrentArgument->clear();
} catch (...) {
}
myEditCurrentArgument->clear();
if (aResult) {
myEditCurrentArgument->clear();
mySelector->ClearIndex();
SMESH::UpdateView();
SMESH::UpdateView( /*withChildrenOfSelected=*/true );
SMESHGUI::Modified();
}
}

View File

@ -439,7 +439,7 @@ void SMESHGUI_SingleEditDlg::onSelectionDone()
//=======================================================================
// name : onDeactivate()
// Purpose : SLOT called when dialog must be deativated
// Purpose : SLOT called when dialog must be deactivated
//=======================================================================
void SMESHGUI_SingleEditDlg::onDeactivate()
{

View File

@ -191,7 +191,7 @@ void SMESHGUI_TransparencyDlg::ClickOnHelp()
//=================================================================================
// function : SetTransparency()
// purpose : Called when value of slider change
// : or the first time as initilisation
// : or the first time as initialisation
//=================================================================================
void SMESHGUI_TransparencyDlg::SetTransparency()
{

View File

@ -794,12 +794,13 @@ namespace SMESH
return false;
}
void UpdateView(){
void UpdateView( bool withChildrenOfSelected )
{
if ( SVTK_ViewWindow* aWnd = SMESH::GetCurrentVtkView()) {
LightApp_SelectionMgr* mgr = SMESHGUI::selectionMgr();
SALOME_ListIO selected; mgr->selectedObjects( selected );
if( selected.Extent() == 0){
if ( selected.Extent() == 0 ) {
vtkRenderer* aRenderer = aWnd->getRenderer();
VTK::ActorCollectionCopy aCopy(aRenderer->GetActors());
vtkActorCollection *aCollection = aCopy.GetActors();
@ -811,12 +812,36 @@ namespace SMESH
break; // avoid multiple warinings if visu failed
}
}
}else{
}
else
{
SALOME_ListIteratorOfListIO anIter( selected );
for( ; anIter.More(); anIter.Next()){
for( ; anIter.More(); anIter.Next())
{
Handle(SALOME_InteractiveObject) anIO = anIter.Value();
if ( !Update(anIO,true) )
if ( !Update( anIO, true ))
break; // avoid multiple warinings if visu failed
if ( withChildrenOfSelected ) // update all visible children
{
QString aFatherID = anIO->getEntry();
vtkRenderer* aRenderer = aWnd->getRenderer();
VTK::ActorCollectionCopy aCopy(aRenderer->GetActors());
vtkActorCollection *aCollection = aCopy.GetActors();
aCollection->InitTraversal();
while ( vtkActor *anAct = aCollection->GetNextActor() ) {
if ( SMESH_Actor *anActor = dynamic_cast<SMESH_Actor*>( anAct )) {
if ( anActor->hasIO() && anActor->GetVisibility() )
{
QString aChildID = anActor->getIO()->getEntry();
if ( aChildID.size() > aFatherID.size() &&
aChildID.startsWith( aFatherID ))
if ( ! Update( anActor->getIO(), true ))
break;
}
}
}
}
}
}
RepaintCurrentView();

View File

@ -120,7 +120,7 @@ SMESHGUI_EXPORT
bool UpdateView( EDisplaing, const char* = "" );
SMESHGUI_EXPORT
void UpdateView();
void UpdateView( bool withChildrenOfSelected = false );
SMESHGUI_EXPORT
bool UpdateNulData( const Handle(SALOME_InteractiveObject)& theIO, bool theDisplay);

View File

@ -85,7 +85,7 @@ bool SMESHGUI_XmlHandler::startElement (const QString&, const QString&,
myPluginName = atts.value("name");
myServerLib = atts.value("server-lib");
myClientLib = atts.value("gui-lib");
/* It's Need to tranlate lib name for WIN32 or X platform
/* It's Need to translate lib name for WIN32 or X platform
* (only client lib, because server lib translates in SMESH_Gen_i::createHypothesis
* for normal work of *.py files )
*/

View File

@ -7107,7 +7107,7 @@ It is impossible to read point coordinates from file</translation>
<name>SMESHGUI_MeshOrderOp</name>
<message>
<source>SMESH_NO_CONCURENT_MESH</source>
<translation>No concurent sub-meshes detected</translation>
<translation>No concurrent sub-meshes detected</translation>
</message>
</context>
<context>

View File

@ -268,14 +268,14 @@ int SMESH_Tree<BND_BOX,NB_CHILDREN>::getHeight(const bool full) const
if ( isLeaf() )
return 1;
int heigth = 0;
int height = 0;
for (int i = 0; i<NB_CHILDREN; i++)
{
int h = myChildren[i]->getHeight( false );
if ( h > heigth )
heigth = h;
if ( h > height )
height = h;
}
return heigth + 1;
return height + 1;
}
#endif

View File

@ -5056,7 +5056,7 @@ bool _pyStringFamily::Add( const char* str )
_strings.erase( itLess, ++itMore );
}
else // to few string to make a family fot them
else // too few string to make a family for them
{
_strings.insert( itStr, str );
}

View File

@ -564,7 +564,7 @@ SMESH::Hypothesis_Status SMESH_Mesh_i::ConvertHypothesisStatus
switch (theStatus) {
RETURNCASE( HYP_OK );
RETURNCASE( HYP_MISSING );
RETURNCASE( HYP_CONCURENT );
RETURNCASE( HYP_CONCURRENT );
RETURNCASE( HYP_BAD_PARAMETER );
RETURNCASE( HYP_HIDDEN_ALGO );
RETURNCASE( HYP_HIDING_ALGO );

View File

@ -87,8 +87,8 @@ ret = mesh.Compute()
print ret
if ret != 0:
log = mesh.GetLog(0) # no erase trace
for linelog in log:
print linelog
# for linelog in log:
# print linelog
print "Information about the MeshcompShel:"
print "Number of nodes : ", mesh.NbNodes()
print "Number of edges : ", mesh.NbEdges()

View File

@ -231,7 +231,7 @@ def TreatHypoStatus(status, hypName, geomName, isAlgo, mesh):
reason = hypType + " of the same dimension is already assigned to this shape"
elif status == HYP_BAD_DIM :
reason = hypType + " mismatches the shape"
elif status == HYP_CONCURENT :
elif status == HYP_CONCURRENT :
reason = "there are concurrent hypotheses on sub-shapes"
elif status == HYP_BAD_SUBSHAPE :
reason = "the shape is neither the main one, nor its sub-shape, nor a valid group"

View File

@ -207,7 +207,7 @@ public:
double constValue = 0) const;
/*!
* \brief Return nodes in the order they encounter while walking along
* the while side or a specified EDGE. For a closed side, the 1st point repeats at end.
* the whole side or a specified EDGE. For a closed side, the 1st point repeats at end.
* \param iE - index of the EDGE. Default is "all EDGEs".
*/
std::vector<const SMDS_MeshNode*> GetOrderedNodes( int iE = ALL_EDGES ) const;

View File

@ -65,10 +65,11 @@
#include "Utils_ExceptHandlers.hxx"
#include <boost/container/flat_set.hpp>
#include <boost/intrusive/circular_list_algorithms.hpp>
typedef NCollection_Array2<const SMDS_MeshNode*> StdMeshers_Array2OfNode;
typedef gp_XY gp_UV;
typedef gp_XY gp_UV;
typedef SMESH_Comment TComm;
using namespace std;
@ -1020,30 +1021,454 @@ bool StdMeshers_Quadrangle_2D::IsApplicable( const TopoDS_Shape & aShape, bool t
return ( toCheckAll && nbFoundFaces != 0 );
}
namespace
{
//================================================================================
/*!
* \brief Return true if only two given edges meat at their common vertex
*/
//================================================================================
bool twoEdgesMeatAtVertex(const TopoDS_Edge& e1,
const TopoDS_Edge& e2,
SMESH_Mesh & mesh)
{
TopoDS_Vertex v;
if (!TopExp::CommonVertex(e1, e2, v))
return false;
TopTools_ListIteratorOfListOfShape ancestIt(mesh.GetAncestors(v));
for (; ancestIt.More() ; ancestIt.Next())
if (ancestIt.Value().ShapeType() == TopAbs_EDGE)
if (!e1.IsSame(ancestIt.Value()) && !e2.IsSame(ancestIt.Value()))
return false;
return true;
}
//--------------------------------------------------------------------------------
/*!
* \brief EDGE of a FACE
*/
struct Edge
{
TopoDS_Edge myEdge;
TopoDS_Vertex my1stVertex;
int myIndex;
double myAngle; // angle at my1stVertex
int myNbSegments; // discretization
Edge* myPrev; // preceding EDGE
Edge* myNext; // next EDGE
// traits used by boost::intrusive::circular_list_algorithms
typedef Edge node;
typedef Edge * node_ptr;
typedef const Edge * const_node_ptr;
static node_ptr get_next(const_node_ptr n) { return n->myNext; }
static void set_next(node_ptr n, node_ptr next) { n->myNext = next; }
static node_ptr get_previous(const_node_ptr n) { return n->myPrev; }
static void set_previous(node_ptr n, node_ptr prev){ n->myPrev = prev; }
};
//--------------------------------------------------------------------------------
/*!
* \brief Four sides of a quadrangle evaluating its quality
*/
struct QuadQuality
{
typedef std::set< QuadQuality, QuadQuality > set;
Edge* myCornerE[4];
int myNbSeg [4];
// quality criteria to minimize
int myOppDiff;
double myQuartDiff;
double mySumAngle;
// Compute quality criateria and add self to the set of variants
//
void AddSelf( QuadQuality::set& theVariants )
{
if ( myCornerE[2] == myCornerE[1] || // exclude invalid variants
myCornerE[2] == myCornerE[3] ||
myCornerE[0] == myCornerE[3] )
return;
// count nb segments between corners
mySumAngle = 0;
double totNbSeg = 0;
for ( int i1 = 3, i2 = 0; i2 < 4; i1 = i2++ )
{
myNbSeg[ i1 ] = 0;
for ( Edge* e = myCornerE[ i1 ]; e != myCornerE[ i2 ]; e = e->myNext )
myNbSeg[ i1 ] += e->myNbSegments;
mySumAngle -= myCornerE[ i1 ]->myAngle / M_PI; // [-1,1]
totNbSeg += myNbSeg[ i1 ];
}
myOppDiff = ( Abs( myNbSeg[0] - myNbSeg[2] ) +
Abs( myNbSeg[1] - myNbSeg[3] ));
double nbSideIdeal = totNbSeg / 4.;
myQuartDiff = -( Min( Min( myNbSeg[0], myNbSeg[1] ),
Min( myNbSeg[2], myNbSeg[3] )) / nbSideIdeal );
theVariants.insert( *this );
#ifndef _DEBUG_
if ( theVariants.size() > 1 ) // erase a worse variant
theVariants.erase( ++theVariants.begin() );
#endif
};
// first criterion - equality of nbSeg of opposite sides
int crit1() const { return myOppDiff; }
// second criterion - equality of nbSeg of adjacent sides and sharpness of angles
double crit2() const { return myQuartDiff + mySumAngle; }
bool operator () ( const QuadQuality& q1, const QuadQuality& q2) const
{
if ( q1.crit1() < q2.crit1() )
return true;
if ( q1.crit1() > q2.crit1() )
return false;
return q1.crit2() < q2.crit2();
}
};
//================================================================================
/*!
* \brief Unite EDGEs to get a required number of sides
* \param [in] theNbCorners - the required number of sides
* \param [in] theConsiderMesh - to considered only meshed VERTEXes
* \param [in] theFaceSide - the FACE EDGEs
* \param [out] theVertices - the found corner vertices
*/
//================================================================================
void uniteEdges( const int theNbCorners,
const bool theConsiderMesh,
const StdMeshers_FaceSide& theFaceSide,
const TopoDS_Shape& theBaseVertex,
std::vector<TopoDS_Vertex>& theVertices,
bool& theHaveConcaveVertices)
{
// form a circular list of EDGEs
std::vector< Edge > edges( theFaceSide.NbEdges() );
boost::intrusive::circular_list_algorithms< Edge > circularList;
circularList.init_header( &edges[0] );
edges[0].myEdge = theFaceSide.Edge( 0 );
edges[0].myIndex = 0;
edges[0].myNbSegments = 0;
for ( int i = 1; i < theFaceSide.NbEdges(); ++i )
{
edges[ i ].myEdge = theFaceSide.Edge( i );
edges[ i ].myIndex = i;
edges[ i ].myNbSegments = 0;
circularList.link_after( &edges[ i-1 ], &edges[ i ] );
}
// remove degenerated edges
int nbEdges = edges.size();
Edge* edge0 = &edges[0];
for ( size_t i = 0; i < edges.size(); ++i )
if ( SMESH_Algo::isDegenerated( edges[i].myEdge ))
{
edge0 = circularList.unlink( &edges[i] );
--nbEdges;
}
// sort edges by angle
std::multimap< double, Edge* > edgeByAngle;
int i, iBase = -1, nbConvexAngles = 0, nbSharpAngles = 0;
const double angTol = 5. / 180 * M_PI;
const double sharpAngle = 0.5 * M_PI - angTol;
Edge* e = edge0;
for ( i = 0; i < nbEdges; ++i, e = e->myNext )
{
e->my1stVertex = SMESH_MesherHelper::IthVertex( 0, e->myEdge );
if ( e->my1stVertex.IsSame( theBaseVertex ))
iBase = e->myIndex;
e->myAngle = -2 * M_PI;
if ( !theConsiderMesh || theFaceSide.VertexNode( e->myIndex ))
{
e->myAngle = SMESH_MesherHelper::GetAngle( e->myPrev->myEdge, e->myEdge,
theFaceSide.Face(), e->my1stVertex );
if ( e->myAngle > 2 * M_PI ) // GetAngle() failed
e->myAngle *= -1.;
}
edgeByAngle.insert( std::make_pair( e->myAngle, e ));
nbConvexAngles += ( e->myAngle > angTol );
nbSharpAngles += ( e->myAngle > sharpAngle );
}
theHaveConcaveVertices = ( nbConvexAngles < nbEdges );
if ((int) theVertices.size() == theNbCorners )
return;
theVertices.clear();
if ( !theConsiderMesh || theNbCorners < 4 ||
nbConvexAngles <= theNbCorners ||
nbSharpAngles == theNbCorners )
{
if ( nbEdges == theNbCorners ) // return all vertices
{
for ( e = edge0; (int) theVertices.size() < theNbCorners; e = e->myNext )
theVertices.push_back( e->my1stVertex );
return;
}
// return corners with maximal angles
std::set< int > cornerIndices;
if ( iBase != -1 )
cornerIndices.insert( iBase );
std::multimap< double, Edge* >::reverse_iterator a2e = edgeByAngle.rbegin();
for (; (int) cornerIndices.size() < theNbCorners; ++a2e )
cornerIndices.insert( a2e->second->myIndex );
std::set< int >::iterator i = cornerIndices.begin();
for ( ; i != cornerIndices.end(); ++i )
theVertices.push_back( edges[ *i ].my1stVertex );
return;
}
// get nb of segments
int totNbSeg = 0; // tatal nb segments
std::vector<const SMDS_MeshNode*> nodes;
for ( i = 0, e = edge0; i < nbEdges; ++i, e = e->myNext )
{
nodes.clear();
theFaceSide.GetEdgeNodes( e->myIndex, nodes, /*addVertex=*/true, true );
if ( nodes.size() == 2 && nodes[0] == nodes[1] ) // all nodes merged
{
e->myAngle = -1; // to remove
}
else
{
e->myNbSegments += nodes.size() - 1;
totNbSeg += nodes.size() - 1;
}
// join with the previous edge those edges with concave angles
if ( e->myAngle <= 0 )
{
e->myPrev->myNbSegments += e->myNbSegments;
e = circularList.unlink( e )->myPrev;
--nbEdges;
--i;
}
}
if ( edge0->myNext->myPrev != edge0 ) // edge0 removed, find another edge0
for ( size_t i = 0; i < edges.size(); ++i )
if ( edges[i].myNext->myPrev == & edges[i] )
{
edge0 = &edges[i];
break;
}
// sort different variants by quality
QuadQuality::set quadVariants;
// find index of a corner most opposite to corner of edge0
int iOpposite0, nbHalf = 0;
for ( e = edge0; nbHalf <= totNbSeg / 2; e = e->myNext )
nbHalf += e->myNbSegments;
iOpposite0 = e->myIndex;
// compose different variants of quadrangles
QuadQuality quad;
for ( ; edge0->myIndex != iOpposite0; edge0 = edge0->myNext )
{
quad.myCornerE[ 0 ] = edge0;
// find opposite corner 2
for ( nbHalf = 0, e = edge0; nbHalf < totNbSeg / 2; e = e->myNext )
nbHalf += e->myNbSegments;
if ( e == edge0->myNext ) // no space for corner 1
e = e->myNext;
quad.myCornerE[ 2 ] = e;
bool moreVariants2 = ( totNbSeg % 2 || nbHalf != totNbSeg / 2 );
// enumerate different variants of corners 1 and 3
for ( Edge* e1 = edge0->myNext; e1 != quad.myCornerE[ 2 ]; e1 = e1->myNext )
{
quad.myCornerE[ 1 ] = e1;
// find opposite corner 3
for ( nbHalf = 0, e = e1; nbHalf < totNbSeg / 2; e = e->myNext )
nbHalf += e->myNbSegments;
if ( e == quad.myCornerE[ 2 ] )
e = e->myNext;
quad.myCornerE[ 3 ] = e;
bool moreVariants3 = ( totNbSeg % 2 || nbHalf != totNbSeg / 2 );
quad.AddSelf( quadVariants );
// another variants
if ( moreVariants2 )
{
quad.myCornerE[ 2 ] = quad.myCornerE[ 2 ]->myPrev;
quad.AddSelf( quadVariants );
quad.myCornerE[ 2 ] = quad.myCornerE[ 2 ]->myNext;
}
if ( moreVariants3 )
{
quad.myCornerE[ 3 ] = quad.myCornerE[ 3 ]->myPrev;
quad.AddSelf( quadVariants );
if ( moreVariants2 )
{
quad.myCornerE[ 2 ] = quad.myCornerE[ 2 ]->myPrev;
quad.AddSelf( quadVariants );
quad.myCornerE[ 2 ] = quad.myCornerE[ 2 ]->myNext;
}
}
}
}
const QuadQuality& bestQuad = *quadVariants.begin();
theVertices.resize( 4 );
theVertices[ 0 ] = bestQuad.myCornerE[ 0 ]->my1stVertex;
theVertices[ 1 ] = bestQuad.myCornerE[ 1 ]->my1stVertex;
theVertices[ 2 ] = bestQuad.myCornerE[ 2 ]->my1stVertex;
theVertices[ 3 ] = bestQuad.myCornerE[ 3 ]->my1stVertex;
return;
}
} // namespace
//================================================================================
/*!
* \brief Return true if only two given edges meat at their common vertex
* \brief Finds vertices at the most sharp face corners
* \param [in] theFace - the FACE
* \param [in,out] theWire - the ordered edges of the face. It can be modified to
* have the first VERTEX of the first EDGE in \a vertices
* \param [out] theVertices - the found corner vertices in the order corresponding to
* the order of EDGEs in \a theWire
* \param [out] theNbDegenEdges - nb of degenerated EDGEs in theFace
* \param [in] theConsiderMesh - if \c true, only meshed VERTEXes are considered
* as possible corners
* \return int - number of quad sides found: 0, 3 or 4
*/
//================================================================================
static bool twoEdgesMeatAtVertex(const TopoDS_Edge& e1,
const TopoDS_Edge& e2,
SMESH_Mesh & mesh)
int StdMeshers_Quadrangle_2D::getCorners(const TopoDS_Face& theFace,
SMESH_Mesh & theMesh,
std::list<TopoDS_Edge>& theWire,
std::vector<TopoDS_Vertex>& theVertices,
int & theNbDegenEdges,
const bool theConsiderMesh)
{
TopoDS_Vertex v;
if (!TopExp::CommonVertex(e1, e2, v))
return false;
TopTools_ListIteratorOfListOfShape ancestIt(mesh.GetAncestors(v));
for (; ancestIt.More() ; ancestIt.Next())
if (ancestIt.Value().ShapeType() == TopAbs_EDGE)
if (!e1.IsSame(ancestIt.Value()) && !e2.IsSame(ancestIt.Value()))
return false;
return true;
theNbDegenEdges = 0;
SMESH_MesherHelper helper( theMesh );
if ( myHelper )
helper.CopySubShapeInfo( *myHelper );
StdMeshers_FaceSide faceSide( theFace, theWire, &theMesh,
/*isFwd=*/true, /*skipMedium=*/true, &helper );
// count degenerated EDGEs and possible corner VERTEXes
for ( int iE = 0; iE < faceSide.NbEdges(); ++iE )
{
if ( SMESH_Algo::isDegenerated( faceSide.Edge( iE )))
++theNbDegenEdges;
else if ( !theConsiderMesh || faceSide.VertexNode( iE ))
theVertices.push_back( faceSide.FirstVertex( iE ));
}
// find out required nb of corners (3 or 4)
int nbCorners = 4;
TopoDS_Shape triaVertex = helper.GetMeshDS()->IndexToShape( myTriaVertexID );
if ( !triaVertex.IsNull() &&
triaVertex.ShapeType() == TopAbs_VERTEX &&
helper.IsSubShape( triaVertex, theFace ) &&
theVertices.size() != 4 )
nbCorners = 3;
else
triaVertex.Nullify();
// check nb of available EDGEs
if ( faceSide.NbEdges() < nbCorners )
return error(COMPERR_BAD_SHAPE,
TComm("Face must have 4 sides but not ") << faceSide.NbEdges() );
if ( theConsiderMesh )
{
const int nbSegments = Max( faceSide.NbPoints()-1, faceSide.NbSegments() );
if ( nbSegments < nbCorners )
return error(COMPERR_BAD_INPUT_MESH, TComm("Too few boundary nodes: ") << nbSegments);
}
if ( nbCorners == 3 )
{
if ( theVertices.size() < 3 )
return error(COMPERR_BAD_SHAPE,
TComm("Face must have 3 meshed sides but not ") << theVertices.size() );
}
else // triaVertex not defined or invalid
{
if ( theVertices.size() == 3 && theNbDegenEdges == 0 )
{
if ( myTriaVertexID < 1 )
return error(COMPERR_BAD_PARMETERS,
"No Base vertex provided for a trilateral geometrical face");
TComm comment("Invalid Base vertex: ");
comment << myTriaVertexID << ", which is not in [ ";
comment << helper.GetMeshDS()->ShapeToIndex( faceSide.FirstVertex(0) ) << ", ";
comment << helper.GetMeshDS()->ShapeToIndex( faceSide.FirstVertex(1) ) << ", ";
comment << helper.GetMeshDS()->ShapeToIndex( faceSide.FirstVertex(2) ) << " ]";
return error(COMPERR_BAD_PARMETERS, comment );
}
if ( theVertices.size() + theNbDegenEdges < 4 )
return error(COMPERR_BAD_SHAPE,
TComm("Face must have 4 meshed sides but not ") << theVertices.size() );
}
myCheckOri = false;
if ( theVertices.size() > 3 )
{
uniteEdges( nbCorners, theConsiderMesh, faceSide, triaVertex, theVertices, myCheckOri );
}
if ( nbCorners == 3 && !triaVertex.IsSame( theVertices[0] ))
{
// make theVertices begin from triaVertex
for ( size_t i = 0; i < theVertices.size(); ++i )
if ( triaVertex.IsSame( theVertices[i] ))
{
theVertices.erase( theVertices.begin(), theVertices.begin() + i );
break;
}
else
{
theVertices.push_back( theVertices[i] );
}
}
// make theWire begin from the 1st corner vertex
while ( !theVertices[0].IsSame( helper.IthVertex( 0, theWire.front() )) ||
SMESH_Algo::isDegenerated( theWire.front() ))
theWire.splice( theWire.end(), theWire, theWire.begin() );
return nbCorners;
}
//=============================================================================
/*!
*
*
*/
//=============================================================================
@ -4253,388 +4678,6 @@ bool StdMeshers_Quadrangle_2D::check()
return isOK;
}
//================================================================================
/*!
* \brief Finds vertices at the most sharp face corners
* \param [in] theFace - the FACE
* \param [in,out] theWire - the ordered edges of the face. It can be modified to
* have the first VERTEX of the first EDGE in \a vertices
* \param [out] theVertices - the found corner vertices in the order corresponding to
* the order of EDGEs in \a theWire
* \param [out] theNbDegenEdges - nb of degenerated EDGEs in theFace
* \param [in] theConsiderMesh - if \c true, only meshed VERTEXes are considered
* as possible corners
* \return int - number of quad sides found: 0, 3 or 4
*/
//================================================================================
int StdMeshers_Quadrangle_2D::getCorners(const TopoDS_Face& theFace,
SMESH_Mesh & theMesh,
std::list<TopoDS_Edge>& theWire,
std::vector<TopoDS_Vertex>& theVertices,
int & theNbDegenEdges,
const bool theConsiderMesh)
{
theNbDegenEdges = 0;
SMESH_MesherHelper helper( theMesh );
if ( myHelper )
helper.CopySubShapeInfo( *myHelper );
StdMeshers_FaceSide faceSide( theFace, theWire, &theMesh,
/*isFwd=*/true, /*skipMedium=*/true, &helper );
// sort theVertices by angle
multimap<double, TopoDS_Vertex> vertexByAngle;
TopTools_DataMapOfShapeReal angleByVertex;
TopoDS_Edge prevE = theWire.back();
if ( SMESH_Algo::isDegenerated( prevE ))
{
list<TopoDS_Edge>::reverse_iterator edge = ++theWire.rbegin();
while ( SMESH_Algo::isDegenerated( *edge ) /*|| helper.IsRealSeam( *edge )*/)
++edge;
if ( edge == theWire.rend() )
return false;
prevE = *edge;
}
list<TopoDS_Edge>::iterator edge = theWire.begin();
for ( int iE = 0; edge != theWire.end(); ++edge, ++iE )
{
if ( SMESH_Algo::isDegenerated( *edge ) /*|| helper.IsRealSeam( *edge )*/)
{
++theNbDegenEdges;
continue;
}
if ( !theConsiderMesh || faceSide.VertexNode( iE ))
{
TopoDS_Vertex v = helper.IthVertex( 0, *edge );
double angle = helper.GetAngle( prevE, *edge, theFace, v );
vertexByAngle.insert( make_pair( angle, v ));
angleByVertex.Bind( v, angle );
}
prevE = *edge;
}
// find out required nb of corners (3 or 4)
int nbCorners = 4;
TopoDS_Shape triaVertex = helper.GetMeshDS()->IndexToShape( myTriaVertexID );
if ( !triaVertex.IsNull() &&
triaVertex.ShapeType() == TopAbs_VERTEX &&
helper.IsSubShape( triaVertex, theFace ) &&
( vertexByAngle.size() != 4 || vertexByAngle.begin()->first < 5 * M_PI/180. ))
nbCorners = 3;
else
triaVertex.Nullify();
// check nb of available corners
if ( faceSide.NbEdges() < nbCorners )
return error(COMPERR_BAD_SHAPE,
TComm("Face must have 4 sides but not ") << faceSide.NbEdges() );
if ( theConsiderMesh )
{
const int nbSegments = Max( faceSide.NbPoints()-1, faceSide.NbSegments() );
if ( nbSegments < nbCorners )
return error(COMPERR_BAD_INPUT_MESH, TComm("Too few boundary nodes: ") << nbSegments);
}
if ( nbCorners == 3 )
{
if ( vertexByAngle.size() < 3 )
return error(COMPERR_BAD_SHAPE,
TComm("Face must have 3 sides but not ") << vertexByAngle.size() );
}
else
{
if ( vertexByAngle.size() == 3 && theNbDegenEdges == 0 )
{
if ( myTriaVertexID < 1 )
return error(COMPERR_BAD_PARMETERS,
"No Base vertex provided for a trilateral geometrical face");
TComm comment("Invalid Base vertex: ");
comment << myTriaVertexID << " its ID is not among [ ";
multimap<double, TopoDS_Vertex>::iterator a2v = vertexByAngle.begin();
comment << helper.GetMeshDS()->ShapeToIndex( a2v->second ) << ", "; a2v++;
comment << helper.GetMeshDS()->ShapeToIndex( a2v->second ) << ", "; a2v++;
comment << helper.GetMeshDS()->ShapeToIndex( a2v->second ) << " ]";
return error(COMPERR_BAD_PARMETERS, comment );
}
if ( vertexByAngle.size() + ( theNbDegenEdges > 0 ) < 4 &&
vertexByAngle.size() + theNbDegenEdges != 4 )
return error(COMPERR_BAD_SHAPE,
TComm("Face must have 4 sides but not ") << vertexByAngle.size() );
}
// put all corner vertices in a map
TopTools_MapOfShape vMap;
if ( nbCorners == 3 )
vMap.Add( triaVertex );
multimap<double, TopoDS_Vertex>::reverse_iterator a2v = vertexByAngle.rbegin();
for ( int iC = 0; a2v != vertexByAngle.rend() && iC < nbCorners; ++a2v, ++iC )
vMap.Add( (*a2v).second );
// check if there are possible variations in choosing corners
bool haveVariants = false;
if ((int) vertexByAngle.size() > nbCorners )
{
double lostAngle = a2v->first;
double lastAngle = ( --a2v, a2v->first );
haveVariants = ( lostAngle * 1.1 >= lastAngle );
}
const double angleTol = 5.* M_PI/180;
myCheckOri = ( (int)vertexByAngle.size() > nbCorners ||
vertexByAngle.begin()->first < angleTol );
// make theWire begin from a corner vertex or triaVertex
if ( nbCorners == 3 )
while ( !triaVertex.IsSame( ( helper.IthVertex( 0, theWire.front() ))) ||
SMESH_Algo::isDegenerated( theWire.front() ))
theWire.splice( theWire.end(), theWire, theWire.begin() );
else
while ( !vMap.Contains( helper.IthVertex( 0, theWire.front() )) ||
SMESH_Algo::isDegenerated( theWire.front() ))
theWire.splice( theWire.end(), theWire, theWire.begin() );
// fill the result vector and prepare for its refinement
theVertices.clear();
vector< double > angles;
vector< TopoDS_Edge > edgeVec;
vector< int > cornerInd, nbSeg;
int nbSegTot = 0;
angles .reserve( vertexByAngle.size() );
edgeVec.reserve( vertexByAngle.size() );
nbSeg .reserve( vertexByAngle.size() );
cornerInd.reserve( nbCorners );
for ( edge = theWire.begin(); edge != theWire.end(); ++edge )
{
if ( SMESH_Algo::isDegenerated( *edge ))
continue;
TopoDS_Vertex v = helper.IthVertex( 0, *edge );
bool isCorner = vMap.Contains( v );
if ( isCorner )
{
theVertices.push_back( v );
cornerInd.push_back( angles.size() );
}
angles .push_back( angleByVertex.IsBound( v ) ? angleByVertex( v ) : -M_PI );
edgeVec.push_back( *edge );
if ( theConsiderMesh && haveVariants )
{
if ( SMESHDS_SubMesh* sm = helper.GetMeshDS()->MeshElements( *edge ))
nbSeg.push_back( sm->NbNodes() + 1 );
else
nbSeg.push_back( 0 );
nbSegTot += nbSeg.back();
}
}
// refine the result vector - make sides equal by length if
// there are several equal angles
if ( haveVariants )
{
if ( nbCorners == 3 )
angles[0] = 2 * M_PI; // not to move the base triangle VERTEX
// here we refer to VERTEX'es and EDGEs by indices in angles and edgeVec vectors
typedef int TGeoIndex;
// for each vertex find a vertex till which there are nbSegHalf segments
const int nbSegHalf = ( nbSegTot % 2 || nbCorners == 3 ) ? 0 : nbSegTot / 2;
vector< TGeoIndex > halfDivider( angles.size(), -1 );
int nbHalfDividers = 0;
if ( nbSegHalf )
{
// get min angle of corners
double minAngle = 10.;
for ( size_t iC = 0; iC < cornerInd.size(); ++iC )
minAngle = Min( minAngle, angles[ cornerInd[ iC ]]);
// find halfDivider's
for ( TGeoIndex iV1 = 0; iV1 < TGeoIndex( angles.size() ); ++iV1 )
{
int nbSegs = 0;
TGeoIndex iV2 = iV1;
do {
nbSegs += nbSeg[ iV2 ];
iV2 = helper.WrapIndex( iV2 + 1, nbSeg.size() );
} while ( nbSegs < nbSegHalf );
if ( nbSegs == nbSegHalf &&
angles[ iV1 ] + angleTol >= minAngle &&
angles[ iV2 ] + angleTol >= minAngle )
{
halfDivider[ iV1 ] = iV2;
++nbHalfDividers;
}
}
}
set< TGeoIndex > refinedCorners, treatedCorners;
for ( size_t iC = 0; iC < cornerInd.size(); ++iC )
{
TGeoIndex iV = cornerInd[iC];
if ( !treatedCorners.insert( iV ).second )
continue;
list< TGeoIndex > equVerts; // inds of vertices that can become corners
equVerts.push_back( iV );
int nbC[2] = { 0, 0 };
// find equal angles backward and forward from the iV-th corner vertex
for ( int isFwd = 0; isFwd < 2; ++isFwd )
{
int dV = isFwd ? +1 : -1;
int iCNext = helper.WrapIndex( iC + dV, cornerInd.size() );
TGeoIndex iVNext = helper.WrapIndex( iV + dV, angles.size() );
while ( iVNext != iV )
{
bool equal = Abs( angles[iV] - angles[iVNext] ) < angleTol;
if ( equal )
equVerts.insert( isFwd ? equVerts.end() : equVerts.begin(), iVNext );
if ( iVNext == cornerInd[ iCNext ])
{
if ( !equal )
{
if ( angles[iV] < angles[iVNext] )
refinedCorners.insert( iVNext );
break;
}
nbC[ isFwd ]++;
treatedCorners.insert( cornerInd[ iCNext ] );
iCNext = helper.WrapIndex( iCNext + dV, cornerInd.size() );
}
iVNext = helper.WrapIndex( iVNext + dV, angles.size() );
}
if ( iVNext == iV )
break; // all angles equal
}
const bool allCornersSame = ( nbC[0] == 3 );
if ( allCornersSame && nbHalfDividers > 0 )
{
// select two halfDivider's as corners
TGeoIndex hd1, hd2 = -1;
size_t iC2;
for ( iC2 = 0; iC2 < cornerInd.size() && hd2 < 0; ++iC2 )
{
hd1 = cornerInd[ iC2 ];
hd2 = halfDivider[ hd1 ];
if ( std::find( equVerts.begin(), equVerts.end(), hd2 ) == equVerts.end() )
hd2 = -1; // hd2-th vertex can't become a corner
else
break;
}
if ( hd2 >= 0 )
{
angles[ hd1 ] = 2 * M_PI; // make hd1-th vertex no more "equal"
angles[ hd2 ] = 2 * M_PI;
refinedCorners.insert( hd1 );
refinedCorners.insert( hd2 );
treatedCorners = refinedCorners;
// update cornerInd
equVerts.push_front( equVerts.back() );
equVerts.push_back( equVerts.front() );
list< TGeoIndex >::iterator hdPos =
std::find( equVerts.begin(), equVerts.end(), hd2 );
if ( hdPos == equVerts.end() ) break;
cornerInd[ helper.WrapIndex( iC2 + 0, cornerInd.size()) ] = hd1;
cornerInd[ helper.WrapIndex( iC2 + 1, cornerInd.size()) ] = *( --hdPos );
cornerInd[ helper.WrapIndex( iC2 + 2, cornerInd.size()) ] = hd2;
cornerInd[ helper.WrapIndex( iC2 + 3, cornerInd.size()) ] = *( ++hdPos, ++hdPos );
theVertices[ 0 ] = helper.IthVertex( 0, edgeVec[ cornerInd[0] ]);
theVertices[ 1 ] = helper.IthVertex( 0, edgeVec[ cornerInd[1] ]);
theVertices[ 2 ] = helper.IthVertex( 0, edgeVec[ cornerInd[2] ]);
theVertices[ 3 ] = helper.IthVertex( 0, edgeVec[ cornerInd[3] ]);
iC = -1;
continue;
}
}
// move corners to make sides equal by length
int nbEqualV = equVerts.size();
int nbExcessV = nbEqualV - ( 1 + nbC[0] + nbC[1] );
if ( nbExcessV > 0 ) // there are nbExcessV vertices that can become corners
{
// calculate normalized length of each "side" enclosed between neighbor equVerts
vector< double > accuLength;
double totalLen = 0;
vector< TGeoIndex > evVec( equVerts.begin(), equVerts.end() );
size_t iEV = 0;
TGeoIndex iE = cornerInd[ helper.WrapIndex( iC - nbC[0] - 1, cornerInd.size() )];
TGeoIndex iEEnd = cornerInd[ helper.WrapIndex( iC + nbC[1] + 1, cornerInd.size() )];
while ((int) accuLength.size() < nbEqualV + int( !allCornersSame ) )
{
// accumulate length of edges before iEV-th equal vertex
accuLength.push_back( totalLen );
do {
accuLength.back() += SMESH_Algo::EdgeLength( edgeVec[ iE ]);
iE = helper.WrapIndex( iE + 1, edgeVec.size());
if ( iEV < evVec.size() && iE == evVec[ iEV ] ) {
iEV++;
break; // equal vertex reached
}
}
while( iE != iEEnd );
totalLen = accuLength.back();
}
accuLength.resize( equVerts.size() );
for ( size_t iS = 0; iS < accuLength.size(); ++iS )
accuLength[ iS ] /= totalLen;
// find equVerts most close to the ideal sub-division of all sides
int iBestEV = 0;
int iCorner = helper.WrapIndex( iC - nbC[0], cornerInd.size() );
int nbSides = Min( nbCorners, 2 + nbC[0] + nbC[1] );
for ( int iS = 1; iS < nbSides; ++iS, ++iBestEV )
{
double idealLen = iS / double( nbSides );
double d, bestDist = 2.;
for ( iEV = iBestEV; iEV < accuLength.size(); ++iEV )
{
d = Abs( idealLen - accuLength[ iEV ]);
// take into account presence of a corresponding halfDivider
const double cornerWgt = 0.5 / nbSides;
const double vertexWgt = 0.25 / nbSides;
TGeoIndex hd = halfDivider[ evVec[ iEV ]];
if ( hd < 0 )
d += vertexWgt;
else if( refinedCorners.count( hd ))
d -= cornerWgt;
else
d -= vertexWgt;
// choose vertex with the best d
if ( d < bestDist )
{
bestDist = d;
iBestEV = iEV;
}
}
if ( iBestEV > iS-1 + nbExcessV )
iBestEV = iS-1 + nbExcessV;
theVertices[ iCorner ] = helper.IthVertex( 0, edgeVec[ evVec[ iBestEV ]]);
cornerInd [ iCorner ] = evVec[ iBestEV ];
refinedCorners.insert( evVec[ iBestEV ]);
iCorner = helper.WrapIndex( iCorner + 1, cornerInd.size() );
}
} // if ( nbExcessV > 0 )
else
{
refinedCorners.insert( cornerInd[ iC ]);
}
} // loop on cornerInd
// make theWire begin from the cornerInd[0]-th EDGE
while ( !theWire.front().IsSame( edgeVec[ cornerInd[0] ]))
theWire.splice( theWire.begin(), theWire, --theWire.end() );
} // if ( haveVariants )
return nbCorners;
}
//================================================================================
/*!
* \brief Constructor of a side of quad

View File

@ -669,7 +669,7 @@ public:
return true;
}
// -----------------------------------------------------------------------------
//! Make mesh on an adge using assigned 1d hyp or default nb of segments
//! Make mesh on an edge using assigned 1d hyp or default nb of segments
bool ComputeCircularEdge( SMESH_Mesh& aMesh,
const StdMeshers_FaceSidePtr& aSide )
{
@ -697,7 +697,7 @@ public:
return ok;
}
// -----------------------------------------------------------------------------
//! Make mesh on an adge using assigned 1d hyp or default nb of segments
//! Make mesh on an edge using assigned 1d hyp or default nb of segments
bool EvaluateCircularEdge(SMESH_Mesh& aMesh,
const StdMeshers_FaceSidePtr aSide,
MapShapeNbElems& aResMap)

View File

@ -8771,7 +8771,7 @@ void _LayerEdge::ChooseSmooFunction( const set< TGeomID >& concaveVertices,
}
}
// // this coice is done only if ( !concaveVertices.empty() ) for Grids/smesh/bugs_19/X1
// // this choice is done only if ( !concaveVertices.empty() ) for Grids/smesh/bugs_19/X1
// // where the nodes are smoothed too far along a sphere thus creating
// // inverted _simplices
// double dist[theNbSmooFuns];