X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;f=src%2FBuildPlugin%2FBuildPlugin_Face.cpp;h=022865abdd3682773a3b4a0a1cee2e70858ea434;hb=b22f8bc2d6f96b466583d21445d5c5c719f4c724;hp=fddd223f053a505c2d48cb5b063e7b2a70dbb38f;hpb=eca73b85b6b9e96c4227b52566697d5f9ea4897c;p=modules%2Fshaper.git diff --git a/src/BuildPlugin/BuildPlugin_Face.cpp b/src/BuildPlugin/BuildPlugin_Face.cpp index fddd223f0..022865abd 100644 --- a/src/BuildPlugin/BuildPlugin_Face.cpp +++ b/src/BuildPlugin/BuildPlugin_Face.cpp @@ -1,8 +1,21 @@ -// Copyright (C) 2014-20xx CEA/DEN, EDF R&D - -// File: BuildPlugin_Face.cpp -// Created: 14 April 2016 -// Author: Dmitry Bobylev +// Copyright (C) 2014-2019 CEA/DEN, EDF R&D +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// #include "BuildPlugin_Face.h" @@ -10,11 +23,14 @@ #include #include +#include #include #include +#include #include #include +#include //================================================================================================= BuildPlugin_Face::BuildPlugin_Face() @@ -43,62 +59,100 @@ void BuildPlugin_Face::execute() // Collect base shapes. ListOfShape anEdges; + ListOfShape anOriginalFaces; + ListOfShape aContexts; + getOriginalShapesAndContexts(BASE_OBJECTS_ID(), anOriginalFaces, aContexts); + anOriginalFaces.clear(); + std::list< std::shared_ptr > aListOfNormals; for(int anIndex = 0; anIndex < aSelectionList->size(); ++anIndex) { AttributeSelectionPtr aSelection = aSelectionList->value(anIndex); GeomShapePtr aShape = aSelection->value(); + GeomShapePtr aContext = aSelection->context()->shape(); if(!aShape.get()) { - aShape = aSelection->context()->shape(); + aShape = aContext; + } + // keep selected faces "as is" + if (aShape->shapeType() == GeomAPI_Shape::FACE) { + anOriginalFaces.push_back(aShape); + continue; } + for(GeomAPI_ShapeExplorer anExp(aShape, GeomAPI_Shape::EDGE); anExp.more(); anExp.next()) { GeomShapePtr anEdge = anExp.current(); anEdges.push_back(anEdge); } - } - // Get plane. - std::shared_ptr aPln = GeomAlgoAPI_ShapeTools::findPlane(anEdges); + // check whether the context is a sketch, in this case store its normal for further needs + std::shared_ptr aSketch = + std::dynamic_pointer_cast(aContext); + if (aSketch) + aListOfNormals.push_back(aSketch->norm()); + } - // Get faces. + // Build faces by edges. ListOfShape aFaces; - GeomAlgoAPI_SketchBuilder::createFaces(aPln->location(), aPln->xDirection(), aPln->direction(), anEdges, aFaces); + GeomMakeShapePtr aFaceBuilder; + if (!anEdges.empty()) + buildFacesByEdges(anEdges, aListOfNormals, aFaces, aFaceBuilder); + int aNbFacesFromEdges = (int)aFaces.size(); - // Get wires from faces. - ListOfShape aWires; - for(ListOfShape::const_iterator anIt = aFaces.cbegin(); anIt != aFaces.cend(); ++anIt) { - aWires.push_back(GeomAlgoAPI_ShapeTools::getFaceOuterWire(*anIt)); - //for(GeomAPI_ShapeExplorer anExp(*anIt, GeomAPI_Shape::WIRE); anExp.more(); anExp.next()) { - // if(anExp.current()->orientation() == GeomAPI_Shape::REVERSED) { - // continue; - // } - // aWires.push_back(anExp.current()); - //} - } - - // Make faces with holes. - aFaces.clear(); - GeomAlgoAPI_ShapeTools::makeFacesWithHoles(aPln->location(), aPln->direction(), aWires, aFaces); + // Add faces selected by user. + aFaces.insert(aFaces.end(), anOriginalFaces.begin(), anOriginalFaces.end()); // Store result. int anIndex = 0; for(ListOfShape::const_iterator anIt = aFaces.cbegin(); anIt != aFaces.cend(); ++anIt) { - ResultBodyPtr aResultBody = document()->createBody(data(), anIndex); + std::shared_ptr aMakeShapeList(new GeomAlgoAPI_MakeShapeList); + if (anIndex < aNbFacesFromEdges) + aMakeShapeList->appendAlgo(aFaceBuilder); + GeomShapePtr aShape = *anIt; - aResultBody->store(aShape); + GeomMakeShapePtr aCopy(new GeomAlgoAPI_Copy(aShape)); + aMakeShapeList->appendAlgo(aCopy); + + ListOfShape aBaseShapes; + if (anIndex < aNbFacesFromEdges) + aBaseShapes = anEdges; + else + aBaseShapes.push_back(aShape); + storeResult(aMakeShapeList, aBaseShapes, aContexts, aCopy->shape(), anIndex++); + } - for(GeomAPI_ShapeExplorer anExp(aShape, GeomAPI_Shape::EDGE); anExp.more(); anExp.next()) { - GeomShapePtr anEdgeInResult = anExp.current(); - for(ListOfShape::const_iterator anIt = anEdges.cbegin(); anIt != anEdges.cend(); ++anIt) { - std::shared_ptr anEdgeInList(new GeomAPI_Edge(*anIt)); - if(anEdgeInList->isEqual(anEdgeInResult)) { - aResultBody->modified(anEdgeInList, anEdgeInResult, "Edge"); - break; - } - } - } + removeResults(anIndex); +} - setResult(aResultBody, anIndex); - ++anIndex; +void BuildPlugin_Face::buildFacesByEdges( + const ListOfShape& theEdges, + const std::list< std::shared_ptr >& theNormals, + ListOfShape& theFaces, + std::shared_ptr& theBuilderAlgo) const +{ + // Get plane. + std::shared_ptr aPln = GeomAlgoAPI_ShapeTools::findPlane(theEdges); + std::shared_ptr aNormal = aPln->direction(); + bool isReverse = !theNormals.empty(); + std::list< std::shared_ptr >::const_iterator aNormIt = theNormals.begin(); + for (; aNormIt != theNormals.end() && isReverse; ++aNormIt) + if ((*aNormIt)->dot(aNormal) > 1.e-7) + isReverse = false; + if (isReverse) { + aNormal->reverse(); + aPln = std::shared_ptr(new GeomAPI_Pln(aPln->location(), aNormal)); } - removeResults(anIndex); + // Get faces. + std::shared_ptr aSketchBuilder( + new GeomAlgoAPI_SketchBuilder(aPln, theEdges)); + theFaces = aSketchBuilder->faces(); + theBuilderAlgo = aSketchBuilder; + + // Get wires from faces. + ListOfShape aWires; + for(ListOfShape::const_iterator anIt = theFaces.cbegin(); anIt != theFaces.cend(); ++anIt) + aWires.push_back(GeomAlgoAPI_ShapeTools::getFaceOuterWire(*anIt)); + + // Make faces with holes. + theFaces.clear(); + GeomAlgoAPI_ShapeTools::makeFacesWithHoles(aPln->location(), aPln->direction(), + aWires, theFaces); }