Engauge Digitizer 2
Loading...
Searching...
No Matches
CentipedeEndpointsPolar Class Reference

Compute endpoints for polar centipedes. More...

#include <CentipedeEndpointsPolar.h>

Inheritance diagram for CentipedeEndpointsPolar:
Inheritance graph
Collaboration diagram for CentipedeEndpointsPolar:
Collaboration graph

Public Member Functions

 CentipedeEndpointsPolar (const DocumentModelCoords &modelCoords, const DocumentModelGuideline &modelGuideline, const Transformation &transformation, const QPointF &posClickScreen, const QPointF &posOriginScreen)
 Constructor with individual coordinates.
virtual ~CentipedeEndpointsPolar ()
void ellipseScreenConstantRForTHighLowAngles (const Transformation &transformation, const QPointF &posClickScreen, double &angleRotation, QRectF &rectBounding, CentipedeDebugPolar &DebugPolar)
 Ellipse for R value of circle/coordinate intersection. Start/span angles are calculated separately.
QPointF posScreenConstantRForHighT (double radius) const
 Screen point for R value of circle/coordinate intersection in the increasing T direction.
QPointF posScreenConstantRForLowT (double radius) const
 Screen point for R value of circle/coordinate intersection in the decreasing T direction.
void posScreenConstantRHighLow (double radiusAboutClick, QPointF &posLow, QPointF &posHigh) const
 Return two points (posLow and posHigh) where circle around posClickScreen intersects constant-radiusAboutClick ellipse.
void posScreenConstantTForRHighLow (double radius, QPointF &posLow, QPointF &posHigh) const
 Endpoints for radial line segmentin polar coordinates.
Public Member Functions inherited from CentipedeEndpointsAbstract
 CentipedeEndpointsAbstract (const DocumentModelGuideline &modelGuideline, const Transformation &transformation, const QPointF &posClickScreen)
 Constructor with individual coordinates.
virtual ~CentipedeEndpointsAbstract ()

Additional Inherited Members

Protected Member Functions inherited from CentipedeEndpointsAbstract
const DocumentModelGuidelinemodelGuideline () const
 Settings.
QPointF posClickScreen () const
 Center of circle in screen coordinates.
const Transformationtransformation () const
 Transformation which is static through the entire lifetime of the Centipede class instances.

Detailed Description

Compute endpoints for polar centipedes.

Definition at line 20 of file CentipedeEndpointsPolar.h.

Constructor & Destructor Documentation

◆ CentipedeEndpointsPolar()

CentipedeEndpointsPolar::CentipedeEndpointsPolar ( const DocumentModelCoords & modelCoords,
const DocumentModelGuideline & modelGuideline,
const Transformation & transformation,
const QPointF & posClickScreen,
const QPointF & posOriginScreen )

Constructor with individual coordinates.

Definition at line 21 of file CentipedeEndpointsPolar.cpp.

25 :
29 m_modelCoords (modelCoords),
30 m_posOriginScreen (posOriginScreen)
31{
32}
QPointF posClickScreen() const
Center of circle in screen coordinates.
const DocumentModelGuideline & modelGuideline() const
Settings.
const Transformation & transformation() const
Transformation which is static through the entire lifetime of the Centipede class instances.
CentipedeEndpointsAbstract(const DocumentModelGuideline &modelGuideline, const Transformation &transformation, const QPointF &posClickScreen)
Constructor with individual coordinates.

◆ ~CentipedeEndpointsPolar()

CentipedeEndpointsPolar::~CentipedeEndpointsPolar ( )
virtual

Definition at line 34 of file CentipedeEndpointsPolar.cpp.

35{
36}

Member Function Documentation

◆ ellipseScreenConstantRForTHighLowAngles()

void CentipedeEndpointsPolar::ellipseScreenConstantRForTHighLowAngles ( const Transformation & transformation,
const QPointF & posClickScreen,
double & angleRotation,
QRectF & rectBounding,
CentipedeDebugPolar & DebugPolar )

Ellipse for R value of circle/coordinate intersection. Start/span angles are calculated separately.

Definition at line 55 of file CentipedeEndpointsPolar.cpp.

