X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;ds=sidebyside;f=src%2FConstructionPlugin%2FConstructionPlugin_Plane.cpp;h=3680ab50302fd64895e7c84891b99395a6ee83b3;hb=a99b44f2a23d23faba4610092ac7929eeed6b06c;hp=68f3e5b0a732aa1a05f3026b072696f912c4be85;hpb=5d613df7d51faeba83c5225ac9ba78e35f80094c;p=modules%2Fshaper.git diff --git a/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp b/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp index 68f3e5b0a..3680ab503 100644 --- a/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp +++ b/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp @@ -1,8 +1,22 @@ -// Copyright (C) 2014-20xx CEA/DEN, EDF R&D - -// File: ConstructionPlugin_Plane.cpp -// Created: 12 Dec 2014 -// Author: Vitaly Smetannikov +// Copyright (C) 2014-2017 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 "ConstructionPlugin_Plane.h" @@ -14,11 +28,13 @@ #include #include +#include #include #include #include #include #include +#include #include #include @@ -32,8 +48,9 @@ static GeomShapePtr faceByThreeVertices(const std::shared_ptr theV1, const std::shared_ptr theV2, const std::shared_ptr theV3); -static std::shared_ptr makeRectangularFace(const std::shared_ptr theFace, - const std::shared_ptr thePln); +static std::shared_ptr makeRectangularFace( + const std::shared_ptr theFace, + const std::shared_ptr thePln); //================================================================================================== ConstructionPlugin_Plane::ConstructionPlugin_Plane() @@ -43,8 +60,11 @@ ConstructionPlugin_Plane::ConstructionPlugin_Plane() //================================================================================================== void ConstructionPlugin_Plane::initAttributes() { - data()->addAttribute(ConstructionPlugin_Plane::CREATION_METHOD(), ModelAPI_AttributeString::typeId()); + data()->addAttribute(ConstructionPlugin_Plane::CREATION_METHOD(), + ModelAPI_AttributeString::typeId()); + data()->addAttribute(PLANE(), ModelAPI_AttributeSelection::typeId()); + data()->addAttribute(DISTANCE(), ModelAPI_AttributeDouble::typeId()); // By general equation. data()->addAttribute(A(), ModelAPI_AttributeDouble::typeId()); data()->addAttribute(B(), ModelAPI_AttributeDouble::typeId()); @@ -63,12 +83,11 @@ void ConstructionPlugin_Plane::initAttributes() // By line and point. data()->addAttribute(LINE(), ModelAPI_AttributeSelection::typeId()); data()->addAttribute(POINT(), ModelAPI_AttributeSelection::typeId()); + data()->addAttribute(PERPENDICULAR(), ModelAPI_AttributeBoolean::typeId()); // By other plane. data()->addAttribute(CREATION_METHOD_BY_OTHER_PLANE_OPTION(), ModelAPI_AttributeString::typeId()); - data()->addAttribute(PLANE(), ModelAPI_AttributeSelection::typeId()); - data()->addAttribute(DISTANCE(), ModelAPI_AttributeDouble::typeId()); - data()->addAttribute(DISTANCE_REVERSE(), ModelAPI_AttributeBoolean::typeId()); + data()->addAttribute(REVERSE(), ModelAPI_AttributeBoolean::typeId()); data()->addAttribute(COINCIDENT_POINT(), ModelAPI_AttributeSelection::typeId()); data()->addAttribute(AXIS(), ModelAPI_AttributeSelection::typeId()); data()->addAttribute(ANGLE(), ModelAPI_AttributeDouble::typeId()); @@ -84,7 +103,8 @@ void ConstructionPlugin_Plane::execute() GeomShapePtr aShape; std::string aCreationMethod = string(CREATION_METHOD())->value(); - if(aCreationMethod == CREATION_METHOD_BY_GENERAL_EQUATION()) { + if(aCreationMethod == CREATION_METHOD_BY_GENERAL_EQUATION() || + aCreationMethod == "PlaneByGeneralEquation") { aShape = createByGeneralEquation(); } else if(aCreationMethod == CREATION_METHOD_BY_THREE_POINTS()) { aShape = createByThreePoints(); @@ -101,6 +121,9 @@ void ConstructionPlugin_Plane::execute() } } else if(aCreationMethod == CREATION_METHOD_BY_TWO_PARALLEL_PLANES()) { aShape = createByTwoParallelPlanes(); + } else { + setError("Error: Plane creation method \"" + aCreationMethod + "\" not supported."); + return; } if(!aShape.get()) { @@ -116,11 +139,12 @@ void ConstructionPlugin_Plane::execute() //================================================================================================== bool ConstructionPlugin_Plane::customisePresentation(ResultPtr theResult, AISObjectPtr thePrs, - std::shared_ptr theDefaultPrs) + std::shared_ptr theDefaultPrs) { std::vector aColor; // get color from the attribute of the result - if (theResult.get() != NULL && theResult->data()->attribute(ModelAPI_Result::COLOR_ID()).get() != NULL) { + if (theResult.get() != NULL && + theResult->data()->attribute(ModelAPI_Result::COLOR_ID()).get() != NULL) { AttributeIntArrayPtr aColorAttr = theResult->data()->intArray(ModelAPI_Result::COLOR_ID()); if (aColorAttr.get() && aColorAttr->size()) { aColor.push_back(aColorAttr->value(0)); @@ -129,8 +153,7 @@ bool ConstructionPlugin_Plane::customisePresentation(ResultPtr theResult, AISObj } } if (aColor.empty()) - aColor = Config_PropManager::color("Visualization", "construction_plane_color", - ConstructionPlugin_Plane::DEFAULT_COLOR()); + aColor = Config_PropManager::color("Visualization", "construction_plane_color"); bool isCustomized = false; if (aColor.size() == 3) @@ -155,10 +178,9 @@ std::shared_ptr ConstructionPlugin_Plane::createByGeneralEquation anAttrC->isInitialized() && anAttrD->isInitialized() ) { double aA = anAttrA->value(), aB = anAttrB->value(), aC = anAttrC->value(), aD = anAttrD->value(); - std::shared_ptr aPlane = + std::shared_ptr aPlane = std::shared_ptr(new GeomAPI_Pln(aA, aB, aC, aD)); - std::string kDefaultPlaneSize = "200"; - double aSize = Config_PropManager::integer("Sketch planes", "planes_size", kDefaultPlaneSize); + double aSize = Config_PropManager::integer(SKETCH_TAB_NAME, "planes_size"); aSize *= 4.; aPlaneFace = GeomAlgoAPI_FaceBuilder::squareFace(aPlane, aSize); } @@ -207,9 +229,6 @@ std::shared_ptr ConstructionPlugin_Plane::createByLineAndPoint() aLineShape = anEdgeSelection->context()->shape(); } std::shared_ptr anEdge(new GeomAPI_Edge(aLineShape)); - std::shared_ptr aV1, aV2; - GeomAlgoAPI_ShapeTools::findBounds(anEdge, aV1, aV2); - // Get point. AttributeSelectionPtr aPointSelection = selection(POINT()); @@ -219,7 +238,24 @@ std::shared_ptr ConstructionPlugin_Plane::createByLineAndPoint() } std::shared_ptr aVertex(new GeomAPI_Vertex(aPointShape)); - GeomShapePtr aRes = faceByThreeVertices(aV1, aV2, aVertex); + // Get perpendicular flag. + bool anIsPerpendicular= boolean(PERPENDICULAR())->value(); + + GeomShapePtr aRes; + if(anIsPerpendicular) { + std::shared_ptr aLin = anEdge->line(); + std::shared_ptr aPnt = aVertex->point(); + std::shared_ptr aNewPln(new GeomAPI_Pln(aPnt, aLin->direction())); + double aSize = aLin->distance(aPnt) * 2; + // point may belong to line, so for the face size use maximum distance between point and line + // and the line size (distance between the start and end point) + double aDistance = anEdge->firstPoint()->distance(anEdge->lastPoint()); + aRes = GeomAlgoAPI_FaceBuilder::squareFace(aNewPln, aSize > aDistance ? aSize : aDistance); + } else { + std::shared_ptr aV1, aV2; + GeomAlgoAPI_ShapeTools::findBounds(anEdge, aV1, aV2); + aRes = faceByThreeVertices(aV1, aV2, aVertex); + } return aRes; } @@ -235,6 +271,8 @@ std::shared_ptr ConstructionPlugin_Plane::createByDistanceFromOth aFaceAttr->isInitialized() && aDistAttr->isInitialized()) { double aDist = aDistAttr->value(); + bool anIsReverse = boolean(REVERSE())->value(); + if(anIsReverse) aDist = -aDist; GeomShapePtr aShape = aFaceAttr->value(); if (!aShape.get()) { aShape = aFaceAttr->context()->shape(); @@ -246,7 +284,7 @@ std::shared_ptr ConstructionPlugin_Plane::createByDistanceFromOth std::shared_ptr aFace(new GeomAPI_Face(aShape)); - std::shared_ptr aPln = GeomAlgoAPI_FaceBuilder::plane(aFace); + std::shared_ptr aPln = aFace->getPlane(); std::shared_ptr aOrig = aPln->location(); std::shared_ptr aDir = aPln->direction(); @@ -296,6 +334,7 @@ std::shared_ptr ConstructionPlugin_Plane::createByRotation() aFaceShape = aFaceSelection->context()->shape(); } std::shared_ptr aFace(new GeomAPI_Face(aFaceShape)); + aFace = makeRectangularFace(aFace, aFace->getPlane()); // Get axis. AttributeSelectionPtr anAxisSelection = selection(AXIS()); @@ -305,19 +344,25 @@ std::shared_ptr ConstructionPlugin_Plane::createByRotation() } std::shared_ptr anEdge(new GeomAPI_Edge(anAxisShape)); - std::shared_ptr anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + std::shared_ptr anAxis = + std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); // Getting angle. double anAngle = real(ANGLE())->value(); GeomAlgoAPI_Rotation aRotationAlgo(aFace, anAxis, anAngle); + if (!aRotationAlgo.check()) { + setError(aRotationAlgo.getError()); + return GeomShapePtr(); + } + aRotationAlgo.build(); + if (!aRotationAlgo.isDone()) { + setError("Error: Failed to rotate plane"); + return GeomShapePtr(); + } std::shared_ptr aRes(new GeomAPI_Face(aRotationAlgo.shape())); - std::shared_ptr aNewPln = aRes->getPlane(); - - aRes = makeRectangularFace(aRes, aNewPln); - return aRes; } @@ -342,19 +387,13 @@ std::shared_ptr ConstructionPlugin_Plane::createByTwoParallelPlan std::shared_ptr aFace2(new GeomAPI_Face(aFaceShape2)); std::shared_ptr aPln2 = aFace2->getPlane(); - double aDist = aPln1->distance(aPln2) / 2.0; - - std::shared_ptr aOrig1 = aPln1->location(); - std::shared_ptr aDir1 = aPln1->direction(); + std::shared_ptr anOrig1 = aPln1->location(); + std::shared_ptr aPntOnPln2 = aPln2->project(anOrig1); - aOrig1->translate(aDir1, aDist); - std::shared_ptr aNewPln(new GeomAPI_Pln(aOrig1, aDir1)); + std::shared_ptr aNewOrig(new GeomAPI_Pnt(anOrig1->xyz()->added( + aPntOnPln2->xyz())->multiplied(0.5))); - if((aNewPln->distance(aPln2) - aDist) > 1.e-7) { - aDir1->reverse(); - aOrig1->translate(aDir1, 2.0 * aDist); - aNewPln.reset(new GeomAPI_Pln(aOrig1, aDir1)); - } + std::shared_ptr aNewPln(new GeomAPI_Pln(aNewOrig, aPln1->direction())); std::shared_ptr aRes = makeRectangularFace(aFace1, aNewPln); @@ -366,13 +405,15 @@ GeomShapePtr faceByThreeVertices(const std::shared_ptr theV1, const std::shared_ptr theV2, const std::shared_ptr theV3) { - std::shared_ptr aFace = GeomAlgoAPI_FaceBuilder::planarFaceByThreeVertices(theV1, theV2, theV3); + std::shared_ptr aFace = + GeomAlgoAPI_FaceBuilder::planarFaceByThreeVertices(theV1, theV2, theV3); ListOfShape anObjects; anObjects.push_back(theV1); anObjects.push_back(theV2); anObjects.push_back(theV3); - std::list > aBoundingPoints = GeomAlgoAPI_ShapeTools::getBoundingBox(anObjects, 1.0); + std::list > aBoundingPoints = + GeomAlgoAPI_ShapeTools::getBoundingBox(anObjects, 1.0); GeomShapePtr aRes = GeomAlgoAPI_ShapeTools::fitPlaneToBox(aFace, aBoundingPoints); return aRes; @@ -411,7 +452,8 @@ std::shared_ptr makeRectangularFace(const std::shared_ptr aResFace = GeomAlgoAPI_FaceBuilder::planarFace(thePln, - aMinX2d - aWgap, aMinY2d - aHgap, aMaxX2d - aMinX2d + 2. * aWgap, aMaxY2d - aMinY2d + 2. * aHgap); + aMinX2d - aWgap, aMinY2d - aHgap, aMaxX2d - aMinX2d + 2. * aWgap, + aMaxY2d - aMinY2d + 2. * aHgap); return aResFace; }