KiCad PCB EDA Suite
Loading...
Searching...
No Matches
sch_field.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) 2015 Jean-Pierre Charras, jp.charras at wanadoo.fr
5 * Copyright (C) 2004-2024 KiCad Developers, see AUTHORS.txt for contributors.
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, you may find one here:
19 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
20 * or you may search the http://www.gnu.org website for the version 2 license,
21 * or you may write to the Free Software Foundation, Inc.,
22 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
23 */
24
25/*
26 * Fields are texts attached to a symbol, some of which have a special meaning.
27 * Fields 0 and 1 are very important: reference and value.
28 * Field 2 is used as default footprint name.
29 * Field 3 is used to point to a datasheet (usually a URL).
30 * Fields 4+ are user fields. They can be renamed and can appear in reports.
31 */
32
33#include <wx/log.h>
34#include <wx/menu.h>
35
36#include <advanced_config.h>
37#include <base_units.h>
38#include <common.h> // for ExpandTextVars
39#include <sch_edit_frame.h>
40#include <plotters/plotter.h>
41#include <bitmaps.h>
42#include <core/mirror.h>
43#include <kiway.h>
44#include <symbol_library.h>
45#include <sch_symbol.h>
46#include <sch_field.h>
47#include <sch_label.h>
48#include <schematic.h>
50#include <string_utils.h>
51#include <trace_helpers.h>
52#include <tool/tool_manager.h>
54#include <font/outline_font.h>
55#include "sim/sim_lib_mgr.h"
56
57static const std::vector<KICAD_T> labelTypes = { SCH_LABEL_LOCATE_ANY_T };
58
59
60SCH_FIELD::SCH_FIELD( const VECTOR2I& aPos, int aFieldId, SCH_ITEM* aParent,
61 const wxString& aName ) :
62 SCH_ITEM( aParent, SCH_FIELD_T ),
63 EDA_TEXT( schIUScale, wxEmptyString ),
64 m_id( 0 ),
65 m_showName( false ),
66 m_allowAutoPlace( true ),
67 m_autoAdded( false ),
68 m_showInChooser( true ),
69 m_renderCacheValid( false ),
70 m_lastResolvedColor( COLOR4D::UNSPECIFIED )
71{
72 if( aName.IsEmpty() )
74 else
75 SetName( aName );
76
77 SetTextPos( aPos );
78 SetId( aFieldId ); // will also set the layer
79 SetVisible( true );
80}
81
82
83SCH_FIELD::SCH_FIELD( SCH_ITEM* aParent, int aFieldId, const wxString& aName) :
84 SCH_FIELD( VECTOR2I(), aFieldId, aParent, aName )
85{
86}
87
88
90 SCH_ITEM( aField ),
91 EDA_TEXT( aField )
92{
93 m_private = aField.m_private;
94 m_id = aField.m_id;
95 m_name = aField.m_name;
96 m_showName = aField.m_showName;
99 m_autoAdded = aField.m_autoAdded;
101
102 m_renderCache.clear();
103
104 for( const std::unique_ptr<KIFONT::GLYPH>& glyph : aField.m_renderCache )
105 {
106 if( KIFONT::OUTLINE_GLYPH* outline = dynamic_cast<KIFONT::OUTLINE_GLYPH*>( glyph.get() ) )
107 m_renderCache.emplace_back( std::make_unique<KIFONT::OUTLINE_GLYPH>( *outline ) );
108 else if( KIFONT::STROKE_GLYPH* stroke = dynamic_cast<KIFONT::STROKE_GLYPH*>( glyph.get() ) )
109 m_renderCache.emplace_back( std::make_unique<KIFONT::STROKE_GLYPH>( *stroke ) );
110 }
111
114
116}
117
118
120{
121 EDA_TEXT::operator=( aField );
122
123 m_private = aField.m_private;
124 m_id = aField.m_id;
125 m_name = aField.m_name;
126 m_showName = aField.m_showName;
129
130 m_renderCache.clear();
131
132 for( const std::unique_ptr<KIFONT::GLYPH>& glyph : aField.m_renderCache )
133 {
134 if( KIFONT::OUTLINE_GLYPH* outline = dynamic_cast<KIFONT::OUTLINE_GLYPH*>( glyph.get() ) )
135 m_renderCache.emplace_back( std::make_unique<KIFONT::OUTLINE_GLYPH>( *outline ) );
136 else if( KIFONT::STROKE_GLYPH* stroke = dynamic_cast<KIFONT::STROKE_GLYPH*>( glyph.get() ) )
137 m_renderCache.emplace_back( std::make_unique<KIFONT::STROKE_GLYPH>( *stroke ) );
138 }
139
142
144
145 return *this;
146}
147
148
150{
151 return new SCH_FIELD( *this );
152}
153
154
155void SCH_FIELD::Copy( SCH_FIELD* aTarget ) const
156{
157 *aTarget = *this;
158}
159
160
161void SCH_FIELD::SetId( int aId )
162{
163 m_id = aId;
164
165 if( m_parent && m_parent->Type() == SCH_SHEET_T )
166 {
167 switch( m_id )
168 {
169 case SHEETNAME: SetLayer( LAYER_SHEETNAME ); break;
171 default: SetLayer( LAYER_SHEETFIELDS ); break;
172 }
173 }
174 else if( m_parent && ( m_parent->Type() == SCH_SYMBOL_T || m_parent->Type() == LIB_SYMBOL_T ) )
175 {
176 switch( m_id )
177 {
179 case VALUE_FIELD: SetLayer( LAYER_VALUEPART ); break;
180 default: SetLayer( LAYER_FIELDS ); break;
181 }
182 }
183 else if( m_parent && m_parent->IsType( labelTypes ) )
184 {
185 // We can't use defined IDs for labels because there can be multiple net class
186 // assignments.
187
188 if( GetCanonicalName() == wxT( "Netclass" )
189 || GetCanonicalName() == wxT( "Component Class" ) )
190 {
192 }
193 else if( GetCanonicalName() == wxT( "Intersheetrefs" ) )
194 {
196 }
197 else
198 {
200 }
201 }
202}
203
204
206{
208}
209
210
211wxString SCH_FIELD::GetShownText( const SCH_SHEET_PATH* aPath, bool aAllowExtraText,
212 int aDepth ) const
213{
214 std::function<bool( wxString* )> libSymbolResolver =
215 [&]( wxString* token ) -> bool
216 {
217 LIB_SYMBOL* symbol = static_cast<LIB_SYMBOL*>( m_parent );
218 return symbol->ResolveTextVar( token, aDepth + 1 );
219 };
220
221 std::function<bool( wxString* )> symbolResolver =
222 [&]( wxString* token ) -> bool
223 {
224 SCH_SYMBOL* symbol = static_cast<SCH_SYMBOL*>( m_parent );
225 return symbol->ResolveTextVar( aPath, token, aDepth + 1 );
226 };
227
228 std::function<bool( wxString* )> schematicResolver =
229 [&]( wxString* token ) -> bool
230 {
231 if( !aPath )
232 return false;
233
234 if( SCHEMATIC* schematic = Schematic() )
235 return schematic->ResolveTextVar( aPath, token, aDepth + 1 );
236
237 return false;
238 };
239
240 std::function<bool( wxString* )> sheetResolver =
241 [&]( wxString* token ) -> bool
242 {
243 if( !aPath )
244 return false;
245
246 SCH_SHEET* sheet = static_cast<SCH_SHEET*>( m_parent );
247
248 SCHEMATIC* schematic = Schematic();
249 SCH_SHEET_PATH path = *aPath;
250 path.push_back( sheet );
251
252 bool retval = sheet->ResolveTextVar( &path, token, aDepth + 1 );
253
254 if( schematic )
255 retval |= schematic->ResolveTextVar( &path, token, aDepth + 1 );
256
257 return retval;
258 };
259
260 std::function<bool( wxString* )> labelResolver =
261 [&]( wxString* token ) -> bool
262 {
263 if( !aPath )
264 return false;
265
266 SCH_LABEL_BASE* label = static_cast<SCH_LABEL_BASE*>( m_parent );
267 return label->ResolveTextVar( aPath, token, aDepth + 1 );
268 };
269
270 wxString text = EDA_TEXT::GetShownText( aAllowExtraText, aDepth );
271
272 if( IsNameShown() && aAllowExtraText )
273 text = GetShownName() << wxS( ": " ) << text;
274
275 if( text == wxS( "~" ) ) // Legacy placeholder for empty string
276 text = wxS( "" );
277
278 // The iteration here it to allow for nested variables in the
279 // text strings (e.g. ${${VAR}}). Although the symbols and sheets
280 // and labels recurse, text that is none of those types such as text
281 // boxes and labels do not. This only loops if there is still a
282 // variable to resolve.
283 for( int ii = 0; ii < 10 && text.Contains( wxT( "${" ) ); ++ii )
284 {
285 if( aDepth < ADVANCED_CFG::GetCfg().m_ResolveTextRecursionDepth )
286 {
287 if( m_parent && m_parent->Type() == LIB_SYMBOL_T )
288 text = ExpandTextVars( text, &libSymbolResolver );
289 else if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
290 text = ExpandTextVars( text, &symbolResolver );
291 else if( m_parent && m_parent->Type() == SCH_SHEET_T )
292 text = ExpandTextVars( text, &sheetResolver );
293 else if( m_parent && m_parent->IsType( labelTypes ) )
294 text = ExpandTextVars( text, &labelResolver );
295 else if( Schematic() )
296 {
298 text = ExpandTextVars( text, &schematicResolver );
299 }
300 }
301 }
302
303 // WARNING: the IDs of FIELDS and SHEETS overlap, so one must check *both* the
304 // id and the parent's type.
305
306 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
307 {
308 SCH_SYMBOL* parentSymbol = static_cast<SCH_SYMBOL*>( m_parent );
309
310 if( m_id == REFERENCE_FIELD && aPath )
311 {
312 // For more than one part per package, we must add the part selection
313 // A, B, ... or 1, 2, .. to the reference.
314 if( parentSymbol->GetUnitCount() > 1 )
315 text << parentSymbol->SubReference( parentSymbol->GetUnitSelection( aPath ) );
316 }
317 }
318 else if( m_parent && m_parent->Type() == SCH_SHEET_T )
319 {
320 if( m_id == SHEETFILENAME && aAllowExtraText && !IsNameShown() )
321 text = _( "File:" ) + wxS( " " ) + text;
322 }
323
324 return text;
325}
326
327
328wxString SCH_FIELD::GetShownText( bool aAllowExtraText, int aDepth ) const
329{
330 if( SCHEMATIC* schematic = Schematic() )
331 return GetShownText( &schematic->CurrentSheet(), aAllowExtraText, aDepth );
332 else
333 return GetShownText( nullptr, aAllowExtraText, aDepth );
334}
335
336
337wxString SCH_FIELD::GetFullText( int unit ) const
338{
339 if( GetId() != REFERENCE_FIELD )
340 return GetText();
341
342 wxString text = GetText();
343 text << wxT( "?" );
344
345 if( GetParentSymbol() && GetParentSymbol()->IsMulti() )
346 text << LIB_SYMBOL::LetterSubReference( unit, 'A' );
347
348 return text;
349}
350
351
353{
355}
356
357
359{
361
362 if( !font )
364
365 return font;
366}
367
368
370{
373}
374
375
377{
379 m_renderCacheValid = false;
380}
381
382
383std::vector<std::unique_ptr<KIFONT::GLYPH>>*
384SCH_FIELD::GetRenderCache( const wxString& forResolvedText, const VECTOR2I& forPosition,
385 TEXT_ATTRIBUTES& aAttrs ) const
386{
387 KIFONT::FONT* font = GetFont();
388
389 if( !font )
391
392 if( font->IsOutline() )
393 {
394 KIFONT::OUTLINE_FONT* outlineFont = static_cast<KIFONT::OUTLINE_FONT*>( font );
395
396 if( m_renderCache.empty() || !m_renderCacheValid )
397 {
398 m_renderCache.clear();
399
400 outlineFont->GetLinesAsGlyphs( &m_renderCache, forResolvedText, forPosition, aAttrs,
401 GetFontMetrics() );
402
403 m_renderCachePos = forPosition;
404 m_renderCacheValid = true;
405 }
406
407 if( m_renderCachePos != forPosition )
408 {
409 VECTOR2I delta = forPosition - m_renderCachePos;
410
411 for( std::unique_ptr<KIFONT::GLYPH>& glyph : m_renderCache )
412 {
413 if( glyph->IsOutline() )
414 static_cast<KIFONT::OUTLINE_GLYPH*>( glyph.get() )->Move( delta );
415 else
416 static_cast<KIFONT::STROKE_GLYPH*>( glyph.get() )->Move( delta );
417 }
418
419 m_renderCachePos = forPosition;
420 }
421
422 return &m_renderCache;
423 }
424
425 return nullptr;
426}
427
428
429void SCH_FIELD::Print( const SCH_RENDER_SETTINGS* aSettings, int aUnit, int aBodyStyle,
430 const VECTOR2I& aOffset, bool aForceNoFill, bool aDimmed )
431{
432 wxString text;
433
434 if( Schematic() )
435 text = GetShownText( &Schematic()->CurrentSheet(), true );
436 else
437 text = GetShownText( true );
438
439 if( ( !IsVisible() && !IsForceVisible() ) || text.IsEmpty() )
440 return;
441
442 wxDC* DC = aSettings->GetPrintDC();
444 bool blackAndWhiteMode = GetGRForceBlackPenState();
445 int penWidth = GetEffectiveTextPenWidth( aSettings->GetDefaultPenWidth() );
446
447 COLOR4D bg = aSettings->GetBackgroundColor();
448
449 if( bg == COLOR4D::UNSPECIFIED || GetGRForceBlackPenState() )
450 bg = COLOR4D::WHITE;
451
452 if( IsForceVisible() )
453 bg = aSettings->GetLayerColor( LAYER_HIDDEN );
454
455 if( !blackAndWhiteMode && GetTextColor() != COLOR4D::UNSPECIFIED )
457
458 if( aDimmed )
459 {
460 color.Desaturate( );
461 color = color.Mix( bg, 0.5f );
462 }
463
464 // Calculate the text orientation according to the symbol orientation.
465 EDA_ANGLE orient = GetTextAngle();
466 VECTOR2I textpos = GetTextPos();
469 KIFONT::FONT* font = GetFont();
470
471 if( !font )
472 font = KIFONT::FONT::GetFont( aSettings->GetDefaultFont(), IsBold(), IsItalic() );
473
474 if( m_parent && m_parent->Type() == LIB_SYMBOL_T )
475 {
476 textpos = aSettings->TransformCoordinate( GetTextPos() ) + aOffset;
477 }
478 else if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
479 {
480 /*
481 * Calculate the text justification, according to the symbol orientation/mirror.
482 * This is a bit complicated due to cumulative calculations:
483 * - numerous cases (mirrored or not, rotation)
484 * - the GRText function will also recalculate H and V justifications according to the
485 * text orientation.
486 * - when symbol is mirrored, the text is not mirrored and justifications are complicated
487 * to calculate so the easier way is to use no justifications (centered text) and use
488 * GetBoundingBox to know the text coordinate considered as centered
489 */
490 hjustify = GR_TEXT_H_ALIGN_CENTER;
491 vjustify = GR_TEXT_V_ALIGN_CENTER;
492 textpos = GetBoundingBox().Centre() + aOffset;
493
494 if( aSettings->m_Transform.y1 ) // Rotate symbol 90 degrees.
495 {
496 if( orient == ANGLE_HORIZONTAL )
497 orient = ANGLE_VERTICAL;
498 else
499 orient = ANGLE_HORIZONTAL;
500 }
501 }
502 else if( m_parent && m_parent->Type() == SCH_GLOBAL_LABEL_T )
503 {
504 SCH_GLOBALLABEL* label = static_cast<SCH_GLOBALLABEL*>( GetParent() );
505 textpos += label->GetSchematicTextOffset( aSettings );
506 }
507
508 GRPrintText( DC, textpos, color, text, orient, GetTextSize(), hjustify, vjustify, penWidth,
509 IsItalic(), IsBold(), font, GetFontMetrics() );
510}
511
512
513void SCH_FIELD::ImportValues( const SCH_FIELD& aSource )
514{
515 SetAttributes( aSource );
516 SetNameShown( aSource.IsNameShown() );
517 SetCanAutoplace( aSource.CanAutoplace() );
518}
519
520
522{
523 wxCHECK_RET( aItem && aItem->Type() == SCH_FIELD_T, wxT( "Cannot swap with invalid item." ) );
524
525 SCH_ITEM::SwapFlags( aItem );
526
527 SCH_FIELD* item = static_cast<SCH_FIELD*>( aItem );
528
529 std::swap( m_layer, item->m_layer );
530 std::swap( m_showName, item->m_showName );
531 std::swap( m_allowAutoPlace, item->m_allowAutoPlace );
532 std::swap( m_isNamedVariable, item->m_isNamedVariable );
533 std::swap( m_private, item->m_private );
534 SwapText( *item );
535 SwapAttributes( *item );
536
537 std::swap( m_lastResolvedColor, item->m_lastResolvedColor );
538}
539
540
542{
543 if( GetTextColor() != COLOR4D::UNSPECIFIED )
544 {
546 }
547 else
548 {
549 SCH_LABEL_BASE* parentLabel = dynamic_cast<SCH_LABEL_BASE*>( GetParent() );
550
551 if( parentLabel && !parentLabel->IsConnectivityDirty() )
552 m_lastResolvedColor = parentLabel->GetEffectiveNetClass()->GetSchematicColor();
553 else
555 }
556
557 return m_lastResolvedColor;
558}
559
560
561std::vector<int> SCH_FIELD::ViewGetLayers() const
562{
564}
565
566
568{
569 if( m_parent && ( m_parent->Type() == LIB_SYMBOL_T || m_parent->Type() == SCH_SYMBOL_T ) )
570 {
571 if( m_id == REFERENCE_FIELD )
572 return LAYER_REFERENCEPART;
573 else if( m_id == VALUE_FIELD )
574 return LAYER_VALUEPART;
575 }
576 else if( m_parent && m_parent->Type() == SCH_SHEET_T )
577 {
578 if( m_id == SHEETNAME )
579 return LAYER_SHEETNAME;
580 else if( m_id == SHEETFILENAME )
581 return LAYER_SHEETFILENAME;
582 else
583 return LAYER_SHEETFIELDS;
584 }
585 else if( m_parent && m_parent->Type() == SCH_LABEL_T )
586 {
587 if( GetCanonicalName() == wxT( "Netclass" ) )
588 return LAYER_NETCLASS_REFS;
589 }
590
591 return LAYER_FIELDS;
592}
593
594
596{
597 // Calculate the text orientation according to the symbol orientation.
598 EDA_ANGLE orient = GetTextAngle();
599
600 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
601 {
602 SCH_SYMBOL* parentSymbol = static_cast<SCH_SYMBOL*>( m_parent );
603
604 if( parentSymbol && parentSymbol->GetTransform().y1 ) // Rotate symbol 90 degrees.
605 {
606 if( orient.IsHorizontal() )
607 orient = ANGLE_VERTICAL;
608 else
609 orient = ANGLE_HORIZONTAL;
610 }
611 }
612
613 return orient;
614}
615
616
618{
619 BOX2I bbox = GetTextBox();
620
621 // Calculate the bounding box position relative to the parent:
622 VECTOR2I origin = GetParentPosition();
623 VECTOR2I pos = GetTextPos() - origin;
624 VECTOR2I begin = bbox.GetOrigin() - origin;
625 VECTOR2I end = bbox.GetEnd() - origin;
626 RotatePoint( begin, pos, GetTextAngle() );
627 RotatePoint( end, pos, GetTextAngle() );
628
629 // Now, apply the symbol transform (mirror/rot)
630 TRANSFORM transform;
631
632 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
633 transform = static_cast<SCH_SYMBOL*>( m_parent )->GetTransform();
634
635 bbox.SetOrigin( transform.TransformCoordinate( begin ) );
636 bbox.SetEnd( transform.TransformCoordinate( end ) );
637
638 bbox.Move( origin );
639 bbox.Normalize();
640
641 return bbox;
642}
643
644
646{
647 VECTOR2I render_center = GetBoundingBox().Centre();
648 VECTOR2I pos = GetPosition();
649
650 switch( GetHorizJustify() )
651 {
653 if( GetDrawRotation().IsVertical() )
654 return render_center.y > pos.y;
655 else
656 return render_center.x < pos.x;
658 if( GetDrawRotation().IsVertical() )
659 return render_center.y < pos.y;
660 else
661 return render_center.x > pos.x;
662 default:
663 return false;
664 }
665}
666
667
669{
670 GR_TEXT_H_ALIGN_T actualJustify;
671
672 switch( aJustify )
673 {
676 break;
679 break;
680 default:
681 actualJustify = aJustify;
682 }
683
684 SetHorizJustify( actualJustify );
685}
686
687
689{
690 switch( GetHorizJustify() )
691 {
696 default:
698 }
699}
700
701
703{
704 VECTOR2I render_center = GetBoundingBox().Centre();
705 VECTOR2I pos = GetPosition();
706
707 switch( GetVertJustify() )
708 {
710 if( GetDrawRotation().IsVertical() )
711 return render_center.x < pos.x;
712 else
713 return render_center.y < pos.y;
715 if( GetDrawRotation().IsVertical() )
716 return render_center.x > pos.x;
717 else
718 return render_center.y > pos.y;
719 default:
720 return false;
721 }
722}
723
724
726{
727 GR_TEXT_V_ALIGN_T actualJustify;
728
729 switch( aJustify )
730 {
733 break;
736 break;
737 default:
738 actualJustify = aJustify;
739 }
740
741 SetVertJustify( actualJustify );
742}
743
744
746{
747 switch( GetVertJustify() )
748 {
753 default:
755 }
756}
757
758
759bool SCH_FIELD::Matches( const EDA_SEARCH_DATA& aSearchData, void* aAuxData ) const
760{
761 bool searchHiddenFields = false;
762 bool searchAndReplace = false;
763 bool replaceReferences = false;
764
765 try
766 {
767 const SCH_SEARCH_DATA& schSearchData = dynamic_cast<const SCH_SEARCH_DATA&>( aSearchData ); // downcast
768 searchHiddenFields = schSearchData.searchAllFields;
769 searchAndReplace = schSearchData.searchAndReplace;
770 replaceReferences = schSearchData.replaceReferences;
771 }
772 catch( const std::bad_cast& )
773 {
774 }
775
776 wxString text = UnescapeString( GetText() );
777
778 if( !IsVisible() && !searchHiddenFields )
779 return false;
780
782 {
783 if( searchAndReplace && !replaceReferences )
784 return false;
785
786 SCH_SYMBOL* parentSymbol = static_cast<SCH_SYMBOL*>( m_parent );
787 wxASSERT( aAuxData );
788
789 // Take sheet path into account which effects the reference field and the unit for
790 // symbols with multiple parts.
791 if( aAuxData )
792 {
793 SCH_SHEET_PATH* sheet = (SCH_SHEET_PATH*) aAuxData;
794 text = parentSymbol->GetRef( sheet );
795
796 if( SCH_ITEM::Matches( text, aSearchData ) )
797 return true;
798
799 if( parentSymbol->GetUnitCount() > 1 )
800 text << parentSymbol->SubReference( parentSymbol->GetUnitSelection( sheet ) );
801 }
802 }
803
804 return SCH_ITEM::Matches( text, aSearchData );
805}
806
807
809 wxStyledTextEvent &aEvent ) const
810{
811 SCH_ITEM* parent = dynamic_cast<SCH_ITEM*>( GetParent() );
812 SCHEMATIC* schematic = parent ? parent->Schematic() : nullptr;
813
814 if( !schematic )
815 return;
816
817 wxStyledTextCtrl* scintilla = aScintillaTricks->Scintilla();
818 int key = aEvent.GetKey();
819
820 wxArrayString autocompleteTokens;
821 int pos = scintilla->GetCurrentPos();
822 int start = scintilla->WordStartPosition( pos, true );
823 wxString partial;
824
825 // Multi-line fields are not allowed. So remove '\n' if entered.
826 if( key == '\n' )
827 {
828 wxString text = scintilla->GetText();
829 int currpos = scintilla->GetCurrentPos();
830 text.Replace( wxS( "\n" ), wxS( "" ) );
831 scintilla->SetText( text );
832 scintilla->GotoPos( currpos-1 );
833 return;
834 }
835
836 auto textVarRef =
837 [&]( int pt )
838 {
839 return pt >= 2
840 && scintilla->GetCharAt( pt - 2 ) == '$'
841 && scintilla->GetCharAt( pt - 1 ) == '{';
842 };
843
844 // Check for cross-reference
845 if( start > 1 && scintilla->GetCharAt( start - 1 ) == ':' )
846 {
847 int refStart = scintilla->WordStartPosition( start - 1, true );
848
849 if( textVarRef( refStart ) )
850 {
851 partial = scintilla->GetRange( start, pos );
852
853 wxString ref = scintilla->GetRange( refStart, start - 1 );
854
855 if( ref == wxS( "OP" ) )
856 {
857 // SPICE operating points use ':' syntax for ports
858 if( SCH_SYMBOL* symbol = dynamic_cast<SCH_SYMBOL*>( parent ) )
859 {
860 NULL_REPORTER devnull;
861 SCH_SHEET_PATH& sheet = schematic->CurrentSheet();
862 SIM_LIB_MGR mgr( &schematic->Prj() );
863 SIM_MODEL& model = mgr.CreateModel( &sheet, *symbol, devnull ).model;
864
865 for( wxString pin : model.GetPinNames() )
866 {
867 if( pin.StartsWith( '<' ) && pin.EndsWith( '>' ) )
868 autocompleteTokens.push_back( pin.Mid( 1, pin.Length() - 2 ) );
869 else
870 autocompleteTokens.push_back( pin );
871 }
872 }
873 }
874 else
875 {
877 SCH_SYMBOL* refSymbol = nullptr;
878
879 schematic->Hierarchy().GetSymbols( refs );
880
881 for( size_t jj = 0; jj < refs.GetCount(); jj++ )
882 {
883 if( refs[ jj ].GetSymbol()->GetRef( &refs[ jj ].GetSheetPath(), true ) == ref )
884 {
885 refSymbol = refs[ jj ].GetSymbol();
886 break;
887 }
888 }
889
890 if( refSymbol )
891 refSymbol->GetContextualTextVars( &autocompleteTokens );
892 }
893 }
894 }
895 else if( textVarRef( start ) )
896 {
897 partial = scintilla->GetTextRange( start, pos );
898
899 SCH_SYMBOL* symbol = dynamic_cast<SCH_SYMBOL*>( parent );
900 SCH_SHEET* sheet = dynamic_cast<SCH_SHEET*>( parent );
901 SCH_LABEL_BASE* label = dynamic_cast<SCH_LABEL_BASE*>( parent );
902
903 if( symbol )
904 {
905 symbol->GetContextualTextVars( &autocompleteTokens );
906
907 if( schematic->CurrentSheet().Last() )
908 schematic->CurrentSheet().Last()->GetContextualTextVars( &autocompleteTokens );
909 }
910
911 if( sheet )
912 sheet->GetContextualTextVars( &autocompleteTokens );
913
914 if( label )
915 label->GetContextualTextVars( &autocompleteTokens );
916
917 for( std::pair<wxString, wxString> entry : schematic->Prj().GetTextVars() )
918 autocompleteTokens.push_back( entry.first );
919 }
920
921 aScintillaTricks->DoAutocomplete( partial, autocompleteTokens );
922 scintilla->SetFocus();
923}
924
925
927{
928 if( m_parent && m_parent->Type() == SCH_SHEET_T )
929 {
930 // See comments in SCH_FIELD::Replace(), below.
931 if( m_id == SHEETFILENAME )
932 return false;
933 }
934 else if( m_parent && m_parent->Type() == SCH_GLOBAL_LABEL_T )
935 {
936 if( m_id == 0 /* IntersheetRefs */ )
937 return false;
938 }
939
940 return true;
941}
942
943
944bool SCH_FIELD::Replace( const EDA_SEARCH_DATA& aSearchData, void* aAuxData )
945{
946 bool replaceReferences = false;
947
948 try
949 {
950 const SCH_SEARCH_DATA& schSearchData = dynamic_cast<const SCH_SEARCH_DATA&>( aSearchData );
951 replaceReferences = schSearchData.replaceReferences;
952 }
953 catch( const std::bad_cast& )
954 {
955 }
956
957 wxString text;
958 bool isReplaced = false;
959
960 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
961 {
962 SCH_SYMBOL* parentSymbol = static_cast<SCH_SYMBOL*>( m_parent );
963
964 switch( m_id )
965 {
966 case REFERENCE_FIELD:
967 wxCHECK_MSG( aAuxData, false, wxT( "Need sheetpath to replace in refdes." ) );
968
969 if( !replaceReferences )
970 return false;
971
972 text = parentSymbol->GetRef( (SCH_SHEET_PATH*) aAuxData );
973 isReplaced = EDA_ITEM::Replace( aSearchData, text );
974
975 if( isReplaced )
976 parentSymbol->SetRef( (SCH_SHEET_PATH*) aAuxData, text );
977
978 break;
979
980 case VALUE_FIELD:
981 wxCHECK_MSG( aAuxData, false, wxT( "Need sheetpath to replace in value field." ) );
982
983 text = parentSymbol->GetField( VALUE_FIELD )->GetText();
984 isReplaced = EDA_ITEM::Replace( aSearchData, text );
985
986 if( isReplaced )
987 parentSymbol->SetValueFieldText( text );
988
989 break;
990
991 case FOOTPRINT_FIELD:
992 wxCHECK_MSG( aAuxData, false, wxT( "Need sheetpath to replace in footprint field." ) );
993
994 text = parentSymbol->GetField( FOOTPRINT_FIELD )->GetText();
995 isReplaced = EDA_ITEM::Replace( aSearchData, text );
996
997 if( isReplaced )
998 parentSymbol->SetFootprintFieldText( text );
999
1000 break;
1001
1002 default:
1003 isReplaced = EDA_TEXT::Replace( aSearchData );
1004 }
1005 }
1006 else if( m_parent && m_parent->Type() == SCH_SHEET_T )
1007 {
1008 isReplaced = EDA_TEXT::Replace( aSearchData );
1009
1010 if( m_id == SHEETFILENAME && isReplaced )
1011 {
1012 // If we allowed this we'd have a bunch of work to do here, including warning
1013 // about it not being undoable, checking for recursive hierarchies, reloading
1014 // sheets, etc. See DIALOG_SHEET_PROPERTIES::TransferDataFromWindow().
1015 }
1016 }
1017 else
1018 {
1019 isReplaced = EDA_TEXT::Replace( aSearchData );
1020 }
1021
1022 return isReplaced;
1023}
1024
1025
1026void SCH_FIELD::Rotate( const VECTOR2I& aCenter, bool aRotateCCW )
1027{
1029
1030 if( GetTextAngle().IsVertical() )
1031 {
1032 switch( horizJustify )
1033 {
1035 if( aRotateCCW )
1037
1038 break;
1040 if( aRotateCCW )
1042 break;
1045 }
1047 }
1048 else if( GetTextAngle().IsHorizontal() )
1049 {
1050 switch( horizJustify )
1051 {
1053 if( !aRotateCCW )
1055 break;
1057 if( !aRotateCCW )
1059 break;
1062 }
1064 }
1065 else
1066 {
1067 wxASSERT_MSG(
1068 false,
1069 wxString::Format( wxT( "SCH_FIELD text angle is not horizontal or vertical: %d" ),
1070 GetTextAngle().AsDegrees() ) );
1071 }
1072
1073 VECTOR2I pt = GetPosition();
1074 RotatePoint( pt, aCenter, aRotateCCW ? ANGLE_90 : ANGLE_270 );
1075 SetPosition( pt );
1076}
1077
1078
1080{
1081 int x = GetTextPos().x;
1082
1083 x -= aCenter;
1084 x *= -1;
1085 x += aCenter;
1086
1087 SetTextX( x );
1088}
1089
1090
1092{
1093 int y = GetTextPos().y;
1094
1095 y -= aCenter;
1096 y *= -1;
1097 y += aCenter;
1098
1099 SetTextY( y );
1100}
1101
1102
1103void SCH_FIELD::BeginEdit( const VECTOR2I& aPosition )
1104{
1105 SetTextPos( aPosition );
1106}
1107
1108
1109void SCH_FIELD::CalcEdit( const VECTOR2I& aPosition )
1110{
1111 SetTextPos( aPosition );
1112}
1113
1114
1115wxString SCH_FIELD::GetItemDescription( UNITS_PROVIDER* aUnitsProvider, bool aFull ) const
1116{
1117 return wxString::Format( _( "Field %s '%s'" ),
1119 aFull ? GetShownText( false ) : KIUI::EllipsizeMenuText( GetText() ) );
1120}
1121
1122
1123void SCH_FIELD::GetMsgPanelInfo( EDA_DRAW_FRAME* aFrame, std::vector<MSG_PANEL_ITEM>& aList )
1124{
1125 wxString msg;
1126
1127 aList.emplace_back( _( "Symbol Field" ), UnescapeString( GetName() ) );
1128
1129 // Don't use GetShownText() here; we want to show the user the variable references
1130 aList.emplace_back( _( "Text" ), KIUI::EllipsizeStatusText( aFrame, GetText() ) );
1131
1132 aList.emplace_back( _( "Visible" ), IsVisible() ? _( "Yes" ) : _( "No" ) );
1133
1134 aList.emplace_back( _( "Font" ), GetFont() ? GetFont()->GetName() : _( "Default" ) );
1135
1136 aList.emplace_back( _( "Style" ), GetTextStyleName() );
1137
1138 aList.emplace_back( _( "Text Size" ), aFrame->MessageTextFromValue( GetTextWidth() ) );
1139
1140 switch ( GetHorizJustify() )
1141 {
1142 case GR_TEXT_H_ALIGN_LEFT: msg = _( "Left" ); break;
1143 case GR_TEXT_H_ALIGN_CENTER: msg = _( "Center" ); break;
1144 case GR_TEXT_H_ALIGN_RIGHT: msg = _( "Right" ); break;
1146 }
1147
1148 aList.emplace_back( _( "H Justification" ), msg );
1149
1150 switch ( GetVertJustify() )
1151 {
1152 case GR_TEXT_V_ALIGN_TOP: msg = _( "Top" ); break;
1153 case GR_TEXT_V_ALIGN_CENTER: msg = _( "Center" ); break;
1154 case GR_TEXT_V_ALIGN_BOTTOM: msg = _( "Bottom" ); break;
1156 }
1157
1158 aList.emplace_back( _( "V Justification" ), msg );
1159}
1160
1161
1163{
1164 constexpr int START_ID = 1;
1165
1166 if( IsHypertext() )
1167 {
1168 SCH_LABEL_BASE* label = static_cast<SCH_LABEL_BASE*>( m_parent );
1169 SCH_SHEET_PATH* sheet = &label->Schematic()->CurrentSheet();
1170 wxMenu menu;
1171 wxString href;
1172
1173 std::vector<std::pair<wxString, wxString>> pages;
1174
1175 label->GetIntersheetRefs( sheet, &pages );
1176
1177 for( int i = 0; i < (int) pages.size(); ++i )
1178 {
1179 menu.Append( i + START_ID, wxString::Format( _( "Go to Page %s (%s)" ),
1180 pages[i].first,
1181 pages[i].second ) );
1182 }
1183
1184 menu.AppendSeparator();
1185 menu.Append( 999 + START_ID, _( "Back to Previous Selected Sheet" ) );
1186
1187 int sel = aFrame->GetPopupMenuSelectionFromUser( menu ) - START_ID;
1188
1189 if( sel >= 0 && sel < (int) pages.size() )
1190 href = wxT( "#" ) + pages[ sel ].first;
1191 else if( sel == 999 )
1193
1194 if( !href.IsEmpty() )
1195 {
1197 navTool->HypertextCommand( href );
1198 }
1199 }
1200}
1201
1202
1203void SCH_FIELD::SetName( const wxString& aName )
1204{
1205 m_name = aName;
1206 m_isNamedVariable = m_name.StartsWith( wxT( "${" ) );
1207
1208 if( m_isNamedVariable )
1209 EDA_TEXT::SetText( aName );
1210}
1211
1212
1213void SCH_FIELD::SetText( const wxString& aText )
1214{
1215 // Don't allow modification of text value when using named variables
1216 // as field name.
1217 if( m_isNamedVariable )
1218 return;
1219
1220 // Mandatory fields should not have leading or trailing whitespace.
1221 if( IsMandatory() )
1222 EDA_TEXT::SetText( aText.Strip( wxString::both ) );
1223 else
1224 EDA_TEXT::SetText( aText );
1225}
1226
1227
1228wxString SCH_FIELD::GetName( bool aUseDefaultName ) const
1229{
1230 if( m_parent && ( m_parent->Type() == SCH_SYMBOL_T || m_parent->Type() == LIB_SYMBOL_T ) )
1231 {
1232 if( IsMandatory() )
1233 return GetCanonicalFieldName( m_id );
1234 else if( m_name.IsEmpty() && aUseDefaultName )
1236 }
1237 else if( m_parent && m_parent->Type() == SCH_SHEET_T )
1238 {
1239 if( IsMandatory() )
1241 else if( m_name.IsEmpty() && aUseDefaultName )
1243 }
1244 else if( m_parent && m_parent->IsType( labelTypes ) )
1245 {
1246 return SCH_LABEL_BASE::GetDefaultFieldName( m_name, aUseDefaultName );
1247 }
1248
1249 return m_name;
1250}
1251
1252
1254{
1255 if( m_parent && ( m_parent->Type() == SCH_SYMBOL_T || m_parent->Type() == LIB_SYMBOL_T ) )
1256 {
1257 if( IsMandatory() )
1258 return GetCanonicalFieldName( m_id );
1259 }
1260 else if( m_parent && m_parent->Type() == SCH_SHEET_T )
1261 {
1262 if( m_id == SHEETNAME )
1263 return wxT( "Sheetname" );
1264 else if( m_id == SHEETFILENAME )
1265 return wxT( "Sheetfile" );
1266 }
1267 else if( m_parent && m_parent->IsType( labelTypes ) )
1268 {
1269 // These should be stored in canonical format, but just in case:
1270 if( m_name == _( "Net Class" ) || m_name == wxT( "Net Class" ) )
1271 {
1272 return wxT( "Netclass" );
1273 }
1274 else if( m_name == _( "Sheet References" )
1275 || m_name == wxT( "Sheet References" )
1276 || m_name == wxT( "Intersheet References" ) )
1277 {
1278 return wxT( "Intersheetrefs" );
1279 }
1280 }
1281
1282 return m_name;
1283}
1284
1285
1287{
1288 if( m_parent && ( m_parent->Type() == SCH_SYMBOL_T || m_parent->Type() == LIB_SYMBOL_T ) )
1289 {
1290 switch( m_id )
1291 {
1292 case REFERENCE_FIELD: return BITMAPS::edit_comp_ref;
1293 case VALUE_FIELD: return BITMAPS::edit_comp_value;
1294 case FOOTPRINT_FIELD: return BITMAPS::edit_comp_footprint;
1295 default: return BITMAPS::text;
1296 }
1297 }
1298
1299 return BITMAPS::text;
1300}
1301
1302
1303bool SCH_FIELD::HitTest( const VECTOR2I& aPosition, int aAccuracy ) const
1304{
1305 if( GetShownText( true ).IsEmpty() )
1306 return false;
1307
1308 BOX2I rect = GetBoundingBox();
1309
1310 // Text in symbol editor can have additional chars (ie: reference designators U? or U?A)
1311 if( m_parent && m_parent->Type() == LIB_SYMBOL_T )
1312 {
1313 SCH_FIELD temp( *this );
1314 temp.SetText( GetFullText() );
1315 rect = temp.GetBoundingBox();
1316 }
1317
1318 rect.Inflate( aAccuracy );
1319
1321 {
1322 SCH_GLOBALLABEL* label = static_cast<SCH_GLOBALLABEL*>( GetParent() );
1323 rect.Offset( label->GetSchematicTextOffset( nullptr ) );
1324 }
1325
1326 return rect.Contains( aPosition );
1327}
1328
1329
1330bool SCH_FIELD::HitTest( const BOX2I& aRect, bool aContained, int aAccuracy ) const
1331{
1332 if( GetShownText( true ).IsEmpty() )
1333 return false;
1334
1336 return false;
1337
1338 BOX2I rect = aRect;
1339
1340 rect.Inflate( aAccuracy );
1341
1342 if( GetParent() && GetParent()->Type() == SCH_GLOBAL_LABEL_T )
1343 {
1344 SCH_GLOBALLABEL* label = static_cast<SCH_GLOBALLABEL*>( GetParent() );
1345 rect.Offset( label->GetSchematicTextOffset( nullptr ) );
1346 }
1347
1348 if( aContained )
1349 return rect.Contains( GetBoundingBox() );
1350
1351 return rect.Intersects( GetBoundingBox() );
1352}
1353
1354
1355void SCH_FIELD::Plot( PLOTTER* aPlotter, bool aBackground, const SCH_PLOT_OPTS& aPlotOpts,
1356 int aUnit, int aBodyStyle, const VECTOR2I& aOffset, bool aDimmed )
1357{
1358 wxString text;
1359
1360 if( Schematic() )
1361 text = GetShownText( &Schematic()->CurrentSheet(), true );
1362 else
1363 text = GetShownText( true );
1364
1365 if( ( !IsVisible() && !IsForceVisible() ) || text.IsEmpty() || aBackground )
1366 return;
1367
1368 SCH_RENDER_SETTINGS* renderSettings = getRenderSettings( aPlotter );
1369 COLOR4D color = renderSettings->GetLayerColor( GetLayer() );
1370 int penWidth = GetEffectiveTextPenWidth( renderSettings->GetDefaultPenWidth() );
1371
1372 COLOR4D bg = renderSettings->GetBackgroundColor();;
1373
1374 if( bg == COLOR4D::UNSPECIFIED || !aPlotter->GetColorMode() )
1375 bg = COLOR4D::WHITE;
1376
1377 if( aPlotter->GetColorMode() && GetTextColor() != COLOR4D::UNSPECIFIED )
1378 color = GetTextColor();
1379
1380 if( aDimmed )
1381 {
1382 color.Desaturate( );
1383 color = color.Mix( bg, 0.5f );
1384 }
1385
1386 penWidth = std::max( penWidth, renderSettings->GetMinPenWidth() );
1387
1388 // clamp the pen width to be sure the text is readable
1389 penWidth = std::min( penWidth, std::min( GetTextSize().x, GetTextSize().y ) / 4 );
1390
1391 if( !IsVisible() && !renderSettings->m_ShowHiddenFields )
1392 return;
1393
1394 // Calculate the text orientation, according to the symbol orientation/mirror
1395 EDA_ANGLE orient = GetTextAngle();
1396 VECTOR2I textpos = GetTextPos();
1398 GR_TEXT_V_ALIGN_T vjustify = GetVertJustify();
1399
1400 if( renderSettings->m_Transform.y1 ) // Rotate symbol 90 deg.
1401 {
1402 if( orient.IsHorizontal() )
1403 orient = ANGLE_VERTICAL;
1404 else
1405 orient = ANGLE_HORIZONTAL;
1406 }
1407
1408 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
1409 {
1410 /*
1411 * Calculate the text justification, according to the symbol orientation/mirror. This is
1412 * a bit complicated due to cumulative calculations:
1413 * - numerous cases (mirrored or not, rotation)
1414 * - the plotter's Text() function will also recalculate H and V justifications according
1415 * to the text orientation
1416 * - when a symbol is mirrored the text is not, and justifications become a nightmare
1417 *
1418 * So the easier way is to use no justifications (centered text) and use GetBoundingBox
1419 * to know the text coordinate considered as centered.
1420 */
1421 hjustify = GR_TEXT_H_ALIGN_CENTER;
1422 vjustify = GR_TEXT_V_ALIGN_CENTER;
1423 textpos = GetBoundingBox().Centre();
1424 }
1425 else if( m_parent && m_parent->Type() == SCH_GLOBAL_LABEL_T )
1426 {
1427 SCH_GLOBALLABEL* label = static_cast<SCH_GLOBALLABEL*>( m_parent );
1428 textpos += label->GetSchematicTextOffset( renderSettings );
1429 }
1430
1431 KIFONT::FONT* font = GetFont();
1432
1433 if( !font )
1434 font = KIFONT::FONT::GetFont( renderSettings->GetDefaultFont(), IsBold(), IsItalic() );
1435
1437 attrs.m_StrokeWidth = penWidth;
1438 attrs.m_Halign = hjustify;
1439 attrs.m_Valign = vjustify;
1440 attrs.m_Angle = orient;
1441 attrs.m_Multiline = false;
1442
1443 aPlotter->PlotText( textpos, color, text, attrs, font, GetFontMetrics() );
1444
1445 if( IsHypertext() && Schematic() )
1446 {
1447 SCH_LABEL_BASE* label = static_cast<SCH_LABEL_BASE*>( m_parent );
1448 std::vector<std::pair<wxString, wxString>> pages;
1449 std::vector<wxString> pageHrefs;
1450 BOX2I bbox = GetBoundingBox();
1451
1452 wxCHECK( label, /* void */ );
1453
1454 label->GetIntersheetRefs( &Schematic()->CurrentSheet(), &pages );
1455
1456 for( const auto& [ pageNumber, sheetName ] : pages )
1457 pageHrefs.push_back( wxT( "#" ) + pageNumber );
1458
1459 bbox.Offset( label->GetSchematicTextOffset( renderSettings ) );
1460
1461 aPlotter->HyperlinkMenu( bbox, pageHrefs );
1462 }
1463}
1464
1465
1466void SCH_FIELD::SetPosition( const VECTOR2I& aPosition )
1467{
1468 // Actual positions are calculated by the rotation/mirror transform of the parent symbol
1469 // of the field. The inverse transform is used to calculate the position relative to the
1470 // parent symbol.
1471 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
1472 {
1473 SCH_SYMBOL* parentSymbol = static_cast<SCH_SYMBOL*>( m_parent );
1474 VECTOR2I relPos = aPosition - parentSymbol->GetPosition();
1475
1476 relPos = parentSymbol->GetTransform().InverseTransform().TransformCoordinate( relPos );
1477
1478 SetTextPos( relPos + parentSymbol->GetPosition() );
1479 return;
1480 }
1481
1482 SetTextPos( aPosition );
1483}
1484
1485
1487{
1488 if( m_parent && m_parent->Type() == SCH_SYMBOL_T )
1489 {
1490 SCH_SYMBOL* parentSymbol = static_cast<SCH_SYMBOL*>( m_parent );
1491 VECTOR2I relativePos = GetTextPos() - parentSymbol->GetPosition();
1492
1493 relativePos = parentSymbol->GetTransform().TransformCoordinate( relativePos );
1494
1495 return relativePos + parentSymbol->GetPosition();
1496 }
1497
1498 return GetTextPos();
1499}
1500
1501
1503{
1504 return m_parent ? m_parent->GetPosition() : VECTOR2I( 0, 0 );
1505}
1506
1507
1509{
1510 if( m_parent && m_parent->Type() == SCH_SHEET_T )
1511 return m_id >= 0 && m_id < SHEET_MANDATORY_FIELDS;
1512 else
1513 return m_id >= 0 && m_id < MANDATORY_FIELDS;
1514}
1515
1516
1517bool SCH_FIELD::operator<( const SCH_ITEM& aItem ) const
1518{
1519 if( Type() != aItem.Type() )
1520 return Type() < aItem.Type();
1521
1522 auto field = static_cast<const SCH_FIELD*>( &aItem );
1523
1524 if( GetId() != field->GetId() )
1525 return GetId() < field->GetId();
1526
1527 if( GetText() != field->GetText() )
1528 return GetText() < field->GetText();
1529
1530 if( GetLibPosition().x != field->GetLibPosition().x )
1531 return GetLibPosition().x < field->GetLibPosition().x;
1532
1533 if( GetLibPosition().y != field->GetLibPosition().y )
1534 return GetLibPosition().y < field->GetLibPosition().y;
1535
1536 return GetName() < field->GetName();
1537}
1538
1539
1540bool SCH_FIELD::operator==(const SCH_ITEM& aOther) const
1541{
1542 if( Type() != aOther.Type() )
1543 return false;
1544
1545 const SCH_FIELD& field = static_cast<const SCH_FIELD&>( aOther );
1546
1547 return *this == field;
1548}
1549
1550
1551bool SCH_FIELD::operator==( const SCH_FIELD& aOther ) const
1552{
1553 // Identical fields of different symbols are not equal.
1554 if( !GetParentSymbol() || !aOther.GetParentSymbol()
1555 || GetParentSymbol()->m_Uuid != aOther.GetParentSymbol()->m_Uuid )
1556 {
1557 return false;
1558 }
1559
1560 if( GetId() != aOther.GetId() )
1561 return false;
1562
1563 if( GetPosition() != aOther.GetPosition() )
1564 return false;
1565
1566 if( IsNamedVariable() != aOther.IsNamedVariable() )
1567 return false;
1568
1569 if( IsNameShown() != aOther.IsNameShown() )
1570 return false;
1571
1572 if( CanAutoplace() != aOther.CanAutoplace() )
1573 return false;
1574
1575 return EDA_TEXT::operator==( aOther );
1576}
1577
1578
1579double SCH_FIELD::Similarity( const SCH_ITEM& aOther ) const
1580{
1581 if( Type() != aOther.Type() )
1582 return 0.0;
1583
1584 if( m_Uuid == aOther.m_Uuid )
1585 return 1.0;
1586
1587 const SCH_FIELD& field = static_cast<const SCH_FIELD&>( aOther );
1588
1589 double similarity = 0.99; // The UUIDs are different, so we start with non-identity
1590
1591 if( GetId() != field.GetId() )
1592 {
1593 // We don't allow swapping of mandatory fields, so these cannot be the same item
1594 if( GetId() < MANDATORY_FIELDS || field.GetId() < MANDATORY_FIELDS )
1595 return 0.0;
1596 else
1597 similarity *= 0.5;
1598 }
1599
1600 similarity *= SimilarityBase( aOther );
1601
1602 similarity *= EDA_TEXT::Similarity( field );
1603
1604 if( GetPosition() != field.GetPosition() )
1605 similarity *= 0.5;
1606
1607 if( IsNamedVariable() != field.IsNamedVariable() )
1608 similarity *= 0.5;
1609
1610 if( IsNameShown() != field.IsNameShown() )
1611 similarity *= 0.5;
1612
1613 if( CanAutoplace() != field.CanAutoplace() )
1614 similarity *= 0.5;
1615
1616 return similarity;
1617}
1618
1619
1620int SCH_FIELD::compare( const SCH_ITEM& aOther, int aCompareFlags ) const
1621{
1622 wxASSERT( aOther.Type() == SCH_FIELD_T );
1623
1624 int compareFlags = aCompareFlags;
1625
1626 // For ERC tests, the field position has no matter, so do not test it
1627 if( aCompareFlags & SCH_ITEM::COMPARE_FLAGS::ERC )
1629
1630 int retv = SCH_ITEM::compare( aOther, compareFlags );
1631
1632 if( retv )
1633 return retv;
1634
1635 const SCH_FIELD* tmp = static_cast<const SCH_FIELD*>( &aOther );
1636
1637 // Equality test will vary depending whether or not the field is mandatory. Otherwise,
1638 // sorting is done by ordinal.
1639 if( aCompareFlags & SCH_ITEM::COMPARE_FLAGS::EQUALITY )
1640 {
1641 // Mandatory fields have fixed ordinals and their names can vary due to translated field
1642 // names. Optional fields have fixed names and their ordinals can vary.
1643 if( IsMandatory() )
1644 {
1645 if( m_id != tmp->m_id )
1646 return m_id - tmp->m_id;
1647 }
1648 else
1649 {
1650 retv = m_name.Cmp( tmp->m_name );
1651
1652 if( retv )
1653 return retv;
1654 }
1655 }
1656 else // assume we're sorting
1657 {
1658 if( m_id != tmp->m_id )
1659 return m_id - tmp->m_id;
1660 }
1661
1662 bool ignoreFieldText = false;
1663
1664 if( m_id == REFERENCE_FIELD && !( aCompareFlags & SCH_ITEM::COMPARE_FLAGS::EQUALITY ) )
1665 ignoreFieldText = true;
1666
1667 if( m_id == VALUE_FIELD && ( aCompareFlags & SCH_ITEM::COMPARE_FLAGS::ERC ) )
1668 ignoreFieldText = true;
1669
1670 if( !ignoreFieldText )
1671 {
1672 retv = GetText().CmpNoCase( tmp->GetText() );
1673
1674 if( retv != 0 )
1675 return retv;
1676 }
1677
1678 if( aCompareFlags & SCH_ITEM::COMPARE_FLAGS::EQUALITY )
1679 {
1680 if( GetTextPos().x != tmp->GetTextPos().x )
1681 return GetTextPos().x - tmp->GetTextPos().x;
1682
1683 if( GetTextPos().y != tmp->GetTextPos().y )
1684 return GetTextPos().y - tmp->GetTextPos().y;
1685 }
1686
1687 // For ERC tests, the field size has no matter, so do not test it
1688 if( !( aCompareFlags & SCH_ITEM::COMPARE_FLAGS::ERC ) )
1689 {
1690 if( GetTextWidth() != tmp->GetTextWidth() )
1691 return GetTextWidth() - tmp->GetTextWidth();
1692
1693 if( GetTextHeight() != tmp->GetTextHeight() )
1694 return GetTextHeight() - tmp->GetTextHeight();
1695 }
1696
1697 return 0;
1698}
1699
1700
1701static struct SCH_FIELD_DESC
1702{
1704 {
1705 // These are defined in EDA_TEXT as well but initialization order is
1706 // not defined, so this needs to be conditional. Defining in both
1707 // places leads to duplicate symbols.
1709
1710 if( h_inst.Choices().GetCount() == 0)
1711 {
1712 h_inst.Map( GR_TEXT_H_ALIGN_LEFT, _( "Left" ) );
1713 h_inst.Map( GR_TEXT_H_ALIGN_CENTER, _( "Center" ) );
1714 h_inst.Map( GR_TEXT_H_ALIGN_RIGHT, _( "Right" ) );
1715 }
1716
1718
1719 if( v_inst.Choices().GetCount() == 0)
1720 {
1721 v_inst.Map( GR_TEXT_V_ALIGN_TOP, _( "Top" ) );
1722 v_inst.Map( GR_TEXT_V_ALIGN_CENTER, _( "Center" ) );
1723 v_inst.Map( GR_TEXT_V_ALIGN_BOTTOM, _( "Bottom" ) );
1724 }
1725
1732
1733 const wxString textProps = _HKI( "Text Properties" );
1734
1735 auto horiz = new PROPERTY_ENUM<SCH_FIELD, GR_TEXT_H_ALIGN_T>( _HKI( "Horizontal Justification" ),
1737
1738 propMgr.ReplaceProperty( TYPE_HASH( EDA_TEXT ), _HKI( "Horizontal Justification" ), horiz, textProps );
1739
1740 auto vert = new PROPERTY_ENUM<SCH_FIELD, GR_TEXT_V_ALIGN_T>( _HKI( "Vertical Justification" ),
1742
1743 propMgr.ReplaceProperty( TYPE_HASH( EDA_TEXT ), _HKI( "Vertical Justification" ), vert, textProps );
1744
1745 propMgr.AddProperty( new PROPERTY<SCH_FIELD, bool>( _HKI( "Show Field Name" ),
1747
1748 propMgr.AddProperty( new PROPERTY<SCH_FIELD, bool>( _HKI( "Allow Autoplacement" ),
1750
1751 propMgr.Mask( TYPE_HASH( SCH_FIELD ), TYPE_HASH( EDA_TEXT ), _HKI( "Hyperlink" ) );
1752 propMgr.Mask( TYPE_HASH( SCH_FIELD ), TYPE_HASH( EDA_TEXT ), _HKI( "Thickness" ) );
1753 propMgr.Mask( TYPE_HASH( SCH_FIELD ), TYPE_HASH( EDA_TEXT ), _HKI( "Mirrored" ) );
1754 propMgr.Mask( TYPE_HASH( SCH_FIELD ), TYPE_HASH( EDA_TEXT ), _HKI( "Width" ) );
1755 propMgr.Mask( TYPE_HASH( SCH_FIELD ), TYPE_HASH( EDA_TEXT ), _HKI( "Height" ) );
1756
1757
1758 propMgr.AddProperty( new PROPERTY<SCH_FIELD, int>( _HKI( "Text Size" ),
1759 &SCH_FIELD::SetSchTextSize, &SCH_FIELD::GetSchTextSize, PROPERTY_DISPLAY::PT_SIZE ),
1760 _HKI( "Text Properties" ) );
1761
1762 propMgr.Mask( TYPE_HASH( SCH_FIELD ), TYPE_HASH( EDA_TEXT ), _HKI( "Orientation" ) );
1763
1764 auto isNotNamedVariable =
1765 []( INSPECTABLE* aItem ) -> bool
1766 {
1767 if( SCH_FIELD* field = dynamic_cast<SCH_FIELD*>( aItem ) )
1768 return !field->IsNamedVariable();
1769
1770 return true;
1771 };
1772
1774 isNotNamedVariable );
1775 }
1777
1778
int color
Definition: DXF_plotter.cpp:58
constexpr EDA_IU_SCALE schIUScale
Definition: base_units.h:110
BITMAPS
A list of all bitmap identifiers.
Definition: bitmaps_list.h:33
static const ADVANCED_CFG & GetCfg()
Get the singleton instance's config, which is shared by all consumers.
constexpr BOX2< Vec > & Inflate(coord_type dx, coord_type dy)
Inflates the rectangle horizontally by dx and vertically by dy.
Definition: box2.h:558
constexpr const Vec GetEnd() const
Definition: box2.h:212
constexpr void SetOrigin(const Vec &pos)
Definition: box2.h:237
constexpr BOX2< Vec > & Normalize()
Ensure that the height and width are positive.
Definition: box2.h:146
constexpr Vec Centre() const
Definition: box2.h:97
constexpr bool Contains(const Vec &aPoint) const
Definition: box2.h:168
constexpr void Move(const Vec &aMoveVector)
Move the rectangle by the aMoveVector.
Definition: box2.h:138
constexpr const Vec & GetOrigin() const
Definition: box2.h:210
constexpr void SetEnd(coord_type x, coord_type y)
Definition: box2.h:297
constexpr void Offset(coord_type dx, coord_type dy)
Definition: box2.h:259
constexpr bool Intersects(const BOX2< Vec > &aRect) const
Definition: box2.h:311
bool IsHorizontal() const
Definition: eda_angle.h:138
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:89
virtual VECTOR2I GetPosition() const
Definition: eda_item.h:243
const KIID m_Uuid
Definition: eda_item.h:489
KICAD_T Type() const
Returns the type of object.
Definition: eda_item.h:101
EDA_ITEM_FLAGS m_flags
Definition: eda_item.h:499
virtual bool Matches(const EDA_SEARCH_DATA &aSearchData, void *aAuxData) const
Compare the item against the search criteria in aSearchData.
Definition: eda_item.h:377
virtual bool IsType(const std::vector< KICAD_T > &aScanTypes) const
Check whether the item is one of the listed types.
Definition: eda_item.h:176
EDA_ITEM * GetParent() const
Definition: eda_item.h:103
EDA_ITEM * m_parent
Linked list: Link (parent struct)
Definition: eda_item.h:500
bool IsForceVisible() const
Definition: eda_item.h:195
static bool Replace(const EDA_SEARCH_DATA &aSearchData, wxString &aText)
Perform a text replace on aText using the find and replace criteria in aSearchData on items that supp...
Definition: eda_item.cpp:189
A mix-in class (via multiple inheritance) that handles texts such as labels, parts,...
Definition: eda_text.h:80
int GetTextHeight() const
Definition: eda_text.h:251
const VECTOR2I & GetTextPos() const
Definition: eda_text.h:257
COLOR4D GetTextColor() const
Definition: eda_text.h:254
wxString GetTextStyleName() const
Definition: eda_text.cpp:949
bool IsItalic() const
Definition: eda_text.h:156
const EDA_ANGLE & GetTextAngle() const
Definition: eda_text.h:134
virtual const wxString & GetText() const
Return the string associated with the text object.
Definition: eda_text.h:98
virtual bool IsVisible() const
Definition: eda_text.h:174
void SetTextPos(const VECTOR2I &aPoint)
Definition: eda_text.cpp:551
void SetTextX(int aX)
Definition: eda_text.cpp:557
KIFONT::FONT * GetFont() const
Definition: eda_text.h:234
void SetAttributes(const EDA_TEXT &aSrc, bool aSetPosition=true)
Set the text attributes from another instance.
Definition: eda_text.cpp:424
BOX2I GetTextBox(int aLine=-1) const
Useful in multiline texts to calculate the full text or a line area (for zones filling,...
Definition: eda_text.cpp:703
void SetTextY(int aY)
Definition: eda_text.cpp:563
EDA_TEXT & operator=(const EDA_TEXT &aItem)
Definition: eda_text.cpp:154
int GetTextWidth() const
Definition: eda_text.h:248
void SetVertJustify(GR_TEXT_V_ALIGN_T aType)
Definition: eda_text.cpp:408
GR_TEXT_H_ALIGN_T GetHorizJustify() const
Definition: eda_text.h:187
bool Replace(const EDA_SEARCH_DATA &aSearchData)
Helper function used in search and replace dialog.
Definition: eda_text.cpp:477
virtual void SetVisible(bool aVisible)
Definition: eda_text.cpp:377
virtual void ClearBoundingBoxCache()
Definition: eda_text.cpp:637
double Similarity(const EDA_TEXT &aOther) const
Definition: eda_text.cpp:1269
virtual void ClearRenderCache()
Definition: eda_text.cpp:631
const TEXT_ATTRIBUTES & GetAttributes() const
Definition: eda_text.h:218
int GetEffectiveTextPenWidth(int aDefaultPenWidth=0) const
The EffectiveTextPenWidth uses the text thickness if > 1 or aDefaultPenWidth.
Definition: eda_text.cpp:456
void SwapAttributes(EDA_TEXT &aTradingPartner)
Swap the text attributes of the two involved instances.
Definition: eda_text.cpp:443
bool IsBold() const
Definition: eda_text.h:171
GR_TEXT_V_ALIGN_T GetVertJustify() const
Definition: eda_text.h:190
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 SetText(const wxString &aText)
Definition: eda_text.cpp:269
virtual void SetTextAngle(const EDA_ANGLE &aAngle)
Definition: eda_text.cpp:291
void SwapText(EDA_TEXT &aTradingPartner)
Definition: eda_text.cpp:436
bool operator==(const EDA_TEXT &aRhs) const
Definition: eda_text.h:379
VECTOR2I GetTextSize() const
Definition: eda_text.h:245
void SetHorizJustify(GR_TEXT_H_ALIGN_T aType)
Definition: eda_text.cpp:400
static ENUM_MAP< T > & Instance()
Definition: property.h:663
Class that other classes need to inherit from, in order to be inspectable.
Definition: inspectable.h:36
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, const std::vector< wxString > *aEmbeddedFiles=nullptr, bool aForDrawingSheet=false)
Definition: font.cpp:146
virtual bool IsOutline() const
Definition: font.h:139
Class OUTLINE_FONT implements outline font drawing.
Definition: outline_font.h:53
void GetLinesAsGlyphs(std::vector< std::unique_ptr< GLYPH > > *aGlyphs, const wxString &aText, const VECTOR2I &aPosition, const TEXT_ATTRIBUTES &aAttrs, const METRICS &aFontMetrics) const
A color representation with 4 components: red, green, blue, alpha.
Definition: color4d.h:104
int GetDefaultPenWidth() const
const wxString & GetDefaultFont() const
const COLOR4D & GetLayerColor(int aLayer) const
Return the color used to draw a layer.
wxDC * GetPrintDC() const
Define a library symbol object.
Definition: lib_symbol.h:78
bool ResolveTextVar(wxString *token, int aDepth=0) const
Resolve any references to system tokens supported by the symbol.
Definition: lib_symbol.cpp:466
static wxString LetterSubReference(int aUnit, int aFirstId)
Definition: lib_symbol.cpp:447
A singleton reporter that reports to nowhere.
Definition: reporter.h:203
Base plotter engine class.
Definition: plotter.h:105
bool GetColorMode() const
Definition: plotter.h:133
virtual void PlotText(const VECTOR2I &aPos, const COLOR4D &aColor, const wxString &aText, const TEXT_ATTRIBUTES &aAttributes, KIFONT::FONT *aFont=nullptr, const KIFONT::METRICS &aFontMetrics=KIFONT::METRICS::Default(), void *aData=nullptr)
Definition: plotter.cpp:754
virtual void HyperlinkMenu(const BOX2I &aBox, const std::vector< wxString > &aDestURLs)
Create a clickable hyperlink menu with a rectangular click area.
Definition: plotter.h:465
virtual std::map< wxString, wxString > & GetTextVars() const
Definition: project.cpp:84
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.
PROPERTY_BASE & ReplaceProperty(size_t aBase, const wxString &aName, PROPERTY_BASE *aNew, const wxString &aGroup=wxEmptyString)
Replace an existing property for a specific type.
void OverrideWriteability(TYPE_ID aDerived, TYPE_ID aBase, const wxString &aName, std::function< bool(INSPECTABLE *)> aFunc)
Sets an override writeability functor for a base class property of a given derived class.
void AddTypeCast(TYPE_CAST_BASE *aCast)
Register a type converter.
Holds all the data relating to one schematic.
Definition: schematic.h:77
SCH_SHEET_PATH & CurrentSheet() const override
Definition: schematic.h:156
SCH_SHEET_LIST Hierarchy() const override
Return the full schematic flattened hierarchical sheet list.
Definition: schematic.cpp:214
bool ResolveTextVar(const SCH_SHEET_PATH *aSheetPath, wxString *token, int aDepth) const
Definition: schematic.cpp:253
PROJECT & Prj() const override
Return a reference to the project this schematic is part of.
Definition: schematic.h:92
Instances are attached to a symbol or sheet and provide a place for the symbol's value,...
Definition: sch_field.h:51
void ClearRenderCache() override
Definition: sch_field.cpp:376
int compare(const SCH_ITEM &aOther, int aCompareFlags=0) const override
Provide the draw object specific comparison called by the == and < operators.
Definition: sch_field.cpp:1620
COLOR4D m_lastResolvedColor
Definition: sch_field.h:348
GR_TEXT_V_ALIGN_T GetEffectiveVertJustify() const
Definition: sch_field.cpp:745
bool IsMandatory() const
Definition: sch_field.cpp:1508
wxString GetItemDescription(UNITS_PROVIDER *aUnitsProvider, bool aFull) const override
Return a user-visible description string of this item.
Definition: sch_field.cpp:1115
void Rotate(const VECTOR2I &aCenter, bool aRotateCCW) override
Rotate the item around aCenter 90 degrees in the clockwise direction.
Definition: sch_field.cpp:1026
wxString GetFullText(int unit=1) const
Return the text of a field.
Definition: sch_field.cpp:337
const BOX2I GetBoundingBox() const override
Return the orthogonal bounding box of this object for display purposes.
Definition: sch_field.cpp:617
std::vector< std::unique_ptr< KIFONT::GLYPH > > m_renderCache
Definition: sch_field.h:346
VECTOR2I GetPosition() const override
Definition: sch_field.cpp:1486
void SetEffectiveHorizJustify(GR_TEXT_H_ALIGN_T)
Definition: sch_field.cpp:668
int GetSchTextSize() const
Definition: sch_field.h:171
bool Replace(const EDA_SEARCH_DATA &aSearchData, void *aAuxData=nullptr) override
Perform a text replace using the find and replace criteria in aSearchData on items that support text ...
Definition: sch_field.cpp:944
bool m_showName
Render the field name in addition to its value.
Definition: sch_field.h:336
void Plot(PLOTTER *aPlotter, bool aBackground, const SCH_PLOT_OPTS &aPlotOpts, int aUnit, int aBodyStyle, const VECTOR2I &aOffset, bool aDimmed) override
Plot the item to aPlotter.
Definition: sch_field.cpp:1355
EDA_ITEM * Clone() const override
Create a duplicate of this item with linked list members set to NULL.
Definition: sch_field.cpp:149
BITMAPS GetMenuImage() const override
Return a pointer to an image to be used in menus.
Definition: sch_field.cpp:1286
bool IsNameShown() const
Definition: sch_field.h:208
bool IsHypertext() const override
Allow items to support hypertext actions when hovered/clicked.
Definition: sch_field.h:101
bool m_autoAdded
Was this field automatically added to a LIB_SYMBOL?
Definition: sch_field.h:341
double Similarity(const SCH_ITEM &aItem) const override
Return a measure of how likely the other object is to represent the same object.
Definition: sch_field.cpp:1579
void Print(const SCH_RENDER_SETTINGS *aSettings, int aUnit, int aBodyStyle, const VECTOR2I &aOffset, bool aForceNoFill, bool aDimmed) override
Print an item.
Definition: sch_field.cpp:429
bool HitTest(const VECTOR2I &aPosition, int aAccuracy=0) const override
Test if aPosition is inside or on the boundary of this item.
Definition: sch_field.cpp:1303
SCH_LAYER_ID GetDefaultLayer() const
Definition: sch_field.cpp:567
bool IsHorizJustifyFlipped() const
Return whether the field will be rendered with the horizontal justification inverted due to rotation ...
Definition: sch_field.cpp:645
bool IsVertJustifyFlipped() const
Definition: sch_field.cpp:702
EDA_ANGLE GetDrawRotation() const override
Adjusters to allow EDA_TEXT to draw/print/etc.
Definition: sch_field.cpp:595
void SetEffectiveVertJustify(GR_TEXT_V_ALIGN_T)
Definition: sch_field.cpp:725
void CalcEdit(const VECTOR2I &aPosition) override
Calculate the attributes of an item at aPosition when it is being edited.
Definition: sch_field.cpp:1109
bool Matches(const EDA_SEARCH_DATA &aSearchData, void *aAuxData) const override
Compare the item against the search criteria in aSearchData.
Definition: sch_field.cpp:759
void MirrorVertically(int aCenter) override
Mirror item vertically about aCenter.
Definition: sch_field.cpp:1091
void SetCanAutoplace(bool aCanPlace)
Definition: sch_field.h:220
bool m_isNamedVariable
If the field name is a variable name, e.g.
Definition: sch_field.h:338
void DoHypertextAction(EDA_DRAW_FRAME *aFrame) const override
Definition: sch_field.cpp:1162
int GetPenWidth() const override
Definition: sch_field.cpp:352
wxString GetCanonicalName() const
Get a non-language-specific name for a field which can be used for storage, variable look-up,...
Definition: sch_field.cpp:1253
COLOR4D GetFieldColor() const
Definition: sch_field.cpp:541
bool IsNamedVariable() const
Named variables are fields whose names are variables like ${VAR}.
Definition: sch_field.h:217
int GetId() const
Definition: sch_field.h:133
bool operator==(const SCH_ITEM &aItem) const override
Definition: sch_field.cpp:1540
SCH_FIELD & operator=(const SCH_FIELD &aField)
Definition: sch_field.cpp:119
void ImportValues(const SCH_FIELD &aSource)
Copy parameters from a SCH_FIELD source.
Definition: sch_field.cpp:513
bool operator<(const SCH_ITEM &aItem) const override
Definition: sch_field.cpp:1517
wxString GetShownName() const
Gets the fields name as displayed on the schematic or in the symbol fields table.
Definition: sch_field.cpp:205
VECTOR2I GetLibPosition() const
Definition: sch_field.h:265
bool IsEmpty()
Return true if both the name and value of the field are empty.
Definition: sch_field.h:163
SCH_FIELD(const VECTOR2I &aPos, int aFieldId, SCH_ITEM *aParent, const wxString &aName=wxEmptyString)
Definition: sch_field.cpp:60
bool m_renderCacheValid
Definition: sch_field.h:344
void BeginEdit(const VECTOR2I &aStartPoint) override
Begin drawing a symbol library draw item at aPosition.
Definition: sch_field.cpp:1103
bool IsReplaceable() const override
Override this method in any derived object that supports test find and replace.
Definition: sch_field.cpp:926
void SetSchTextSize(int aSize)
Definition: sch_field.h:172
GR_TEXT_H_ALIGN_T GetEffectiveHorizJustify() const
Definition: sch_field.cpp:688
std::vector< int > ViewGetLayers() const override
Return the all the layers within the VIEW the object is painted on.
Definition: sch_field.cpp:561
wxString GetName(bool aUseDefaultName=true) const
Return the field name (not translated).
Definition: sch_field.cpp:1228
void SetPosition(const VECTOR2I &aPosition) override
Definition: sch_field.cpp:1466
void SwapData(SCH_ITEM *aItem) override
Swap the internal data structures aItem with the schematic item.
Definition: sch_field.cpp:521
void SetName(const wxString &aName)
Definition: sch_field.cpp:1203
wxString GetShownText(const SCH_SHEET_PATH *aPath, bool aAllowExtraText, int aDepth=0) const
Definition: sch_field.cpp:211
void Move(const VECTOR2I &aMoveVector) override
Move the item by aMoveVector to a new position.
Definition: sch_field.h:239
VECTOR2I m_renderCachePos
Definition: sch_field.h:345
bool CanAutoplace() const
Definition: sch_field.h:219
std::vector< std::unique_ptr< KIFONT::GLYPH > > * GetRenderCache(const wxString &forResolvedText, const VECTOR2I &forPosition, TEXT_ATTRIBUTES &aAttrs) const
Definition: sch_field.cpp:384
void SetId(int aId)
Definition: sch_field.cpp:161
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: sch_field.cpp:1123
void ClearCaches() override
Definition: sch_field.cpp:369
void SetText(const wxString &aText) override
Definition: sch_field.cpp:1213
VECTOR2I GetParentPosition() const
Definition: sch_field.cpp:1502
int m_id
Field index,.
Definition: sch_field.h:332
bool m_showInChooser
This field is available as a data column for the chooser.
Definition: sch_field.h:342
void OnScintillaCharAdded(SCINTILLA_TRICKS *aScintillaTricks, wxStyledTextEvent &aEvent) const
Definition: sch_field.cpp:808
wxString m_name
Definition: sch_field.h:334
void SetNameShown(bool aShown=true)
Definition: sch_field.h:209
void MirrorHorizontally(int aCenter) override
Mirror item horizontally about aCenter.
Definition: sch_field.cpp:1079
void Copy(SCH_FIELD *aTarget) const
Copy parameters of this field to another field.
Definition: sch_field.cpp:155
KIFONT::FONT * getDrawFont() const override
Definition: sch_field.cpp:358
bool m_allowAutoPlace
This field can be autoplaced.
Definition: sch_field.h:337
VECTOR2I GetSchematicTextOffset(const RENDER_SETTINGS *aSettings) const override
This offset depends on the orientation, the type of text, and the area required to draw the associate...
Definition: sch_label.cpp:1823
Base class for any item which can be embedded within the SCHEMATIC container class,...
Definition: sch_item.h:166
const wxString & GetDefaultFont() const
Definition: sch_item.cpp:455
SCH_RENDER_SETTINGS * getRenderSettings(PLOTTER *aPlotter) const
Definition: sch_item.h:670
const SYMBOL * GetParentSymbol() const
Definition: sch_item.cpp:166
SCHEMATIC * Schematic() const
Searches the item hierarchy to find a SCHEMATIC.
Definition: sch_item.cpp:150
@ SKIP_TST_POS
Definition: sch_item.h:662
@ EQUALITY
Definition: sch_item.h:660
std::shared_ptr< NETCLASS > GetEffectiveNetClass(const SCH_SHEET_PATH *aSheet=nullptr) const
Definition: sch_item.cpp:247
void SetLayer(SCH_LAYER_ID aLayer)
Definition: sch_item.h:282
SCH_LAYER_ID GetLayer() const
Return the layer this item is on.
Definition: sch_item.h:281
virtual int compare(const SCH_ITEM &aOther, int aCompareFlags=0) const
Provide the draw object specific comparison called by the == and < operators.
Definition: sch_item.cpp:416
bool IsConnectivityDirty() const
Definition: sch_item.h:510
void SwapFlags(SCH_ITEM *aItem)
Swap the non-temp and non-edit flags.
Definition: sch_item.cpp:351
bool m_private
Definition: sch_item.h:726
const KIFONT::METRICS & GetFontMetrics() const
Definition: sch_item.cpp:464
SCH_LAYER_ID m_layer
Definition: sch_item.h:723
double SimilarityBase(const SCH_ITEM &aItem) const
Calculate the boilerplate similarity for all LIB_ITEMs without preventing the use above of a pure vir...
Definition: sch_item.h:316
void GetIntersheetRefs(const SCH_SHEET_PATH *aPath, std::vector< std::pair< wxString, wxString > > *pages)
Builds an array of { pageNumber, pageName } pairs.
Definition: sch_label.cpp:634
virtual bool ResolveTextVar(const SCH_SHEET_PATH *aPath, wxString *token, int aDepth) const
Resolve any references to system tokens supported by the label.
Definition: sch_label.cpp:684
static const wxString GetDefaultFieldName(const wxString &aName, bool aUseDefaultName)
Definition: sch_label.cpp:203
void GetContextualTextVars(wxArrayString *aVars) const
Return the list of system text vars & fields for this label.
Definition: sch_label.cpp:671
VECTOR2I GetSchematicTextOffset(const RENDER_SETTINGS *aSettings) const override
This offset depends on the orientation, the type of text, and the area required to draw the associate...
Definition: sch_label.cpp:351
Handle actions specific to the schematic editor.
static wxString g_BackLink
void HypertextCommand(const wxString &href)
Container to create a flattened list of symbols because in a complex hierarchy, a symbol can be used ...
size_t GetCount() const
VECTOR2I TransformCoordinate(const VECTOR2I &aPoint) const
const KIGFX::COLOR4D & GetBackgroundColor() const override
Return current background color settings.
void GetSymbols(SCH_REFERENCE_LIST &aReferences, bool aIncludePowerSymbols=true, bool aForceIncludeOrphanSymbols=false) const
Add a SCH_REFERENCE object to aReferences for each symbol in the list of sheets.
Handle access to a stack of flattened SCH_SHEET objects by way of a path for creating a flattened sch...
SCH_SHEET * Last() const
Return a pointer to the last SCH_SHEET of the list.
Sheet symbol placed in a schematic, and is the entry point for a sub schematic.
Definition: sch_sheet.h:57
void GetContextualTextVars(wxArrayString *aVars) const
Return the list of system text vars & fields for this sheet.
Definition: sch_sheet.cpp:213
static const wxString GetDefaultFieldName(int aFieldNdx, bool aTranslated=true)
Definition: sch_sheet.cpp:57
bool ResolveTextVar(const SCH_SHEET_PATH *aPath, wxString *token, int aDepth=0) const
Resolve any references to system tokens supported by the sheet.
Definition: sch_sheet.cpp:254
Schematic symbol object.
Definition: sch_symbol.h:104
wxString SubReference(int aUnit, bool aAddSeparator=true) const
Definition: sch_symbol.cpp:856
void SetValueFieldText(const wxString &aValue)
Definition: sch_symbol.cpp:917
SCH_FIELD * GetField(MANDATORY_FIELD_T aFieldType)
Return a mandatory field in this symbol.
Definition: sch_symbol.cpp:939
void SetRef(const SCH_SHEET_PATH *aSheet, const wxString &aReference)
Set the reference for the given sheet path for this symbol.
Definition: sch_symbol.cpp:779
void SetFootprintFieldText(const wxString &aFootprint)
Definition: sch_symbol.cpp:933
VECTOR2I GetPosition() const override
Definition: sch_symbol.h:807
bool ResolveTextVar(const SCH_SHEET_PATH *aPath, wxString *token, int aDepth=0) const
Resolve any references to system tokens supported by the symbol.
void GetContextualTextVars(wxArrayString *aVars) const
Return the list of system text vars & fields for this symbol.
TRANSFORM & GetTransform()
Definition: sch_symbol.h:288
int GetUnitSelection(const SCH_SHEET_PATH *aSheet) const
Return the instance-specific unit selection for the given sheet path.
Definition: sch_symbol.cpp:865
int GetUnitCount() const override
Return the number of units per package of the symbol.
Definition: sch_symbol.cpp:468
const wxString GetRef(const SCH_SHEET_PATH *aSheet, bool aIncludeUnit=false) const override
Definition: sch_symbol.cpp:737
Add cut/copy/paste, dark theme, autocomplete and brace highlighting to a wxStyleTextCtrl instance.
wxStyledTextCtrl * Scintilla() const
void DoAutocomplete(const wxString &aPartial, const wxArrayString &aTokens)
SIM_MODEL & CreateModel(SIM_MODEL::TYPE aType, const std::vector< SCH_PIN * > &aPins, REPORTER &aReporter)
virtual std::vector< std::string > GetPinNames() const
Definition: sim_model.h:469
GR_TEXT_H_ALIGN_T m_Halign
GR_TEXT_V_ALIGN_T m_Valign
TOOL_MANAGER * GetToolManager() const
Return the MVC controller.
Definition: tools_holder.h:55
for transforming drawing coordinates for a wxDC device context.
Definition: transform.h:46
int y1
Definition: transform.h:49
TRANSFORM InverseTransform() const
Calculate the Inverse mirror/rotation transform.
Definition: transform.cpp:59
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().
wxString ExpandTextVars(const wxString &aSource, const PROJECT *aProject, int aFlags)
Definition: common.cpp:59
wxString GetTextVars(const wxString &aSource)
Returns any variables unexpanded, e.g.
Definition: common.cpp:121
The common library.
#define _HKI(x)
#define _(s)
static constexpr EDA_ANGLE ANGLE_90
Definition: eda_angle.h:403
static constexpr EDA_ANGLE ANGLE_VERTICAL
Definition: eda_angle.h:398
static constexpr EDA_ANGLE ANGLE_HORIZONTAL
Definition: eda_angle.h:397
static constexpr EDA_ANGLE ANGLE_270
Definition: eda_angle.h:406
#define STRUCT_DELETED
flag indication structures to be erased
#define SKIP_STRUCT
flag indicating that the structure should be ignored
bool GetGRForceBlackPenState(void)
Definition: gr_basic.cpp:165
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
PROJECT & Prj()
Definition: kicad.cpp:597
SCH_LAYER_ID
Eeschema drawing layers.
Definition: layer_ids.h:353
@ LAYER_SHEETNAME
Definition: layer_ids.h:376
@ LAYER_HIDDEN
Definition: layer_ids.h:395
@ LAYER_VALUEPART
Definition: layer_ids.h:365
@ LAYER_FIELDS
Definition: layer_ids.h:366
@ LAYER_SHEETFIELDS
Definition: layer_ids.h:378
@ LAYER_REFERENCEPART
Definition: layer_ids.h:364
@ LAYER_NETCLASS_REFS
Definition: layer_ids.h:368
@ LAYER_SELECTION_SHADOWS
Definition: layer_ids.h:397
@ LAYER_INTERSHEET_REFS
Definition: layer_ids.h:367
@ LAYER_SHEETFILENAME
Definition: layer_ids.h:377
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
static GR_TEXT_H_ALIGN_T horizJustify(const char *horizontal)
#define TYPE_HASH(x)
Definition: property.h:71
#define DECLARE_ENUM_TO_WXANY(type)
Definition: property.h:729
#define REGISTER_TYPE(x)
Definition: property_mgr.h:371
static const std::vector< KICAD_T > labelTypes
Definition: sch_field.cpp:57
static struct SCH_FIELD_DESC _SCH_FIELD_DESC
@ SHEET_MANDATORY_FIELDS
The first 2 are mandatory, and must be instantiated in SCH_SHEET.
Definition: sch_sheet.h:49
@ SHEETNAME
Definition: sch_sheet.h:45
@ SHEETFILENAME
Definition: sch_sheet.h:46
wxString UnescapeString(const wxString &aSource)
static const wxString GetDefaultFieldName(int aFieldNdx, bool aTranslateForHI=false)
Return a default symbol field name for field aFieldNdx for all components.
Definition for symbol library class.
wxString GetCanonicalFieldName(int idx)
@ FOOTPRINT_FIELD
Field Name Module PCB, i.e. "16DIP300".
@ VALUE_FIELD
Field Value of part, i.e. "3.3K".
@ MANDATORY_FIELDS
The first 5 are mandatory, and must be instantiated in SCH_COMPONENT and LIB_PART constructors.
@ REFERENCE_FIELD
Field Reference of part, i.e. "IC21".
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_T
@ GR_TEXT_V_ALIGN_BOTTOM
@ GR_TEXT_V_ALIGN_INDETERMINATE
@ GR_TEXT_V_ALIGN_CENTER
@ GR_TEXT_V_ALIGN_TOP
wxLogTrace helper definitions.
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:229
@ LIB_SYMBOL_T
Definition: typeinfo.h:148
@ SCH_SYMBOL_T
Definition: typeinfo.h:172
@ SCH_FIELD_T
Definition: typeinfo.h:150
@ SCH_LABEL_T
Definition: typeinfo.h:167
@ SCH_SHEET_T
Definition: typeinfo.h:174
@ SCH_LABEL_LOCATE_ANY_T
Definition: typeinfo.h:190
@ SCH_GLOBAL_LABEL_T
Definition: typeinfo.h:168
#define INDETERMINATE_STATE
Used for holding indeterminate values, such as with multiple selections holding different values or c...
Definition: ui_common.h:46
VECTOR2< int32_t > VECTOR2I
Definition: vector2d.h:691