60{
61 // LOG4CPP is below
62
63 QPointF posClickGraph;
64 transformation.transformScreenToRawGraph (posClickScreen,
65 posClickGraph);
66 double rGraph = posClickGraph.y();
67
68 // Points at origin, then 0 degrees at range rGraph
69 QPointF posScreenOrigin, posScreen0, posScreen90, posScreen180;
70 transformation.transformRawGraphToScreen (QPointF (tAtOrigin (), rAtOrigin ()),
71 posScreenOrigin);
72 transformation.transformRawGraphToScreen (QPointF (0, rGraph),
73 posScreen0);
74 transformation.transformRawGraphToScreen (QPointF (90.0, rGraph),
75 posScreen90);
76 transformation.transformRawGraphToScreen (QPointF (180.0, rGraph),
77 posScreen180);
78
79 QPointF centerTo90 = posScreen90 - posScreenOrigin;
80
81 // Corners of parallelogram circumscribing the ellipse
82 QPointF posScreenTL = posScreen180 + centerTo90;
83 QPointF posScreenTR = posScreen0 + centerTo90;
84 QPointF posScreenBL = posScreen180 - centerTo90;
85 QPointF posScreenBR = posScreen0 - centerTo90;
86
87 double aAligned = 0, bAligned = 0;
88 ellipseFromParallelogram (posScreenTL.x() - posScreenOrigin.x(),
89 posScreenTL.y() - posScreenOrigin.y(),
90 posScreenTR.x() - posScreenOrigin.x(),
91 posScreenTR.y() - posScreenOrigin.y(),
92 posScreenBR.x() - posScreenOrigin.x(),
93 posScreenBR.y() - posScreenOrigin.y(),
94 angleRotation,
95 aAligned,
96 bAligned);
97
98 double angleGraphAxisFromScreenAxis = qAtan2 (posScreen0.y() - posScreenOrigin.y(),
99 posScreen0.x() - posScreenOrigin.x());
100
101 debugPolar = CentipedeDebugPolar (posScreenTL,
102 posScreenTR,
103 posScreenBL,
104 posScreenBR,
105 angleGraphAxisFromScreenAxis,
106 angleRotation,
107 aAligned,
108 bAligned,
109 rGraph);
110
111 // Bounding rectangle before rotation. We make sure the rectangle is normalized which at one point
112 // seemed to prevent drawing artifacts
113 rectBounding = QRectF (-1.0 * aAligned,
114 -1.0 * bAligned,
115 2.0 * aAligned,
116 2.0 * bAligned);
117
118 LOG4CPP_INFO_S ((*mainCat)) << "CentipedeEndpointsPolar::ellipseScreenConstantRForTHighLowAngles angleRotation="
119 << qRadiansToDegrees (angleRotation) << " posScreen0=" << QPointFToString (posScreen0).toLatin1().data()
120 << " posScreen90=" << QPointFToString (posScreen90).toLatin1().data()
121 << " a=" << aAligned
122 << " b=" << bAligned;
123}
log4cpp::Category * mainCat
Definition Logger.cpp:14
QString QPointFToString(const QPointF &pos)
#define LOG4CPP_INFO_S(logger)
Definition convenience.h:18
void ellipseFromParallelogram(double xTL, double yTL, double xTR, double yTR, double xBR, double yBR, double &angleRadians, double &aAligned, double &bAligned)
Calculate ellipse parameters that is incribed in a parallelogram centered at the origin,...
Definition mmsubs.cpp:70

◆ posScreenConstantRForHighT()

QPointF CentipedeEndpointsPolar::posScreenConstantRForHighT ( double radius) const

Screen point for R value of circle/coordinate intersection in the increasing T direction.

Definition at line 212 of file CentipedeEndpointsPolar.cpp.

