#include <GeomAPI_Vertex.h>
#include <GeomAPI_Dir.h>
+#include <BRepExtrema_ExtPC.hxx>
+#include <TopoDS_Vertex.hxx>
+#include <Geom_Curve.hxx>
+
static SketcherPrs_PositionMgr* MyPosMgr = NULL;
// The class is implemented as a singlton
}
}
-gp_Pnt SketcherPrs_PositionMgr::getPosition(ObjectPtr theShape,
- const SketcherPrs_SymbolPrs* thePrs,
- double theStep)
+
+gp_Vec getVector(ObjectPtr theShape, GeomDirPtr theDir, gp_Pnt theP)
{
+ gp_Vec aVec;
std::shared_ptr<GeomAPI_Shape> aShape = SketcherPrs_Tools::getShape(theShape);
- gp_Pnt aP; // Central point
- gp_Vec aVec1; // main vector
if (aShape->isEdge()) {
std::shared_ptr<GeomAPI_Curve> aCurve =
std::shared_ptr<GeomAPI_Curve>(new GeomAPI_Curve(aShape));
- std::shared_ptr<GeomAPI_Pnt> aPnt1; // Start point of main vector
- std::shared_ptr<GeomAPI_Pnt> aPnt2; // End point of main vector
- if (aCurve->isLine()) {
- std::shared_ptr<GeomAPI_Edge> aEdge =
- std::shared_ptr<GeomAPI_Edge>(new GeomAPI_Edge(aShape));
- aPnt1 = aEdge->firstPoint();
- aPnt2 = aEdge->lastPoint();
+ if (aCurve->isCircle()) {
+ GeomEdgePtr aEdgePtr(new GeomAPI_Edge(aShape));
+ GeomVertexPtr aVertexPtr(new GeomAPI_Vertex(theP.X(), theP.Y(), theP.Z()));
+ BRepExtrema_ExtPC aExtrema(aVertexPtr->impl<TopoDS_Vertex>(),
+ aEdgePtr->impl<TopoDS_Edge>());
+ int aNb = aExtrema.NbExt();
+ if (aNb > 0) {
+ for (int i = 1; i <= aNb; i++) {
+ if (aExtrema.IsMin(i)) {
+ double aParam = aExtrema.Parameter(i);
+ Handle(Geom_Curve) aCurv = aCurve->impl<Handle_Geom_Curve>();
+ gp_Pnt aP;
+ aCurv->D1(aParam, aP, aVec);
+ break;
+ }
+ }
+ }
+ } else {
+ double aMidParam = (aCurve->startParam() + aCurve->endParam()) / 2.;
+ GeomPointPtr aPnt1 = aCurve->getPoint((aMidParam + aCurve->endParam()) / 2.);
+ GeomPointPtr aPnt2 = aCurve->getPoint((aMidParam + aCurve->startParam()) / 2.);
- // Find the middle point
- aP = gp_Pnt((aPnt1->x() + aPnt2->x())/2.,
- (aPnt1->y() + aPnt2->y())/2.,
- (aPnt1->z() + aPnt2->z())/2.);
+ aVec = gp_Vec(aPnt1->impl<gp_Pnt>(), aPnt2->impl<gp_Pnt>());
+ }
+ } else {
+ aVec = gp_Vec(theDir->impl<gp_Dir>());
+ }
+ return aVec;
+}
- } else {
+gp_Pnt SketcherPrs_PositionMgr::getPosition(ObjectPtr theShape,
+ const SketcherPrs_SymbolPrs* thePrs,
+ double theStep, GeomPointPtr thePnt)
+{
+ std::shared_ptr<GeomAPI_Shape> aShape = SketcherPrs_Tools::getShape(theShape);
+ gp_Pnt aP; // Central point
+
+ if (thePnt.get()) {
+ aP = thePnt->impl<gp_Pnt>();
+ } else {
+ if (aShape->isEdge()) {
+ std::shared_ptr<GeomAPI_Curve> aCurve =
+ std::shared_ptr<GeomAPI_Curve>(new GeomAPI_Curve(aShape));
// this is a circle or arc
double aMidParam = (aCurve->startParam() + aCurve->endParam()) / 2.;
std::shared_ptr<GeomAPI_Pnt> aPnt = aCurve->getPoint(aMidParam);
aP = aPnt->impl<gp_Pnt>();
-
- aPnt1 = aCurve->getPoint((aMidParam + aCurve->endParam()) / 2.);
- aPnt2 = aCurve->getPoint((aMidParam + aCurve->startParam()) / 2.);
+ } else {
+ // This is a point
+ std::shared_ptr<GeomAPI_Vertex> aVertex =
+ std::shared_ptr<GeomAPI_Vertex>(new GeomAPI_Vertex(aShape));
+ std::shared_ptr<GeomAPI_Pnt> aPnt = aVertex->point();
+ aP = aPnt->impl<gp_Pnt>();
}
- aVec1 = gp_Vec(aPnt1->impl<gp_Pnt>(), aPnt2->impl<gp_Pnt>());
- } else {
- // This is a point
- std::shared_ptr<GeomAPI_Vertex> aVertex =
- std::shared_ptr<GeomAPI_Vertex>(new GeomAPI_Vertex(aShape));
- std::shared_ptr<GeomAPI_Pnt> aPnt = aVertex->point();
- aP = aPnt->impl<gp_Pnt>();
-
- std::shared_ptr<GeomAPI_Dir> aDir = thePrs->plane()->dirX();
- aVec1 = gp_Vec(aDir->impl<gp_Dir>());
}
+ // main vector
+ gp_Vec aVec1 = getVector(theShape, thePrs->plane()->dirX(), aP);
+
// Compute shifting vector for a one symbol
gp_Vec aShift = aVec1.Crossed(thePrs->plane()->normal()->impl<gp_Dir>());
aShift.Normalize();
- aShift.Multiply(theStep * 0.8);
+ // For point based symbols step = 1.2, for line based = 0.8
+ aShift.Multiply(theStep * (thePnt.get()? 1.2 : 0.8));
// Shift the position coordinate according to position index
int aPos = getPositionIndex(theShape, thePrs);
ObjectPtr aObj2 =
SketcherPrs_Tools::getResult(myConstraint, SketchPlugin_Constraint::ENTITY_B());
+ GeomShapePtr aShp1 = SketcherPrs_Tools::getShape(aObj1);
+ GeomShapePtr aShp2 = SketcherPrs_Tools::getShape(aObj2);
+
+ GeomCurvePtr aCurv1 = std::shared_ptr<GeomAPI_Curve>(new GeomAPI_Curve(aShp1));
+ GeomCurvePtr aCurv2 = std::shared_ptr<GeomAPI_Curve>(new GeomAPI_Curve(aShp2));
+
+ GeomPointPtr aPnt1_1 = aCurv1->getPoint(aCurv1->startParam());
+ GeomPointPtr aPnt1_2 = aCurv1->getPoint(aCurv1->endParam());
+
+ GeomPointPtr aPnt2_1 = aCurv2->getPoint(aCurv2->startParam());
+ GeomPointPtr aPnt2_2 = aCurv2->getPoint(aCurv2->endParam());
+
+ GeomPointPtr aPnt;
+ if (aPnt1_1->isEqual(aPnt2_1) || aPnt1_1->isEqual(aPnt2_2))
+ aPnt = aPnt1_1;
+ else if (aPnt1_2->isEqual(aPnt2_1) || aPnt1_2->isEqual(aPnt2_2))
+ aPnt = aPnt1_2;
+
// Compute points coordinates
SketcherPrs_PositionMgr* aMgr = SketcherPrs_PositionMgr::get();
- gp_Pnt aP1 = aMgr->getPosition(aObj1, this, theStep);
- gp_Pnt aP2 = aMgr->getPosition(aObj2, this, theStep);
- myPntArray = new Graphic3d_ArrayOfPoints(2, withColor);
+ gp_Pnt aP1 = aMgr->getPosition(aObj1, this, theStep, aPnt);
+ myPntArray = new Graphic3d_ArrayOfPoints(1, withColor);
myPntArray->AddVertex(aP1);
- myPntArray->AddVertex(aP2);
return true;
}