]> SALOME platform Git repositories - modules/shaper.git/commitdiff
Salome HOME
Issue 1299 angle constraint: final correction to calculate reverse state in SketcherP...
authornds <nds@opencascade.com>
Fri, 8 Apr 2016 05:56:05 +0000 (08:56 +0300)
committernds <nds@opencascade.com>
Fri, 8 Apr 2016 05:56:30 +0000 (08:56 +0300)
src/SketchPlugin/SketchPlugin_ConstraintAngle.cpp
src/SketcherPrs/AIS_AngleDimension.cxx
src/SketcherPrs/AIS_AngleDimension.hxx
src/SketcherPrs/SketcherPrs_Angle.cpp
src/SketcherPrs/SketcherPrs_Angle.h

index 7b60a594c70e40a4bb8cd7f4fa0d70f9ad05f87f..712d436af2aefdf0ad2f536693d4749a8b0ea45e 100644 (file)
@@ -199,23 +199,19 @@ double SketchPlugin_ConstraintAngle::getAngleForType(double theAngle)
 {
   double anAngle = theAngle;
 
-  std::shared_ptr<GeomAPI_Ax3> aPlane = SketchPlugin_Sketch::plane(sketch());
-  std::shared_ptr<GeomAPI_Dir> aNormal = aPlane->normal();
-  bool aPositiveNormal = !(aNormal->x() < 0 || aNormal->y() < 0 || aNormal->z() < 0);
-
   std::shared_ptr<ModelAPI_Data> aData = data();
   std::shared_ptr<ModelAPI_AttributeInteger> aTypeAttr = std::dynamic_pointer_cast<
       ModelAPI_AttributeInteger>(aData->attribute(SketchPlugin_ConstraintAngle::TYPE_ID()));
   SketcherPrs_Tools::AngleType anAngleType = (SketcherPrs_Tools::AngleType)(aTypeAttr->value());
   switch (anAngleType) {
     case SketcherPrs_Tools::ANGLE_DIRECT:
-      anAngle = aPositiveNormal ? theAngle : 360 - theAngle;
+      anAngle = theAngle;
     break;
     case SketcherPrs_Tools::ANGLE_COMPLEMENTARY:
-      anAngle = fabs(180 - theAngle);
+      anAngle = fabs(180.0 - theAngle);
     break;
     case SketcherPrs_Tools::ANGLE_BACKWARD:
-      anAngle = aPositiveNormal ? 360 - theAngle : theAngle;
+      anAngle = 360.0 - theAngle;
     break;
     default:
       break;
index 492dabbbaeb37be811777397e3a11d7556b38b3f..ba7fdb5b4705b58f9a0c1e809ac3586c37487767 100755 (executable)
@@ -277,8 +277,8 @@ void AIS_AngleDimension::SetMeasuredGeometry (const TopoDS_Face& theFirstFace,
 //=======================================================================
 void AIS_AngleDimension::Init()
 {
-  SetGeometryOrientedAngle (Standard_False, Standard_False);
-  SetArrowVisible(Standard_True, Standard_True);
+  SetAngleReversed (Standard_False);
+  SetArrowVisible (Standard_True, Standard_True);
   SetSpecialSymbol (THE_DEGREE_SYMBOL);
   SetDisplaySpecialSymbol (AIS_DSS_After);
   SetFlyout (15.0);
@@ -339,23 +339,11 @@ void AIS_AngleDimension::DrawArc (const Handle(Prs3d_Presentation)& thePresentat
   }
 
   gp_Pln aPlane = aConstructPlane.Value();
-  if (myGeometryOrientedAngle) {
-    gp_Dir aCPlaneDir = GetPlane().Axis().Direction();
-    bool aCPlaneDirToReverse = !(aCPlaneDir.X() < 0 || aCPlaneDir.Y() < 0 || aCPlaneDir.Z() < 0);
-    // have similar direction for all cases
-    if (!aCPlaneDirToReverse && myUseReverse) {
-      gp_Ax1 anAxis = aPlane.Axis();
-      gp_Dir aDir = anAxis.Direction();
-      aDir.Reverse();
-      aPlane.SetAxis(gp_Ax1(anAxis.Location(), aDir));
-    }
-
-    if (aCPlaneDirToReverse && !myUseReverse) {
-      gp_Ax1 anAxis = aPlane.Axis();
-      gp_Dir aDir = anAxis.Direction();
-      aDir.Reverse();
-      aPlane.SetAxis(gp_Ax1(anAxis.Location(), aDir));
-    }
+  if (myUseReverse) {
+    gp_Ax1 anAxis = aPlane.Axis();
+    gp_Dir aDir = anAxis.Direction();
+    aDir.Reverse();
+    aPlane.SetAxis(gp_Ax1(anAxis.Location(), aDir));
   }
   
   // construct circle forming the arc
@@ -382,9 +370,14 @@ void AIS_AngleDimension::DrawArc (const Handle(Prs3d_Presentation)& thePresentat
   // compute number of discretization elements in old-fanshioned way
   gp_Vec aCenterToFirstVec  (theCenter, theFirstAttach);
   gp_Vec aCenterToSecondVec (theCenter, theSecondAttach);
-  const Standard_Real anAngle = aCenterToFirstVec.Angle (aCenterToSecondVec);
-  const Standard_Integer aNbPoints = myGeometryOrientedAngle ? 40 :
-                                     Max (4, Standard_Integer (50.0 * anAngle / M_PI));
+
+  gp_Ax1 anAxis = aPlane.Axis();
+  gp_Dir aDir = anAxis.Direction();
+  gp_Vec aRefVec(aDir);
+  Standard_Real anAngle = aCenterToFirstVec.AngleWithRef (aCenterToSecondVec, aRefVec);
+  if (anAngle < 0)
+    anAngle = 2.0 * M_PI + anAngle;
+  const Standard_Integer aNbPoints = Max (4, Standard_Integer (50.0 * anAngle / M_PI));
 
   GCPnts_UniformAbscissa aMakePnts (anArcAdaptor, aNbPoints);
   if (!aMakePnts.IsDone())
@@ -1253,13 +1246,11 @@ void AIS_AngleDimension::SetTextPosition (const gp_Pnt& theTextPos)
 }
 
 //=======================================================================
-//function : SetGeometryOrientedAngle
+//function : SetAngleReversed
 //purpose  : 
 //=======================================================================
-void AIS_AngleDimension::SetGeometryOrientedAngle(const Standard_Boolean& theState,
-                                                  const Standard_Boolean& theUseReverse)
+void AIS_AngleDimension::SetAngleReversed(const Standard_Boolean& theUseReverse)
 {
-  myGeometryOrientedAngle = theState;
   myUseReverse = theUseReverse;
 }
 
index acf4299a72b45938bc4ac2fe10c67426e031093f..beb32a47aa2fadcd7b36ec648292e98171338614 100755 (executable)
@@ -207,10 +207,10 @@ public:
 
   Standard_EXPORT virtual const gp_Pnt GetTextPosition () const;
 
-  //! Sets state if the create arc should be built depending on the input geometry orientation
-  //! or to be always oriented in [0,0,1]. The last case propose angles more than 180 degree.
-  //! @param theSecondAttach [in] the second attachment point.
-  void SetGeometryOrientedAngle(const Standard_Boolean& theState, const Standard_Boolean& theUseReverse);
+  //! Sets state if the angle arc should be built reversing to the presentation plane.
+  //! Default state is not reversed
+  //! @param theUseReverse [in] the boolean state.
+  void SetAngleReversed(const Standard_Boolean& theUseReverse);
 
   //! Sets visible state of angle arrows. Default value is true for both
   //! @param theFirstArrowVisible [in] the visibility of the first arrow.
@@ -346,7 +346,6 @@ protected:
                                                   const gp_Pnt& theSecondPoint) const;
 
 private:
-  Standard_Boolean myGeometryOrientedAngle;
   Standard_Boolean myUseReverse;
 
   Standard_Boolean myFirstArrowVisible;
index cbc4b9f8256ed58239ab2c709b5ff9de4e2ca566..98493c04355145e07d1e2ff755770a9267d585e6 100644 (file)
@@ -100,12 +100,6 @@ void SketcherPrs_Angle::Compute(const Handle(PrsMgr_PresentationManager3d)& theP
       ModelAPI_AttributeInteger>(aData->attribute(SketchPlugin_ConstraintAngle::TYPE_ID()));
   SketcherPrs_Tools::AngleType anAngleType = (SketcherPrs_Tools::AngleType)(aTypeAttr->value());
 
-  // Flyout point
-  std::shared_ptr<GeomDataAPI_Point2D> aFlyoutAttr = 
-    std::dynamic_pointer_cast<GeomDataAPI_Point2D>
-    (aData->attribute(SketchPlugin_Constraint::FLYOUT_VALUE_PNT()));
-  std::shared_ptr<GeomAPI_Pnt> aFlyoutPnt = myPlane->to3D(aFlyoutAttr->x(), aFlyoutAttr->y());
-
   AttributeRefAttrPtr anAttr1 = aData->refattr(SketchPlugin_Constraint::ENTITY_A());
   AttributeRefAttrPtr anAttr2 = aData->refattr(SketchPlugin_Constraint::ENTITY_B());
 
@@ -122,48 +116,50 @@ void SketcherPrs_Angle::Compute(const Handle(PrsMgr_PresentationManager3d)& theP
   TopoDS_Edge aEdge1 = TopoDS::Edge(aTEdge1);
   TopoDS_Edge aEdge2 = TopoDS::Edge(aTEdge2);
 
+  double aDist = -1;
+
   switch (anAngleType) {
     case SketcherPrs_Tools::ANGLE_DIRECT: {
-      SetGeometryOrientedAngle(true, false);
-      SetArrowVisible(Standard_False, Standard_True);
+      SetArrowVisible(Standard_False/*first*/, Standard_True/*second*/);
+
       SetMeasuredGeometry(aEdge1, aEdge2);
+      bool isReversedPlanes = isAnglePlaneReversedToSketchPlane();
+      SetAngleReversed(!isReversedPlanes);
     }
     break;
     case SketcherPrs_Tools::ANGLE_COMPLEMENTARY: {
+      SetArrowVisible(Standard_True/*first*/, Standard_False/*second*/);
       // to calculate center, first and end points
-      SetGeometryOrientedAngle(false, false);
+      SetAngleReversed(false);
       SetMeasuredGeometry(aEdge1, aEdge2);
-      gp_Pnt aCenterPnt = CenterPoint();
-      gp_Pnt aFirstPnt = FirstPoint();
-      gp_Pnt aSecondPnt = SecondPoint();
-      double anEdge2Length = aCenterPnt.Distance(aSecondPnt);
-      aSecondPnt = aCenterPnt.Translated (gp_Vec(aCenterPnt, aSecondPnt).Normalized() * (-anEdge2Length));
-      SetArrowVisible(Standard_True, Standard_False);
-      SetMeasuredGeometry(aFirstPnt, aCenterPnt, aSecondPnt);
+      /// the first point will be moved, so it is necessary to find distance
+      /// after applying initial parameters of geometry but before correcting them
+      /// for the current type of angle(complementary)
+      aDist = calculateDistanceToFlyoutPoint();
+      /// invert the first edge according to the angle center
+      gp_Pnt aCenter = CenterPoint();
+      gp_Pnt aFirst = FirstPoint();
+      gp_Pnt aSecond = SecondPoint();
+      double anEdge1Length = aCenter.Distance(aFirst);
+      aFirst = aCenter.Translated (gp_Vec(aCenter, aFirst).Normalized() * (-anEdge1Length));
+      anEdge1Length = aCenter.Distance(aFirst);
+
+      SetMeasuredGeometry(aFirst, aCenter, aSecond);
     }
     break;
     case SketcherPrs_Tools::ANGLE_BACKWARD: {
-      SetGeometryOrientedAngle(true, true);
-      SetArrowVisible(Standard_False, Standard_True);
+      SetArrowVisible(Standard_False/*first*/, Standard_True/*second*/);
+
       SetMeasuredGeometry(aEdge1, aEdge2);
+      bool isReversedPlanes = isAnglePlaneReversedToSketchPlane();
+      SetAngleReversed(isReversedPlanes);
     }
     break;
     default:
       break;
   }
-
-
-  const gp_Pnt& aCenter = CenterPoint();
-  const gp_Pnt& aFirst = FirstPoint();
-  const gp_Pnt& aSecond = SecondPoint();
-
-  gp_Dir aBisector((aFirst.XYZ() + aSecond.XYZ()) * 0.5 - aCenter.XYZ());
-
-  gp_Pnt aFlyPnt(aFlyoutPnt->x(), aFlyoutPnt->y(), aFlyoutPnt->z());
-  gp_XYZ aFlyDir = aFlyPnt.XYZ() - aCenter.XYZ();
-  double aDist = aFlyDir.Dot(aBisector.XYZ());
-  // make a positive distance in order to AIS angle presentation is not reversed
-  aDist = fabs(aDist);
+  if (aDist < 0) /// it was not calculated yet
+    aDist = calculateDistanceToFlyoutPoint();
   SetFlyout(aDist);
 
   // Angle value is in degrees
@@ -204,3 +200,38 @@ void SketcherPrs_Angle::ComputeSelection(const Handle(SelectMgr_Selection)& aSel
   }
   AIS_AngleDimension::ComputeSelection(aSelection, aMode);
 }
+
+bool SketcherPrs_Angle::isAnglePlaneReversedToSketchPlane()
+{
+  bool aReversed = false;
+  if (!myPlane.get())
+    return aReversed;
+
+  gp_Pln aPlane = GetPlane();
+  gp_Dir aDir = aPlane.Axis().Direction();
+  double aDot = myPlane->normal()->dot(
+                std::shared_ptr<GeomAPI_Dir>(new GeomAPI_Dir(aDir.X(), aDir.Y(), aDir.Z())));
+  return aDot < 0;
+}
+
+double SketcherPrs_Angle::calculateDistanceToFlyoutPoint()
+{
+  const gp_Pnt& aCenter = CenterPoint();
+  const gp_Pnt& aFirst = FirstPoint();
+  const gp_Pnt& aSecond = SecondPoint();
+
+  // Flyout point
+  DataPtr aData = myConstraint->data();
+  std::shared_ptr<GeomDataAPI_Point2D> aFlyoutAttr = 
+                              std::dynamic_pointer_cast<GeomDataAPI_Point2D>
+                              (aData->attribute(SketchPlugin_Constraint::FLYOUT_VALUE_PNT()));
+  std::shared_ptr<GeomAPI_Pnt> aFlyoutPnt = myPlane->to3D(aFlyoutAttr->x(), aFlyoutAttr->y());
+
+  gp_Dir aBisector((aFirst.XYZ() + aSecond.XYZ()) * 0.5 - aCenter.XYZ());
+  gp_Pnt aFlyPnt(aFlyoutPnt->x(), aFlyoutPnt->y(), aFlyoutPnt->z());
+  gp_XYZ aFlyDir = aFlyPnt.XYZ() - aCenter.XYZ();
+  double aDistance = aFlyDir.Dot(aBisector.XYZ());
+  // make a positive distance in order to AIS angle presentation is not reversed
+  aDistance = fabs(aDistance);
+  return aDistance;
+}
index e178a1b8cc01241c2d4b9a6c40cb729000a1a6aa..d2f4c3c35a95cf20e6d289456e141bcd1a7e747b 100644 (file)
@@ -51,6 +51,17 @@ protected:
   Standard_EXPORT virtual void ComputeSelection(const Handle(SelectMgr_Selection)& aSelection,
     const Standard_Integer aMode);
 
+  /// Checks is the angle plane has inverted direction of normal to the plane of current sketcher
+  /// Returns true if crossed product is negative.
+  /// \return bolean value
+  bool isAnglePlaneReversedToSketchPlane();
+
+  /// Calculates a distance between center of the angle presentation and the value of flyout point
+  /// attribute. It should be used after setting measured geometry for the angle presentation as
+  /// it uses calculated center/first/second point coordinates
+  /// \return real value
+  double calculateDistanceToFlyoutPoint();
+
 private:
   /// Constraint feature
   ModelAPI_Feature* myConstraint;