213{
214 return posScreenConstantRCommon (radius,
216}
@ CENTIPEDE_INTERSECTION_HIGH
Intersection along circle perimeter with lowest value of XT or YR.

◆ posScreenConstantRForLowT()

QPointF CentipedeEndpointsPolar::posScreenConstantRForLowT ( double radius) const

Screen point for R value of circle/coordinate intersection in the decreasing T direction.

Definition at line 218 of file CentipedeEndpointsPolar.cpp.

219{
220 return posScreenConstantRCommon (radius,
222}
@ CENTIPEDE_INTERSECTION_LOW

◆ posScreenConstantRHighLow()

void CentipedeEndpointsPolar::posScreenConstantRHighLow ( double radiusAboutClick,
QPointF & posLow,
QPointF & posHigh ) const

Return two points (posLow and posHigh) where circle around posClickScreen intersects constant-radiusAboutClick ellipse.

Definition at line 224 of file CentipedeEndpointsPolar.cpp.

227{
228 // Click point
229 QPointF posClickGraph;
231 posClickGraph);
232 double yClick = posClickGraph.y();
233
234 // Iterate points around the circle starting at angleCenter, and going in two different
235 // directions (clockwise for angleHigh and counterclockwise for angleLow)
236 bool isFirstLow = true, isFirstHigh = true;
237 QPointF posLowGraph, posHighGraph;
238 for (int i = 0; i < NUM_CIRCLE_POINTS; i++) {
239 QPointF posGraphPreviousLow, posGraphNextLow, posScreenPreviousLow;
240 QPointF posGraphPreviousHigh, posGraphNextHigh, posScreenPreviousHigh;
241 generatePreviousAndNextPointsConstantR (radiusAboutClick,
242 i,
243 i + 1,
244 posGraphPreviousLow,
245 posGraphNextLow,
246 posScreenPreviousLow);
247 generatePreviousAndNextPointsConstantR (radiusAboutClick,
248 - i,
249 - i - 1,
250 posGraphPreviousHigh,
251 posGraphNextHigh,
252 posScreenPreviousHigh);
253
254 double epsilon = qAbs (posGraphPreviousLow.y() - posGraphNextLow.y()) / 10.0; // Allow for roundoff
255
256 bool transitionUpLow = (posGraphPreviousLow.y() - epsilon <= yClick) && (yClick < posGraphNextLow.y() + epsilon);
257 bool transitionDownLow = (posGraphNextLow.y() - epsilon <= yClick) && (yClick < posGraphPreviousLow.y() + epsilon);
258 bool transitionUpHigh = (posGraphPreviousHigh.y() - epsilon <= yClick) && (yClick < posGraphNextHigh.y() + epsilon);
259 bool transitionDownHigh = (posGraphNextHigh.y() - epsilon <= yClick) && (yClick < posGraphPreviousHigh.y() + epsilon);
260
261 if (isFirstLow && (transitionDownLow || transitionUpLow)) {
262 // Found the first (=best) low value
263 isFirstLow = false;
264 posLowGraph = (posGraphPreviousLow + posGraphNextLow) / 2.0; // Average
265 if (!isFirstHigh) {
266 break; // Done
267 }
268 }
269
270 if (isFirstHigh && (transitionDownHigh || transitionUpHigh)) {
271 // Found the first (=best) high value
272 isFirstHigh = false;
273 posHighGraph = (posGraphPreviousHigh + posGraphNextHigh) / 2.0;
274 if (!isFirstLow) {
275 break; // Done
276 }
277 }
278 }
279
280 // Convert from graph to screen coordinates
282 posLow);
284 posHigh);
285}
const int NUM_CIRCLE_POINTS
void transformRawGraphToScreen(const QPointF &pointRaw, QPointF &pointScreen) const
Transform from raw graph coordinates to linear cartesian graph coordinates, then to screen coordinate...
void transformScreenToRawGraph(const QPointF &coordScreen, QPointF &coordGraph) const
Transform from cartesian pixel screen coordinates to cartesian/polar graph coordinates.

◆ posScreenConstantTForRHighLow()

void CentipedeEndpointsPolar::posScreenConstantTForRHighLow ( double radius,
QPointF & posLow,
QPointF & posHigh ) const

Endpoints for radial line segmentin polar coordinates.

Definition at line 287 of file CentipedeEndpointsPolar.cpp.

290{
291 // This replaces CentipedeSegmentAbstract::posScreenConstantXTCommon since the polar coordinate radial vector
292 // can be on the other side of the origin if the ellipse center is within radius of the origin. This routine
293 // uses a different strategy of iterating on a line rather than a circle (since circle has tough issues with quadrants
294 // and 360 rollover)
295
296 // Origin and screen vector to center
297 QPointF posOriginScreen;
298 transformation().transformRawGraphToScreen (QPointF (tAtOrigin (), rAtOrigin ()),
299 posOriginScreen);
300 QPointF vecCenter = posClickScreen() - posOriginScreen;
301
302 // Number of solutions found
303 int numberFound = 0;
304
305 // Iterate points along the line from -2*vecCenterMagnitude to +2*vecCenterMagnitude
306 const double DOUBLE_PLUS_EXTRA = 2.1;
307 double maxRadius = DOUBLE_PLUS_EXTRA * (magnitude (vecCenter) + radius);
308 QPointF posStart = posOriginScreen - 2 * maxRadius * normalize (vecCenter);
309 QPointF posStop = posOriginScreen + 2 * maxRadius * normalize (vecCenter);
310 for (int i = 0; i < NUM_LINE_POINTS; i++) {
311 double sPrevious = (double) i / (double) NUM_LINE_POINTS;
312 double sNext = (double) (i + 1) / (double) NUM_LINE_POINTS;
313
314 QPointF posPrevious = (1.0 - sPrevious) * posStart + sPrevious * posStop;
315 QPointF posNext = (1.0 - sNext) * posStart + sNext * posStop;
316
317 double distancePrevious = magnitude (posPrevious - posClickScreen());
318 double distanceNext = magnitude (posNext - posClickScreen());
319
320 if ((distancePrevious < radius && radius <= distanceNext) ||
321 (distancePrevious > radius && radius >= distanceNext)) {
322
323 if (numberFound == 0) {
324 posLow = (posPrevious + posNext) / 2.0; // Average for accuracy
325 } else if (numberFound == 1) {
326 posHigh = (posPrevious + posNext) / 2.0; // Average for accuracy
327 break; // Done
328 }
329
330 ++numberFound;
331 }
332 }
333}
const int NUM_LINE_POINTS
double magnitude(const QPointF &vec)
Norm of vector.
Definition mmsubs.cpp:193
QPointF normalize(const QPointF &vec)
Return normalized vector.
Definition mmsubs.cpp:198

The documentation for this class was generated from the following files: