KiCad PCB EDA Suite
Loading...
Searching...
No Matches
lib_pin.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) 2016 Jean-Pierre Charras, jp.charras at wanadoo.fr
5 * Copyright (C) 2015 Wayne Stambaugh <[email protected]>
6 * Copyright (C) 1992-2023 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 <base_units.h>
27#include <pgm_base.h>
28#include <sch_draw_panel.h>
29#include <sch_edit_frame.h>
30#include <symbol_edit_frame.h>
31#include <lib_pin.h>
34#include <trigo.h>
35#include <string_utils.h>
36#include "sch_painter.h"
37#include "plotters/plotter.h"
38
39
40// small margin in internal units between the pin text and the pin line
41#define PIN_TEXT_MARGIN 4
42
44{
45 // These strings are the canonical name of the electrictal type
46 // Not translated, no space in name, only ASCII chars.
47 // to use when the string name must be known and well defined
48 // must have same order than enum ELECTRICAL_PINTYPE (see lib_pin.h)
49 static const wxChar* msgPinElectricType[] =
50 {
51 wxT( "input" ),
52 wxT( "output" ),
53 wxT( "bidirectional" ),
54 wxT( "tri_state" ),
55 wxT( "passive" ),
56 wxT( "free" ),
57 wxT( "unspecified" ),
58 wxT( "power_in" ),
59 wxT( "power_out" ),
60 wxT( "open_collector" ),
61 wxT( "open_emitter" ),
62 wxT( "no_connect" )
63 };
64
65 return msgPinElectricType[static_cast<int>( aType )];
66}
67
68
70// i.e. the clock symbols (falling clock is actually external but is of
71// the same kind)
72
73static int internalPinDecoSize( const RENDER_SETTINGS* aSettings, const LIB_PIN &aPin )
74{
75 const KIGFX::SCH_RENDER_SETTINGS* settings = static_cast<const KIGFX::SCH_RENDER_SETTINGS*>( aSettings );
76
77 if( settings && settings->m_PinSymbolSize )
78 return settings->m_PinSymbolSize;
79
80 return aPin.GetNameTextSize() != 0 ? aPin.GetNameTextSize() / 2 : aPin.GetNumberTextSize() / 2;
81}
82
84// i.e. the negation circle, the polarity 'slopes' and the nonlogic
85// marker
86static int externalPinDecoSize( const RENDER_SETTINGS* aSettings, const LIB_PIN &aPin )
87{
88 const KIGFX::SCH_RENDER_SETTINGS* settings = static_cast<const KIGFX::SCH_RENDER_SETTINGS*>( aSettings );
89
90 if( settings && settings->m_PinSymbolSize )
91 return settings->m_PinSymbolSize;
92
93 return aPin.GetNumberTextSize() / 2;
94}
95
96
98 LIB_ITEM( LIB_PIN_T, aParent ),
99 m_orientation( PIN_ORIENTATION::PIN_RIGHT ),
100 m_shape( GRAPHIC_PINSHAPE::LINE ),
102 m_attributes( 0 )
103{
104 // Use the application settings for pin sizes if exists.
105 // pgm can be nullptr when running a shared lib from a script, not from a kicad appl
106 PGM_BASE* pgm = PgmOrNull();
107
108 if( pgm )
109 {
111 m_length = schIUScale.MilsToIU( settings->m_Defaults.pin_length );
112 m_numTextSize = schIUScale.MilsToIU( settings->m_Defaults.pin_num_size );
113 m_nameTextSize = schIUScale.MilsToIU( settings->m_Defaults.pin_name_size );
114 }
115 else // Use hardcoded eeschema defaults: symbol_editor settings are not existing.
116 {
120 }
121}
122
123
124LIB_PIN::LIB_PIN( LIB_SYMBOL* aParent, const wxString& aName, const wxString& aNumber,
125 PIN_ORIENTATION aOrientation, ELECTRICAL_PINTYPE aPinType, int aLength,
126 int aNameTextSize, int aNumTextSize, int aBodyStyle, const VECTOR2I& aPos,
127 int aUnit ) :
128 LIB_ITEM( LIB_PIN_T, aParent ),
129 m_position( aPos ),
130 m_length( aLength ),
131 m_orientation( aOrientation ),
132 m_shape( GRAPHIC_PINSHAPE::LINE ),
133 m_type( aPinType ),
134 m_attributes( 0 ),
135 m_numTextSize( aNumTextSize ),
136 m_nameTextSize( aNameTextSize )
137{
138 SetName( aName );
139 SetNumber( aNumber );
140 SetUnit( aUnit );
141 SetBodyStyle( aBodyStyle );
142}
143
144
145bool LIB_PIN::HitTest( const VECTOR2I& aPosition, int aAccuracy ) const
146{
147 BOX2I rect = GetBoundingBox( false, true, m_flags & SHOW_ELEC_TYPE );
148
149 return rect.Inflate( aAccuracy ).Contains( aPosition );
150}
151
152
153bool LIB_PIN::HitTest( const BOX2I& aRect, bool aContained, int aAccuracy ) const
154{
156 return false;
157
158 BOX2I sel = aRect;
159
160 if ( aAccuracy )
161 sel.Inflate( aAccuracy );
162
163 if( aContained )
164 return sel.Contains( GetBoundingBox( false, false, false ) );
165
166 return sel.Intersects( GetBoundingBox( false, true, m_flags & SHOW_ELEC_TYPE ) );
167}
168
169
171{
172 return 0;
173}
174
175
176wxString LIB_PIN::GetShownName() const
177{
178 if( m_name == wxS( "~" ) )
179 return wxEmptyString;
180 else
181 return m_name;
182}
183
184
186{
187 switch( m_orientation )
188 {
189 default:
190 case PIN_ORIENTATION::PIN_RIGHT: return VECTOR2I( m_position.x + m_length, -( m_position.y ) );
191 case PIN_ORIENTATION::PIN_LEFT: return VECTOR2I( m_position.x - m_length, -( m_position.y ) );
192 case PIN_ORIENTATION::PIN_UP: return VECTOR2I( m_position.x, -( m_position.y + m_length ) );
193 case PIN_ORIENTATION::PIN_DOWN: return VECTOR2I( m_position.x, -( m_position.y - m_length ) );
194 }
195}
196
197
198void LIB_PIN::print( const RENDER_SETTINGS* aSettings, const VECTOR2I& aOffset, void* aData,
199 const TRANSFORM& aTransform, bool aDimmed )
200{
201 LIB_SYMBOL_OPTIONS* opts = (LIB_SYMBOL_OPTIONS*) aData;
202 bool drawHiddenFields = opts ? opts->draw_hidden_fields : false;
203 bool showPinType = opts ? opts->show_elec_type : false;
204 bool show_connect_point = opts ? opts->show_connect_point : false;
205
206 LIB_SYMBOL* part = GetParent();
207
208 wxCHECK( part && opts, /* void */ );
209
210 /* Calculate pin orient taking in account the symbol orientation. */
211 PIN_ORIENTATION orient = PinDrawOrient( aTransform );
212
213 /* Calculate the pin position */
214 VECTOR2I pos1 = aTransform.TransformCoordinate( m_position ) + aOffset;
215
216 if( IsVisible() || drawHiddenFields )
217 {
218 printPinSymbol( aSettings, pos1, orient, aDimmed );
219
220 printPinTexts( aSettings, pos1, orient, part->GetPinNameOffset(),
221 opts->force_draw_pin_text || part->ShowPinNumbers(),
222 opts->force_draw_pin_text || part->ShowPinNames(),
223 aDimmed );
224
225 if( showPinType )
226 printPinElectricalTypeName( aSettings, pos1, orient, aDimmed );
227
228 if( show_connect_point
229 && m_type != ELECTRICAL_PINTYPE::PT_NC
230 && m_type != ELECTRICAL_PINTYPE::PT_NIC )
231 {
232 wxDC* DC = aSettings->GetPrintDC();
234
235 COLOR4D bg = aSettings->GetBackgroundColor();
236
237 if( bg == COLOR4D::UNSPECIFIED || GetGRForceBlackPenState() )
238 bg = COLOR4D::WHITE;
239
240 if( aDimmed )
241 {
242 color.Desaturate( );
243 color = color.Mix( bg, 0.5f );
244 }
245
246 GRCircle( DC, pos1, TARGET_PIN_RADIUS, 0, color );
247 }
248 }
249}
250
251
252void LIB_PIN::printPinSymbol( const RENDER_SETTINGS* aSettings, const VECTOR2I& aPos,
253 PIN_ORIENTATION aOrient, bool aDimmed )
254{
255 wxDC* DC = aSettings->GetPrintDC();
256 int MapX1, MapY1, x1, y1;
257 int width = GetEffectivePenWidth( aSettings );
258 int posX = aPos.x, posY = aPos.y, len = m_length;
260 COLOR4D bg = aSettings->GetBackgroundColor();
261
262 if( bg == COLOR4D::UNSPECIFIED || GetGRForceBlackPenState() )
263 bg = COLOR4D::WHITE;
264
265 if( !IsVisible() )
266 bg = aSettings->GetLayerColor( LAYER_HIDDEN );
267
268 if( aDimmed )
269 {
270 color.Desaturate( );
271 color = color.Mix( bg, 0.5f );
272 }
273
274 MapX1 = MapY1 = 0;
275 x1 = posX;
276 y1 = posY;
277
278 switch( aOrient )
279 {
280 case PIN_ORIENTATION::PIN_UP: y1 = posY - len; MapY1 = 1; break;
281 case PIN_ORIENTATION::PIN_DOWN: y1 = posY + len; MapY1 = -1; break;
282 case PIN_ORIENTATION::PIN_LEFT: x1 = posX - len; MapX1 = 1; break;
283 case PIN_ORIENTATION::PIN_RIGHT: x1 = posX + len; MapX1 = -1; break;
284 }
285
286 if( m_shape == GRAPHIC_PINSHAPE::INVERTED || m_shape == GRAPHIC_PINSHAPE::INVERTED_CLOCK )
287 {
288 const int radius = externalPinDecoSize( aSettings, *this );
289 GRCircle( DC, VECTOR2I( MapX1 * radius + x1, MapY1 * radius + y1 ), radius, width, color );
290
291 GRMoveTo( MapX1 * radius * 2 + x1, MapY1 * radius * 2 + y1 );
292 GRLineTo( DC, posX, posY, width, color );
293 }
294 else
295 {
296 GRMoveTo( x1, y1 );
297 GRLineTo( DC, posX, posY, width, color );
298 }
299
300 // Draw the clock shape (>)inside the symbol
301 if( m_shape == GRAPHIC_PINSHAPE::CLOCK
302 || m_shape == GRAPHIC_PINSHAPE::INVERTED_CLOCK
303 || m_shape == GRAPHIC_PINSHAPE::FALLING_EDGE_CLOCK
304 || m_shape == GRAPHIC_PINSHAPE::CLOCK_LOW )
305 {
306 const int clock_size = internalPinDecoSize( aSettings, *this );
307 if( MapY1 == 0 ) /* MapX1 = +- 1 */
308 {
309 GRMoveTo( x1, y1 + clock_size );
310 GRLineTo( DC, x1 - MapX1 * clock_size * 2, y1, width, color );
311 GRLineTo( DC, x1, y1 - clock_size, width, color );
312 }
313 else /* MapX1 = 0 */
314 {
315 GRMoveTo( x1 + clock_size, y1 );
316 GRLineTo( DC, x1, y1 - MapY1 * clock_size * 2, width, color );
317 GRLineTo( DC, x1 - clock_size, y1, width, color );
318 }
319 }
320
321 // Draw the active low (or H to L active transition)
322 if( m_shape == GRAPHIC_PINSHAPE::INPUT_LOW
323 || m_shape == GRAPHIC_PINSHAPE::FALLING_EDGE_CLOCK
324 || m_shape == GRAPHIC_PINSHAPE::CLOCK_LOW )
325 {
326 const int deco_size = externalPinDecoSize( aSettings, *this );
327 if( MapY1 == 0 ) /* MapX1 = +- 1 */
328 {
329 GRMoveTo( x1 + MapX1 * deco_size * 2, y1 );
330 GRLineTo( DC, x1 + MapX1 * deco_size * 2, y1 - deco_size * 2, width, color );
331 GRLineTo( DC, x1, y1, width, color );
332 }
333 else /* MapX1 = 0 */
334 {
335 GRMoveTo( x1, y1 + MapY1 * deco_size * 2 );
336 GRLineTo( DC, x1 - deco_size * 2, y1 + MapY1 * deco_size * 2, width, color );
337 GRLineTo( DC, x1, y1, width, color );
338 }
339 }
340
341 if( m_shape == GRAPHIC_PINSHAPE::OUTPUT_LOW ) /* IEEE symbol "Active Low Output" */
342 {
343 const int deco_size = externalPinDecoSize( aSettings, *this );
344 if( MapY1 == 0 ) /* MapX1 = +- 1 */
345 {
346 GRMoveTo( x1, y1 - deco_size * 2 );
347 GRLineTo( DC, x1 + MapX1 * deco_size * 2, y1, width, color );
348 }
349 else /* MapX1 = 0 */
350 {
351 GRMoveTo( x1 - deco_size * 2, y1 );
352 GRLineTo( DC, x1, y1 + MapY1 * deco_size * 2, width, color );
353 }
354 }
355 else if( m_shape == GRAPHIC_PINSHAPE::NONLOGIC ) /* NonLogic pin symbol */
356 {
357 const int deco_size = externalPinDecoSize( aSettings, *this );
358 GRMoveTo( x1 - (MapX1 + MapY1) * deco_size, y1 - (MapY1 - MapX1) * deco_size );
359 GRLineTo( DC, x1 + (MapX1 + MapY1) * deco_size, y1 + ( MapY1 - MapX1 ) * deco_size, width,
360 color );
361 GRMoveTo( x1 - (MapX1 - MapY1) * deco_size, y1 - (MapY1 + MapX1) * deco_size );
362 GRLineTo( DC, x1 + (MapX1 - MapY1) * deco_size, y1 + ( MapY1 + MapX1 ) * deco_size, width,
363 color );
364 }
365
366 if( m_type == ELECTRICAL_PINTYPE::PT_NC ) // Draw a N.C. symbol
367 {
368 const int deco_size = TARGET_PIN_RADIUS;
369 GRLine( DC, posX - deco_size, posY - deco_size, posX + deco_size, posY + deco_size, width,
370 color );
371 GRLine( DC, posX + deco_size, posY - deco_size, posX - deco_size, posY + deco_size, width,
372 color );
373 }
374}
375
376
377void LIB_PIN::printPinTexts( const RENDER_SETTINGS* aSettings, VECTOR2I& aPinPos,
378 PIN_ORIENTATION aPinOrient, int aTextInside, bool aDrawPinNum,
379 bool aDrawPinName, bool aDimmed )
380{
381 if( !aDrawPinName && !aDrawPinNum )
382 return;
383
384 KIFONT::FONT* font = KIFONT::FONT::GetFont( aSettings->GetDefaultFont(), false, false );
385 wxString name = GetShownName();
386 wxString number = GetShownNumber();
389 int nameWidth = std::max( Clamp_Text_PenSize( GetPenWidth(), m_nameTextSize, true ),
390 aSettings->GetDefaultPenWidth() );
391 int numWidth = std::max( Clamp_Text_PenSize( GetPenWidth(), m_numTextSize, true ),
392 aSettings->GetDefaultPenWidth() );
393 int name_offset = schIUScale.MilsToIU( PIN_TEXT_MARGIN ) + nameWidth;
394 int num_offset = schIUScale.MilsToIU( PIN_TEXT_MARGIN ) + numWidth;
395
396 /* Get the num and name colors */
397 COLOR4D nameColor = aSettings->GetLayerColor( IsVisible() ? LAYER_PINNAM : LAYER_HIDDEN );
398 COLOR4D numColor = aSettings->GetLayerColor( IsVisible() ? LAYER_PINNUM : LAYER_HIDDEN );
399 COLOR4D bg = aSettings->GetBackgroundColor();
400
401 if( bg == COLOR4D::UNSPECIFIED || GetGRForceBlackPenState() )
402 bg = COLOR4D::WHITE;
403
404 if( !IsVisible() )
405 bg = aSettings->GetLayerColor( LAYER_HIDDEN );
406
407 if( aDimmed )
408 {
409 nameColor.Desaturate();
410 numColor.Desaturate();
411 nameColor = nameColor.Mix( bg, 0.5f );
412 numColor = numColor.Mix( bg, 0.5f );
413 }
414
415 int x1 = aPinPos.x;
416 int y1 = aPinPos.y;
417
418 switch( aPinOrient )
419 {
420 case PIN_ORIENTATION::PIN_UP: y1 -= m_length; break;
421 case PIN_ORIENTATION::PIN_DOWN: y1 += m_length; break;
422 case PIN_ORIENTATION::PIN_LEFT: x1 -= m_length; break;
423 case PIN_ORIENTATION::PIN_RIGHT: x1 += m_length; break;
424 }
425
426 if( name.IsEmpty() || m_nameTextSize == 0 )
427 aDrawPinName = false;
428
429 if( number.IsEmpty() || m_numTextSize == 0 )
430 aDrawPinNum = false;
431
432 auto printName =
433 [&]( int x, int y, const EDA_ANGLE& angle, enum GR_TEXT_H_ALIGN_T hAlign,
434 enum GR_TEXT_V_ALIGN_T vAlign )
435 {
436 GRPrintText( aSettings->GetPrintDC(), VECTOR2I( x, y ), nameColor, name, angle,
437 nameSize, hAlign, vAlign, nameWidth, false, false, font, GetFontMetrics() );
438 };
439
440 auto printNum =
441 [&]( int x, int y, const EDA_ANGLE& angle, enum GR_TEXT_H_ALIGN_T hAlign,
442 enum GR_TEXT_V_ALIGN_T vAlign )
443 {
444 GRPrintText( aSettings->GetPrintDC(), VECTOR2I( x, y ), numColor, number, angle,
445 numSize, hAlign, vAlign, numWidth, false, false, font, GetFontMetrics() );
446 };
447
448 if( aTextInside ) // Draw the text inside, but the pin numbers outside.
449 {
450 if( ( aPinOrient == PIN_ORIENTATION::PIN_LEFT )
451 || ( aPinOrient == PIN_ORIENTATION::PIN_RIGHT ) )
452 {
453 // It is an horizontal line
454 if( aDrawPinName )
455 {
456 if( aPinOrient == PIN_ORIENTATION::PIN_RIGHT )
457 {
458 printName( x1 + aTextInside, y1, ANGLE_HORIZONTAL,
460 }
461 else // Orient == PIN_LEFT
462 {
463 printName( x1 - aTextInside, y1, ANGLE_HORIZONTAL,
465 }
466 }
467
468 if( aDrawPinNum )
469 {
470 printNum( ( x1 + aPinPos.x ) / 2, y1 - num_offset, ANGLE_HORIZONTAL,
472 }
473 }
474 else /* Its a vertical line. */
475 {
476 // Text is drawn from bottom to top (i.e. to negative value for Y axis)
477 if( aPinOrient == PIN_ORIENTATION::PIN_DOWN )
478 {
479 if( aDrawPinName )
480 {
481 printName( x1, y1 + aTextInside, ANGLE_VERTICAL,
483 }
484
485 if( aDrawPinNum )
486 {
487 printNum( x1 - num_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
489 }
490 }
491 else /* PIN_UP */
492 {
493 if( aDrawPinName )
494 {
495 printName( x1, y1 - aTextInside, ANGLE_VERTICAL,
497 }
498
499 if( aDrawPinNum )
500 {
501 printNum( x1 - num_offset, ( y1 + aPinPos.y) / 2, ANGLE_VERTICAL,
503 }
504 }
505 }
506 }
507 else /**** Draw num & text pin outside ****/
508 {
509 if( ( aPinOrient == PIN_ORIENTATION::PIN_LEFT )
510 || ( aPinOrient == PIN_ORIENTATION::PIN_RIGHT ) )
511 {
512 /* Its an horizontal line. */
513 if( aDrawPinName && aDrawPinNum )
514 {
515 printName( ( x1 + aPinPos.x ) / 2, y1 - name_offset, ANGLE_HORIZONTAL,
517
518 printNum( ( x1 + aPinPos.x ) / 2, y1 + num_offset, ANGLE_HORIZONTAL,
520 }
521 else if( aDrawPinName )
522 {
523 printName( ( x1 + aPinPos.x ) / 2, y1 - name_offset, ANGLE_HORIZONTAL,
525 }
526 else if( aDrawPinNum )
527 {
528 printNum( ( x1 + aPinPos.x ) / 2, y1 - num_offset, ANGLE_HORIZONTAL,
530 }
531 }
532 else /* Its a vertical line. */
533 {
534 if( aDrawPinName && aDrawPinNum )
535 {
536 printName( x1 - name_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
538
539 printNum( x1 + num_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
541 }
542 else if( aDrawPinName )
543 {
544 printName( x1 - name_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
546 }
547 else if( aDrawPinNum )
548 {
549 printNum( x1 - num_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
551 }
552 }
553 }
554}
555
556
558 PIN_ORIENTATION aOrientation, bool aDimmed )
559{
560 wxDC* DC = aSettings->GetPrintDC();
561 wxString typeName = GetElectricalTypeName();
562
563 // Use a reasonable (small) size to draw the text
564 int textSize = ( m_nameTextSize * 3 ) / 4;
565
566 #define ETXT_MAX_SIZE schIUScale.mmToIU( 0.7 )
567
568 if( textSize > ETXT_MAX_SIZE )
569 textSize = ETXT_MAX_SIZE;
570
571 // Use a reasonable pen size to draw the text
572 int pensize = textSize/6;
573
574 // Get a suitable color
576 COLOR4D bg = aSettings->GetBackgroundColor();
577
578 if( bg == COLOR4D::UNSPECIFIED || GetGRForceBlackPenState() )
579 bg = COLOR4D::WHITE;
580
581 if( !IsVisible() )
582 bg = aSettings->GetLayerColor( LAYER_HIDDEN );
583
584 if( aDimmed )
585 {
586 color.Desaturate( );
587 color = color.Mix( bg, 0.5f );
588 }
589
590 VECTOR2I txtpos = aPosition;
591 int offset = schIUScale.mmToIU( 0.4 );
594 KIFONT::FONT* font = KIFONT::FONT::GetFont( aSettings->GetDefaultFont(), false, false );
595
596 switch( aOrientation )
597 {
598 case PIN_ORIENTATION::PIN_UP:
599 txtpos.y += offset;
600 orient = ANGLE_VERTICAL;
601 hjustify = GR_TEXT_H_ALIGN_RIGHT;
602 break;
603
604 case PIN_ORIENTATION::PIN_DOWN:
605 txtpos.y -= offset;
606 orient = ANGLE_VERTICAL;
607 break;
608
609 case PIN_ORIENTATION::PIN_LEFT:
610 txtpos.x += offset;
611 break;
612
613 case PIN_ORIENTATION::PIN_RIGHT:
614 txtpos.x -= offset;
615 hjustify = GR_TEXT_H_ALIGN_RIGHT;
616 break;
617 }
618
619 GRPrintText( DC, txtpos, color, typeName, orient, VECTOR2I( textSize, textSize ), hjustify,
620 GR_TEXT_V_ALIGN_CENTER, pensize, false, false, font, GetFontMetrics() );
621}
622
623
624void LIB_PIN::PlotSymbol( PLOTTER *aPlotter, const VECTOR2I &aPosition,
625 PIN_ORIENTATION aOrientation, bool aDimmed ) const
626{
627 int MapX1, MapY1, x1, y1;
629 COLOR4D bg = aPlotter->RenderSettings()->GetBackgroundColor();
630 int penWidth = GetEffectivePenWidth( aPlotter->RenderSettings() );
631
632 if( bg == COLOR4D::UNSPECIFIED || !aPlotter->GetColorMode() )
633 bg = COLOR4D::WHITE;
634
635 if( aDimmed )
636 {
637 color.Desaturate( );
638 color = color.Mix( bg, 0.5f );
639 }
640
641 aPlotter->SetColor( color );
642 aPlotter->SetCurrentLineWidth( penWidth );
643
644 MapX1 = MapY1 = 0;
645 x1 = aPosition.x; y1 = aPosition.y;
646
647 switch( aOrientation )
648 {
649 case PIN_ORIENTATION::PIN_UP: y1 = aPosition.y - m_length; MapY1 = 1; break;
650 case PIN_ORIENTATION::PIN_DOWN: y1 = aPosition.y + m_length; MapY1 = -1; break;
651 case PIN_ORIENTATION::PIN_LEFT: x1 = aPosition.x - m_length; MapX1 = 1; break;
652 case PIN_ORIENTATION::PIN_RIGHT: x1 = aPosition.x + m_length; MapX1 = -1; break;
653 }
654
655 if( m_shape == GRAPHIC_PINSHAPE::INVERTED || m_shape == GRAPHIC_PINSHAPE::INVERTED_CLOCK )
656 {
657 const int radius = externalPinDecoSize( aPlotter->RenderSettings(), *this );
658 aPlotter->Circle( VECTOR2I( MapX1 * radius + x1, MapY1 * radius + y1 ), radius * 2,
659 FILL_T::NO_FILL, penWidth );
660
661 aPlotter->MoveTo( VECTOR2I( MapX1 * radius * 2 + x1, MapY1 * radius * 2 + y1 ) );
662 aPlotter->FinishTo( aPosition );
663 }
664 else if( m_shape == GRAPHIC_PINSHAPE::FALLING_EDGE_CLOCK )
665 {
666 const int deco_size = internalPinDecoSize( aPlotter->RenderSettings(), *this );
667 if( MapY1 == 0 ) /* MapX1 = +- 1 */
668 {
669 aPlotter->MoveTo( VECTOR2I( x1, y1 + deco_size ) );
670 aPlotter->LineTo( VECTOR2I( x1 + MapX1 * deco_size * 2, y1 ) );
671 aPlotter->FinishTo( VECTOR2I( x1, y1 - deco_size ) );
672 }
673 else /* MapX1 = 0 */
674 {
675 aPlotter->MoveTo( VECTOR2I( x1 + deco_size, y1 ) );
676 aPlotter->LineTo( VECTOR2I( x1, y1 + MapY1 * deco_size * 2 ) );
677 aPlotter->FinishTo( VECTOR2I( x1 - deco_size, y1 ) );
678 }
679
680 aPlotter->MoveTo( VECTOR2I( MapX1 * deco_size * 2 + x1, MapY1 * deco_size * 2 + y1 ) );
681 aPlotter->FinishTo( aPosition );
682 }
683 else
684 {
685 aPlotter->MoveTo( VECTOR2I( x1, y1 ) );
686 aPlotter->FinishTo( aPosition );
687 }
688
689 if( m_shape == GRAPHIC_PINSHAPE::CLOCK
690 || m_shape == GRAPHIC_PINSHAPE::INVERTED_CLOCK
691 || m_shape == GRAPHIC_PINSHAPE::CLOCK_LOW )
692 {
693 const int deco_size = internalPinDecoSize( aPlotter->RenderSettings(), *this );
694 if( MapY1 == 0 ) /* MapX1 = +- 1 */
695 {
696 aPlotter->MoveTo( VECTOR2I( x1, y1 + deco_size ) );
697 aPlotter->LineTo( VECTOR2I( x1 - MapX1 * deco_size * 2, y1 ) );
698 aPlotter->FinishTo( VECTOR2I( x1, y1 - deco_size ) );
699 }
700 else /* MapX1 = 0 */
701 {
702 aPlotter->MoveTo( VECTOR2I( x1 + deco_size, y1 ) );
703 aPlotter->LineTo( VECTOR2I( x1, y1 - MapY1 * deco_size * 2 ) );
704 aPlotter->FinishTo( VECTOR2I( x1 - deco_size, y1 ) );
705 }
706 }
707
708 if( m_shape == GRAPHIC_PINSHAPE::INPUT_LOW
709 || m_shape == GRAPHIC_PINSHAPE::CLOCK_LOW ) /* IEEE symbol "Active Low Input" */
710 {
711 const int deco_size = externalPinDecoSize( aPlotter->RenderSettings(), *this );
712
713 if( MapY1 == 0 ) /* MapX1 = +- 1 */
714 {
715 aPlotter->MoveTo( VECTOR2I( x1 + MapX1 * deco_size * 2, y1 ) );
716 aPlotter->LineTo( VECTOR2I( x1 + MapX1 * deco_size * 2, y1 - deco_size * 2 ) );
717 aPlotter->FinishTo( VECTOR2I( x1, y1 ) );
718 }
719 else /* MapX1 = 0 */
720 {
721 aPlotter->MoveTo( VECTOR2I( x1, y1 + MapY1 * deco_size * 2 ) );
722 aPlotter->LineTo( VECTOR2I( x1 - deco_size * 2, y1 + MapY1 * deco_size * 2 ) );
723 aPlotter->FinishTo( VECTOR2I( x1, y1 ) );
724 }
725 }
726
727 if( m_shape == GRAPHIC_PINSHAPE::OUTPUT_LOW ) /* IEEE symbol "Active Low Output" */
728 {
729 const int symbol_size = externalPinDecoSize( aPlotter->RenderSettings(), *this );
730
731 if( MapY1 == 0 ) /* MapX1 = +- 1 */
732 {
733 aPlotter->MoveTo( VECTOR2I( x1, y1 - symbol_size * 2 ) );
734 aPlotter->FinishTo( VECTOR2I( x1 + MapX1 * symbol_size * 2, y1 ) );
735 }
736 else /* MapX1 = 0 */
737 {
738 aPlotter->MoveTo( VECTOR2I( x1 - symbol_size * 2, y1 ) );
739 aPlotter->FinishTo( VECTOR2I( x1, y1 + MapY1 * symbol_size * 2 ) );
740 }
741 }
742 else if( m_shape == GRAPHIC_PINSHAPE::NONLOGIC ) /* NonLogic pin symbol */
743 {
744 const int deco_size = externalPinDecoSize( aPlotter->RenderSettings(), *this );
745 aPlotter->MoveTo( VECTOR2I( x1 - ( MapX1 + MapY1 ) * deco_size,
746 y1 - ( MapY1 - MapX1 ) * deco_size ) );
747 aPlotter->FinishTo( VECTOR2I( x1 + ( MapX1 + MapY1 ) * deco_size,
748 y1 + ( MapY1 - MapX1 ) * deco_size ) );
749 aPlotter->MoveTo( VECTOR2I( x1 - ( MapX1 - MapY1 ) * deco_size,
750 y1 - ( MapY1 + MapX1 ) * deco_size ) );
751 aPlotter->FinishTo( VECTOR2I( x1 + ( MapX1 - MapY1 ) * deco_size,
752 y1 + ( MapY1 + MapX1 ) * deco_size ) );
753 }
754
755 if( m_type == ELECTRICAL_PINTYPE::PT_NC ) // Draw a N.C. symbol
756 {
757 const int deco_size = TARGET_PIN_RADIUS;
758 const int ex1 = aPosition.x;
759 const int ey1 = aPosition.y;
760 aPlotter->MoveTo( VECTOR2I( ex1 - deco_size, ey1 - deco_size ) );
761 aPlotter->FinishTo( VECTOR2I( ex1 + deco_size, ey1 + deco_size ) );
762 aPlotter->MoveTo( VECTOR2I( ex1 + deco_size, ey1 - deco_size ) );
763 aPlotter->FinishTo( VECTOR2I( ex1 - deco_size, ey1 + deco_size ) );
764 }
765}
766
767
768void LIB_PIN::PlotPinTexts( PLOTTER *aPlotter, const VECTOR2I &aPinPos, PIN_ORIENTATION aPinOrient,
769 int aTextInside, bool aDrawPinNum, bool aDrawPinName,
770 bool aDimmed ) const
771{
772 RENDER_SETTINGS* settings = aPlotter->RenderSettings();
773 KIFONT::FONT* font = KIFONT::FONT::GetFont( settings->GetDefaultFont(), false, false );
774 wxString name = GetShownName();
775 wxString number = GetShownNumber();
776
777 if( name.IsEmpty() || m_nameTextSize == 0 )
778 aDrawPinName = false;
779
780 if( number.IsEmpty() || m_numTextSize == 0 )
781 aDrawPinNum = false;
782
783 if( !aDrawPinNum && !aDrawPinName )
784 return;
785
786 int namePenWidth = std::max( Clamp_Text_PenSize( GetPenWidth(), m_nameTextSize, true ),
787 settings->GetDefaultPenWidth() );
788 int numPenWidth = std::max( Clamp_Text_PenSize( GetPenWidth(), m_numTextSize, true ),
789 settings->GetDefaultPenWidth() );
790 int name_offset = schIUScale.MilsToIU( PIN_TEXT_MARGIN ) + namePenWidth;
791 int num_offset = schIUScale.MilsToIU( PIN_TEXT_MARGIN ) + numPenWidth;
792
793 /* Get the num and name colors */
794 COLOR4D nameColor = settings->GetLayerColor( LAYER_PINNAM );
795 COLOR4D numColor = settings->GetLayerColor( LAYER_PINNUM );
796 COLOR4D bg = settings->GetBackgroundColor();
797
798 if( bg == COLOR4D::UNSPECIFIED || !aPlotter->GetColorMode() )
799 bg = COLOR4D::WHITE;
800
801 if( aDimmed )
802 {
803 nameColor.Desaturate( );
804 numColor.Desaturate( );
805 nameColor = nameColor.Mix( bg, 0.5f );
806 numColor = numColor.Mix( bg, 0.5f );
807 }
808
809 int x1 = aPinPos.x;
810 int y1 = aPinPos.y;
811
812 switch( aPinOrient )
813 {
814 case PIN_ORIENTATION::PIN_UP: y1 -= m_length; break;
815 case PIN_ORIENTATION::PIN_DOWN: y1 += m_length; break;
816 case PIN_ORIENTATION::PIN_LEFT: x1 -= m_length; break;
817 case PIN_ORIENTATION::PIN_RIGHT: x1 += m_length; break;
818 }
819
820 auto plotName =
821 [&]( int x, int y, const EDA_ANGLE& angle, GR_TEXT_H_ALIGN_T hJustify,
822 GR_TEXT_V_ALIGN_T vJustify )
823 {
824 TEXT_ATTRIBUTES attrs;
825 attrs.m_StrokeWidth = namePenWidth;
826 attrs.m_Angle = angle;
828 attrs.m_Halign = hJustify;
829 attrs.m_Valign = vJustify;
830 attrs.m_Multiline = false;
831
832 aPlotter->PlotText( VECTOR2I( x, y ), nameColor, name, attrs, font, GetFontMetrics() );
833 };
834
835 auto plotNum =
836 [&]( int x, int y, const EDA_ANGLE& angle, GR_TEXT_H_ALIGN_T hJustify,
837 GR_TEXT_V_ALIGN_T vJustify )
838 {
839 TEXT_ATTRIBUTES attrs;
840 attrs.m_StrokeWidth = numPenWidth;
841 attrs.m_Angle = angle;
843 attrs.m_Halign = hJustify;
844 attrs.m_Valign = vJustify;
845 attrs.m_Multiline = false;
846
847 aPlotter->PlotText( VECTOR2I( x, y ), numColor, number, attrs, font, GetFontMetrics() );
848 };
849
850 /* Draw the text inside, but the pin numbers outside. */
851 if( aTextInside )
852 {
853 if( ( aPinOrient == PIN_ORIENTATION::PIN_LEFT )
854 || ( aPinOrient == PIN_ORIENTATION::PIN_RIGHT ) ) /* Its an horizontal line. */
855 {
856 if( aDrawPinName )
857 {
858 if( aPinOrient == PIN_ORIENTATION::PIN_RIGHT )
859 {
860 plotName( x1 + aTextInside, y1, ANGLE_HORIZONTAL,
862 }
863 else // orient == PIN_LEFT
864 {
865 plotName( x1 - aTextInside, y1, ANGLE_HORIZONTAL,
867 }
868 }
869
870 if( aDrawPinNum )
871 {
872 plotNum( ( x1 + aPinPos.x) / 2, y1 - num_offset, ANGLE_HORIZONTAL,
874 }
875 }
876 else /* Its a vertical line. */
877 {
878 if( aPinOrient == PIN_ORIENTATION::PIN_DOWN )
879 {
880 if( aDrawPinName )
881 {
882 plotName( x1, y1 + aTextInside, ANGLE_VERTICAL,
884 }
885
886 if( aDrawPinNum )
887 {
888 plotNum( x1 - num_offset, ( y1 + aPinPos.y) / 2, ANGLE_VERTICAL,
890 }
891 }
892 else /* PIN_UP */
893 {
894 if( aDrawPinName )
895 {
896 plotName( x1, y1 - aTextInside, ANGLE_VERTICAL,
898 }
899
900 if( aDrawPinNum )
901 {
902 plotNum( x1 - num_offset, ( y1 + aPinPos.y) / 2, ANGLE_VERTICAL,
904 }
905 }
906 }
907 }
908 else /* Draw num & text pin outside */
909 {
910 if( ( aPinOrient == PIN_ORIENTATION::PIN_LEFT )
911 || ( aPinOrient == PIN_ORIENTATION::PIN_RIGHT ) )
912 {
913 /* Its an horizontal line. */
914 if( aDrawPinName && aDrawPinNum )
915 {
916 plotName( ( x1 + aPinPos.x) / 2, y1 - name_offset, ANGLE_HORIZONTAL,
918
919 plotNum( ( x1 + aPinPos.x) / 2, y1 + num_offset, ANGLE_HORIZONTAL,
921 }
922 else if( aDrawPinName )
923 {
924 plotName( ( x1 + aPinPos.x) / 2, y1 - name_offset, ANGLE_HORIZONTAL,
926 }
927 else if( aDrawPinNum )
928 {
929 plotNum( ( x1 + aPinPos.x) / 2, y1 - name_offset, ANGLE_HORIZONTAL,
931 }
932 }
933 else
934 {
935 /* Its a vertical line. */
936 if( aDrawPinName && aDrawPinNum )
937 {
938 plotName( x1 - name_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
940
941 plotNum( x1 + num_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
943 }
944 else if( aDrawPinName )
945 {
946 plotName( x1 - name_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
948 }
949 else if( aDrawPinNum )
950 {
951 plotNum( x1 - num_offset, ( y1 + aPinPos.y ) / 2, ANGLE_VERTICAL,
953 }
954 }
955 }
956}
957
958
960{
961 PIN_ORIENTATION orient;
962 VECTOR2I end; // position of pin end starting at 0,0 according to its orientation, length = 1
963
964 switch( m_orientation )
965 {
966 case PIN_ORIENTATION::PIN_UP: end.y = 1; break;
967 case PIN_ORIENTATION::PIN_DOWN: end.y = -1; break;
968 case PIN_ORIENTATION::PIN_LEFT: end.x = -1; break;
969 case PIN_ORIENTATION::PIN_RIGHT: end.x = 1; break;
970 }
971
972 // = pos of end point, according to the symbol orientation.
973 end = aTransform.TransformCoordinate( end );
974 orient = PIN_ORIENTATION::PIN_UP;
975
976 if( end.x == 0 )
977 {
978 if( end.y > 0 )
979 orient = PIN_ORIENTATION::PIN_DOWN;
980 }
981 else
982 {
983 orient = PIN_ORIENTATION::PIN_RIGHT;
984
985 if( end.x < 0 )
986 orient = PIN_ORIENTATION::PIN_LEFT;
987 }
988
989 return orient;
990}
991
992
994{
995 return new LIB_PIN( *this );
996}
997
998
999int LIB_PIN::compare( const LIB_ITEM& aOther, int aCompareFlags ) const
1000{
1001 wxASSERT( aOther.Type() == LIB_PIN_T );
1002
1003 int retv = LIB_ITEM::compare( aOther, aCompareFlags );
1004
1005 if( retv )
1006 return retv;
1007
1008 const LIB_PIN* tmp = (LIB_PIN*) &aOther;
1009
1010 // When comparing units, we do not compare the part numbers. If everything else is
1011 // identical, then we can just renumber the parts for the inherited symbol.
1012 if( !( aCompareFlags & COMPARE_FLAGS::UNIT ) && m_number != tmp->m_number )
1013 return m_number.Cmp( tmp->m_number );
1014
1015 int result = m_name.Cmp( tmp->m_name );
1016
1017 if( result )
1018 return result;
1019
1020 if( m_position.x != tmp->m_position.x )
1021 return m_position.x - tmp->m_position.x;
1022
1023 if( m_position.y != tmp->m_position.y )
1024 return m_position.y - tmp->m_position.y;
1025
1026 if( m_length != tmp->m_length )
1027 return m_length - tmp->m_length;
1028
1029 if( m_orientation != tmp->m_orientation )
1030 return static_cast<int>( m_orientation ) - static_cast<int>( tmp->m_orientation );
1031
1032 if( m_shape != tmp->m_shape )
1033 return static_cast<int>( m_shape ) - static_cast<int>( tmp->m_shape );
1034
1035 if( m_type != tmp->m_type )
1036 return static_cast<int>( m_type ) - static_cast<int>( tmp->m_type );
1037
1038 if( m_attributes != tmp->m_attributes )
1039 return m_attributes - tmp->m_attributes;
1040
1041 if( m_numTextSize != tmp->m_numTextSize )
1042 return m_numTextSize - tmp->m_numTextSize;
1043
1044 if( m_nameTextSize != tmp->m_nameTextSize )
1045 return m_nameTextSize - tmp->m_nameTextSize;
1046
1047 if( m_alternates.size() != tmp->m_alternates.size() )
1048 return m_alternates.size() - tmp->m_alternates.size();
1049
1050 auto lhsItem = m_alternates.begin();
1051 auto rhsItem = tmp->m_alternates.begin();
1052
1053 while( lhsItem != m_alternates.end() )
1054 {
1055 const ALT& lhsAlt = lhsItem->second;
1056 const ALT& rhsAlt = rhsItem->second;
1057
1058 retv = lhsAlt.m_Name.Cmp( rhsAlt.m_Name );
1059
1060 if( retv )
1061 return retv;
1062
1063 if( lhsAlt.m_Type != rhsAlt.m_Type )
1064 return static_cast<int>( lhsAlt.m_Type ) - static_cast<int>( rhsAlt.m_Type );
1065
1066 if( lhsAlt.m_Shape != rhsAlt.m_Shape )
1067 return static_cast<int>( lhsAlt.m_Shape ) - static_cast<int>( rhsAlt.m_Shape );
1068
1069 ++lhsItem;
1070 ++rhsItem;
1071 }
1072
1073 return 0;
1074}
1075
1076void LIB_PIN::ChangeLength( int aLength )
1077{
1078 int lengthChange = m_length - aLength;
1079 int offsetX = 0;
1080 int offsetY = 0;
1081
1082 switch( m_orientation )
1083 {
1084 case PIN_ORIENTATION::PIN_RIGHT:
1085 offsetX = lengthChange;
1086 break;
1087 case PIN_ORIENTATION::PIN_LEFT:
1088 offsetX = -1 * lengthChange;
1089 break;
1090 case PIN_ORIENTATION::PIN_UP:
1091 offsetY = lengthChange;
1092 break;
1093 case PIN_ORIENTATION::PIN_DOWN:
1094 offsetY = -1 * lengthChange;
1095 break;
1096 }
1097
1098 VECTOR2I offset = VECTOR2I( offsetX, offsetY );
1099 Offset( offset );
1100
1101 m_length = aLength;
1102}
1103
1104void LIB_PIN::Offset( const VECTOR2I& aOffset )
1105{
1106 m_position += aOffset;
1107}
1108
1109
1110void LIB_PIN::MoveTo( const VECTOR2I& aNewPosition )
1111{
1112 m_position = aNewPosition;
1113}
1114
1115
1117{
1118 m_position.x -= aCenter.x;
1119 m_position.x *= -1;
1120 m_position.x += aCenter.x;
1121
1122 if( m_orientation == PIN_ORIENTATION::PIN_RIGHT )
1123 m_orientation = PIN_ORIENTATION::PIN_LEFT;
1124 else if( m_orientation == PIN_ORIENTATION::PIN_LEFT )
1125 m_orientation = PIN_ORIENTATION::PIN_RIGHT;
1126}
1127
1128
1129void LIB_PIN::MirrorVertical( const VECTOR2I& aCenter )
1130{
1131 m_position.y -= aCenter.y;
1132 m_position.y *= -1;
1133 m_position.y += aCenter.y;
1134
1135 if( m_orientation == PIN_ORIENTATION::PIN_UP )
1136 m_orientation = PIN_ORIENTATION::PIN_DOWN;
1137 else if( m_orientation == PIN_ORIENTATION::PIN_DOWN )
1138 m_orientation = PIN_ORIENTATION::PIN_UP;
1139}
1140
1141
1142void LIB_PIN::Rotate( const VECTOR2I& aCenter, bool aRotateCCW )
1143{
1144 EDA_ANGLE rot_angle = aRotateCCW ? -ANGLE_90 : ANGLE_90;
1145
1146 RotatePoint( m_position, aCenter, rot_angle );
1147
1148 if( aRotateCCW )
1149 {
1150 switch( m_orientation )
1151 {
1152 case PIN_ORIENTATION::PIN_RIGHT: m_orientation = PIN_ORIENTATION::PIN_UP; break;
1153 case PIN_ORIENTATION::PIN_UP: m_orientation = PIN_ORIENTATION::PIN_LEFT; break;
1154 case PIN_ORIENTATION::PIN_LEFT: m_orientation = PIN_ORIENTATION::PIN_DOWN; break;
1155 case PIN_ORIENTATION::PIN_DOWN: m_orientation = PIN_ORIENTATION::PIN_RIGHT; break;
1156 }
1157 }
1158 else
1159 {
1160 switch( m_orientation )
1161 {
1162 case PIN_ORIENTATION::PIN_RIGHT: m_orientation = PIN_ORIENTATION::PIN_DOWN; break;
1163 case PIN_ORIENTATION::PIN_UP: m_orientation = PIN_ORIENTATION::PIN_RIGHT; break;
1164 case PIN_ORIENTATION::PIN_LEFT: m_orientation = PIN_ORIENTATION::PIN_UP; break;
1165 case PIN_ORIENTATION::PIN_DOWN: m_orientation = PIN_ORIENTATION::PIN_LEFT; break;
1166 }
1167 }
1168}
1169
1170
1171void LIB_PIN::Plot( PLOTTER* aPlotter, bool aBackground, const VECTOR2I& aOffset,
1172 const TRANSFORM& aTransform, bool aDimmed ) const
1173{
1174 if( !IsVisible() || aBackground )
1175 return;
1176
1177 PIN_ORIENTATION orient = PinDrawOrient( aTransform );
1178 VECTOR2I pos = aTransform.TransformCoordinate( m_position ) + aOffset;
1179
1180 PlotSymbol( aPlotter, pos, orient, aDimmed );
1181 PlotPinTexts( aPlotter, pos, orient, GetParent()->GetPinNameOffset(),
1182 GetParent()->ShowPinNumbers(), GetParent()->ShowPinNames(),
1183 aDimmed );
1184}
1185
1186
1187void LIB_PIN::GetMsgPanelInfo( EDA_DRAW_FRAME* aFrame, std::vector<MSG_PANEL_ITEM>& aList )
1188{
1189 LIB_ITEM::GetMsgPanelInfo( aFrame, aList );
1190
1191 aList.emplace_back( _( "Name" ), UnescapeString( GetShownName() ) );
1192 aList.emplace_back( _( "Number" ), GetShownNumber() );
1193 aList.emplace_back( _( "Type" ), ElectricalPinTypeGetText( m_type ) );
1194 aList.emplace_back( _( "Style" ), PinShapeGetText( m_shape ) );
1195
1196 aList.emplace_back( _( "Style" ), IsVisible() ? _( "Yes" ) : _( "No" ) );
1197
1198 // Display pin length
1199 aList.emplace_back( _( "Length" ), aFrame->MessageTextFromValue( m_length, true ) );
1200
1201 aList.emplace_back( _( "Orientation" ), PinOrientationName( m_orientation ) );
1202
1203 VECTOR2I pinpos = GetPosition();
1204 pinpos.y = -pinpos.y; // Display coords are top to bottom; lib item coords are bottom to top
1205
1206 aList.emplace_back( _( "Pos X" ), aFrame->MessageTextFromValue( pinpos.x, true ) );
1207 aList.emplace_back( _( "Pos Y" ), aFrame->MessageTextFromValue( pinpos.y, true ) );
1208
1209 #if 0 // For debug purpose only
1210 aList.emplace_back( _( "Flags" ), wxString::Format( "%8.8X", (long)GetFlags() ) );
1211 #endif
1212}
1213
1214
1216{
1217 return GetBoundingBox( false, true, true );
1218}
1219
1220
1221void LIB_PIN::ViewGetLayers( int aLayers[], int& aCount ) const
1222{
1223 aCount = 6;
1224 aLayers[0] = LAYER_DANGLING; // We don't really show dangling vs non-dangling (since there
1225 // are no connections in the symbol editor), but it's still
1226 // a good visual indication of which end of the pin is which.
1227 aLayers[1] = LAYER_DEVICE;
1228 aLayers[2] = LAYER_SELECTION_SHADOWS;
1229 aLayers[3] = LAYER_OP_CURRENTS;
1230 aLayers[4] = LAYER_PINNAM;
1231 aLayers[5] = LAYER_PINNUM;
1232}
1233
1234
1235void LIB_PIN::validateExtentsCache( KIFONT::FONT* aFont, int aSize, const wxString& aText,
1236 EXTENTS_CACHE* aCache ) const
1237{
1238 if( aCache->m_Font == aFont
1239 && aCache->m_FontSize == aSize
1240 && aCache->m_Extents != VECTOR2I() )
1241 {
1242 return;
1243 }
1244
1245 aCache->m_Font = aFont;
1246 aCache->m_FontSize = aSize;
1247
1248 VECTOR2D fontSize( aSize, aSize );
1249 int penWidth = GetPenSizeForNormal( aSize );
1250
1251 aCache->m_Extents = aFont->StringBoundaryLimits( aText, fontSize, penWidth, false, false,
1252 GetFontMetrics() );
1253}
1254
1255
1256const BOX2I LIB_PIN::GetBoundingBox( bool aIncludeInvisiblePins, bool aIncludeNameAndNumber,
1257 bool aIncludeElectricalType ) const
1258{
1259 EESCHEMA_SETTINGS* cfg = Pgm().GetSettingsManager().GetAppSettings<EESCHEMA_SETTINGS>();
1261
1262 BOX2I bbox;
1263 VECTOR2I begin;
1264 VECTOR2I end;
1265 int pinNameOffset = 0;
1266 int nameTextLength = 0;
1267 int nameTextHeight = 0;
1268 int numberTextLength = 0;
1269 int numberTextHeight = 0;
1270 int typeTextLength = 0;
1271 bool includeName = aIncludeNameAndNumber && !GetShownName().IsEmpty();
1272 bool includeNumber = aIncludeNameAndNumber && !GetShownNumber().IsEmpty();
1273 bool includeType = aIncludeElectricalType;
1274 int minsizeV = TARGET_PIN_RADIUS;
1275
1276 if( !aIncludeInvisiblePins && !IsVisible() )
1277 {
1278 includeName = false;
1279 includeType = false;
1280 }
1281
1282 if( GetParent() )
1283 {
1284 if( GetParent()->ShowPinNames() )
1285 pinNameOffset = GetParent()->GetPinNameOffset();
1286 else
1287 includeName = false;
1288
1289 if( !GetParent()->ShowPinNumbers() )
1290 includeNumber = false;
1291 }
1292
1293 if( includeNumber )
1294 {
1296 numberTextLength = m_numExtentsCache.m_Extents.x;
1297 numberTextHeight = m_numExtentsCache.m_Extents.y;
1298 }
1299
1300 if( includeName )
1301 {
1303 nameTextLength = m_nameExtentsCache.m_Extents.x + pinNameOffset;
1305 }
1306
1307 if( includeType )
1308 {
1309 double fontSize = std::max( m_nameTextSize * 3 / 4, schIUScale.mmToIU( 0.7 ) );
1310 double stroke = fontSize / 8.0;
1311 VECTOR2I typeTextSize = font->StringBoundaryLimits( GetElectricalTypeName(),
1312 VECTOR2D( fontSize, fontSize ),
1313 KiROUND( stroke ), false, false,
1314 GetFontMetrics() );
1315
1316 typeTextLength = typeTextSize.x + schIUScale.MilsToIU( PIN_TEXT_MARGIN ) + TARGET_PIN_RADIUS;
1317 minsizeV = std::max( minsizeV, typeTextSize.y / 2 );
1318 }
1319
1320 // First, calculate boundary box corners position
1321 if( m_shape == GRAPHIC_PINSHAPE::INVERTED || m_shape == GRAPHIC_PINSHAPE::INVERTED_CLOCK )
1322 minsizeV = std::max( TARGET_PIN_RADIUS, externalPinDecoSize( nullptr, *this ) );
1323
1324 // Calculate topLeft & bottomRight corner positions for the default pin orientation (PIN_RIGHT)
1325 if( pinNameOffset || !includeName )
1326 {
1327 // pin name is inside the body (or invisible)
1328 // pin number is above the line
1329 begin.y = std::max( minsizeV, numberTextHeight );
1330 begin.x = std::min( -typeTextLength, m_length - ( numberTextLength / 2 ) );
1331
1332 end.x = m_length + nameTextLength;
1333 end.y = std::min( -minsizeV, -nameTextHeight / 2 );
1334 }
1335 else
1336 {
1337 // pin name is above pin line
1338 // pin number is below line
1339 begin.y = std::max( minsizeV, nameTextHeight );
1340 begin.x = -typeTextLength;
1341 begin.x = std::min( begin.x, ( m_length - numberTextLength ) / 2 );
1342 begin.x = std::min( begin.x, ( m_length - nameTextLength ) / 2 );
1343
1344 end.x = m_length;
1345 end.x = std::max( end.x, ( m_length + nameTextLength ) / 2 );
1346 end.x = std::max( end.x, ( m_length + numberTextLength ) / 2 );
1347 end.y = std::min( -minsizeV, -numberTextHeight );
1348 }
1349
1350 // Now, calculate boundary box corners position for the actual pin orientation
1352
1353 /* Calculate the pin position */
1354 switch( orient )
1355 {
1356 case PIN_ORIENTATION::PIN_UP:
1357 // Pin is rotated and texts positions are mirrored
1358 RotatePoint( begin, VECTOR2I( 0, 0 ), -ANGLE_90 );
1359 RotatePoint( end, VECTOR2I( 0, 0 ), -ANGLE_90 );
1360 break;
1361
1362 case PIN_ORIENTATION::PIN_DOWN:
1363 RotatePoint( begin, VECTOR2I( 0, 0 ), ANGLE_90 );
1364 RotatePoint( end, VECTOR2I( 0, 0 ), ANGLE_90 );
1365 begin.x = -begin.x;
1366 end.x = -end.x;
1367 break;
1368
1369 case PIN_ORIENTATION::PIN_LEFT:
1370 begin.x = -begin.x;
1371 end.x = -end.x;
1372 break;
1373
1374 case PIN_ORIENTATION::PIN_RIGHT:
1375 break;
1376 }
1377
1378 begin += m_position;
1379 end += m_position;
1380
1381 bbox.SetOrigin( begin );
1382 bbox.SetEnd( end );
1383 bbox.Normalize();
1384 bbox.Inflate( ( GetPenWidth() / 2 ) + 1 );
1385
1386 // Draw Y axis is reversed in schematic:
1387 bbox.RevertYAxis();
1388
1389 return bbox;
1390}
1391
1392
1394{
1396}
1397
1398
1399wxString LIB_PIN::GetItemDescription( UNITS_PROVIDER* aUnitsProvider, ALT* aAlt ) const
1400{
1401 return getItemDescription( aAlt );
1402}
1403
1404
1405wxString LIB_PIN::GetItemDescription( UNITS_PROVIDER* aUnitsProvider ) const
1406{
1407 return getItemDescription( nullptr );
1408}
1409
1410
1411wxString LIB_PIN::getItemDescription( ALT* aAlt ) const
1412{
1413 // This code previously checked "m_name.IsEmpty()" to choose the correct
1414 // formatting path, but that check fails if the pin is called "~" which is
1415 // the default for an empty pin name. Instead we get the final display string
1416 // that will be shown and check if it's empty.
1417
1418 wxString name = UnescapeString( aAlt ? aAlt->m_Name : GetShownName() );
1419 wxString electricalTypeName = ElectricalPinTypeGetText( aAlt ? aAlt->m_Type : m_type );
1420 wxString pinShapeName = PinShapeGetText( aAlt ? aAlt->m_Shape : m_shape );
1421
1422 if( IsVisible() )
1423 {
1424 if ( !name.IsEmpty() )
1425 {
1426 return wxString::Format( _( "Pin %s [%s, %s, %s]" ),
1428 name,
1429 electricalTypeName,
1430 pinShapeName );
1431 }
1432 else
1433 {
1434 return wxString::Format( _( "Pin %s [%s, %s]" ),
1436 electricalTypeName,
1437 pinShapeName );
1438 }
1439 }
1440 else
1441 {
1442 if( !name.IsEmpty() )
1443 {
1444 return wxString::Format( _( "Hidden pin %s [%s, %s, %s]" ),
1446 name,
1447 electricalTypeName,
1448 pinShapeName );
1449 }
1450 else
1451 {
1452 return wxString::Format( _( "Hidden pin %s [%s, %s]" ),
1454 electricalTypeName,
1455 pinShapeName );
1456 }
1457 }
1458}
1459
1460
1461bool LIB_PIN::operator==( const LIB_ITEM& aOther ) const
1462{
1463 if( aOther.Type() != LIB_PIN_T )
1464 return false;
1465
1466 const LIB_PIN* other = static_cast<const LIB_PIN*>( &aOther );
1467
1468 if( m_name != other->m_name )
1469 return false;
1470
1471 if( m_number != other->m_number )
1472 return false;
1473
1474 if( m_position != other->m_position )
1475 return false;
1476
1477 if( m_length != other->m_length )
1478 return false;
1479
1480 if( m_orientation != other->m_orientation )
1481 return false;
1482
1483 if( m_shape != other->m_shape )
1484 return false;
1485
1486 if( m_type != other->m_type )
1487 return false;
1488
1489 if( m_attributes != other->m_attributes )
1490 return false;
1491
1492 if( m_numTextSize != other->m_numTextSize )
1493 return false;
1494
1495 if( m_nameTextSize != other->m_nameTextSize )
1496 return false;
1497
1498 if( m_alternates.size() != other->m_alternates.size() )
1499 return false;
1500
1501 auto lhsItem = m_alternates.begin();
1502 auto rhsItem = other->m_alternates.begin();
1503
1504 while( lhsItem != m_alternates.end() )
1505 {
1506 if( rhsItem == other->m_alternates.end() )
1507 return false;
1508
1509 const ALT& lhsAlt = lhsItem->second;
1510 const ALT& rhsAlt = rhsItem->second;
1511
1512 if( lhsAlt.m_Name != rhsAlt.m_Name )
1513 return false;
1514
1515 if( lhsAlt.m_Type != rhsAlt.m_Type )
1516 return false;
1517
1518 if( lhsAlt.m_Shape != rhsAlt.m_Shape )
1519 return false;
1520
1521 ++lhsItem;
1522 ++rhsItem;
1523 }
1524
1525 return rhsItem == other->m_alternates.end();
1526}
1527
1528
1529double LIB_PIN::Similarity( const LIB_ITEM& aOther ) const
1530{
1531 if( aOther.m_Uuid == m_Uuid )
1532 return 1.0;
1533
1534 if( aOther.Type() != LIB_PIN_T )
1535 return 0.0;
1536
1537 const LIB_PIN* other = static_cast<const LIB_PIN*>( &aOther );
1538
1539 double similarity = SimilarityBase( aOther );
1540
1541 if( m_name != other->m_name )
1542 similarity *= 0.9;
1543
1544 if( m_number != other->m_number )
1545 similarity *= 0.9;
1546
1547 if( m_position != other->m_position )
1548 similarity *= 0.9;
1549
1550 if( m_length != other->m_length )
1551 similarity *= 0.9;
1552
1553 if( m_orientation != other->m_orientation )
1554 similarity *= 0.9;
1555
1556 if( m_shape != other->m_shape )
1557 similarity *= 0.9;
1558
1559 if( m_type != other->m_type )
1560 similarity *= 0.9;
1561
1562 if( m_attributes != other->m_attributes )
1563 similarity *= 0.9;
1564
1565 if( m_numTextSize != other->m_numTextSize )
1566 similarity *= 0.9;
1567
1568 if( m_nameTextSize != other->m_nameTextSize )
1569 similarity *= 0.9;
1570
1571 if( m_alternates.size() != other->m_alternates.size() )
1572 similarity *= 0.9;
1573
1574 return similarity;
1575}
1576
1577
1578std::ostream& LIB_PIN::operator<<( std::ostream& aStream )
1579{
1580 aStream << "LIB_PIN:" << std::endl
1581 << " Name: \"" << m_name << "\"" << std::endl
1582 << " Number: \"" << m_number << "\"" << std::endl
1583 << " Position: " << m_position << std::endl
1584 << " Length: " << m_length << std::endl
1585 << " Orientation: " << PinOrientationName( m_orientation ) << std::endl
1586 << " Shape: " << PinShapeGetText( m_shape ) << std::endl
1587 << " Type: " << ElectricalPinTypeGetText( m_type ) << std::endl
1588 << " Name Text Size: " << m_nameTextSize << std::endl
1589 << " Number Text Size: " << m_numTextSize << std::endl;
1590
1591 return aStream;
1592}
1593
1594
1595#if defined(DEBUG)
1596
1597void LIB_PIN::Show( int nestLevel, std::ostream& os ) const
1598{
1599 NestedSpace( nestLevel, os ) << '<' << GetClass().Lower().mb_str()
1600 << " num=\"" << m_number.mb_str()
1601 << '"' << "/>\n";
1602
1603// NestedSpace( nestLevel, os ) << "</" << GetClass().Lower().mb_str() << ">\n";
1604}
1605
1606#endif
1607
1608void LIB_PIN::CalcEdit( const VECTOR2I& aPosition )
1609{
1610 if( IsMoving() )
1611 MoveTo( aPosition );
1612}
1613
1614
1615static struct LIB_PIN_DESC
1616{
1618 {
1619 auto& pinTypeEnum = ENUM_MAP<ELECTRICAL_PINTYPE>::Instance();
1620
1621 if( pinTypeEnum.Choices().GetCount() == 0 )
1622 {
1623 pinTypeEnum.Map( ELECTRICAL_PINTYPE::PT_INPUT, _HKI( "Input" ) )
1624 .Map( ELECTRICAL_PINTYPE::PT_OUTPUT, _HKI( "Output" ) )
1625 .Map( ELECTRICAL_PINTYPE::PT_BIDI, _HKI( "Bidirectional" ) )
1626 .Map( ELECTRICAL_PINTYPE::PT_TRISTATE, _HKI( "Tri-state" ) )
1627 .Map( ELECTRICAL_PINTYPE::PT_PASSIVE, _HKI( "Passive" ) )
1628 .Map( ELECTRICAL_PINTYPE::PT_NIC, _HKI( "Free" ) )
1629 .Map( ELECTRICAL_PINTYPE::PT_UNSPECIFIED, _HKI( "Unspecified" ) )
1630 .Map( ELECTRICAL_PINTYPE::PT_POWER_IN, _HKI( "Power input" ) )
1631 .Map( ELECTRICAL_PINTYPE::PT_POWER_OUT, _HKI( "Power output" ) )
1632 .Map( ELECTRICAL_PINTYPE::PT_OPENCOLLECTOR, _HKI( "Open collector" ) )
1633 .Map( ELECTRICAL_PINTYPE::PT_OPENEMITTER, _HKI( "Open emitter" ) )
1634 .Map( ELECTRICAL_PINTYPE::PT_NC, _HKI( "Unconnected" ) );
1635 }
1636
1637 auto& pinShapeEnum = ENUM_MAP<GRAPHIC_PINSHAPE>::Instance();
1638
1639 if( pinShapeEnum.Choices().GetCount() == 0 )
1640 {
1641 pinShapeEnum.Map( GRAPHIC_PINSHAPE::LINE, _HKI( "Line" ) )
1642 .Map( GRAPHIC_PINSHAPE::INVERTED, _HKI( "Inverted" ) )
1643 .Map( GRAPHIC_PINSHAPE::CLOCK, _HKI( "Clock" ) )
1644 .Map( GRAPHIC_PINSHAPE::INVERTED_CLOCK, _HKI( "Inverted clock" ) )
1645 .Map( GRAPHIC_PINSHAPE::INPUT_LOW, _HKI( "Input low" ) )
1646 .Map( GRAPHIC_PINSHAPE::CLOCK_LOW, _HKI( "Clock low" ) )
1647 .Map( GRAPHIC_PINSHAPE::OUTPUT_LOW, _HKI( "Output low" ) )
1648 .Map( GRAPHIC_PINSHAPE::FALLING_EDGE_CLOCK, _HKI( "Falling edge clock" ) )
1649 .Map( GRAPHIC_PINSHAPE::NONLOGIC, _HKI( "NonLogic" ) );
1650 }
1651
1652 auto& orientationEnum = ENUM_MAP<PIN_ORIENTATION>::Instance();
1653
1654 if( orientationEnum.Choices().GetCount() == 0 )
1655 {
1656 orientationEnum.Map( PIN_ORIENTATION::PIN_RIGHT, _( "Right" ) )
1657 .Map( PIN_ORIENTATION::PIN_LEFT, _( "Left" ) )
1658 .Map( PIN_ORIENTATION::PIN_UP, _( "Up" ) )
1659 .Map( PIN_ORIENTATION::PIN_DOWN, _( "Down" ) );
1660 }
1661
1665
1666 propMgr.AddProperty( new PROPERTY<LIB_PIN, wxString>( _HKI( "Pin Name" ),
1668
1669 propMgr.AddProperty( new PROPERTY<LIB_PIN, wxString>( _HKI( "Pin Number" ),
1671
1673 _HKI( "Electrical Type" ),
1675
1677 _HKI( "Graphic Style" ),
1679
1680 propMgr.AddProperty( new PROPERTY<LIB_PIN, int>( _HKI( "Position X" ),
1681 &LIB_PIN::SetX, &LIB_PIN::GetX, PROPERTY_DISPLAY::PT_COORD ) );
1682
1683 propMgr.AddProperty( new PROPERTY<LIB_PIN, int>( _HKI( "Position Y" ),
1684 &LIB_PIN::SetY, &LIB_PIN::GetY, PROPERTY_DISPLAY::PT_COORD ) );
1685
1686 propMgr.AddProperty( new PROPERTY_ENUM<LIB_PIN, PIN_ORIENTATION>( _HKI( "Orientation" ),
1688
1689 propMgr.AddProperty( new PROPERTY<LIB_PIN, int>( _HKI( "Length" ),
1691 PROPERTY_DISPLAY::PT_SIZE ) );
1692
1693 propMgr.AddProperty( new PROPERTY<LIB_PIN, int>( _HKI( "Name Text Size" ),
1695 PROPERTY_DISPLAY::PT_SIZE ) );
1696
1697 propMgr.AddProperty( new PROPERTY<LIB_PIN, int>( _HKI( "Number Text Size" ),
1699 PROPERTY_DISPLAY::PT_SIZE ) );
1700
1701 propMgr.AddProperty( new PROPERTY<LIB_PIN, bool>( _HKI( "Visible" ),
1703 }
1705
1706
int color
Definition: DXF_plotter.cpp:58
const char * name
Definition: DXF_plotter.cpp:57
constexpr EDA_IU_SCALE schIUScale
Definition: base_units.h:111
BITMAPS
A list of all bitmap identifiers.
Definition: bitmaps_list.h:33
void SetOrigin(const Vec &pos)
Definition: box2.h:203
BOX2< Vec > & Normalize()
Ensure that the height and width are positive.
Definition: box2.h:120
void RevertYAxis()
Mirror the rectangle from the X axis (negate Y pos and size).
Definition: box2.h:690
bool Intersects(const BOX2< Vec > &aRect) const
Definition: box2.h:270
bool Contains(const Vec &aPoint) const
Definition: box2.h:142
BOX2< Vec > & Inflate(coord_type dx, coord_type dy)
Inflates the rectangle horizontally by dx and vertically by dy.
Definition: box2.h:507
void SetEnd(coord_type x, coord_type y)
Definition: box2.h:256
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:85
const KIID m_Uuid
Definition: eda_item.h:482
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:97
EDA_ITEM_FLAGS m_flags
Definition: eda_item.h:487
EDA_ITEM_FLAGS GetFlags() const
Definition: eda_item.h:126
bool IsMoving() const
Definition: eda_item.h:104
static ENUM_MAP< T > & Instance()
Definition: property.h:653
FONT is an abstract base class for both outline and stroke fonts.
Definition: font.h:131
static FONT * GetFont(const wxString &aFontName=wxEmptyString, bool aBold=false, bool aItalic=false)
Definition: font.cpp:146
VECTOR2I StringBoundaryLimits(const wxString &aText, const VECTOR2I &aSize, int aThickness, bool aBold, bool aItalic, const METRICS &aFontMetrics) const
Compute the boundary limits of aText (the bounding box of all shapes).
Definition: font.cpp:434
A color representation with 4 components: red, green, blue, alpha.
Definition: color4d.h:104
COLOR4D & Desaturate()
Removes color (in HSL model)
Definition: color4d.cpp:511
COLOR4D Mix(const COLOR4D &aColor, double aFactor) const
Return a color that is mixed with the input by a factor.
Definition: color4d.h:295
Container for all the knowledge about how graphical objects are drawn on any output surface/device.
int GetDefaultPenWidth() const
const wxString & GetDefaultFont() const
const COLOR4D & GetLayerColor(int aLayer) const
Return the color used to draw a layer.
virtual const COLOR4D & GetBackgroundColor() const =0
Return current background color settings.
wxDC * GetPrintDC() const
Store schematic specific render settings.
Definition: sch_painter.h:72
The base class for drawable items used by schematic library symbols.
Definition: lib_item.h:68
@ UNIT
Definition: lib_item.h:95
virtual int compare(const LIB_ITEM &aOther, int aCompareFlags=0) const
Provide the draw object specific comparison called by the == and < operators.
Definition: lib_item.cpp:88
virtual int GetEffectivePenWidth(const RENDER_SETTINGS *aSettings) const
Definition: lib_item.h:196
double SimilarityBase(const LIB_ITEM &aItem) const
Calculate the boilerplate similarity for all LIB_ITEMs without preventing the use above of a pure vir...
Definition: lib_item.h:227
const KIFONT::METRICS & GetFontMetrics() const
Definition: lib_item.cpp:165
void GetMsgPanelInfo(EDA_DRAW_FRAME *aFrame, std::vector< MSG_PANEL_ITEM > &aList) override
Display basic info (type, part and convert) about the current item in message panel.
Definition: lib_item.cpp:68
void SetBodyStyle(int aBodyStyle)
Definition: lib_item.h:345
LIB_SYMBOL * GetParent() const
Definition: lib_item.h:209
void SetUnit(int aUnit)
Definition: lib_item.h:342
void printPinElectricalTypeName(const RENDER_SETTINGS *aSettings, VECTOR2I &aPosition, PIN_ORIENTATION aOrientation, bool aDimmed)
Draw the electrical type text of the pin (only for the footprint editor)
Definition: lib_pin.cpp:557
void SetShape(GRAPHIC_PINSHAPE aShape)
Definition: lib_pin.h:72
int m_attributes
Definition: lib_pin.h:333
void ViewGetLayers(int aLayers[], int &aCount) const override
Return the all the layers within the VIEW the object is painted on.
Definition: lib_pin.cpp:1221
void MirrorHorizontal(const VECTOR2I &aCenter) override
Mirror the draw object along the horizontal (X) axis about aCenter point.
Definition: lib_pin.cpp:1116
int GetLength() const
Definition: lib_pin.h:74
void Offset(const VECTOR2I &aOffset) override
Set the drawing object by aOffset from the current position.
Definition: lib_pin.cpp:1104
ELECTRICAL_PINTYPE GetType() const
Definition: lib_pin.h:84
const BOX2I GetBoundingBox() const override
Definition: lib_pin.h:193
void SetName(const wxString &aName)
Definition: lib_pin.h:108
void MirrorVertical(const VECTOR2I &aCenter) override
Mirror the draw object along the MirrorVertical (Y) axis about aCenter point.
Definition: lib_pin.cpp:1129
int compare(const LIB_ITEM &aOther, int aCompareFlags=0) const override
Provide the draw object specific comparison called by the == and < operators.
Definition: lib_pin.cpp:999
int GetX() const
Definition: lib_pin.h:236
void SetNameTextSize(int aSize)
Definition: lib_pin.h:129
wxString m_name
Definition: lib_pin.h:334
void validateExtentsCache(KIFONT::FONT *aFont, int aSize, const wxString &aText, EXTENTS_CACHE *aCache) const
Definition: lib_pin.cpp:1235
void PlotPinTexts(PLOTTER *aPlotter, const VECTOR2I &aPinPos, PIN_ORIENTATION aPinOrient, int aTextInside, bool aDrawPinNum, bool aDrawPinName, bool aDimmed) const
Plot the pin number and pin text info, given the pin line coordinates.
Definition: lib_pin.cpp:768
void SetType(ELECTRICAL_PINTYPE aType)
Definition: lib_pin.h:85
const BOX2I ViewBBox() const override
Return the bounding box of the item covering all its layers.
Definition: lib_pin.cpp:1215
PIN_ORIENTATION GetOrientation() const
Definition: lib_pin.h:68
int m_nameTextSize
Definition: lib_pin.h:337
wxString getItemDescription(ALT *aAlt) const
Definition: lib_pin.cpp:1411
std::ostream & operator<<(std::ostream &aStream)
Definition: lib_pin.cpp:1578
void SetY(int aY)
Definition: lib_pin.h:239
wxString GetShownNumber() const
Definition: lib_pin.h:118
LIB_PIN(LIB_SYMBOL *aParent)
Definition: lib_pin.cpp:97
int GetNumberTextSize() const
Definition: lib_pin.h:135
void SetVisible(bool aVisible)
Definition: lib_pin.h:98
void GetMsgPanelInfo(EDA_DRAW_FRAME *aFrame, std::vector< MSG_PANEL_ITEM > &aList) override
Display basic info (type, part and convert) about the current item in message panel.
Definition: lib_pin.cpp:1187
wxString GetItemDescription(UNITS_PROVIDER *aUnitsProvider) const override
Return a user-visible description string of this item.
Definition: lib_pin.cpp:1405
wxString GetShownName() const
Definition: lib_pin.cpp:176
int m_length
Definition: lib_pin.h:329
void Rotate(const VECTOR2I &aCenter, bool aRotateCCW=true) override
Rotate the object about aCenter point.
Definition: lib_pin.cpp:1142
void ChangeLength(int aLength)
Change the length of a pin and adjust its position based on orientation.
Definition: lib_pin.cpp:1076
wxString const GetCanonicalElectricalTypeName() const
Definition: lib_pin.h:87
BITMAPS GetMenuImage() const override
Return a pointer to an image to be used in menus.
Definition: lib_pin.cpp:1393
void SetX(int aX)
Definition: lib_pin.h:237
void MoveTo(const VECTOR2I &aNewPosition) override
Move a draw object to aPosition.
Definition: lib_pin.cpp:1110
wxString GetClass() const override
Return the class name.
Definition: lib_pin.h:53
VECTOR2I m_position
Definition: lib_pin.h:328
bool operator==(const LIB_ITEM &aItem) const override
Test LIB_ITEM objects for equivalence.
Definition: lib_pin.cpp:1461
int m_numTextSize
Definition: lib_pin.h:336
GRAPHIC_PINSHAPE m_shape
Definition: lib_pin.h:331
EXTENTS_CACHE m_nameExtentsCache
Definition: lib_pin.h:346
VECTOR2I GetPosition() const override
Definition: lib_pin.h:232
void CalcEdit(const VECTOR2I &aPosition) override
Calculate the attributes of an item at aPosition when it is being edited.
Definition: lib_pin.cpp:1608
const wxString & GetNumber() const
Definition: lib_pin.h:117
PIN_ORIENTATION PinDrawOrient(const TRANSFORM &aTransform) const
Return the pin real orientation (PIN_UP, PIN_DOWN, PIN_RIGHT, PIN_LEFT), according to its orientation...
Definition: lib_pin.cpp:959
wxString const GetElectricalTypeName() const
Definition: lib_pin.h:92
std::map< wxString, ALT > m_alternates
Definition: lib_pin.h:339
int GetY() const
Definition: lib_pin.h:238
void SetOrientation(PIN_ORIENTATION aOrientation)
Definition: lib_pin.h:69
EXTENTS_CACHE m_numExtentsCache
Definition: lib_pin.h:345
GRAPHIC_PINSHAPE GetShape() const
Definition: lib_pin.h:71
bool IsVisible() const
Definition: lib_pin.h:97
void SetNumber(const wxString &aNumber)
Definition: lib_pin.h:119
void print(const RENDER_SETTINGS *aSettings, const VECTOR2I &aOffset, void *aData, const TRANSFORM &aTransform, bool aDimmed) override
Print a pin, with or without the pin texts.
Definition: lib_pin.cpp:198
void printPinSymbol(const RENDER_SETTINGS *aSettings, const VECTOR2I &aPos, PIN_ORIENTATION aOrientation, bool aDimmed)
Print the pin symbol without text.
Definition: lib_pin.cpp:252
PIN_ORIENTATION m_orientation
Definition: lib_pin.h:330
void printPinTexts(const RENDER_SETTINGS *aSettings, VECTOR2I &aPinPos, PIN_ORIENTATION aPinOrient, int aTextInside, bool aDrawPinNum, bool aDrawPinName, bool aDimmed)
Put the pin number and pin text info, given the pin line coordinates.
Definition: lib_pin.cpp:377
ELECTRICAL_PINTYPE m_type
Definition: lib_pin.h:332
const wxString & GetName() const
Definition: lib_pin.h:106
void Plot(PLOTTER *aPlotter, bool aBackground, const VECTOR2I &aOffset, const TRANSFORM &aTransform, bool aDimmed) const override
Plot the draw item using the plot object.
Definition: lib_pin.cpp:1171
double Similarity(const LIB_ITEM &aItem) const override
Return a measure of how likely the other object is to represent the same object.
Definition: lib_pin.cpp:1529
wxString m_number
Definition: lib_pin.h:335
void SetLength(int aLength)
Definition: lib_pin.h:75
void PlotSymbol(PLOTTER *aPlotter, const VECTOR2I &aPosition, PIN_ORIENTATION aOrientation, bool aDimmed) const
Definition: lib_pin.cpp:624
int GetNameTextSize() const
Definition: lib_pin.h:128
EDA_ITEM * Clone() const override
Create a duplicate of this item with linked list members set to NULL.
Definition: lib_pin.cpp:993
VECTOR2I GetPinRoot() const
Definition: lib_pin.cpp:185
bool HitTest(const VECTOR2I &aPosition, int aAccuracy=0) const override
Test if aPosition is inside or on the boundary of this item.
Definition: lib_pin.cpp:145
int GetPenWidth() const override
Definition: lib_pin.cpp:170
void SetNumberTextSize(int aSize)
Definition: lib_pin.h:136
Define a library symbol object.
Definition: lib_symbol.h:99
int GetPinNameOffset() const
Definition: lib_symbol.h:625
bool ShowPinNames() const
Definition: lib_symbol.h:633
bool ShowPinNumbers() const
Definition: lib_symbol.h:641
Container for data for KiCad programs.
Definition: pgm_base.h:96
virtual SETTINGS_MANAGER & GetSettingsManager() const
Definition: pgm_base.h:136
Base plotter engine class.
Definition: plotter.h:104
virtual void Circle(const VECTOR2I &pos, int diametre, FILL_T fill, int width=USE_DEFAULT_LINE_WIDTH)=0
void MoveTo(const VECTOR2I &pos)
Definition: plotter.h:243
void FinishTo(const VECTOR2I &pos)
Definition: plotter.h:253
RENDER_SETTINGS * RenderSettings()
Definition: plotter.h:135
bool GetColorMode() const
Definition: plotter.h:132
virtual void SetCurrentLineWidth(int width, void *aData=nullptr)=0
Set the line width for the next drawing.
void LineTo(const VECTOR2I &pos)
Definition: plotter.h:248
virtual void PlotText(const VECTOR2I &aPos, const COLOR4D &aColor, const wxString &aText, const TEXT_ATTRIBUTES &aAttributes, KIFONT::FONT *aFont, const KIFONT::METRICS &aFontMetrics, void *aData=nullptr)
Definition: plotter.cpp:753
virtual void SetColor(const COLOR4D &color)=0
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.
static PROPERTY_MANAGER & Instance()
Definition: property_mgr.h:87
PROPERTY_BASE & AddProperty(PROPERTY_BASE *aProperty, const wxString &aGroup=wxEmptyString)
Register a property.
Base class for any item which can be embedded within the SCHEMATIC container class,...
Definition: sch_item.h:165
T * GetAppSettings()
Returns a handle to the a given settings by type If the settings have already been loaded,...
GR_TEXT_H_ALIGN_T m_Halign
GR_TEXT_V_ALIGN_T m_Valign
for transforming drawing coordinates for a wxDC device context.
Definition: transform.h:46
VECTOR2I TransformCoordinate(const VECTOR2I &aPoint) const
Calculate a new coordinate according to the mirror/rotation transform.
Definition: transform.cpp:44
wxString MessageTextFromValue(double aValue, bool aAddUnitLabel=true, EDA_DATA_TYPE aType=EDA_DATA_TYPE::DISTANCE) const
A lower-precision version of StringFromValue().
PGM_BASE * PgmOrNull()
similar to PGM_BASE& Pgm(), but return a reference that can be nullptr when running a shared lib from...
Definition: cvpcb.cpp:160
#define DEFAULT_PINNUM_SIZE
The default pin name size when creating pins(can be changed in preference menu)
#define DEFAULT_PINNAME_SIZE
The default selection highlight thickness (can be changed in preference menu)
#define DEFAULT_PIN_LENGTH
The default pin number size when creating pins(can be changed in preference menu)
#define _HKI(x)
#define _(s)
static constexpr EDA_ANGLE ANGLE_90
Definition: eda_angle.h:437
static constexpr EDA_ANGLE ANGLE_VERTICAL
Definition: eda_angle.h:432
static constexpr EDA_ANGLE ANGLE_HORIZONTAL
Definition: eda_angle.h:431
#define STRUCT_DELETED
flag indication structures to be erased
#define SKIP_STRUCT
flag indicating that the structure should be ignored
#define SHOW_ELEC_TYPE
Show pin electrical type. Shared with IS_ROLLOVER.
TRANSFORM DefaultTransform
Definition: transform.cpp:32
void GRLineTo(wxDC *DC, int x, int y, int width, const COLOR4D &Color)
Definition: gr_basic.cpp:195
void GRCircle(wxDC *aDC, const VECTOR2I &aPos, int aRadius, int aWidth, const COLOR4D &aColor)
Definition: gr_basic.cpp:357
void GRMoveTo(int x, int y)
Definition: gr_basic.cpp:188
void GRLine(wxDC *DC, int x1, int y1, int x2, int y2, int width, const COLOR4D &Color, wxPenStyle aStyle)
Definition: gr_basic.cpp:171
bool GetGRForceBlackPenState(void)
Definition: gr_basic.cpp:165
int GetPenSizeForNormal(int aTextSize)
Definition: gr_text.cpp:64
int Clamp_Text_PenSize(int aPenSize, int aSize, bool aStrict)
Pen width should not allow characters to become cluttered up in their own fatness.
Definition: gr_text.cpp:87
void GRPrintText(wxDC *aDC, const VECTOR2I &aPos, const COLOR4D &aColor, const wxString &aText, const EDA_ANGLE &aOrient, const VECTOR2I &aSize, enum GR_TEXT_H_ALIGN_T aH_justify, enum GR_TEXT_V_ALIGN_T aV_justify, int aWidth, bool aItalic, bool aBold, KIFONT::FONT *aFont, const KIFONT::METRICS &aFontMetrics)
Print a graphic text through wxDC.
Definition: gr_text.cpp:142
@ LAYER_DANGLING
Definition: layer_ids.h:379
@ LAYER_PINNUM
Definition: layer_ids.h:361
@ LAYER_DEVICE
Definition: layer_ids.h:368
@ LAYER_HIDDEN
Definition: layer_ids.h:392
@ LAYER_PINNAM
Definition: layer_ids.h:362
@ LAYER_PRIVATE_NOTES
Definition: layer_ids.h:370
@ LAYER_PIN
Definition: layer_ids.h:372
@ LAYER_OP_CURRENTS
Definition: layer_ids.h:400
@ LAYER_SELECTION_SHADOWS
Definition: layer_ids.h:393
#define ETXT_MAX_SIZE
#define PIN_TEXT_MARGIN
Definition: lib_pin.cpp:41
static int externalPinDecoSize(const RENDER_SETTINGS *aSettings, const LIB_PIN &aPin)
Utility for getting the size of the 'external' pin decorators (as a radius)
Definition: lib_pin.cpp:86
static struct LIB_PIN_DESC _LIB_PIN_DESC
static int internalPinDecoSize(const RENDER_SETTINGS *aSettings, const LIB_PIN &aPin)
Utility for getting the size of the 'internal' pin decorators (as a radius)
Definition: lib_pin.cpp:73
#define TARGET_PIN_RADIUS
Definition: lib_pin.h:35
see class PGM_BASE
wxString ElectricalPinTypeGetText(ELECTRICAL_PINTYPE aType)
Definition: pin_type.cpp:196
BITMAPS ElectricalPinTypeGetBitmap(ELECTRICAL_PINTYPE aType)
Definition: pin_type.cpp:224
wxString PinShapeGetText(GRAPHIC_PINSHAPE aShape)
Definition: pin_type.cpp:234
wxString PinOrientationName(PIN_ORIENTATION aOrientation)
Definition: pin_type.cpp:254
ELECTRICAL_PINTYPE
The symbol library pin object electrical types used in ERC tests.
Definition: pin_type.h:36
@ PT_UNSPECIFIED
unknown electrical properties: creates always a warning when connected
PIN_ORIENTATION
The symbol library pin object orientations.
Definition: pin_type.h:75
GRAPHIC_PINSHAPE
Definition: pin_type.h:56
#define TYPE_HASH(x)
Definition: property.h:67
#define ENUM_TO_WXANY(type)
Macro to define read-only fields (no setter method available)
Definition: property.h:755
#define REGISTER_TYPE(x)
Definition: property_mgr.h:366
KIWAY Kiway & Pgm(), KFCTL_STANDALONE
The global Program "get" accessor.
Definition: single_top.cpp:119
wxString UnescapeString(const wxString &aSource)
constexpr int MilsToIU(int mils) const
Definition: base_units.h:94
constexpr int mmToIU(double mm) const
Definition: base_units.h:89
GRAPHIC_PINSHAPE m_Shape
Definition: lib_pin.h:47
ELECTRICAL_PINTYPE m_Type
Definition: lib_pin.h:48
wxString m_Name
Definition: lib_pin.h:46
KIFONT::FONT * m_Font
Definition: lib_pin.h:281
bool force_draw_pin_text
Definition: lib_symbol.h:65
GR_TEXT_H_ALIGN_T
@ GR_TEXT_H_ALIGN_CENTER
@ GR_TEXT_H_ALIGN_RIGHT
@ GR_TEXT_H_ALIGN_LEFT
GR_TEXT_V_ALIGN_T
@ GR_TEXT_V_ALIGN_BOTTOM
@ GR_TEXT_V_ALIGN_CENTER
@ 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
@ LIB_PIN_T
Definition: typeinfo.h:206
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:85
VECTOR2< double > VECTOR2D
Definition: vector2d.h:587
VECTOR2< int > VECTOR2I
Definition: vector2d.h:588