diff --git a/qgroundcontrol.pro b/qgroundcontrol.pro index 201c14ba08b9869b1fb616d27ba1a908e6e8bd9d..0d746d3a982daa43efdd1020576f049d6d0bb06e 100644 --- a/qgroundcontrol.pro +++ b/qgroundcontrol.pro @@ -427,7 +427,8 @@ HEADERS += \ src/Wima/SphereCalculus.h \ src/Wima/CircularSurveyComplexItem.h \ src/Wima/PlanimetryCalculus.h \ - src/Wima/Circle.h + src/Wima/Circle.h \ + src/Wima/PolygonCalculus.h SOURCES += \ src/api/QGCCorePlugin.cc \ src/api/QGCOptions.cc \ @@ -453,7 +454,8 @@ SOURCES += \ src/Wima/SphereCalculus.cc \ src/Wima/CircularSurveyComplexItem.cc \ src/Wima/PlanimetryCalculus.cc \ - src/Wima/Circle.cc + src/Wima/Circle.cc \ + src/Wima/PolygonCalculus.cc # # Unit Test specific configuration goes here (requires full debug build with all plugins) diff --git a/src/Wima/Circle.cc b/src/Wima/Circle.cc index f755a0016cac84e89fba5dc15bc35515b7d323de..ab3bb19f75e531b478a77918192e1970757739c4 100644 --- a/src/Wima/Circle.cc +++ b/src/Wima/Circle.cc @@ -97,16 +97,47 @@ QPolygonF Circle::approximate(int numberOfCorners) const { if ( numberOfCorners < 3) return QPolygonF(); + return approximateSektor(numberOfCorners, 0, 2*M_PI); +} + +QPolygonF Circle::approximate(double angleDiscretisation) const +{ + return approximateSektor(angleDiscretisation, 0, 2*M_PI); +} + +QPolygonF Circle::approximateSektor(int numberOfCorners, double alpha1, double alpha2) const +{ + return approximateSektor((alpha2-alpha1)/double(numberOfCorners-1), alpha1, alpha2); +} + +QPolygonF Circle::approximateSektor(double angleDiscretisation, double alpha1, double alpha2) const +{ + // truncate alpha1 to [0, 2*pi], fmod() does not work in this case + alpha1 = PlanimetryCalculus::truncateAngle(alpha1); + alpha2 = PlanimetryCalculus::truncateAngle(alpha2); + double deltaAlpha = PlanimetryCalculus::truncateAngle(alpha2 - alpha1); + angleDiscretisation = PlanimetryCalculus::truncateAngle(angleDiscretisation); + + if (angleDiscretisation > deltaAlpha || qFuzzyIsNull(angleDiscretisation)) + return QPolygonF(); - double rotationAngle = 2*M_PI/numberOfCorners; QPolygonF polygon; QPointF vertex(-_circleRadius,0); // initial vertex - polygon.append(vertex + _circleOrigin); + double currentAngle = alpha1; // rotate the vertex numberOfCorners-1 times add the origin and append to the polygon. - for(int i = 0; i < numberOfCorners; i++) { - rotatePoint(vertex, rotationAngle); + while(currentAngle < alpha2) { + PlanimetryCalculus::rotatePoint(vertex, currentAngle); polygon.append(vertex + _circleOrigin); + currentAngle = PlanimetryCalculus::truncateAngle(currentAngle + angleDiscretisation); + } + + // append last point if necessarry + PlanimetryCalculus::rotatePoint(vertex, alpha2); + vertex = vertex + _circleOrigin; + if ( !qFuzzyIsNull(PlanimetryCalculus::distance(polygon.first(), vertex)) + && !qFuzzyIsNull(PlanimetryCalculus::distance(polygon.last(), vertex )) ){ + polygon.append(vertex); } return polygon; diff --git a/src/Wima/Circle.h b/src/Wima/Circle.h index 0b6e3a54a25c282d9001c10d3bdc4494a7d35e64..9aa0488bbf2457cab380364f82cede829282685e 100644 --- a/src/Wima/Circle.h +++ b/src/Wima/Circle.h @@ -4,9 +4,11 @@ #include #include +#include + #include "PlanimetryCalculus.h" -class Circle : public QObject, protected PlanimetryCalculus +class Circle : public QObject { Q_OBJECT public: @@ -25,7 +27,10 @@ public: QPointF origin() const; // Member methodes - QPolygonF approximate(int numberOfCorners) const; + QPolygonF approximate (int numberOfCorners) const; + QPolygonF approximate (double angleDiscretisation) const; + QPolygonF approximateSektor(int numberOfCorners, double alpha1, double alpha2) const; + QPolygonF approximateSektor(double angleDiscretisation, double alpha1, double alpha2) const; bool isNull() const; signals: diff --git a/src/Wima/PlanimetryCalculus.cc b/src/Wima/PlanimetryCalculus.cc index 3f2275064d06f51d978b383eca9bfa1a0527290c..23990521121a2b53e8154ced07d734d62d72fa50 100644 --- a/src/Wima/PlanimetryCalculus.cc +++ b/src/Wima/PlanimetryCalculus.cc @@ -1,283 +1,300 @@ #include "PlanimetryCalculus.h" +#include "Circle.h" + + +namespace PlanimetryCalculus { + namespace { + /*! + \fn IntersectType intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints, bool calcInstersect) + Returns the Intersection type of \a circle and \a line. + Stores the intersection points in \a intersectionPoints if \a calcIntersect is \c true. + Returns \c Error if either line or circe \c {isNull() == true}. + + \sa QPointF, Circle + */ + IntersectType intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints, bool calcInstersect) + { + if (!circle.isNull() && ! line.isNull()) { + QPointF translationVector = line.p1(); + double angleWLDegree = line.angle(); // angle between wold and line coordinate system + + QPointF originCircleL = circle.origin() - translationVector; + rotatePoint(originCircleL, -angleWLDegree); // circle origin in line corrdinate system + + double y = originCircleL.y(); + double r = circle.radius(); + if (qAbs(y) > r) + return NoIntersection; + else if ( qFuzzyCompare(qFabs(y), r) ) { // tangent + double x_ori = originCircleL.x(); + + if (x_ori >= 0 && x_ori <= line.length()) { + if (calcInstersect) { + QPointF intersectionPt = QPointF(x_ori, 0); + rotatePoint(intersectionPt, angleWLDegree); + intersectionPoints.append(intersectionPt + translationVector); + } + + return Tangent; + } + + return NoIntersection; + } else { // sekant + double x_ori = originCircleL.x(); + double y_ori = originCircleL.y(); + double delta = qSqrt(qPow(r, 2)-qPow(y_ori, 2)); + double x1 = x_ori + delta; // x coordinate (line system) of fist intersection point + double x2 = x_ori - delta;// x coordinate (line system) of second intersection point + bool doesIntersect = false; // remember if actual intersection was on the line + + if (x1 >= 0 && x1 <= line.length()) { // check if intersection point is on the line + if (calcInstersect) { + QPointF intersectionPt = QPointF(x1, 0); // first intersection point (line system) + rotatePoint(intersectionPt, angleWLDegree); + intersectionPoints.append(intersectionPt + translationVector); // transform (to world system) and append first intersection point + } + doesIntersect = true; + } + if (x2 >= 0 && x2 <= line.length()) { // check if intersection point is on the line + if (calcInstersect) { + QPointF intersectionPt = QPointF(x2, 0); // second intersection point (line system) + rotatePoint(intersectionPt, angleWLDegree); + intersectionPoints.append(intersectionPt + translationVector); // transform (to world system) and append second intersection point + } + doesIntersect = true; + } + + return doesIntersect ? Secant : NoIntersection; + } + } - -PlanimetryCalculus::PlanimetryCalculus() -{ - -} - -/*! - \fn void PlanimetryCalculus::rotatePoint(QPointF &point, double alpha) - Rotates the \a point counter clockwisely by the angle \a alpha (in radiants). -*/ -void PlanimetryCalculus::rotatePoint(QPointF &point, double alpha) -{ - if (!point.isNull()) { - double x = point.x(); - double y = point.y(); - - point.setX(x*qCos(alpha) - y*qSin(alpha)); - point.setY(x*qSin(alpha) + y*qCos(alpha)); + return Error; + } + } // end anonymous namespace + + /*! + \fn void rotatePoint(QPointF &point, double alpha) + Rotates the \a point counter clockwisely by the angle \a alpha (in radiants). + */ + void rotatePoint(QPointF &point, double alpha) + { + if (!point.isNull()) { + double x = point.x(); + double y = point.y(); + + point.setX(x*qCos(alpha) - y*qSin(alpha)); + point.setY(x*qSin(alpha) + y*qCos(alpha)); + } } -} -void PlanimetryCalculus::rotatePoint(QList &points, double alpha) -{ - for (int i = 0; i < points.size(); i++) { - rotatePoint(points[i], alpha); + void rotatePoint(QList &points, double alpha) + { + for (int i = 0; i < points.size(); i++) { + rotatePoint(points[i], alpha); + } } -} -/*! - \fn void PlanimetryCalculus::rotatePointDegree(QPointF &point, double alpha) - Rotates the \a point counter clockwisely by the angle \a alpha (in degrees). -*/ -void PlanimetryCalculus::rotatePointDegree(QPointF &point, double alpha) -{ - rotatePoint(point, alpha/180*M_PI); -} - -void PlanimetryCalculus::rotatePointDegree(QList &points, double alpha) -{ - for (int i = 0; i < points.size(); i++) { - rotatePointDegree(points[i], alpha); + /*! + \fn void rotatePointDegree(QPointF &point, double alpha) + Rotates the \a point counter clockwisely by the angle \a alpha (in degrees). + */ + void rotatePointDegree(QPointF &point, double alpha) + { + rotatePoint(point, alpha/180*M_PI); } -} - -/*! - \fn PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle1, const Circle &circle2) - Returns the intersection type of the two cirles \a circle1 and \a circle2. - \note Returns Error if circle.isNull() returns true; - - \sa Circle -*/ -PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle1, const Circle &circle2) -{ - // r1 == 0 || r2 == 0 results in indefined behavior - if (!circle1.isNull() && !circle2.isNull()) { - double r1 = circle1.radius(); - double r2 = circle2.radius(); - double d = distance(circle1.origin(), circle2.origin()); - double r = 0; - double R = 0; - if (r1 > r2) { - R = r1; // large - r = r2; // small - } else { - // this branch is also choosen if r1 == r2 - R = r2; - r = r1; + void rotatePointDegree(QList &points, double alpha) + { + for (int i = 0; i < points.size(); i++) { + rotatePointDegree(points[i], alpha); } + } - if (r + d < R) { - // this branch is also reached if d < rLarge && rSmall == 0 - return PlanimetryCalculus::InsideNoIntersection; - } else if (qFuzzyCompare(r + d, R)) { - if (qFuzzyIsNull(d)) - return PlanimetryCalculus::CirclesEqual; - else - return PlanimetryCalculus::InsideTouching; - } else if (d < R) { - return PlanimetryCalculus::InsideIntersection; - } else if (d - r < R) { - return PlanimetryCalculus::OutsideIntersection; - } else if (qFuzzyCompare(d - r, R)) { - return PlanimetryCalculus::OutsideTouching; - } else { - return PlanimetryCalculus::OutsideNoIntersection; + /*! + \fn IntersectType intersects(const Circle &circle1, const Circle &circle2) + Returns the intersection type of the two cirles \a circle1 and \a circle2. + + \note Returns Error if circle.isNull() returns true; + + \sa Circle + */ + IntersectType intersects(const Circle &circle1, const Circle &circle2) + { + // r1 == 0 || r2 == 0 results in indefined behavior + if (!circle1.isNull() && !circle2.isNull()) { + double r1 = circle1.radius(); + double r2 = circle2.radius(); + double d = distance(circle1.origin(), circle2.origin()); + double r = 0; + double R = 0; + if (r1 > r2) { + R = r1; // large + r = r2; // small + } else { + // this branch is also choosen if r1 == r2 + R = r2; + r = r1; + } + + if (r + d < R) { + // this branch is also reached if d < rLarge && rSmall == 0 + return InsideNoIntersection; + } else if (qFuzzyCompare(r + d, R)) { + if (qFuzzyIsNull(d)) + return CirclesEqual; + else + return InsideTouching; + } else if (d < R) { + return InsideIntersection; + } else if (d - r < R) { + return OutsideIntersection; + } else if (qFuzzyCompare(d - r, R)) { + return OutsideTouching; + } else { + return OutsideNoIntersection; + } } + return Error; } - return PlanimetryCalculus::Error; -} -/*! - \fn PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle1, const Circle &circle2, QList intersectionPoints) - Calculates the intersection points of two circles if present and stores the result in \a intersectionPoints. - Returns the intersection type of the two cirles \a circle1 and \a circle2. + /*! + \fn IntersectType intersects(const Circle &circle1, const Circle &circle2, QList intersectionPoints) + Calculates the intersection points of two circles if present and stores the result in \a intersectionPoints. + Returns the intersection type of the two cirles \a circle1 and \a circle2. - The function assumes that the list \a intersectionPoints is empty. + The function assumes that the list \a intersectionPoints is empty. - \note Returns Error if circle.isNull() returns true; + \note Returns Error if circle.isNull() returns true; - \sa Circle -*/ -PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle1, const Circle &circle2, QList &intersectionPoints) -{ - PlanimetryCalculus::IntersectType returnValue = intersects(circle1, circle2); - - if ( returnValue == PlanimetryCalculus::InsideNoIntersection - || returnValue == PlanimetryCalculus::OutsideNoIntersection - || returnValue == PlanimetryCalculus::CirclesEqual - || returnValue == PlanimetryCalculus::Error ) { - return returnValue; // No intersection Points, or infinitly many (in case of CirclesEqual). - } else { - double r1 = circle1.radius(); - double r2 = circle2.radius(); - double d = distance(circle1.origin(), circle2.origin()); - double alpha = angle(circle1.origin(), circle2.origin()); - double r = 0; - double R = 0; - if (r1 > r2) { - R = r1; - r = r2; + \sa Circle + */ + IntersectType intersects(const Circle &circle1, const Circle &circle2, QList &intersectionPoints) + { + IntersectType returnValue = intersects(circle1, circle2); + + if ( returnValue == InsideNoIntersection + || returnValue == OutsideNoIntersection + || returnValue == CirclesEqual + || returnValue == Error ) { + return returnValue; // No intersection Points, or infinitly many (in case of CirclesEqual). } else { - // this branch is also choosen if r1 == r2 - R = r2; - r = r1; - } + double r1 = circle1.radius(); + double r2 = circle2.radius(); + double d = distance(circle1.origin(), circle2.origin()); + double alpha = angle(circle1.origin(), circle2.origin()); + double r = 0; + double R = 0; + if (r1 > r2) { + R = r1; + r = r2; + } else { + // this branch is also choosen if r1 == r2 + R = r2; + r = r1; + } - if ( returnValue == PlanimetryCalculus::InsideTouching - || returnValue == PlanimetryCalculus::OutsideTouching) { - // Intersection point in coordinate system of circle 1. - // Coordinate system circle1: origin = circle1.origin(), x-axis towars circle2.origin() y-axis such that the - // coordinate system is dextrorse with z-axis outward faceing with respect to the drawing plane. - intersectionPoints.append(QPointF(0, r1)); - } else { //triggered if ( returnValue == PlanimetryCalculus::InsideIntersection - // || returnValue == PlanimetryCalculus::OutsideIntersection) - // See fist branch for explanation - - // this equations are obtained by solving x^2+y^2=R^2 and (x - d)^2+y^2=r^2 - double x = (qPow(d, 2) - qPow(r, 2) + qPow(R, 2))/2/d; - double y = 1/2/d*qSqrt(4*qPow(d*R, 2) - qPow(qPow(d, 2) - qPow(r, 2) + qPow(R, 2), 2)); - - intersectionPoints.append(QPointF(x, y)); - intersectionPoints.append(QPointF(x, -y)); - } - // Transform the coordinate to the world coordinate system. Alpha is the angle between world and circle1 coordinate system. - rotatePoint(intersectionPoints, alpha); + if ( returnValue == InsideTouching + || returnValue == OutsideTouching) { + // Intersection point in coordinate system of circle 1. + // Coordinate system circle1: origin = circle1.origin(), x-axis towars circle2.origin() y-axis such that the + // coordinate system is dextrorse with z-axis outward faceing with respect to the drawing plane. + intersectionPoints.append(QPointF(0, r1)); + } else { //triggered if ( returnValue == InsideIntersection + // || returnValue == OutsideIntersection) + // See fist branch for explanation + + // this equations are obtained by solving x^2+y^2=R^2 and (x - d)^2+y^2=r^2 + double x = (qPow(d, 2) - qPow(r, 2) + qPow(R, 2))/2/d; + double y = 1/2/d*qSqrt(4*qPow(d*R, 2) - qPow(qPow(d, 2) - qPow(r, 2) + qPow(R, 2), 2)); + + intersectionPoints.append(QPointF(x, y)); + intersectionPoints.append(QPointF(x, -y)); + } + // Transform the coordinate to the world coordinate system. Alpha is the angle between world and circle1 coordinate system. + rotatePoint(intersectionPoints, alpha); - return returnValue; + return returnValue; + } } -} -/*! - \fn PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle, const QLineF &line) - Returns the Intersection type of \a circle and \a line. - Returns \c Error if either line or circe \c {isNull() == true}. + /*! + \fn IntersectType intersects(const Circle &circle, const QLineF &line) + Returns the Intersection type of \a circle and \a line. + Returns \c Error if either line or circe \c {isNull() == true}. - \sa QPointF, Circle -*/ -PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle, const QLineF &line) -{ - QList dummyList; - return intersects(circle, line, dummyList, false /* calculate intersection points*/); -} - -PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints) -{ - return intersects(circle, line, intersectionPoints, true /* calculate intersection points*/); -} + \sa QPointF, Circle + */ + IntersectType intersects(const Circle &circle, const QLineF &line) + { + QList dummyList; + return intersects(circle, line, dummyList, false /* calculate intersection points*/); + } -/*! - \fn double PlanimetryCalculus::distance(const QPointF &p1, const QPointF p2) - Calculates the distance (2-norm) between \a p1 and \a p2. - \sa QPointF -*/ -double PlanimetryCalculus::distance(const QPointF &p1, const QPointF p2) -{ - double dx = p2.x()-p1.x(); - double dy = p2.y()-p1.y(); + IntersectType intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints) + { + return intersects(circle, line, intersectionPoints, true /* calculate intersection points*/); + } - return qSqrt(dx*dx+dy*dy); -} + /*! + \fn double distance(const QPointF &p1, const QPointF p2) + Calculates the distance (2-norm) between \a p1 and \a p2. + \sa QPointF + */ + double distance(const QPointF &p1, const QPointF p2) + { + double dx = p2.x()-p1.x(); + double dy = p2.y()-p1.y(); + + return qSqrt(dx*dx+dy*dy); + } -/*! - \fn double PlanimetryCalculus::distance(const QPointF &p1, const QPointF p2) - Calculates the angle (in radiants) between the line defined by \a p1 and \a p2 and the x-axis according to the following rule. - Angle = qAtan2(dy, dx), where dx = p2.x()-p1.x() and dy = p2.y()-p1.y(). + /*! + \fn double distance(const QPointF &p1, const QPointF p2) + Calculates the angle (in radiants) between the line defined by \a p1 and \a p2 and the x-axis according to the following rule. + Angle = qAtan2(dy, dx), where dx = p2.x()-p1.x() and dy = p2.y()-p1.y(). - \note The order of \a p1 and \a p2 matters. Swapping \a p1 and \a p2 will result in a angle of oposite sign. - \sa QPointF -*/ -double PlanimetryCalculus::angle(const QPointF &p1, const QPointF p2) -{ - double dx = p2.x()-p1.x(); - double dy = p2.y()-p1.y(); + \note The order of \a p1 and \a p2 matters. Swapping \a p1 and \a p2 will result in a angle of oposite sign. + \sa QPointF + */ + double angle(const QPointF &p1, const QPointF p2) + { + double dx = p2.x()-p1.x(); + double dy = p2.y()-p1.y(); - return qAtan2(dy, dx); -} + return qAtan2(dy, dx); + } -/*! - \fn double PlanimetryCalculus::distance(const QPointF &p1, const QPointF p2) - Calculates the angle (in degrees) between the line defined by \a p1 and \a p2 and the x-axis according to the following rule. - Angle = qAtan2(dy, dx)*180/pi, where dx = p2.x()-p1.x() and dy = p2.y()-p1.y(). + /*! + \fn double distance(const QPointF &p1, const QPointF p2) + Calculates the angle (in degrees) between the line defined by \a p1 and \a p2 and the x-axis according to the following rule. + Angle = qAtan2(dy, dx)*180/pi, where dx = p2.x()-p1.x() and dy = p2.y()-p1.y(). + + \note The order of \a p1 and \a p2 matters. Swapping \a p1 and \a p2 will result in a angle of oposite sign. + \sa QPointF + */ + double angleDegree(const QPointF &p1, const QPointF p2) + { + return angle(p1, p2)*180/M_PI; + } - \note The order of \a p1 and \a p2 matters. Swapping \a p1 and \a p2 will result in a angle of oposite sign. - \sa QPointF -*/ -double PlanimetryCalculus::angleDegree(const QPointF &p1, const QPointF p2) -{ - return angle(p1, p2)*180/M_PI; -} + double truncateAngle(double angle) + { + while (angle < 0 ) { angle += 2*M_PI;} + while (angle > 2*M_PI) { angle -= 2*M_PI;} -/*! - \fn PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints, bool calcInstersect) - Returns the Intersection type of \a circle and \a line. - Stores the intersection points in \a intersectionPoints if \a calcIntersect is \c true. - Returns \c Error if either line or circe \c {isNull() == true}. + return angle; + } - \sa QPointF, Circle -*/ -PlanimetryCalculus::IntersectType PlanimetryCalculus::intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints, bool calcInstersect) -{ - if (!circle.isNull() && ! line.isNull()) { - QPointF translationVector = line.p1(); - double angleWLDegree = line.angle(); // angle between wold and line coordinate system - - QPointF originCircleL = circle.origin() - translationVector; - rotatePoint(originCircleL, -angleWLDegree); // circle origin in line corrdinate system - - double y = originCircleL.y(); - double r = circle.radius(); - if (qAbs(y) > r) - return PlanimetryCalculus::NoIntersection; - else if ( qFuzzyCompare(qFabs(y), r) ) { // tangent - double x_ori = originCircleL.x(); - - if (x_ori >= 0 && x_ori <= line.length()) { - if (calcInstersect) { - QPointF intersectionPt = QPointF(x_ori, 0); - rotatePoint(intersectionPt, angleWLDegree); - intersectionPoints.append(intersectionPt + translationVector); - } + double truncateAngleDegree(double angle) + { + return truncateAngle(angle/180*M_PI); + } - return PlanimetryCalculus::Tangent; - } - return PlanimetryCalculus::NoIntersection; - } else { // sekant - double x_ori = originCircleL.x(); - double y_ori = originCircleL.y(); - double delta = qSqrt(qPow(r, 2)-qPow(y_ori, 2)); - double x1 = x_ori + delta; // x coordinate (line system) of fist intersection point - double x2 = x_ori - delta;// x coordinate (line system) of second intersection point - bool doesIntersect = false; // remember if actual intersection was on the line - - if (x1 >= 0 && x1 <= line.length()) { // check if intersection point is on the line - if (calcInstersect) { - QPointF intersectionPt = QPointF(x1, 0); // first intersection point (line system) - rotatePoint(intersectionPt, angleWLDegree); - intersectionPoints.append(intersectionPt + translationVector); // transform (to world system) and append first intersection point - } - doesIntersect = true; - } - if (x2 >= 0 && x2 <= line.length()) { // check if intersection point is on the line - if (calcInstersect) { - QPointF intersectionPt = QPointF(x2, 0); // second intersection point (line system) - rotatePoint(intersectionPt, angleWLDegree); - intersectionPoints.append(intersectionPt + translationVector); // transform (to world system) and append second intersection point - } - doesIntersect = true; - } +} // end namespace PlanimetryCalculus - return doesIntersect ? PlanimetryCalculus::Secant : PlanimetryCalculus::NoIntersection; - } - } - return PlanimetryCalculus::Error; -} /*! \class PlanimetryCalculus diff --git a/src/Wima/PlanimetryCalculus.h b/src/Wima/PlanimetryCalculus.h index 9dccf5d42a2fcaefffbc8fbae44615955fce1828..12e2574636feec44c9c6662ebf6043d13e6205d2 100644 --- a/src/Wima/PlanimetryCalculus.h +++ b/src/Wima/PlanimetryCalculus.h @@ -5,11 +5,9 @@ #include #include -#include "Circle.h" -class PlanimetryCalculus -{ -public: - PlanimetryCalculus(); +class Circle; + +namespace PlanimetryCalculus { enum IntersectType{InsideNoIntersection, InsideTouching, InsideIntersection, OutsideIntersection, OutsideTouching, OutsideNoIntersection, @@ -31,8 +29,9 @@ public: double distance(const QPointF &p1, const QPointF p2); double angle(const QPointF &p1, const QPointF p2); double angleDegree(const QPointF &p1, const QPointF p2); + double truncateAngle(double angle); + double truncateAngleDegree(double angle); +} + -private: - IntersectType intersects(const Circle &circle, const QLineF &line, QList &intersectionPoints, bool calcIntersect); -}; diff --git a/src/Wima/PolygonCalculus.cc b/src/Wima/PolygonCalculus.cc new file mode 100644 index 0000000000000000000000000000000000000000..55bc1ea3b852924eca7636a314df345202d44966 --- /dev/null +++ b/src/Wima/PolygonCalculus.cc @@ -0,0 +1,2 @@ +#include "PolygonCalculus.h" + diff --git a/src/Wima/PolygonCalculus.h b/src/Wima/PolygonCalculus.h new file mode 100644 index 0000000000000000000000000000000000000000..96cbaabbf0152316fc4cc884601035d45b941aed --- /dev/null +++ b/src/Wima/PolygonCalculus.h @@ -0,0 +1,9 @@ +#ifndef POLYGONCALCULUS_H +#define POLYGONCALCULUS_H + + +namespace PolygonCalculus { + +} + +#endif // POLYGONCALCULUS_H diff --git a/src/Wima/WimaArea.cc b/src/Wima/WimaArea.cc index e770572671b0198f6e422b26e0eab55e22228901..0fad49c9921e2943a5b12231f264f025c41fc4ac 100644 --- a/src/Wima/WimaArea.cc +++ b/src/Wima/WimaArea.cc @@ -668,23 +668,7 @@ void WimaArea::saveToJson(QJsonObject &json) bool WimaArea::loadFromJson(const QJsonObject &json, QString& errorString) { if ( this->QGCMapPolygon::loadFromJson(json, false /*no poly required*/, errorString) ) { - if ( json.contains(maxAltitudeName) && json[maxAltitudeName].i// Overrides from ComplexMissionItem - bool load (const QJsonObject& complexObject, int sequenceNumber, QString& errorString) final; - QString mapVisualQML (void) const final { return QStringLiteral("SurveyMapVisual.qml"); } - - // Overrides from TransectStyleComplexItem - void save (QJsonArray& planItems) final; - bool specifiesCoordinate (void) const final { return true; } - void appendMissionItems (QList& items, QObject* missionItemParent) final; - void applyNewAltitude (double newAltitude) final; - double timeBetweenShots (void) final; - - // Overrides from VisualMissionionItem - QString commandDescription (void) const final { return tr("Survey"); } - QString commandName (void) const final { return tr("Survey"); } - QString abbreviation (void) const final { return tr("S"); } - bool readyForSave (void) const final; - double additionalTimeDelay (void) const final;sDouble()) { + if ( json.contains(maxAltitudeName) && json[maxAltitudeName].isDouble()) { _maxAltitude = json[maxAltitudeName].toDouble(); return true; } else {