KiCad PCB EDA Suite
Loading...
Searching...
No Matches
point_editor_behavior.cpp
Go to the documentation of this file.
1/*
2 * This program source code file is part of KICAD, a free EDA CAD application.
3 *
4 * Copyright The KiCad Developers, see AUTHORS.txt for contributors.
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version 2
9 * of the License, or (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, you may find one here:
18 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
19 * or you may search the http://www.gnu.org website for the version 2 license,
20 * or you may write to the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
22 */
23
25
26#include <advanced_config.h>
27#include <commit.h>
29
30
32 const SHAPE_POLY_SET& aOutline )
33{
34 const int cornersCount = aOutline.TotalVertices();
35
36 for( auto iterator = aOutline.CIterateWithHoles(); iterator; iterator++ )
37 {
38 aPoints.AddPoint( *iterator );
39
40 if( iterator.IsEndContour() )
41 aPoints.AddBreak();
42 }
43
44 // Lines have to be added after creating edit points, as they use EDIT_POINT references
45 for( int i = 0; i < cornersCount - 1; ++i )
46 {
47 if( aPoints.IsContourEnd( i ) )
48 aPoints.AddLine( aPoints.Point( i ), aPoints.Point( aPoints.GetContourStartIdx( i ) ) );
49 else
50 aPoints.AddLine( aPoints.Point( i ), aPoints.Point( i + 1 ) );
51
52 aPoints.Line( i ).SetConstraint( new EC_PERPLINE( aPoints.Line( i ) ) );
53 }
54
55 // The last missing line, connecting the last and the first polygon point
56 aPoints.AddLine( aPoints.Point( cornersCount - 1 ),
57 aPoints.Point( aPoints.GetContourStartIdx( cornersCount - 1 ) ) );
58
59 aPoints.Line( aPoints.LinesSize() - 1 )
60 .SetConstraint( new EC_PERPLINE( aPoints.Line( aPoints.LinesSize() - 1 ) ) );
61}
62
63
65 EDIT_POINTS& aPoints )
66{
67 // No size check here, as we can and will rebuild if that fails
68 if( aPoints.PointsSize() != (unsigned) aOutline.TotalVertices() )
69 {
70 // Rebuild the points list
71 aPoints.Clear();
72 BuildForPolyOutline( aPoints, aOutline );
73 }
74 else
75 {
76 for( int i = 0; i < aOutline.TotalVertices(); ++i )
77 {
78 aPoints.Point( i ).SetPosition( aOutline.CVertex( i ) );
79 }
80 }
81}
82
83
85 const EDIT_POINT& aEditedPoint,
86 EDIT_POINTS& aPoints )
87{
88 CHECK_POINT_COUNT_GE( aPoints, (unsigned) aOutline.TotalVertices() );
89
90 for( int i = 0; i < aOutline.TotalVertices(); ++i )
91 {
92 aOutline.SetVertex( i, aPoints.Point( i ).GetPosition() );
93 }
94
95 for( unsigned i = 0; i < aPoints.LinesSize(); ++i )
96 {
97 if( !isModified( aEditedPoint, aPoints.Line( i ) ) )
98 {
99 aPoints.Line( i ).SetConstraint( new EC_PERPLINE( aPoints.Line( i ) ) );
100 }
101 }
102}
103
104
106{
107 m_polygon.RemoveNullSegments();
108}
109
111{
112 aPoints.AddPoint( m_segment.GetStart() );
113 aPoints.AddPoint( m_segment.GetEnd() );
114}
115
116
118{
120
121 aPoints.Point( SEGMENT_START ) = m_segment.GetStart();
122 aPoints.Point( SEGMENT_END ) = m_segment.GetEnd();
123}
124
125
127 EDIT_POINTS& aPoints, COMMIT& aCommit,
128 std::vector<EDA_ITEM*>& aUpdatedItems )
129{
131
132 if( isModified( aEditedPoint, aPoints.Point( SEGMENT_START ) ) )
133 m_segment.SetStart( aPoints.Point( SEGMENT_START ).GetPosition() );
134
135 else if( isModified( aEditedPoint, aPoints.Point( SEGMENT_END ) ) )
136 m_segment.SetEnd( aPoints.Point( SEGMENT_END ).GetPosition() );
137}
138
141 EDIT_POINTS& aPoints ) const
142{
143 // Select the other end of line
144 return aPoints.Next( aEditedPoint )->GetPosition();
145}
146
147
149{
150 aPoints.AddPoint( m_circle.getCenter() );
151 aPoints.AddPoint( m_circle.GetEnd() );
152}
153
154
156{
158
159 aPoints.Point( CIRC_CENTER ).SetPosition( m_circle.getCenter() );
160 aPoints.Point( CIRC_END ).SetPosition( m_circle.GetEnd() );
161}
162
163
165 EDIT_POINTS& aPoints, COMMIT& aCommit,
166 std::vector<EDA_ITEM*>& aUpdatedItems )
167{
169
170 const VECTOR2I& center = aPoints.Point( CIRC_CENTER ).GetPosition();
171 const VECTOR2I& end = aPoints.Point( CIRC_END ).GetPosition();
172
173 if( isModified( aEditedPoint, aPoints.Point( CIRC_CENTER ) ) )
174 {
175 m_circle.SetCenter( center );
176 }
177 else
178 {
179 m_circle.SetEnd( VECTOR2I( end.x, end.y ) );
180 }
181}
182
183
186 EDIT_POINTS& aPoints ) const
187{
188 return aPoints.Point( CIRC_CENTER ).GetPosition();
189}
190
191
193{
194 aPoints.AddPoint( m_bezier.GetStart() );
195 aPoints.AddPoint( m_bezier.GetBezierC1() );
196 aPoints.AddPoint( m_bezier.GetBezierC2() );
197 aPoints.AddPoint( m_bezier.GetEnd() );
198
199 aPoints.AddIndicatorLine( aPoints.Point( BEZIER_START ), aPoints.Point( BEZIER_CTRL_PT1 ) );
200 aPoints.AddIndicatorLine( aPoints.Point( BEZIER_CTRL_PT2 ), aPoints.Point( BEZIER_END ) );
201}
202
203
205{
207
208 aPoints.Point( BEZIER_START ).SetPosition( m_bezier.GetStart() );
209 aPoints.Point( BEZIER_CTRL_PT1 ).SetPosition( m_bezier.GetBezierC1() );
210 aPoints.Point( BEZIER_CTRL_PT2 ).SetPosition( m_bezier.GetBezierC2() );
211 aPoints.Point( BEZIER_END ).SetPosition( m_bezier.GetEnd() );
212}
213
214
216 EDIT_POINTS& aPoints, COMMIT& aCommit,
217 std::vector<EDA_ITEM*>& aUpdatedItems )
218{
220
221 if( isModified( aEditedPoint, aPoints.Point( BEZIER_START ) ) )
222 {
223 m_bezier.SetStart( aPoints.Point( BEZIER_START ).GetPosition() );
224 }
225 else if( isModified( aEditedPoint, aPoints.Point( BEZIER_CTRL_PT1 ) ) )
226 {
227 m_bezier.SetBezierC1( aPoints.Point( BEZIER_CTRL_PT1 ).GetPosition() );
228 }
229 else if( isModified( aEditedPoint, aPoints.Point( BEZIER_CTRL_PT2 ) ) )
230 {
231 m_bezier.SetBezierC2( aPoints.Point( BEZIER_CTRL_PT2 ).GetPosition() );
232 }
233 else if( isModified( aEditedPoint, aPoints.Point( BEZIER_END ) ) )
234 {
235 m_bezier.SetEnd( aPoints.Point( BEZIER_END ).GetPosition() );
236 }
237
238 m_bezier.RebuildBezierToSegmentsPointsList( m_maxError );
239}
240
241
242// Note: these static arc functions don't have to be in here - we could ship them out
243// to a utils area for use by other code (e.g. polygon fillet editing).
244
248static void editArcEndpointKeepTangent( EDA_SHAPE& aArc, const VECTOR2I& aCenter, const VECTOR2I& aStart,
249 const VECTOR2I& aMid, const VECTOR2I& aEnd, const VECTOR2I& aCursor )
250{
251 VECTOR2I center = aCenter;
252 bool movingStart;
253 bool arcValid = true;
254
255 VECTOR2I p1, p2, p3;
256 // p1 does not move, p2 does.
257
258 if( aStart != aArc.GetStart() )
259 {
260 p1 = aEnd;
261 p2 = aStart;
262 p3 = aMid;
263 movingStart = true;
264 }
265 else if( aEnd != aArc.GetEnd() )
266 {
267 p1 = aStart;
268 p2 = aEnd;
269 p3 = aMid;
270 movingStart = false;
271 }
272 else
273 {
274 return;
275 }
276
277 VECTOR2D v1, v2, v3, v4;
278
279 // Move the coordinate system
280 v1 = p1 - aCenter;
281 v2 = p2 - aCenter;
282 v3 = p3 - aCenter;
283
284 VECTOR2D u1, u2;
285
286 // A point cannot be both the center and on the arc.
287 if( ( v1.EuclideanNorm() == 0 ) || ( v2.EuclideanNorm() == 0 ) )
288 return;
289
290 u1 = v1 / v1.EuclideanNorm();
291 u2 = v3 - ( u1.x * v3.x + u1.y * v3.y ) * u1;
292 u2 = u2 / u2.EuclideanNorm();
293
294 // [ u1, u3 ] is a base centered on the circle with:
295 // u1 : unit vector toward the point that does not move
296 // u2 : unit vector toward the mid point.
297
298 // Get vectors v1, and v2 in that coordinate system.
299
300 double det = u1.x * u2.y - u2.x * u1.y;
301
302 // u1 and u2 are unit vectors, and perpendicular.
303 // det should not be 0. In case it is, do not change the arc.
304 if( det == 0 )
305 return;
306
307 double tmpx = v1.x * u2.y - v1.y * u2.x;
308 double tmpy = -v1.x * u1.y + v1.y * u1.x;
309 v1.x = tmpx;
310 v1.y = tmpy;
311 v1 = v1 / det;
312
313 tmpx = v2.x * u2.y - v2.y * u2.x;
314 tmpy = -v2.x * u1.y + v2.y * u1.x;
315 v2.x = tmpx;
316 v2.y = tmpy;
317 v2 = v2 / det;
318
319 double R = v1.EuclideanNorm();
320 bool transformCircle = false;
321
322 /* p2
323 * X***
324 * ** <---- This is the arc
325 * y ^ **
326 * | R *
327 * | <-----------> *
328 * x------x------>--------x p1
329 * C' <----> C x
330 * delta
331 *
332 * p1 does not move, and the tangent at p1 remains the same.
333 * => The new center, C', will be on the C-p1 axis.
334 * p2 moves
335 *
336 * The radius of the new circle is delta + R
337 *
338 * || C' p2 || = || C' P1 ||
339 * is the same as :
340 * ( delta + p2.x ) ^ 2 + p2.y ^ 2 = ( R + delta ) ^ 2
341 *
342 * delta = ( R^2 - p2.x ^ 2 - p2.y ^2 ) / ( 2 * p2.x - 2 * R )
343 *
344 * We can use this equation for any point p2 with p2.x < R
345 */
346
347 if( v2.x == R )
348 {
349 // Straight line, do nothing
350 }
351 else
352 {
353 if( v2.x > R )
354 {
355 // If we need to invert the curvature.
356 // We modify the input so we can use the same equation
357 transformCircle = true;
358 v2.x = 2 * R - v2.x;
359 }
360
361 // We can keep the tangent constraint.
362 double delta = ( R * R - v2.x * v2.x - v2.y * v2.y ) / ( 2 * v2.x - 2 * R );
363
364 // This is just to limit the radius, so nothing overflows later when drawing.
365 if( abs( v2.y / ( R - v2.x ) ) > ADVANCED_CFG::GetCfg().m_DrawArcCenterMaxAngle )
366 arcValid = false;
367
368 // Never recorded a problem, but still checking.
369 if( !std::isfinite( delta ) )
370 arcValid = false;
371
372 // v4 is the new center
373 v4 = ( !transformCircle ) ? VECTOR2D( -delta, 0 ) : VECTOR2D( 2 * R + delta, 0 );
374
375 tmpx = v4.x * u1.x + v4.y * u2.x;
376 tmpy = v4.x * u1.y + v4.y * u2.y;
377 v4.x = tmpx;
378 v4.y = tmpy;
379
380 center = v4 + aCenter;
381
382 if( arcValid )
383 {
384 aArc.SetCenter( center );
385
386 if( movingStart )
387 aArc.SetStart( aStart );
388 else
389 aArc.SetEnd( aEnd );
390 }
391 }
392}
393
394
398static void editArcCenterKeepEndpoints( EDA_SHAPE& aArc, const VECTOR2I& aCenter, const VECTOR2I& aStart,
399 const VECTOR2I& aMid, const VECTOR2I& aEnd )
400{
401 const int c_snapEpsilon_sq = 4;
402
403 VECTOR2I m = ( aStart / 2 + aEnd / 2 );
404 VECTOR2I perp = ( aEnd - aStart ).Perpendicular().Resize( INT_MAX / 2 );
405
406 SEG legal( m - perp, m + perp );
407
408 const SEG testSegments[] = {
409 SEG( aCenter, aCenter + VECTOR2( 1, 0 ) ),
410 SEG( aCenter, aCenter + VECTOR2( 0, 1 ) ),
411 };
412
413 std::vector<VECTOR2I> points = { legal.A, legal.B };
414
415 for( const SEG& seg : testSegments )
416 {
417 OPT_VECTOR2I vec = legal.IntersectLines( seg );
418
419 if( vec && legal.SquaredDistance( *vec ) <= c_snapEpsilon_sq )
420 points.push_back( *vec );
421 }
422
423 OPT_VECTOR2I nearest;
425
426 // Snap by distance between cursor and intersections
427 for( const VECTOR2I& pt : points )
428 {
429 SEG::ecoord d_sq = ( pt - aCenter ).SquaredEuclideanNorm();
430
431 if( d_sq < min_d_sq - c_snapEpsilon_sq )
432 {
433 min_d_sq = d_sq;
434 nearest = pt;
435 }
436 }
437
438 if( nearest )
439 aArc.SetCenter( *nearest );
440}
441
442
446static void editArcEndpointKeepCenter( EDA_SHAPE& aArc, const VECTOR2I& aCenter, const VECTOR2I& aStart,
447 const VECTOR2I& aMid, const VECTOR2I& aEnd, const VECTOR2I& aCursor )
448{
449 int minRadius = EDA_UNIT_UTILS::Mils2IU( pcbIUScale, 1 );
450 bool movingStart;
451
452 VECTOR2I p1, p2, prev_p1;
453
454 // user is moving p1, we want to move p2 to the new radius.
455
456 if( aStart != aArc.GetStart() )
457 {
458 prev_p1 = aArc.GetStart();
459 p1 = aStart;
460 p2 = aEnd;
461 movingStart = true;
462 }
463 else
464 {
465 prev_p1 = aArc.GetEnd();
466 p1 = aEnd;
467 p2 = aStart;
468 movingStart = false;
469 }
470
471 p1 = p1 - aCenter;
472 p2 = p2 - aCenter;
473
474 if( p1.x == 0 && p1.y == 0 )
475 p1 = prev_p1 - aCenter;
476
477 if( p2.x == 0 && p2.y == 0 )
478 p2 = { 1, 0 };
479
480 double radius = p1.EuclideanNorm();
481
482 if( radius < minRadius )
483 radius = minRadius;
484
485 p1 = aCenter + p1.Resize( radius );
486 p2 = aCenter + p2.Resize( radius );
487
488 aArc.SetCenter( aCenter );
489
490 if( movingStart )
491 {
492 aArc.SetStart( p1 );
493 aArc.SetEnd( p2 );
494 }
495 else
496 {
497 aArc.SetStart( p2 );
498 aArc.SetEnd( p1 );
499 }
500}
501
502
503static void editArcEndpointKeepCenterAndRadius( EDA_SHAPE& aArc, const VECTOR2I& aCenter, const VECTOR2I& aStart,
504 const VECTOR2I& aMid, const VECTOR2I& aEnd )
505{
506 VECTOR2I p1;
507 bool movingStart = false;
508
509 // User is moving p1, we need to update whichever end that is
510 // The other end won't move.
511
512 if( aStart != aArc.GetStart() )
513 {
514 p1 = aStart;
515 movingStart = true;
516 }
517 else
518 {
519 p1 = aEnd;
520 movingStart = false;
521 }
522
523 // Do not change the radius
524 p1 = p1 - aCenter;
525 p1 = aCenter + p1.Resize( aArc.GetRadius() );
526
527 if( movingStart )
528 {
529 aArc.SetStart( p1 );
530 }
531 else
532 {
533 aArc.SetEnd( p1 );
534 }
535}
536
537
541static void editArcMidKeepCenter( EDA_SHAPE& aArc, const VECTOR2I& aCenter, const VECTOR2I& aStart,
542 const VECTOR2I& aMid, const VECTOR2I& aEnd, const VECTOR2I& aCursor )
543{
544 int minRadius = EDA_UNIT_UTILS::Mils2IU( pcbIUScale, 1 );
545
546 SEG chord( aStart, aEnd );
547
548 // Now, update the edit point position
549 // Express the point in a circle-centered coordinate system.
550 VECTOR2I start = aStart - aCenter;
551 VECTOR2I end = aEnd - aCenter;
552
553 double radius = ( aCursor - aCenter ).EuclideanNorm();
554
555 if( radius < minRadius )
556 radius = minRadius;
557
558 start = start.Resize( radius );
559 end = end.Resize( radius );
560
561 start = start + aCenter;
562 end = end + aCenter;
563
564 aArc.SetStart( start );
565 aArc.SetEnd( end );
566}
567
568
572static void editArcMidKeepEndpoints( EDA_SHAPE& aArc, const VECTOR2I& aStart, const VECTOR2I& aEnd,
573 const VECTOR2I& aCursor )
574{
575 // Let 'm' be the middle point of the chord between the start and end points
576 VECTOR2I m = ( aStart + aEnd ) / 2;
577
578 // Legal midpoints lie on a vector starting just off the chord midpoint and extending out
579 // past the existing midpoint. We do not allow arc inflection while point editing.
580 const int JUST_OFF = ( aStart - aEnd ).EuclideanNorm() / 100;
581 VECTOR2I v = (VECTOR2I) aArc.GetArcMid() - m;
582 SEG legal( m + v.Resize( JUST_OFF ), m + v.Resize( INT_MAX / 2 ) );
583 VECTOR2I mid = legal.NearestPoint( aCursor );
584
585 aArc.SetArcGeometry( aStart, mid, aEnd );
586}
587
588
590 KIGFX::VIEW_CONTROLS& aViewContols ) :
591 m_arc( aArc ), m_arcEditMode( aArcEditMode ), m_viewControls( aViewContols )
592{
593 wxASSERT( m_arc.GetShape() == SHAPE_T::ARC );
594}
595
596
598{
599 aPoints.AddPoint( m_arc.GetStart() );
600 aPoints.AddPoint( m_arc.GetArcMid() );
601 aPoints.AddPoint( m_arc.GetEnd() );
602 aPoints.AddPoint( m_arc.getCenter() );
603
604 aPoints.AddIndicatorLine( aPoints.Point( ARC_CENTER ), aPoints.Point( ARC_START ) );
605 aPoints.AddIndicatorLine( aPoints.Point( ARC_CENTER ), aPoints.Point( ARC_END ) );
606}
607
608
610{
611 CHECK_POINT_COUNT( aPoints, 4 );
612
613 aPoints.Point( ARC_START ).SetPosition( m_arc.GetStart() );
614 aPoints.Point( ARC_MID ).SetPosition( m_arc.GetArcMid() );
615 aPoints.Point( ARC_END ).SetPosition( m_arc.GetEnd() );
616 aPoints.Point( ARC_CENTER ).SetPosition( m_arc.getCenter() );
617}
618
619
620void EDA_ARC_POINT_EDIT_BEHAVIOR::UpdateItem( const EDIT_POINT& aEditedPoint, EDIT_POINTS& aPoints, COMMIT& aCommit,
621 std::vector<EDA_ITEM*>& aUpdatedItems )
622{
623 CHECK_POINT_COUNT( aPoints, 4 );
624
626 VECTOR2I mid = aPoints.Point( ARC_MID ).GetPosition();
627 VECTOR2I start = aPoints.Point( ARC_START ).GetPosition();
628 VECTOR2I end = aPoints.Point( ARC_END ).GetPosition();
629
630 if( isModified( aEditedPoint, aPoints.Point( ARC_CENTER ) ) )
631 {
632 switch( m_arcEditMode )
633 {
636 break;
639 {
640 // Both these modes just move the arc
641 VECTOR2I moveVector = VECTOR2I( center.x, center.y ) - m_arc.getCenter();
642
643 m_arc.SetArcGeometry( m_arc.GetStart() + moveVector, m_arc.GetArcMid() + moveVector,
644 m_arc.GetEnd() + moveVector );
645 break;
646 }
647 }
648 }
649 else if( isModified( aEditedPoint, aPoints.Point( ARC_MID ) ) )
650 {
651 const VECTOR2I& cursorPos = m_viewControls.GetCursorPosition( false );
652
653 switch( m_arcEditMode )
654 {
656 editArcMidKeepEndpoints( m_arc, start, end, cursorPos );
657 break;
660 editArcMidKeepCenter( m_arc, center, start, mid, end, cursorPos );
661 break;
662 }
663 }
664 else if( isModified( aEditedPoint, aPoints.Point( ARC_START ) )
665 || isModified( aEditedPoint, aPoints.Point( ARC_END ) ) )
666 {
667 const VECTOR2I& cursorPos = m_viewControls.GetCursorPosition();
668
669 switch( m_arcEditMode )
670 {
672 editArcEndpointKeepCenter( m_arc, center, start, mid, end, cursorPos );
673 break;
676 break;
678 editArcEndpointKeepTangent( m_arc, center, start, mid, end, cursorPos );
679 break;
680 }
681 }
682}
683
684
686 EDIT_POINTS& aPoints ) const
687{
688 return aPoints.Point( ARC_CENTER ).GetPosition();
689}
690
691
693{
694 aPoints.AddPoint( m_cell.GetEnd() - VECTOR2I( 0, m_cell.GetRectangleHeight() / 2 ) );
695 aPoints.AddPoint( m_cell.GetEnd() - VECTOR2I( m_cell.GetRectangleWidth() / 2, 0 ) );
696}
697
698
700{
701 aPoints.Point( COL_WIDTH )
702 .SetPosition( m_cell.GetEnd() - VECTOR2I( 0, m_cell.GetRectangleHeight() / 2 ) );
703 aPoints.Point( ROW_HEIGHT )
704 .SetPosition( m_cell.GetEnd() - VECTOR2I( m_cell.GetRectangleWidth() / 2, 0 ) );
705}
706
707
ARC_EDIT_MODE
Settings for arc editing.
@ KEEP_ENDPOINTS_OR_START_DIRECTION
Whe editing endpoints, the other end remains in place.
@ KEEP_CENTER_ENDS_ADJUST_ANGLE
When editing endpoints, only the angle is adjusted.
@ KEEP_CENTER_ADJUST_ANGLE_RADIUS
When editing endpoints, the angle and radius are adjusted.
constexpr EDA_IU_SCALE pcbIUScale
Definition base_units.h:112
static const ADVANCED_CFG & GetCfg()
Get the singleton instance's config, which is shared by all consumers.
Represent a set of changes (additions, deletions or modifications) of a data model (e....
Definition commit.h:72
EDIT_CONSTRAINT for a EDIT_LINE, that constrains the line to move perpendicular to the line itself.
const ARC_EDIT_MODE & m_arcEditMode
void UpdateItem(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints, COMMIT &aCommit, std::vector< EDA_ITEM * > &aUpdatedItems) override
Update the item with the new positions of the edit points.
void MakePoints(EDIT_POINTS &aPoints) override
Construct the initial set of edit points for the item and append to the given list.
OPT_VECTOR2I Get45DegreeConstrainer(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints) const override
Get the 45-degree constrainer for the item, when the given point is moved.
KIGFX::VIEW_CONTROLS & m_viewControls
EDA_ARC_POINT_EDIT_BEHAVIOR(EDA_SHAPE &aArc, const ARC_EDIT_MODE &aArcEditMode, KIGFX::VIEW_CONTROLS &aViewContols)
void UpdatePoints(EDIT_POINTS &aPoints) override
Update the list of the edit points for the item.
void UpdateItem(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints, COMMIT &aCommit, std::vector< EDA_ITEM * > &aUpdatedItems) override
Update the item with the new positions of the edit points.
void MakePoints(EDIT_POINTS &aPoints) override
Construct the initial set of edit points for the item and append to the given list.
void UpdatePoints(EDIT_POINTS &aPoints) override
Update the list of the edit points for the item.
OPT_VECTOR2I Get45DegreeConstrainer(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints) const override
Get the 45-degree constrainer for the item, when the given point is moved.
void UpdateItem(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints, COMMIT &aCommit, std::vector< EDA_ITEM * > &aUpdatedItems) override
Update the item with the new positions of the edit points.
void UpdatePoints(EDIT_POINTS &aPoints) override
Update the list of the edit points for the item.
void MakePoints(EDIT_POINTS &aPoints) override
Construct the initial set of edit points for the item and append to the given list.
OPT_VECTOR2I Get45DegreeConstrainer(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints) const override
Get the 45-degree constrainer for the item, when the given point is moved.
void UpdatePoints(EDIT_POINTS &aPoints) override
Update the list of the edit points for the item.
void MakePoints(EDIT_POINTS &aPoints) override
Construct the initial set of edit points for the item and append to the given list.
void UpdateItem(const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints, COMMIT &aCommit, std::vector< EDA_ITEM * > &aUpdatedItems) override
Update the item with the new positions of the edit points.
void SetCenter(const VECTOR2I &aCenter)
int GetRadius() const
const VECTOR2I & GetEnd() const
Return the ending point of the graphic.
Definition eda_shape.h:215
void SetStart(const VECTOR2I &aStart)
Definition eda_shape.h:177
const VECTOR2I & GetStart() const
Return the starting point of the graphic.
Definition eda_shape.h:173
void SetEnd(const VECTOR2I &aEnd)
Definition eda_shape.h:219
void SetArcGeometry(const VECTOR2I &aStart, const VECTOR2I &aMid, const VECTOR2I &aEnd)
Set the three controlling points for an arc.
VECTOR2I GetArcMid() const
void MakePoints(EDIT_POINTS &aPoints) override
Construct the initial set of edit points for the item and append to the given list.
void UpdatePoints(EDIT_POINTS &aPoints) override
Update the list of the edit points for the item.
void SetConstraint(EDIT_CONSTRAINT< EDIT_LINE > *aConstraint)
Set a constraint for and EDIT_POINT.
EDIT_POINTS is a VIEW_ITEM that manages EDIT_POINTs and EDIT_LINEs and draws them.
unsigned int PointsSize() const
Return number of stored EDIT_POINTs.
void AddPoint(const EDIT_POINT &aPoint)
Add an EDIT_POINT.
void Clear()
Clear all stored EDIT_POINTs and EDIT_LINEs.
EDIT_POINT * Next(const EDIT_POINT &aPoint, bool aTraverseContours=true)
Return the point that is before the given point in the list.
EDIT_LINE & Line(unsigned int aIndex)
bool IsContourEnd(int aPointIdx) const
Check is a point with given index is a contour finish.
void AddIndicatorLine(EDIT_POINT &aOrigin, EDIT_POINT &aEnd)
Adds an EDIT_LINE that is shown as an indicator, rather than an editable line (no center point drag,...
void AddBreak()
Adds a break, indicating the end of a contour.
int GetContourStartIdx(int aPointIdx) const
Return index of the contour origin for a point with given index.
unsigned int LinesSize() const
Return number of stored EDIT_LINEs.
EDIT_POINT & Point(unsigned int aIndex)
void AddLine(const EDIT_LINE &aLine)
Adds an EDIT_LINE.
Represent a single point that can be used for modifying items.
Definition edit_points.h:48
virtual void SetPosition(const VECTOR2I &aPosition)
Set new coordinates for an EDIT_POINT.
virtual VECTOR2I GetPosition() const
Return coordinates of an EDIT_POINT.
Definition edit_points.h:72
An interface for classes handling user events controlling the view behavior such as zooming,...
static bool isModified(const EDIT_POINT &aEditedPoint, const EDIT_POINT &aPoint)
Checks if two points are the same instance - which means the point is being edited.
static void UpdateOutlineFromPoints(SHAPE_POLY_SET &aOutline, const EDIT_POINT &aEditedPoint, EDIT_POINTS &aPoints)
Update the polygon outline with the new positions of the edit points.
static void UpdatePointsFromOutline(const SHAPE_POLY_SET &aOutline, EDIT_POINTS &aPoints)
Update the edit points with the current polygon outline.
void FinalizeItem(EDIT_POINTS &aPoints, COMMIT &aCommit) override
Finalize the edit operation.
static void BuildForPolyOutline(EDIT_POINTS &aPoints, const SHAPE_POLY_SET &aOutline)
Build the edit points for the given polygon outline.
Definition seg.h:42
VECTOR2I A
Definition seg.h:49
ecoord SquaredDistance(const SEG &aSeg) const
Definition seg.cpp:80
VECTOR2I::extended_type ecoord
Definition seg.h:44
VECTOR2I B
Definition seg.h:50
const VECTOR2I NearestPoint(const VECTOR2I &aP) const
Compute a point on the segment (this) that is closest to point aP.
Definition seg.cpp:604
OPT_VECTOR2I IntersectLines(const SEG &aSeg) const
Compute the intersection point of lines passing through ends of (this) and aSeg.
Definition seg.h:220
Represent a set of closed polygons.
void SetVertex(const VERTEX_INDEX &aIndex, const VECTOR2I &aPos)
Accessor function to set the position of a specific point.
int TotalVertices() const
Return total number of vertices stored in the set.
const VECTOR2I & CVertex(int aIndex, int aOutline, int aHole) const
Return the index-th vertex in a given hole outline within a given outline.
CONST_ITERATOR CIterateWithHoles(int aOutline) const
Define a general 2D-vector/point.
Definition vector2d.h:71
static constexpr extended_type ECOORD_MAX
Definition vector2d.h:76
T EuclideanNorm() const
Compute the Euclidean norm of the vector, which is defined as sqrt(x ** 2 + y ** 2).
Definition vector2d.h:283
VECTOR2< T > Resize(T aNewLength) const
Return a vector of the same direction, but length specified in aNewLength.
Definition vector2d.h:385
constexpr int Mils2IU(const EDA_IU_SCALE &aIuScale, int mils)
Definition eda_units.h:166
static void editArcEndpointKeepCenterAndRadius(EDA_SHAPE &aArc, const VECTOR2I &aCenter, const VECTOR2I &aStart, const VECTOR2I &aMid, const VECTOR2I &aEnd)
static void editArcEndpointKeepCenter(EDA_SHAPE &aArc, const VECTOR2I &aCenter, const VECTOR2I &aStart, const VECTOR2I &aMid, const VECTOR2I &aEnd, const VECTOR2I &aCursor)
Move an end point of the arc around the circumference.
ARC_EDIT_MODE IncrementArcEditMode(ARC_EDIT_MODE aMode)
static void editArcCenterKeepEndpoints(EDA_SHAPE &aArc, const VECTOR2I &aCenter, const VECTOR2I &aStart, const VECTOR2I &aMid, const VECTOR2I &aEnd)
Move the arc center but keep endpoint locations.
static void editArcMidKeepEndpoints(EDA_SHAPE &aArc, const VECTOR2I &aStart, const VECTOR2I &aEnd, const VECTOR2I &aCursor)
Move the mid point of the arc, while keeping the angle.
static void editArcMidKeepCenter(EDA_SHAPE &aArc, const VECTOR2I &aCenter, const VECTOR2I &aStart, const VECTOR2I &aMid, const VECTOR2I &aEnd, const VECTOR2I &aCursor)
Move the mid point of the arc, while keeping the two endpoints.
static void editArcEndpointKeepTangent(EDA_SHAPE &aArc, const VECTOR2I &aCenter, const VECTOR2I &aStart, const VECTOR2I &aMid, const VECTOR2I &aEnd, const VECTOR2I &aCursor)
Move an end point of the arc, while keeping the tangent at the other endpoint.
#define CHECK_POINT_COUNT(aPoints, aExpected)
#define CHECK_POINT_COUNT_GE(aPoints, aExpected)
std::optional< VECTOR2I > OPT_VECTOR2I
Definition seg.h:39
VECTOR3I v1(5, 5, 5)
VECTOR2I center
int radius
VECTOR2I end
VECTOR2I v2(1, 0)
VECTOR2I v4(1, 1)
VECTOR2I v3(-2, 1)
int delta
VECTOR2< int32_t > VECTOR2I
Definition vector2d.h:695
VECTOR2< double > VECTOR2D
Definition vector2d.h:694