KiCad PCB EDA Suite
pcb_text.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) 2012 Jean-Pierre Charras, jean-pierre.charras@ujf-grenoble.fr
5  * Copyright (C) 2012 SoftPLC Corporation, Dick Hollenbeck <dick@softplc.com>
6  * Copyright (C) 1992-2020 KiCad Developers, see AUTHORS.txt for contributors.
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, you may find one here:
20  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
21  * or you may search the http://www.gnu.org website for the version 2 license,
22  * or you may write to the Free Software Foundation, Inc.,
23  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
24  */
25 
26 #include <eda_item.h>
27 #include <pcb_edit_frame.h>
28 #include <base_units.h>
29 #include <bitmaps.h>
30 #include <board.h>
31 #include <board_design_settings.h>
32 #include <core/mirror.h>
33 #include <footprint.h>
34 #include <pcb_text.h>
35 #include <pcb_painter.h>
36 #include <trigo.h>
37 #include <kicad_string.h>
39 
41 
42 
44  BOARD_ITEM( parent, PCB_TEXT_T ),
45  EDA_TEXT()
46 {
47  SetMultilineAllowed( true );
48 }
49 
50 
52 {
53 }
54 
55 
56 wxString PCB_TEXT::GetShownText( int aDepth ) const
57 {
58  BOARD* board = dynamic_cast<BOARD*>( GetParent() );
59 
60  std::function<bool( wxString* )> pcbTextResolver =
61  [&]( wxString* token ) -> bool
62  {
63  if( token->IsSameAs( wxT( "LAYER" ) ) )
64  {
65  *token = GetLayerName();
66  return true;
67  }
68 
69  if( token->Contains( ':' ) )
70  {
71  wxString remainder;
72  wxString ref = token->BeforeFirst( ':', &remainder );
73  BOARD_ITEM* refItem = board->GetItem( KIID( ref ) );
74 
75  if( refItem && refItem->Type() == PCB_FOOTPRINT_T )
76  {
77  FOOTPRINT* refFP = static_cast<FOOTPRINT*>( refItem );
78 
79  if( refFP->ResolveTextVar( &remainder, aDepth + 1 ) )
80  {
81  *token = remainder;
82  return true;
83  }
84  }
85  }
86  return false;
87  };
88 
89  std::function<bool( wxString* )> boardTextResolver =
90  [&]( wxString* token ) -> bool
91  {
92  return board->ResolveTextVar( token, aDepth + 1 );
93  };
94 
95  wxString text = EDA_TEXT::GetShownText();
96 
97  if( board && HasTextVars() && aDepth < 10 )
98  text = ExpandTextVars( text, &pcbTextResolver, &boardTextResolver, board->GetProject() );
99 
100  return text;
101 }
102 
103 
104 void PCB_TEXT::SetTextAngle( double aAngle )
105 {
107 }
108 
109 
110 void PCB_TEXT::GetMsgPanelInfo( EDA_DRAW_FRAME* aFrame, std::vector<MSG_PANEL_ITEM>& aList )
111 {
112  EDA_UNITS units = aFrame->GetUserUnits();
113 
114  // Don't use GetShownText() here; we want to show the user the variable references
115  aList.emplace_back( _( "PCB Text" ), UnescapeString( GetText() ) );
116 
117  if( IsLocked() )
118  aList.emplace_back( _( "Status" ), _( "Locked" ) );
119 
120  aList.emplace_back( _( "Layer" ), GetLayerName() );
121 
122  aList.emplace_back( _( "Mirror" ), IsMirrored() ? _( "Yes" ) : _( "No" ) );
123 
124  aList.emplace_back( _( "Angle" ), wxString::Format( "%g", GetTextAngleDegrees() ) );
125 
126  aList.emplace_back( _( "Thickness" ), MessageTextFromValue( units, GetTextThickness() ) );
127  aList.emplace_back( _( "Width" ), MessageTextFromValue( units, GetTextWidth() ) );
128  aList.emplace_back( _( "Height" ), MessageTextFromValue( units, GetTextHeight() ) );
129 }
130 
131 
133 {
134  EDA_RECT rect = GetTextBox();
135 
136  if( GetTextAngle() )
137  rect = rect.GetBoundingBoxRotated( GetTextPos(), GetTextAngle() );
138 
139  return rect;
140 }
141 
142 
143 bool PCB_TEXT::TextHitTest( const wxPoint& aPoint, int aAccuracy ) const
144 {
145  return EDA_TEXT::TextHitTest( aPoint, aAccuracy );
146 }
147 
148 
149 bool PCB_TEXT::TextHitTest( const EDA_RECT& aRect, bool aContains, int aAccuracy ) const
150 {
151  EDA_RECT rect = aRect;
152 
153  rect.Inflate( aAccuracy );
154 
155  if( aContains )
156  return rect.Contains( GetBoundingBox() );
157  else
158  return rect.Intersects( GetTextBox(), GetDrawRotation() );
159 }
160 
161 
162 void PCB_TEXT::Rotate( const wxPoint& aRotCentre, double aAngle )
163 {
164  wxPoint pt = GetTextPos();
165  RotatePoint( &pt, aRotCentre, aAngle );
166  SetTextPos( pt );
167 
168  SetTextAngle( GetTextAngle() + aAngle );
169 }
170 
171 
172 void PCB_TEXT::Flip( const wxPoint& aCentre, bool aFlipLeftRight )
173 {
174  if( aFlipLeftRight )
175  {
176  SetTextX( MIRRORVAL( GetTextPos().x, aCentre.x ) );
178  }
179  else
180  {
181  SetTextY( MIRRORVAL( GetTextPos().y, aCentre.y ) );
182  SetTextAngle( 1800 - GetTextAngle() );
183  }
184 
185  SetLayer( FlipLayer( GetLayer(), GetBoard()->GetCopperLayerCount() ) );
186  SetMirrored( !IsMirrored() );
187 }
188 
189 
190 wxString PCB_TEXT::GetSelectMenuText( EDA_UNITS aUnits ) const
191 {
192  return wxString::Format( _( "PCB Text '%s' on %s"), ShortenedShownText(), GetLayerName() );
193 }
194 
195 
197 {
198  return BITMAPS::text;
199 }
200 
201 
203 {
204  return new PCB_TEXT( *this );
205 }
206 
207 
209 {
210  assert( aImage->Type() == PCB_TEXT_T );
211 
212  std::swap( *((PCB_TEXT*) this), *((PCB_TEXT*) aImage) );
213 }
214 
215 
216 std::shared_ptr<SHAPE> PCB_TEXT::GetEffectiveShape( PCB_LAYER_ID aLayer ) const
217 {
218  return GetEffectiveTextShape();
219 }
220 
221 
222 static struct TEXTE_PCB_DESC
223 {
225  {
232  }
void SetMirrored(bool isMirrored)
Definition: eda_text.h:188
BOARD_ITEM * GetItem(const KIID &aID) const
Definition: board.cpp:867
wxString MessageTextFromValue(EDA_UNITS aUnits, int aValue, bool aAddUnitLabel, EDA_DATA_TYPE aType)
Convert a value to a string using double notation.
Definition: base_units.cpp:104
static PROPERTY_MANAGER & Instance()
Definition: property_mgr.h:65
#define TYPE_HASH(x)
Definition: property.h:59
bool TextHitTest(const wxPoint &aPoint, int aAccuracy=0) const override
Test if aPoint is within the bounds of this object.
Definition: pcb_text.cpp:143
bool IsMirrored() const
Definition: eda_text.h:189
virtual void SwapData(BOARD_ITEM *aImage) override
Swap data between aItem and aImage.
Definition: pcb_text.cpp:208
wxString ExpandTextVars(const wxString &aSource, const PROJECT *aProject)
Definition: common.cpp:64
void Flip(const wxPoint &aCentre, bool aFlipLeftRight) override
Flip this object, i.e.
Definition: pcb_text.cpp:172
BITMAPS GetMenuImage() const override
Return a pointer to an image to be used in menus.
Definition: pcb_text.cpp:196
virtual void SetLayer(PCB_LAYER_ID aLayer)
Set the layer this item is on.
Definition: board_item.h:192
Implementation of conversion functions that require both schematic and board internal units.
A base class for any item which can be embedded within the BOARD container class, and therefore insta...
Definition: board_item.h:80
void SetTextAngle(double aAngle) override
Definition: pcb_text.cpp:104
bool ResolveTextVar(wxString *token, int aDepth=0) const
Resolve any references to system tokens supported by the component.
Definition: footprint.cpp:436
PCB_LAYER_ID FlipLayer(PCB_LAYER_ID aLayerId, int aCopperLayersCount)
Definition: lset.cpp:521
EDA_RECT GetTextBox(int aLine=-1, bool aInvertY=false) const
Useful in multiline texts to calculate the full text or a line area (for zones filling,...
Definition: eda_text.cpp:229
void SetTextPos(const wxPoint &aPoint)
Definition: eda_text.h:246
PROJECT * GetProject() const
Definition: board.h:360
double GetTextAngle() const
Definition: eda_text.h:174
class PCB_TEXT, text on a layer
Definition: typeinfo.h:91
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.
Definition: pcb_text.cpp:110
virtual double GetDrawRotation() const
Definition: eda_text.cpp:646
void RotatePoint(int *pX, int *pY, double angle)
Definition: trigo.cpp:229
static struct TEXTE_PCB_DESC _TEXTE_PCB_DESC
int GetTextThickness() const
Definition: eda_text.h:160
The base class for create windows for drawing purpose.
virtual bool IsLocked() const
Definition: board_item.cpp:65
PCB_TEXT(BOARD_ITEM *parent)
Definition: pcb_text.cpp:43
#define REGISTER_TYPE(x)
Definition: property_mgr.h:248
bool Contains(const wxPoint &aPoint) const
Definition: eda_rect.cpp:57
virtual std::shared_ptr< SHAPE > GetEffectiveShape(PCB_LAYER_ID aLayer=UNDEFINED_LAYER) const override
Some pad shapes can be complex (rounded/chamfered rectangle), even without considering custom shapes.
Definition: pcb_text.cpp:216
int GetTextHeight() const
Definition: eda_text.h:244
void SetTextX(int aX)
Definition: eda_text.h:249
A mix-in class (via multiple inheritance) that handles texts such as labels, parts,...
Definition: eda_text.h:119
PCB specific render settings.
Definition: pcb_painter.h:64
wxString GetShownText(int aDepth=0) const override
Return the string actually shown after processing of the base text.
Definition: pcb_text.cpp:56
Definition: kiid.h:44
~PCB_TEXT()
Definition: pcb_text.cpp:51
PCB_LAYER_ID
A quick note on layer IDs:
bool HasTextVars() const
Indicates the ShownText has text var references which need to be processed.
Definition: eda_text.h:151
virtual BOARD * GetBoard() const
Return the BOARD in which this BOARD_ITEM resides, or NULL if none.
Definition: board_item.cpp:51
void InheritsAfter(TYPE_ID aDerived, TYPE_ID aBase)
Declare an inheritance relationship between types.
wxString ShortenedShownText() const
Returns a shortened version (max 15 characters) of the shown text.
Definition: eda_text.cpp:208
#define _(s)
wxString GetSelectMenuText(EDA_UNITS aUnits) const override
Return the text to display to be used in the selection clarification context menu when multiple items...
Definition: pcb_text.cpp:190
void SetMultilineAllowed(bool aAllow)
Definition: eda_text.h:195
class FOOTPRINT, a footprint
Definition: typeinfo.h:88
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Definition: ptree.cpp:200
EDA_UNITS
Definition: eda_units.h:38
double GetTextAngleDegrees() const
Definition: eda_text.h:176
int GetTextWidth() const
Definition: eda_text.h:241
BITMAPS
A list of all bitmap identifiers.
Definition: bitmaps_list.h:32
std::shared_ptr< SHAPE_COMPOUND > GetEffectiveTextShape() const
Definition: eda_text.cpp:633
Information pertinent to a Pcbnew printed circuit board.
Definition: board.h:190
wxString UnescapeString(const wxString &aSource)
Definition: string.cpp:222
void AddTypeCast(TYPE_CAST_BASE *aCast)
Register a type converter.
Handle the component boundary box.
Definition: eda_rect.h:42
virtual bool TextHitTest(const wxPoint &aPoint, int aAccuracy=0) const
Test if aPoint is within the bounds of this object.
Definition: eda_text.cpp:382
T MIRRORVAL(T aPoint, T aMirrorRef)
Returns the mirror of aPoint relative to the aMirrorRef.
Definition: mirror.h:31
A base class for most all the KiCad significant classes used in schematics and boards.
Definition: eda_item.h:100
void Rotate(const wxPoint &aRotCentre, double aAngle) override
Rotate this object.
Definition: pcb_text.cpp:162
bool Intersects(const EDA_RECT &aRect) const
Test for a common area between rectangles.
Definition: eda_rect.cpp:150
const wxPoint & GetTextPos() const
Definition: eda_text.h:247
Provide class metadata.Helper macro to map type hashes to names.
Definition: property_mgr.h:62
EDA_ITEM * Clone() const override
Create a duplicate of this item with linked list members set to NULL.
Definition: pcb_text.cpp:202
virtual void SetTextAngle(double aAngle)
Definition: eda_text.h:167
const EDA_RECT GetBoundingBox() const override
Return the orthogonal bounding box of this object for display purposes.
Definition: pcb_text.cpp:132
const EDA_RECT GetBoundingBoxRotated(const wxPoint &aRotCenter, double aAngle) const
Useful to calculate bounding box of rotated items, when rotation if not k*90 degrees.
Definition: eda_rect.cpp:513
T NormalizeAngle360Min(T Angle)
Normalize angle to be > -360.0 and < 360.0 Angle equal to -360 or +360 are set to 0.
Definition: trigo.h:254
bool ResolveTextVar(wxString *token, int aDepth) const
Definition: board.cpp:238
BOARD_ITEM_CONTAINER * GetParent() const
Definition: board_item.h:166
wxString GetLayerName() const
Return the name of the PCB layer on which the item resides.
Definition: board_item.cpp:74
virtual PCB_LAYER_ID GetLayer() const
Return the primary layer this item is on.
Definition: board_item.h:171
virtual const wxString & GetText() const
Return the string associated with the text object.
Definition: eda_text.h:133
virtual wxString GetShownText(int aDepth=0) const
Return the string actually shown after processing of the base text.
Definition: eda_text.h:141
EDA_UNITS GetUserUnits() const
Return the user units currently in use.
EDA_RECT & Inflate(wxCoord dx, wxCoord dy)
Inflate the rectangle horizontally by dx and vertically by dy.
Definition: eda_rect.cpp:364
void SetTextY(int aY)
Definition: eda_text.h:250
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:113