KiCad PCB EDA Suite
Loading...
Searching...
No Matches
pcb_textbox.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 (C) 2022-2023 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
24#include <pcb_edit_frame.h>
25#include <base_units.h>
26#include <bitmaps.h>
27#include <board.h>
29#include <footprint.h>
30#include <pcb_textbox.h>
31#include <pcb_painter.h>
32#include <trigo.h>
33#include <string_utils.h>
35#include <callback_gal.h>
37#include <macros.h>
38#include <core/ignore.h>
39
40
42 PCB_SHAPE( aParent, aType, SHAPE_T::RECTANGLE ),
44 m_borderEnabled( true )
45{
48 SetMultilineAllowed( true );
49
50 int defaultMargin = GetLegacyTextMargin();
51 m_marginLeft = defaultMargin;
52 m_marginTop = defaultMargin;
53 m_marginRight = defaultMargin;
54 m_marginBottom = defaultMargin;
55}
56
57
59{
60}
61
62
64{
66
67 SetTextSize( settings.GetTextSize( GetLayer() ) );
69 SetItalic( settings.GetTextItalic( GetLayer() ) );
70 SetKeepUpright( settings.GetTextUpright( GetLayer() ) );
72}
73
74
76{
77 return KiROUND( GetStroke().GetWidth() / 2.0 ) + KiROUND( GetTextSize().y * 0.75 );
78}
79
80
82{
83 EDA_ANGLE rotation = GetDrawRotation();
84
85 if( rotation == ANGLE_90 )
86 return VECTOR2I( GetStartX(), GetEndY() );
87 else if( rotation == ANGLE_180 )
88 return GetEnd();
89 else if( rotation == ANGLE_270 )
90 return VECTOR2I( GetEndX(), GetStartY() );
91 else
92 return GetStart();
93}
94
95
97{
98 EDA_ANGLE rotation = GetDrawRotation();
99
100 if( rotation == ANGLE_90 )
101 return VECTOR2I( GetEndX(), GetStartY() );
102 else if( rotation == ANGLE_180 )
103 return GetStart();
104 else if( rotation == ANGLE_270 )
105 return VECTOR2I( GetStartX(), GetEndY() );
106 else
107 return GetEnd();
108}
109
110
111void PCB_TEXTBOX::SetTop( int aVal )
112{
113 EDA_ANGLE rotation = GetDrawRotation();
114
115 if( rotation == ANGLE_90 || rotation == ANGLE_180 )
116 SetEndY( aVal );
117 else
118 SetStartY( aVal );
119}
120
121
123{
124 EDA_ANGLE rotation = GetDrawRotation();
125
126 if( rotation == ANGLE_90 || rotation == ANGLE_180 )
127 SetStartY( aVal );
128 else
129 SetEndY( aVal );
130}
131
132
133void PCB_TEXTBOX::SetLeft( int aVal )
134{
135 EDA_ANGLE rotation = GetDrawRotation();
136
137 if( rotation == ANGLE_180 || rotation == ANGLE_270 )
138 SetEndX( aVal );
139 else
140 SetStartX( aVal );
141}
142
143
144void PCB_TEXTBOX::SetRight( int aVal )
145{
146 EDA_ANGLE rotation = GetDrawRotation();
147
148 if( rotation == ANGLE_180 || rotation == ANGLE_270 )
149 SetStartX( aVal );
150 else
151 SetEndX( aVal );
152}
153
154
156{
157 EDA_ANGLE delta = aAngle.Normalized() - GetTextAngle();
159}
160
161
162std::vector<VECTOR2I> PCB_TEXTBOX::GetAnchorAndOppositeCorner() const
163{
164 std::vector<VECTOR2I> pts;
165 EDA_ANGLE textAngle( GetDrawRotation() );
166
167 textAngle.Normalize();
168
169 if( textAngle.IsCardinal() )
170 {
172 bbox.Normalize();
173
174 if( textAngle == ANGLE_0 )
175 {
176 pts.emplace_back( VECTOR2I( bbox.GetLeft(), bbox.GetTop() ) );
177 pts.emplace_back( VECTOR2I( bbox.GetRight(), bbox.GetTop() ) );
178 }
179 else if( textAngle == ANGLE_90 )
180 {
181 pts.emplace_back( VECTOR2I( bbox.GetLeft(), bbox.GetBottom() ) );
182 pts.emplace_back( VECTOR2I( bbox.GetLeft(), bbox.GetTop() ) );
183 }
184 else if( textAngle == ANGLE_180 )
185 {
186 pts.emplace_back( VECTOR2I( bbox.GetRight(), bbox.GetBottom() ) );
187 pts.emplace_back( VECTOR2I( bbox.GetLeft(), bbox.GetBottom() ) );
188 }
189 else if( textAngle == ANGLE_270 )
190 {
191 pts.emplace_back( VECTOR2I( bbox.GetRight(), bbox.GetTop() ) );
192 pts.emplace_back( VECTOR2I( bbox.GetRight(), bbox.GetBottom() ) );
193 }
194 }
195 else
196 {
197 std::vector<VECTOR2I> corners = GetCorners();
198
199 VECTOR2I minX = corners[0];
200 VECTOR2I maxX = corners[0];
201 VECTOR2I minY = corners[0];
202 VECTOR2I maxY = corners[0];
203
204 for( const VECTOR2I& corner : corners )
205 {
206 if( corner.x < minX.x )
207 minX = corner;
208
209 if( corner.x > maxX.x )
210 maxX = corner;
211
212 if( corner.y < minY.y )
213 minY = corner;
214
215 if( corner.y > maxY.y )
216 maxY = corner;
217 }
218
219 if( textAngle < ANGLE_90 )
220 {
221 pts.emplace_back( minX );
222 pts.emplace_back( minY );
223 }
224 else if( textAngle < ANGLE_180 )
225 {
226 pts.emplace_back( maxY );
227 pts.emplace_back( minX );
228 }
229 else if( textAngle < ANGLE_270 )
230 {
231 pts.emplace_back( maxX );
232 pts.emplace_back( maxY );
233 }
234 else
235 {
236 pts.emplace_back( minY );
237 pts.emplace_back( maxX );
238 }
239 }
240
241 return pts;
242}
243
244
246{
247 std::vector<VECTOR2I> corners = GetAnchorAndOppositeCorner();
248 GR_TEXT_H_ALIGN_T effectiveAlignment = GetHorizJustify();
249 VECTOR2I textAnchor;
250 VECTOR2I offset;
251
252 if( IsMirrored() )
253 {
254 switch( GetHorizJustify() )
255 {
256 case GR_TEXT_H_ALIGN_LEFT: effectiveAlignment = GR_TEXT_H_ALIGN_RIGHT; break;
257 case GR_TEXT_H_ALIGN_CENTER: effectiveAlignment = GR_TEXT_H_ALIGN_CENTER; break;
258 case GR_TEXT_H_ALIGN_RIGHT: effectiveAlignment = GR_TEXT_H_ALIGN_LEFT; break;
259 case GR_TEXT_H_ALIGN_INDETERMINATE: wxFAIL_MSG( wxT( "Legal only in dialogs" ) ); break;
260 }
261 }
262
263 switch( effectiveAlignment )
264 {
266 textAnchor = corners[0];
267 offset = VECTOR2I( GetMarginLeft(), GetMarginTop() );
268 break;
270 textAnchor = ( corners[0] + corners[1] ) / 2;
271 offset = VECTOR2I( 0, GetMarginTop() );
272 break;
274 textAnchor = corners[1];
275 offset = VECTOR2I( -GetMarginRight(), GetMarginTop() );
276 break;
278 wxFAIL_MSG( wxT( "Indeterminate state legal only in dialogs." ) );
279 break;
280 }
281
282 RotatePoint( offset, GetDrawRotation() );
283 return textAnchor + offset;
284}
285
286
287double PCB_TEXTBOX::ViewGetLOD( int aLayer, KIGFX::VIEW* aView ) const
288{
289 constexpr double HIDE = std::numeric_limits<double>::max();
290
291 KIGFX::PCB_PAINTER* painter = static_cast<KIGFX::PCB_PAINTER*>( aView->GetPainter() );
292 KIGFX::PCB_RENDER_SETTINGS* renderSettings = painter->GetSettings();
293
294 if( aLayer == LAYER_LOCKED_ITEM_SHADOW )
295 {
296 // Hide shadow if the main layer is not shown
297 if( !aView->IsLayerVisible( m_layer ) )
298 return HIDE;
299
300 // Hide shadow on dimmed tracks
301 if( renderSettings->GetHighContrast() )
302 {
303 if( m_layer != renderSettings->GetPrimaryHighContrastLayer() )
304 return HIDE;
305 }
306 }
307
308 return 0.0;
309}
310
311
312void PCB_TEXTBOX::ViewGetLayers( int aLayers[], int& aCount ) const
313{
314 aLayers[0] = GetLayer();
315 aCount = 1;
316
317 if( IsLocked() )
318 aLayers[ aCount++ ] = LAYER_LOCKED_ITEM_SHADOW;
319}
320
321
322wxString PCB_TEXTBOX::GetShownText( bool aAllowExtraText, int aDepth ) const
323{
324 BOARD* board = dynamic_cast<BOARD*>( GetParent() );
325
326 std::function<bool( wxString* )> pcbTextResolver =
327 [&]( wxString* token ) -> bool
328 {
329 if( token->IsSameAs( wxT( "LAYER" ) ) )
330 {
331 *token = GetLayerName();
332 return true;
333 }
334
335 if( board->ResolveTextVar( token, aDepth + 1 ) )
336 {
337 return true;
338 }
339
340 return false;
341 };
342
343 wxString text = EDA_TEXT::GetShownText( aAllowExtraText, aDepth );
344
345 if( board && HasTextVars() && aDepth < 10 )
346 text = ExpandTextVars( text, &pcbTextResolver );
347
348 KIFONT::FONT* font = getDrawFont();
349 std::vector<VECTOR2I> corners = GetAnchorAndOppositeCorner();
350 int colWidth = ( corners[1] - corners[0] ).EuclideanNorm();
351
352 if( GetTextAngle().IsHorizontal() )
353 colWidth -= ( GetMarginLeft() + GetMarginRight() );
354 else
355 colWidth -= ( GetMarginTop() + GetMarginBottom() );
356
357 font->LinebreakText( text, colWidth, GetTextSize(), GetTextThickness(), IsBold(), IsItalic() );
358
359 return text;
360}
361
362
363bool PCB_TEXTBOX::Matches( const EDA_SEARCH_DATA& aSearchData, void* aAuxData ) const
364{
365 return BOARD_ITEM::Matches( UnescapeString( GetText() ), aSearchData );
366}
367
368
369void PCB_TEXTBOX::GetMsgPanelInfo( EDA_DRAW_FRAME* aFrame, std::vector<MSG_PANEL_ITEM>& aList )
370{
371 // Don't use GetShownText() here; we want to show the user the variable references
372 aList.emplace_back( _( "Text Box" ), KIUI::EllipsizeStatusText( aFrame, GetText() ) );
373
374 if( aFrame->GetName() == PCB_EDIT_FRAME_NAME && IsLocked() )
375 aList.emplace_back( _( "Status" ), _( "Locked" ) );
376
377 aList.emplace_back( _( "Layer" ), GetLayerName() );
378 aList.emplace_back( _( "Mirror" ), IsMirrored() ? _( "Yes" ) : _( "No" ) );
379 aList.emplace_back( _( "Angle" ), wxString::Format( "%g", GetTextAngle().AsDegrees() ) );
380
381 aList.emplace_back( _( "Font" ), GetFont() ? GetFont()->GetName() : _( "Default" ) );
382 aList.emplace_back( _( "Text Thickness" ), aFrame->MessageTextFromValue( GetTextThickness() ) );
383 aList.emplace_back( _( "Text Width" ), aFrame->MessageTextFromValue( GetTextWidth() ) );
384 aList.emplace_back( _( "Text Height" ), aFrame->MessageTextFromValue( GetTextHeight() ) );
385
386 aList.emplace_back( _( "Box Width" ),
387 aFrame->MessageTextFromValue( std::abs( GetEnd().x - GetStart().x ) ) );
388
389 aList.emplace_back( _( "Box Height" ),
390 aFrame->MessageTextFromValue( std::abs( GetEnd().y - GetStart().y ) ));
391
392 m_stroke.GetMsgPanelInfo( aFrame, aList );
393}
394
395
396void PCB_TEXTBOX::Move( const VECTOR2I& aMoveVector )
397{
398 PCB_SHAPE::Move( aMoveVector );
399 EDA_TEXT::Offset( aMoveVector );
400}
401
402
403void PCB_TEXTBOX::Rotate( const VECTOR2I& aRotCentre, const EDA_ANGLE& aAngle )
404{
405 PCB_SHAPE::Rotate( aRotCentre, aAngle );
406 EDA_TEXT::SetTextAngle( ( GetTextAngle() + aAngle ).Normalized() );
407
408 if( GetTextAngle().IsCardinal() && GetShape() != SHAPE_T::RECTANGLE )
409 {
410 std::vector<VECTOR2I> corners = GetCorners();
411 VECTOR2I diag = corners[2] - corners[0];
412 EDA_ANGLE angle = GetTextAngle();
413
414 SetShape( SHAPE_T::RECTANGLE );
415 SetStart( corners[0] );
416
417 angle.Normalize();
418
419 if( angle == ANGLE_90 )
420 SetEnd( VECTOR2I( corners[0].x + abs( diag.x ), corners[0].y - abs( diag.y ) ) );
421 else if( angle == ANGLE_180 )
422 SetEnd( VECTOR2I( corners[0].x - abs( diag.x ), corners[0].y - abs( diag.y ) ) );
423 else if( angle == ANGLE_270 )
424 SetEnd( VECTOR2I( corners[0].x - abs( diag.x ), corners[0].y + abs( diag.y ) ) );
425 else
426 SetEnd( VECTOR2I( corners[0].x + abs( diag.x ), corners[0].y + abs( diag.y ) ) );
427 }
428}
429
430
431void PCB_TEXTBOX::Mirror( const VECTOR2I& aCentre, bool aMirrorAroundXAxis )
432{
433 // the position and angle are mirrored, but not the text (or its justification)
434 PCB_SHAPE::Mirror( aCentre, aMirrorAroundXAxis );
435
436 if( aMirrorAroundXAxis )
438 else
440}
441
442
443void PCB_TEXTBOX::Flip( const VECTOR2I& aCentre, bool aFlipLeftRight )
444{
445 PCB_SHAPE::Flip( aCentre, aFlipLeftRight );
446
447 if( aFlipLeftRight )
449 else
451
452 if( ( GetLayerSet() & LSET::SideSpecificMask() ).any() )
454}
455
456
457bool PCB_TEXTBOX::HitTest( const VECTOR2I& aPosition, int aAccuracy ) const
458{
459 BOX2I rect = GetBoundingBox();
460
461 rect.Inflate( aAccuracy );
462
463 return rect.Contains( aPosition );
464}
465
466
467bool PCB_TEXTBOX::HitTest( const BOX2I& aRect, bool aContained, int aAccuracy ) const
468{
469 BOX2I rect = aRect;
470
471 rect.Inflate( aAccuracy );
472
473 if( aContained )
474 return rect.Contains( GetBoundingBox() );
475
476 return rect.Intersects( GetBoundingBox() );
477}
478
479
480wxString PCB_TEXTBOX::GetItemDescription( UNITS_PROVIDER* aUnitsProvider ) const
481{
482 return wxString::Format( _( "PCB Text Box '%s' on %s" ),
484 GetLayerName() );
485}
486
487
489{
490 return BITMAPS::add_textbox;
491}
492
493
495{
496 return new PCB_TEXTBOX( *this );
497}
498
499
501{
502 wxASSERT( aImage->Type() == PCB_TEXTBOX_T );
503
504 std::swap( *((PCB_TEXTBOX*) this), *((PCB_TEXTBOX*) aImage) );
505}
506
507
508std::shared_ptr<SHAPE> PCB_TEXTBOX::GetEffectiveShape( PCB_LAYER_ID aLayer, FLASHING aFlash ) const
509{
510 std::shared_ptr<SHAPE_COMPOUND> shape = GetEffectiveTextShape();
511
512 if( PCB_SHAPE::GetStroke().GetWidth() >= 0 )
513 shape->AddShape( PCB_SHAPE::GetEffectiveShape( aLayer, aFlash ) );
514
515 return shape;
516}
517
518
519void PCB_TEXTBOX::TransformTextToPolySet( SHAPE_POLY_SET& aBuffer, int aClearance, int aMaxError,
520 ERROR_LOC aErrorLoc ) const
521{
523 KIFONT::FONT* font = getDrawFont();
524 int penWidth = GetEffectiveTextPenWidth();
525
526 // Note: this function is mainly used in 3D viewer.
527 // the polygonal shape of a text can have many basic shapes,
528 // so combining these shapes can be very useful to create a final shape
529 // swith a lot less vertices to speedup calculations using this final shape
530 // Simplify shapes is not usually always efficient, but in this case it is.
531 SHAPE_POLY_SET buffer;
532
533 CALLBACK_GAL callback_gal( empty_opts,
534 // Stroke callback
535 [&]( const VECTOR2I& aPt1, const VECTOR2I& aPt2 )
536 {
537 TransformOvalToPolygon( buffer, aPt1, aPt2, penWidth, aMaxError, aErrorLoc );
538 },
539 // Triangulation callback
540 [&]( const VECTOR2I& aPt1, const VECTOR2I& aPt2, const VECTOR2I& aPt3 )
541 {
542 buffer.NewOutline();
543
544 for( const VECTOR2I& point : { aPt1, aPt2, aPt3 } )
545 buffer.Append( point.x, point.y );
546 } );
547
548 font->Draw( &callback_gal, GetShownText( true ), GetDrawPos(), GetAttributes(), GetFontMetrics() );
549
550 if( aClearance > 0 || aErrorLoc == ERROR_OUTSIDE )
551 {
552 if( aErrorLoc == ERROR_OUTSIDE )
553 aClearance += aMaxError;
554
555 buffer.Inflate( aClearance, CORNER_STRATEGY::ROUND_ALL_CORNERS, aMaxError, true );
556 }
557 else
558 {
560 }
561
562 aBuffer.Append( buffer );
563}
564
565
567 int aClearance, int aMaxError, ERROR_LOC aErrorLoc,
568 bool aIgnoreLineWidth ) const
569{
570 // Don't use PCB_SHAPE::TransformShapeToPolygon. We want to treat the textbox as filled even
571 // if there's no background colour.
572
573 int width = GetWidth() + ( 2 * aClearance );
574
575 if( GetShape() == SHAPE_T::RECTANGLE )
576 {
577 std::vector<VECTOR2I> pts = GetRectCorners();
578
579 aBuffer.NewOutline();
580
581 for( const VECTOR2I& pt : pts )
582 aBuffer.Append( pt );
583
584 if( m_borderEnabled && width > 0 )
585 {
586 // Add in segments
587 TransformOvalToPolygon( aBuffer, pts[0], pts[1], width, aMaxError, aErrorLoc );
588 TransformOvalToPolygon( aBuffer, pts[1], pts[2], width, aMaxError, aErrorLoc );
589 TransformOvalToPolygon( aBuffer, pts[2], pts[3], width, aMaxError, aErrorLoc );
590 TransformOvalToPolygon( aBuffer, pts[3], pts[0], width, aMaxError, aErrorLoc );
591 }
592 }
593 else if( GetShape() == SHAPE_T::POLY ) // Non-cardinally-rotated rect
594 {
595 aBuffer.NewOutline();
596
597 const SHAPE_LINE_CHAIN& poly = m_poly.Outline( 0 );
598
599 for( int ii = 0; ii < poly.PointCount(); ++ii )
600 aBuffer.Append( poly.GetPoint( ii ) );
601
602 if( m_borderEnabled && width > 0 )
603 {
604 for( int ii = 0; ii < poly.SegmentCount(); ++ii )
605 {
606 const SEG& seg = poly.GetSegment( ii );
607 TransformOvalToPolygon( aBuffer, seg.A, seg.B, width, aMaxError, aErrorLoc );
608 }
609 }
610 }
611}
612
613
615{
616 return m_borderEnabled;
617}
618
619
621{
622 m_borderEnabled = enabled;
623}
624
625
626void PCB_TEXTBOX::SetBorderWidth( const int aSize )
627{
628 m_stroke.SetWidth( aSize );
629}
630
631
632
633bool PCB_TEXTBOX::operator==( const BOARD_ITEM& aBoardItem ) const
634{
635 if( aBoardItem.Type() != Type() )
636 return false;
637
638 const PCB_TEXTBOX& other = static_cast<const PCB_TEXTBOX&>( aBoardItem );
639
640 return m_borderEnabled == other.m_borderEnabled && EDA_TEXT::operator==( other );
641}
642
643
644double PCB_TEXTBOX::Similarity( const BOARD_ITEM& aBoardItem ) const
645{
646 if( aBoardItem.Type() != Type() )
647 return 0.0;
648
649 const PCB_TEXTBOX& other = static_cast<const PCB_TEXTBOX&>( aBoardItem );
650
651 double similarity = 1.0;
652
653 if( m_borderEnabled != other.m_borderEnabled )
654 similarity *= 0.9;
655
656 if( GetMarginLeft() != other.GetMarginLeft() )
657 similarity *= 0.9;
658
659 if( GetMarginTop() != other.GetMarginTop() )
660 similarity *= 0.9;
661
662 if( GetMarginRight() != other.GetMarginRight() )
663 similarity *= 0.9;
664
665 if( GetMarginBottom() != other.GetMarginBottom() )
666 similarity *= 0.9;
667
668 similarity *= EDA_TEXT::Similarity( other );
669
670 return similarity;
671}
672
673
674static struct PCB_TEXTBOX_DESC
675{
677 {
679
680 if( plotDashTypeEnum.Choices().GetCount() == 0 )
681 {
682 plotDashTypeEnum.Map( LINE_STYLE::DEFAULT, _HKI( "Default" ) )
683 .Map( LINE_STYLE::SOLID, _HKI( "Solid" ) )
684 .Map( LINE_STYLE::DASH, _HKI( "Dashed" ) )
685 .Map( LINE_STYLE::DOT, _HKI( "Dotted" ) )
686 .Map( LINE_STYLE::DASHDOT, _HKI( "Dash-Dot" ) )
687 .Map( LINE_STYLE::DASHDOTDOT, _HKI( "Dash-Dot-Dot" ) );
688 }
689
696
697 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "Shape" ) );
698 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "Start X" ) );
699 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "Start Y" ) );
700 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "End X" ) );
701 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "End Y" ) );
702 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "Line Width" ) );
703 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_SHAPE ), _HKI( "Line Style" ) );
704 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_TEXT ), _HKI( "Visible" ) );
705 propMgr.Mask( TYPE_HASH( PCB_TEXTBOX ), TYPE_HASH( EDA_TEXT ), _HKI( "Color" ) );
706
707 const wxString borderProps = _( "Border Properties" );
708
709 void ( PCB_TEXTBOX::*lineStyleSetter )( LINE_STYLE ) = &PCB_TEXTBOX::SetLineStyle;
710 LINE_STYLE ( PCB_TEXTBOX::*lineStyleGetter )() const = &PCB_TEXTBOX::GetLineStyle;
711
712 propMgr.AddProperty( new PROPERTY<PCB_TEXTBOX, bool>( _HKI( "Border" ),
714 borderProps );
715
716 propMgr.AddProperty( new PROPERTY_ENUM<PCB_TEXTBOX, LINE_STYLE>( _HKI( "Border Style" ),
717 lineStyleSetter, lineStyleGetter ),
718 borderProps );
719
720 propMgr.AddProperty( new PROPERTY<PCB_TEXTBOX, int>( _HKI( "Border Width" ),
722 PROPERTY_DISPLAY::PT_SIZE ),
723 borderProps );
724
725 const wxString marginProps = _( "Margins" );
726
727 propMgr.AddProperty( new PROPERTY<PCB_TEXTBOX, int>( _HKI( "Margin Left" ),
729 PROPERTY_DISPLAY::PT_SIZE ),
730 marginProps );
731 propMgr.AddProperty( new PROPERTY<PCB_TEXTBOX, int>( _HKI( "Margin Top" ),
733 PROPERTY_DISPLAY::PT_SIZE ),
734 marginProps );
735 propMgr.AddProperty( new PROPERTY<PCB_TEXTBOX, int>( _HKI( "Margin Right" ),
737 PROPERTY_DISPLAY::PT_SIZE ),
738 marginProps );
739 propMgr.AddProperty( new PROPERTY<PCB_TEXTBOX, int>( _HKI( "Margin Bottom" ),
741 PROPERTY_DISPLAY::PT_SIZE ),
742 marginProps );
743
744 }
constexpr EDA_IU_SCALE pcbIUScale
Definition: base_units.h:108
BITMAPS
A list of all bitmap identifiers.
Definition: bitmaps_list.h:33
Container for design settings for a BOARD object.
bool GetTextUpright(PCB_LAYER_ID aLayer) const
int GetTextThickness(PCB_LAYER_ID aLayer) const
Return the default text thickness from the layer class for the given layer.
bool GetTextItalic(PCB_LAYER_ID aLayer) const
VECTOR2I GetTextSize(PCB_LAYER_ID aLayer) const
Return the default text size from the layer class for the given layer.
A base class for any item which can be embedded within the BOARD container class, and therefore insta...
Definition: board_item.h:77
PCB_LAYER_ID m_layer
Definition: board_item.h:398
virtual LSET GetLayerSet() const
Return a std::bitset of all layers on which the item physically resides.
Definition: board_item.h:236
const KIFONT::METRICS & GetFontMetrics() const
Definition: board_item.cpp:97
virtual bool IsLocked() const
Definition: board_item.cpp:74
BOARD_ITEM_CONTAINER * GetParent() const
Definition: board_item.h:209
wxString GetLayerName() const
Return the name of the PCB layer on which the item resides.
Definition: board_item.cpp:103
Information pertinent to a Pcbnew printed circuit board.
Definition: board.h:282
bool ResolveTextVar(wxString *token, int aDepth) const
Definition: board.cpp:421
BOX2< Vec > & Normalize()
Ensure that the height and width are positive.
Definition: box2.h:136
bool Intersects(const BOX2< Vec > &aRect) const
Definition: box2.h:294
coord_type GetTop() const
Definition: box2.h:219
bool Contains(const Vec &aPoint) const
Definition: box2.h:158
BOX2< Vec > & Inflate(coord_type dx, coord_type dy)
Inflates the rectangle horizontally by dx and vertically by dy.
Definition: box2.h:541
coord_type GetRight() const
Definition: box2.h:207
coord_type GetLeft() const
Definition: box2.h:218
coord_type GetBottom() const
Definition: box2.h:212
EDA_ANGLE Normalize()
Definition: eda_angle.h:221
bool IsHorizontal() const
Definition: eda_angle.h:138
bool IsCardinal() const
Definition: eda_angle.cpp:40
EDA_ANGLE Normalized() const
Definition: eda_angle.h:232
The base class for create windows for drawing purpose.
A base class for most all the KiCad significant classes used in schematics and boards.
Definition: eda_item.h:88
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:100
virtual bool Matches(const EDA_SEARCH_DATA &aSearchData, void *aAuxData) const
Compare the item against the search criteria in aSearchData.
Definition: eda_item.h:375
void SetStartX(int x)
Definition: eda_shape.h:146
int GetStartY() const
Definition: eda_shape.h:131
void SetEndY(int aY)
Definition: eda_shape.h:177
int GetEndX() const
Definition: eda_shape.h:169
void SetLineStyle(const LINE_STYLE aStyle)
Definition: eda_shape.cpp:1810
void SetStartY(int y)
Definition: eda_shape.h:140
SHAPE_T GetShape() const
Definition: eda_shape.h:125
int GetEndY() const
Definition: eda_shape.h:168
void SetEndX(int aX)
Definition: eda_shape.h:183
const VECTOR2I & GetEnd() const
Return the ending point of the graphic.
Definition: eda_shape.h:167
void SetStart(const VECTOR2I &aStart)
Definition: eda_shape.h:134
LINE_STYLE GetLineStyle() const
Definition: eda_shape.cpp:1816
const VECTOR2I & GetStart() const
Return the starting point of the graphic.
Definition: eda_shape.h:130
void SetShape(SHAPE_T aShape)
Definition: eda_shape.h:124
std::vector< VECTOR2I > GetRectCorners() const
Definition: eda_shape.cpp:1161
void SetEnd(const VECTOR2I &aEnd)
Definition: eda_shape.h:171
int GetStartX() const
Definition: eda_shape.h:132
SHAPE_POLY_SET m_poly
Definition: eda_shape.h:437
STROKE_PARAMS m_stroke
Definition: eda_shape.h:417
A mix-in class (via multiple inheritance) that handles texts such as labels, parts,...
Definition: eda_text.h:83
int GetTextHeight() const
Definition: eda_text.h:228
bool IsItalic() const
Definition: eda_text.h:144
const EDA_ANGLE & GetTextAngle() const
Definition: eda_text.h:134
void SetTextSize(VECTOR2I aNewSize, bool aEnforceMinTextSize=true)
Definition: eda_text.cpp:372
virtual const wxString & GetText() const
Return the string associated with the text object.
Definition: eda_text.h:98
KIFONT::FONT * GetFont() const
Definition: eda_text.h:211
void SetMirrored(bool isMirrored)
Definition: eda_text.cpp:250
virtual EDA_ANGLE GetDrawRotation() const
Definition: eda_text.h:340
int GetTextWidth() const
Definition: eda_text.h:225
void SetVertJustify(GR_TEXT_V_ALIGN_T aType)
Definition: eda_text.cpp:274
void Offset(const VECTOR2I &aOffset)
Definition: eda_text.cpp:435
GR_TEXT_H_ALIGN_T GetHorizJustify() const
Definition: eda_text.h:164
bool HasTextVars() const
Indicates the ShownText has text var references which need to be processed.
Definition: eda_text.h:117
virtual KIFONT::FONT * getDrawFont() const
Definition: eda_text.cpp:480
double Similarity(const EDA_TEXT &aOther) const
Definition: eda_text.cpp:1141
void SetTextThickness(int aWidth)
The TextThickness is that set by the user.
Definition: eda_text.cpp:195
const TEXT_ATTRIBUTES & GetAttributes() const
Definition: eda_text.h:195
bool IsMirrored() const
Definition: eda_text.h:154
int GetEffectiveTextPenWidth(int aDefaultPenWidth=0) const
The EffectiveTextPenWidth uses the text thickness if > 1 or aDefaultPenWidth.
Definition: eda_text.cpp:322
std::shared_ptr< SHAPE_COMPOUND > GetEffectiveTextShape(bool aTriangulate=true, const BOX2I &aBBox=BOX2I(), const EDA_ANGLE &aAngle=ANGLE_0) const
build a list of segments (SHAPE_SEGMENT) to describe a text shape.
Definition: eda_text.cpp:982
bool IsBold() const
Definition: eda_text.h:148
void SetKeepUpright(bool aKeepUpright)
Definition: eda_text.cpp:282
virtual wxString GetShownText(bool aAllowExtraText, int aDepth=0) const
Return the string actually shown after processing of the base text.
Definition: eda_text.h:109
virtual void SetTextAngle(const EDA_ANGLE &aAngle)
Definition: eda_text.cpp:203
int GetTextThickness() const
Definition: eda_text.h:126
void SetItalic(bool aItalic)
Definition: eda_text.cpp:211
bool operator==(const EDA_TEXT &aRhs) const
Definition: eda_text.h:357
void SetMultilineAllowed(bool aAllow)
Definition: eda_text.cpp:258
VECTOR2I GetTextSize() const
Definition: eda_text.h:222
void SetHorizJustify(GR_TEXT_H_ALIGN_T aType)
Definition: eda_text.cpp:266
ENUM_MAP & Map(T aValue, const wxString &aName)
Definition: property.h:669
static ENUM_MAP< T > & Instance()
Definition: property.h:663
wxPGChoices & Choices()
Definition: property.h:712
FONT is an abstract base class for both outline and stroke fonts.
Definition: font.h:131
void Draw(KIGFX::GAL *aGal, const wxString &aText, const VECTOR2I &aPosition, const VECTOR2I &aCursor, const TEXT_ATTRIBUTES &aAttributes, const METRICS &aFontMetrics) const
Draw a string.
Definition: font.cpp:257
void LinebreakText(wxString &aText, int aColumnWidth, const VECTOR2I &aGlyphSize, int aThickness, bool aBold, bool aItalic) const
Insert characters into text to ensure that no lines are wider than aColumnWidth.
Definition: font.cpp:588
Contains methods for drawing PCB-specific items.
Definition: pcb_painter.h:174
virtual PCB_RENDER_SETTINGS * GetSettings() override
Return a pointer to current settings that are going to be used when drawing items.
Definition: pcb_painter.h:179
PCB specific render settings.
Definition: pcb_painter.h:78
PCB_LAYER_ID GetPrimaryHighContrastLayer() const
Return the board layer which is in high-contrast mode.
bool GetHighContrast() const
Hold a (potentially large) number of VIEW_ITEMs and renders them on a graphics device provided by the...
Definition: view.h:68
bool IsLayerVisible(int aLayer) const
Return information about visibility of a particular layer.
Definition: view.h:412
PAINTER * GetPainter() const
Return the painter object used by the view for drawing #VIEW_ITEMS.
Definition: view.h:215
static LSET SideSpecificMask()
Definition: lset.cpp:998
const BOX2I GetBoundingBox() const override
Return the orthogonal bounding box of this object for display purposes.
Definition: pcb_shape.h:115
void Flip(const VECTOR2I &aCentre, bool aFlipLeftRight) override
Flip this object, i.e.
Definition: pcb_shape.cpp:530
void Rotate(const VECTOR2I &aRotCentre, const EDA_ANGLE &aAngle) override
Rotate this object.
Definition: pcb_shape.cpp:524
int GetWidth() const override
Definition: pcb_shape.cpp:367
std::shared_ptr< SHAPE > GetEffectiveShape(PCB_LAYER_ID aLayer=UNDEFINED_LAYER, FLASHING aFlash=FLASHING::DEFAULT) const override
Make a set of SHAPE objects representing the PCB_SHAPE.
Definition: pcb_shape.cpp:740
virtual std::vector< VECTOR2I > GetCorners() const
Return 4 corners for a rectangle or rotated rectangle (stored as a poly).
Definition: pcb_shape.cpp:425
STROKE_PARAMS GetStroke() const override
Definition: pcb_shape.h:85
void StyleFromSettings(const BOARD_DESIGN_SETTINGS &settings) override
Definition: pcb_shape.cpp:377
void Move(const VECTOR2I &aMoveVector) override
Move this object.
Definition: pcb_shape.cpp:453
virtual void Mirror(const VECTOR2I &aCentre, bool aMirrorAroundXAxis)
Definition: pcb_shape.cpp:538
VECTOR2I GetPosition() const override
Definition: pcb_shape.h:73
PCB_LAYER_ID GetLayer() const override
Return the primary layer this item is on.
Definition: pcb_shape.h:70
bool HitTest(const VECTOR2I &aPosition, int aAccuracy) const override
Test if aPosition is inside or on the boundary of this item.
virtual void swapData(BOARD_ITEM *aImage) override
void SetBorderWidth(const int aSize)
double Similarity(const BOARD_ITEM &aBoardItem) const override
Return a measure of how likely the other object is to represent the same object.
bool IsBorderEnabled() const
Disables the border, this is done by changing the stroke internally.
BITMAPS GetMenuImage() const override
Return a pointer to an image to be used in menus.
int GetMarginBottom() const
Definition: pcb_textbox.h:87
PCB_TEXTBOX(BOARD_ITEM *aParent, KICAD_T aType=PCB_TEXTBOX_T)
Definition: pcb_textbox.cpp:41
void TransformShapeToPolygon(SHAPE_POLY_SET &aBuffer, PCB_LAYER_ID aLayer, int aClearance, int aMaxError, ERROR_LOC aErrorLoc, bool aIgnoreLineWidth=false) const override
Convert the shape to a closed polygon.
void Rotate(const VECTOR2I &aRotCentre, const EDA_ANGLE &aAngle) override
Rotate this object.
bool m_borderEnabled
Controls drawing the border (as defined by the stroke members)
Definition: pcb_textbox.h:166
int m_marginLeft
Definition: pcb_textbox.h:173
int m_marginBottom
Definition: pcb_textbox.h:176
bool operator==(const BOARD_ITEM &aBoardItem) const override
void SetBorderEnabled(bool enabled)
void TransformTextToPolySet(SHAPE_POLY_SET &aBuffer, int aClearance, int aMaxError, ERROR_LOC aErrorLoc) const
Function TransformTextToPolySet Convert the text to a polygonSet describing the actual character stro...
int m_marginRight
Definition: pcb_textbox.h:175
std::vector< VECTOR2I > GetAnchorAndOppositeCorner() const
EDA_ITEM * Clone() const override
Tests whether the border is disabled, as configured by the stroke.
std::shared_ptr< SHAPE > GetEffectiveShape(PCB_LAYER_ID aLayer=UNDEFINED_LAYER, FLASHING aFlash=FLASHING::DEFAULT) const override
Make a set of SHAPE objects representing the PCB_SHAPE.
wxString GetItemDescription(UNITS_PROVIDER *aUnitsProvider) const override
Return a user-visible description string of this item.
bool Matches(const EDA_SEARCH_DATA &aSearchData, void *aAuxData) const override
Compare the item against the search criteria in aSearchData.
VECTOR2I GetDrawPos() const override
void GetMsgPanelInfo(EDA_DRAW_FRAME *aFrame, std::vector< MSG_PANEL_ITEM > &aList) override
Populate aList of MSG_PANEL_ITEM objects with it's internal state for display purposes.
void SetMarginTop(int aTop)
Definition: pcb_textbox.h:80
void SetLeft(int aVal) override
int GetMarginLeft() const
Definition: pcb_textbox.h:84
void SetMarginLeft(int aLeft)
Definition: pcb_textbox.h:79
void SetMarginBottom(int aBottom)
Definition: pcb_textbox.h:82
double ViewGetLOD(int aLayer, KIGFX::VIEW *aView) const override
Return the level of detail (LOD) of the item.
int GetMarginRight() const
Definition: pcb_textbox.h:86
void SetRight(int aVal) override
void SetTop(int aVal) override
int GetMarginTop() const
Definition: pcb_textbox.h:85
wxString GetShownText(bool aAllowExtraText, int aDepth=0) const override
Return the string actually shown after processing of the base text.
void SetTextAngle(const EDA_ANGLE &aAngle) override
void SetMarginRight(int aRight)
Definition: pcb_textbox.h:81
void Move(const VECTOR2I &aMoveVector) override
Move this object.
int GetLegacyTextMargin() const
Definition: pcb_textbox.cpp:75
void SetBottom(int aVal) override
void Mirror(const VECTOR2I &aCentre, bool aMirrorAroundXAxis) override
void Flip(const VECTOR2I &aCentre, bool aFlipLeftRight) override
Flip this object, i.e.
VECTOR2I GetTopLeft() const override
Definition: pcb_textbox.cpp:81
VECTOR2I GetBotRight() const override
Definition: pcb_textbox.cpp:96
int GetBorderWidth() const
Definition: pcb_textbox.h:159
void StyleFromSettings(const BOARD_DESIGN_SETTINGS &settings) override
Definition: pcb_textbox.cpp:63
void ViewGetLayers(int aLayers[], int &aCount) const override
Provide class metadata.Helper macro to map type hashes to names.
Definition: property_mgr.h:85
void InheritsAfter(TYPE_ID aDerived, TYPE_ID aBase)
Declare an inheritance relationship between types.
void Mask(TYPE_ID aDerived, TYPE_ID aBase, const wxString &aName)
Sets a base class property as masked in a derived class.
static PROPERTY_MANAGER & Instance()
Definition: property_mgr.h:87
PROPERTY_BASE & AddProperty(PROPERTY_BASE *aProperty, const wxString &aGroup=wxEmptyString)
Register a property.
void AddTypeCast(TYPE_CAST_BASE *aCast)
Register a type converter.
Definition: seg.h:42
VECTOR2I A
Definition: seg.h:49
VECTOR2I B
Definition: seg.h:50
Represent a polyline containing arcs as well as line segments: A chain of connected line and/or arc s...
virtual const VECTOR2I GetPoint(int aIndex) const override
int PointCount() const
Return the number of points (vertices) in this line chain.
virtual const SEG GetSegment(int aIndex) const override
int SegmentCount() const
Return the number of segments in this line chain.
Represent a set of closed polygons.
void Inflate(int aAmount, CORNER_STRATEGY aCornerStrategy, int aMaxError, bool aSimplify=false)
Perform outline inflation/deflation.
int Append(int x, int y, int aOutline=-1, int aHole=-1, bool aAllowDuplication=false)
Appends a vertex at the end of the given outline/hole (default: the last outline)
void Simplify(POLYGON_MODE aFastMode)
Simplify the polyset (merges overlapping polys, eliminates degeneracy/self-intersections) For aFastMo...
SHAPE_LINE_CHAIN & Outline(int aIndex)
Return the reference to aIndex-th outline in the set.
int NewOutline()
Creates a new empty polygon in the set and returns its index.
void SetWidth(int aWidth)
Definition: stroke_params.h:92
void GetMsgPanelInfo(UNITS_PROVIDER *aUnitsProvider, std::vector< MSG_PANEL_ITEM > &aList, bool aIncludeStyle=true, bool aIncludeWidth=true)
wxString MessageTextFromValue(double aValue, bool aAddUnitLabel=true, EDA_DATA_TYPE aType=EDA_DATA_TYPE::DISTANCE) const
A lower-precision version of StringFromValue().
wxString ExpandTextVars(const wxString &aSource, const PROJECT *aProject)
Definition: common.cpp:58
void TransformOvalToPolygon(SHAPE_POLY_SET &aBuffer, const VECTOR2I &aStart, const VECTOR2I &aEnd, int aWidth, int aError, ERROR_LOC aErrorLoc, int aMinSegCount=0)
Convert a oblong shape to a polygon, using multiple segments.
#define _HKI(x)
#define _(s)
static constexpr EDA_ANGLE ANGLE_0
Definition: eda_angle.h:401
static constexpr EDA_ANGLE ANGLE_90
Definition: eda_angle.h:403
static constexpr EDA_ANGLE ANGLE_270
Definition: eda_angle.h:406
static constexpr EDA_ANGLE ANGLE_180
Definition: eda_angle.h:405
#define PCB_EDIT_FRAME_NAME
SHAPE_T
Definition: eda_shape.h:42
ERROR_LOC
When approximating an arc or circle, should the error be placed on the outside or inside of the curve...
@ ERROR_OUTSIDE
FLASHING
Enum used during connectivity building to ensure we do not query connectivity while building the data...
Definition: layer_ids.h:149
bool IsBackLayer(PCB_LAYER_ID aLayerId)
Layer classification: check if it's a back layer.
Definition: layer_ids.h:979
@ LAYER_LOCKED_ITEM_SHADOW
shadow layer for locked items
Definition: layer_ids.h:243
PCB_LAYER_ID
A quick note on layer IDs:
Definition: layer_ids.h:60
This file contains miscellaneous commonly used macros and functions.
KICOMMON_API wxString EllipsizeMenuText(const wxString &aString)
Ellipsize text (at the end) to be no more than 36 characters.
Definition: ui_common.cpp:213
KICOMMON_API wxString EllipsizeStatusText(wxWindow *aWindow, const wxString &aString)
Ellipsize text (at the end) to be no more than 1/3 of the window width.
Definition: ui_common.cpp:195
EDA_ANGLE abs(const EDA_ANGLE &aAngle)
Definition: eda_angle.h:390
static struct PCB_TEXTBOX_DESC _PCB_TEXTBOX_DESC
#define TYPE_HASH(x)
Definition: property.h:71
#define REGISTER_TYPE(x)
Definition: property_mgr.h:371
wxString UnescapeString(const wxString &aSource)
LINE_STYLE
Dashed line types.
Definition: stroke_params.h:48
constexpr int delta
GR_TEXT_H_ALIGN_T
@ GR_TEXT_H_ALIGN_CENTER
@ GR_TEXT_H_ALIGN_RIGHT
@ GR_TEXT_H_ALIGN_LEFT
@ GR_TEXT_H_ALIGN_INDETERMINATE
@ GR_TEXT_V_ALIGN_TOP
void RotatePoint(int *pX, int *pY, const EDA_ANGLE &aAngle)
Calculate the new point of coord coord pX, pY, for a rotation center 0, 0.
Definition: trigo.cpp:228
KICAD_T
The set of class identification values stored in EDA_ITEM::m_structType.
Definition: typeinfo.h:78
@ PCB_TEXTBOX_T
class PCB_TEXTBOX, wrapped text on a layer
Definition: typeinfo.h:93
constexpr ret_type KiROUND(fp_type v)
Round a floating point number to an integer using "round halfway cases away from zero".
Definition: util.h:118
VECTOR2< int32_t > VECTOR2I
Definition: vector2d.h:638