35#include <wx/wfstream.h>
58 wxFFileOutputStream stream( aOutFileName );
66 return xdoc.Save( stream, 2 );
113 xroot->AddChild( xchains );
130 wxString description;
132 nlohmann::ordered_map<wxString, wxString> fields;
143 wxString ref = aSymbol->
GetRef( &aSheet );
153 wxString ref2 = symbol2->
GetRef( &sheet );
155 if( ref2.CmpNoCase( ref ) != 0 )
165 if( !candidate.IsEmpty() && ( unit < minUnit || value.IsEmpty() ) )
171 if( !candidate.IsEmpty() && ( unit < minUnit || footprint.IsEmpty() ) )
172 footprint = candidate;
178 if( !candidate.IsEmpty() && ( unit < minUnit ||
datasheet.IsEmpty() ) )
185 if( !candidate.IsEmpty() && ( unit < minUnit || description.IsEmpty() ) )
186 description = candidate;
191 if( field.IsMandatory() || field.IsPrivate() )
194 if( unit < minUnit || fields.count( field.GetName() ) == 0 )
198 minUnit = std::min( unit, minUnit );
215 if( field.IsMandatory() || field.IsPrivate() )
230 aNode->AddChild(
node( wxT(
"value" ), wxT(
"~" ) ) );
232 if( footprint.size() )
238 if( description.size() )
242 aNode->AddChild( xfields =
node( wxT(
"fields" ) ) );
244 for(
const auto& [ fieldName, fieldValue ] : fields )
248 xfields->AddChild( xfield );
255 XNODE* xcomps =
node( wxT(
"components" ) );
277 b->GetRef( &sheet,
false ),
true ) < 0 );
280 std::set<
SCH_SYMBOL*,
decltype( cmp )> ordered_symbols( cmp );
281 std::multiset<
SCH_SYMBOL*,
decltype( cmp )> extra_units( cmp );
286 auto test = ordered_symbols.insert( symbol );
290 if( ( *(
test.first ) )->m_Uuid > symbol->
m_Uuid )
292 extra_units.insert( *(
test.first ) );
293 ordered_symbols.erase(
test.first );
294 ordered_symbols.insert( symbol );
298 extra_units.insert( symbol );
303 for(
EDA_ITEM* item : ordered_symbols )
315 if( forBOM && ( sheet.GetExcludedFromBOM(
m_schematic->GetCurrentVariant() )
321 if( forBoard && ( sheet.GetExcludedFromBoard(
m_schematic->GetCurrentVariant() )
332 xcomps->AddChild( xcomp =
node( wxT(
"comp" ) ) );
338 xcomp->AddChild( xlibsource =
node( wxT(
"libsource" ) ) );
366 std::vector<SCH_FIELD>& fields = symbol->
GetFields();
370 if( field.IsMandatory() || field.IsPrivate() )
373 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
374 xproperty->
AddAttribute( wxT(
"name" ), field.GetUntranslatedName() );
380 for(
const SCH_FIELD& sheetField : sheet.Last()->GetFields() )
382 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
383 xproperty->
AddAttribute( wxT(
"name" ), sheetField.GetUntranslatedName() );
395 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
396 xproperty->
AddAttribute( wxT(
"name" ), wxT(
"exclude_from_bom" ) );
402 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
403 xproperty->
AddAttribute( wxT(
"name" ), wxT(
"exclude_from_sim" ) );
409 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
410 xproperty->
AddAttribute( wxT(
"name" ), wxT(
"exclude_from_board" ) );
417 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
418 xproperty->
AddAttribute( wxT(
"name" ), wxT(
"exclude_from_pos_files" ) );
421 const bool baseDnp = symbol->
ResolveDNP( &sheet ) || sheet.GetDNP();
425 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
431 const std::set<wxString>& variantNames =
m_schematic->GetVariantNames();
436 XNODE* xvariants =
nullptr;
438 for(
const auto& variantName : variantNames )
440 XNODE* xvariant =
nullptr;
443 [
this, &xvariant, &variantName](
XNODE* child ) ->
void
450 xvariant =
node( wxT(
"variant" ) );
453 xvariant->AddChild( child );
457 [
this, &addToVariant]( wxString
const&
name,
bool base,
bool effective ) ->
void
459 if( base == effective )
462 XNODE* xvarprop =
node( wxT(
"property" ) );
464 xvarprop->
AddAttribute( wxT(
"value" ), effective ? wxT(
"1" ) : wxT(
"0" ) );
465 addToVariant( xvarprop );
468 bool effectiveDnp = symbol->
ResolveDNP( &sheet, variantName ) || sheet.GetDNP( variantName );
469 addBinaryProp( wxT(
"dnp" ), baseDnp, effectiveDnp );
472 || sheet.GetExcludedFromBOM( variantName );
473 addBinaryProp( wxT(
"exclude_from_bom" ), baseExcludedFromBOM, effectiveExcludedFromBOM );
476 || sheet.GetExcludedFromSim( variantName );
477 addBinaryProp( wxT(
"exclude_from_sim" ), baseExcludedFromSim, effectiveExcludedFromSim );
480 addBinaryProp( wxT(
"exclude_from_pos_files" ), baseExcludedFromPosFiles,
481 effectiveExcludedFromPosFiles );
487 variant = &instance.
m_Variants.at( variantName );
491 XNODE* xprop =
node( wxT(
"property" ) );
492 xprop->
AddAttribute( wxT(
"name" ), wxT(
"symbol_override" ) );
494 addToVariant( xprop );
499 XNODE* xfields =
nullptr;
501 for(
const auto& [fieldName, fieldValue] : variant->
m_Fields )
503 const wxString baseValue = symbol->
GetFieldText( fieldName, &sheet, wxEmptyString );
505 if( fieldValue == baseValue )
509 xfields =
node( wxT(
"fields" ) );
511 wxString resolvedValue = fieldValue;
514 resolvedValue = symbol->
ResolveText( fieldValue, &sheet );
518 xfields->AddChild( xfield );
528 const wxString& fieldName = baseField.GetName();
530 if( variant->
m_Fields.contains( fieldName ) )
533 const wxString baseValue = symbol->
GetFieldText( fieldName, &sheet, wxEmptyString );
534 const wxString variantValue = symbol->
GetFieldText( fieldName, &sheet, variantName );
536 if( variantValue == baseValue )
540 xfields =
node( wxT(
"fields" ) );
542 wxString resolvedValue = variantValue;
545 resolvedValue = symbol->
ResolveText( variantValue, &sheet );
549 xfields->AddChild( xfield );
556 std::vector<SCH_FIELD*> altFields;
557 altSymbol->GetFields( altFields );
559 for(
const SCH_FIELD* altField : altFields )
561 const wxString& fieldName = altField->GetName();
564 || variant->
m_Fields.contains( fieldName )
565 || altField->GetText().IsEmpty() )
571 xfields =
node( wxT(
"fields" ) );
573 wxString resolvedValue = altField->GetText();
576 resolvedValue = symbol->
ResolveText( resolvedValue, &sheet );
580 xfields->AddChild( xfield );
585 addToVariant( xfields );
591 xvariants =
node( wxT(
"variants" ) );
593 xvariants->AddChild( xvariant );
598 xcomp->AddChild( xvariants );
601 if(
const std::unique_ptr<LIB_SYMBOL>& part = symbol->
GetLibSymbolRef() )
603 if( part->GetKeyWords().size() )
605 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
606 xproperty->
AddAttribute( wxT(
"name" ), wxT(
"ki_keywords" ) );
607 xproperty->
AddAttribute( wxT(
"value" ), part->GetKeyWords() );
610 if( !part->GetFPFilters().IsEmpty() )
614 for(
const wxString&
filter : part->GetFPFilters() )
617 xcomp->AddChild( xproperty =
node( wxT(
"property" ) ) );
618 xproperty->
AddAttribute( wxT(
"name" ), wxT(
"ki_fp_filters" ) );
622 if( part->GetDuplicatePinNumbersAreJumpers() )
623 xcomp->AddChild(
node( wxT(
"duplicate_pin_numbers_are_jumpers" ), wxT(
"1" ) ) );
630 xcomp->AddChild( xproperty =
node( wxT(
"jumper_pin_groups" ) ) );
634 xproperty->AddChild( groupNode =
node( wxT(
"group" ) ) );
636 for(
const wxString& pinName :
group.GetNames() )
637 groupNode->AddChild(
node( wxT(
"pin" ), pinName ) );
643 xcomp->AddChild( xsheetpath =
node( wxT(
"sheetpath" ) ) );
645 xsheetpath->
AddAttribute( wxT(
"names" ), sheet.PathHumanReadable() );
646 xsheetpath->
AddAttribute( wxT(
"tstamps" ), sheet.PathAsString() );
651 if( compClassNames.size() > 0 )
653 XNODE* xcompclasslist;
654 xcomp->AddChild( xcompclasslist =
node( wxT(
"component_classes" ) ) );
656 for(
const wxString& compClass : compClassNames )
661 xcomp->AddChild( xunits =
node( wxT(
"tstamps" ) ) );
663 auto range = extra_units.equal_range( symbol );
667 for(
auto it = range.first; it != range.second; ++it )
669 uuid = ( *it )->m_Uuid.AsString();
676 xunits->AddChild(
new XNODE( wxXML_TEXT_NODE, wxEmptyString, uuid ) );
681 xunits->AddChild(
new XNODE( wxXML_TEXT_NODE, wxEmptyString, uuid ) );
685 xcomp->AddChild( xunitInfo =
node( wxT(
"units" ) ) );
700 const std::vector<LIB_SYMBOL::UNIT_PIN_INFO>& defaultUnitInfo = libSym->GetUnitPinInfo();
701 std::map<int, SCH_SYMBOL*> symbolByUnit;
709 int unit = aUnitSymbol->GetUnitSelection( &sheet );
712 symbolByUnit.try_emplace( unit, aUnitSymbol );
715 addUnitSymbol( symbol );
717 auto extraUnitRange = extra_units.equal_range( symbol );
721 for(
auto it = extraUnitRange.first; it != extraUnitRange.second; ++it )
722 addUnitSymbol( *it );
726 for(
size_t unitIdx = 0; unitIdx < defaultUnitInfo.size(); ++unitIdx )
729 auto symbolIt = symbolByUnit.find( unitIdx + 1 );
731 if( symbolIt != symbolByUnit.end() )
733 const std::unique_ptr<LIB_SYMBOL>& unitLibSym = symbolIt->second->GetLibSymbolRef();
737 const std::vector<LIB_SYMBOL::UNIT_PIN_INFO>& unitSpecificInfo =
738 unitLibSym->GetUnitPinInfo();
740 if( unitIdx < unitSpecificInfo.size() )
741 unitInfo = unitSpecificInfo[unitIdx];
746 xunitInfo->AddChild( xunit =
node( wxT(
"unit" ) ) );
750 xunit->AddChild( xpins =
node( wxT(
"pins" ) ) );
755 xpins->AddChild( xpin =
node( wxT(
"pin" ) ) );
779 std::map<SCH_SCREEN*, int> screenVisits;
782 screenVisits[sheet.LastScreen()]++;
790 wxString instancePrefix = sheet.PathAsString();
795 wxString groupName =
group->GetName();
797 if( screenVisits[sheet.LastScreen()] > 1 )
798 groupName = wxString::Format( wxT(
"%s (%s)" ), groupName, sheet.PathHumanReadable() );
801 xcomps->AddChild( xgroup =
node( wxT(
"group" ) ) );
804 xgroup->
AddAttribute( wxT(
"uuid" ), instancePrefix +
group->m_Uuid.AsString() );
808 xgroup->AddChild( xmembers =
node( wxT(
"members" ) ) );
815 xmembers->AddChild( xmember =
node( wxT(
"member" ) ) );
816 xmember->
AddAttribute( wxT(
"uuid" ), instancePrefix + member->m_Uuid.AsString() );
822 xmembers->AddChild( xmember =
node( wxT(
"member" ) ) );
823 xmember->
AddAttribute( wxT(
"uuid" ), instancePrefix + member->m_Uuid.AsString() );
828 std::vector<SCH_SHEET_PATH> descendantSheets;
838 xmembers->AddChild( xmember =
node( wxT(
"member" ) ) );
840 descendantSheet.PathAsString() + descendantItem->m_Uuid.AsString() );
856 XNODE* xvariants =
node( wxT(
"variants" ) );
858 std::set<wxString> variantNames =
m_schematic->GetVariantNames();
860 for(
const wxString& variantName : variantNames )
863 xvariants->AddChild( xvariant =
node( wxT(
"variant" ) ) );
866 wxString description =
m_schematic->GetVariantDescription( variantName );
868 if( !description.IsEmpty() )
869 xvariant->
AddAttribute( wxT(
"description" ), description );
879 std::vector<SCH_SHEET_PATH> symbolSheets;
880 symbolSheets.push_back( aSymbolSheet );
887 const wxString ref = aSymbol->
GetRef( &aSymbolSheet );
895 wxString ref2 = symbol2->
GetRef( &sheet );
898 if( ref2.CmpNoCase( ref ) != 0 )
901 if( otherUnit == primaryUnit )
904 symbolSheets.push_back( sheet );
908 compClassNames.insert( otherClassNames.begin(), otherClassNames.end() );
918 if( symbolSheetPath.IsContainedWithin( sheetPath ) )
919 compClassNames.insert( sheetCompClasses.begin(), sheetCompClasses.end() );
923 std::vector<wxString> sortedCompClassNames( compClassNames.begin(), compClassNames.end() );
924 std::sort( sortedCompClassNames.begin(), sortedCompClassNames.end(),
925 [](
const wxString& str1,
const wxString& str2 )
927 return str1.Cmp( str2 ) < 0;
930 return sortedCompClassNames;
937 XNODE* xdesign =
node( wxT(
"design" ) );
943 wxFileName sourceFileName;
946 xdesign->AddChild(
node( wxT(
"source" ),
m_schematic->GetFileName() ) );
953 const std::map<wxString, wxString>& properties =
m_schematic->Project().GetTextVars();
955 for(
const std::pair<const wxString, wxString>& prop : properties )
957 xdesign->AddChild( xtextvar =
node( wxT(
"textvar" ), prop.second ) );
964 unsigned sheetIndex = 1;
968 screen = sheet.LastScreen();
970 xdesign->AddChild( xsheet =
node( wxT(
"sheet" ) ) );
973 sheetTxt.Printf( wxT(
"%u" ), sheetIndex++ );
975 xsheet->
AddAttribute( wxT(
"name" ), sheet.PathHumanReadable() );
976 xsheet->
AddAttribute( wxT(
"tstamps" ), sheet.PathAsString() );
981 xsheet->AddChild( xtitleBlock =
node( wxT(
"title_block" ) ) );
989 sourceFileName = wxFileName( screen->
GetFileName() );
990 xtitleBlock->AddChild(
node( wxT(
"source" ), sourceFileName.GetFullName() ) );
992 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
996 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1000 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1004 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1008 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1012 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1016 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1020 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1024 xtitleBlock->AddChild( xcomment =
node( wxT(
"comment" ) ) );
1035 XNODE* xlibs =
node( wxT(
"libraries" ) );
1046 xlibs->AddChild( xlibrary =
node( wxT(
"library" ) ) );
1047 xlibrary->
AddAttribute( wxT(
"logical" ), libNickname );
1048 xlibrary->AddChild(
node( wxT(
"uri" ), *uri ) );
1058 XNODE* xlibparts =
node( wxT(
"libparts" ) );
1059 std::vector<SCH_FIELD*> fieldList;
1065 wxString libNickname = lcomp->GetLibId().GetLibNickname();;
1068 if( !libNickname.IsEmpty() )
1072 xlibparts->AddChild( xlibpart =
node( wxT(
"libpart" ) ) );
1074 xlibpart->
AddAttribute( wxT(
"part" ), lcomp->GetName() );
1077 if( !lcomp->GetDescription().IsEmpty() )
1078 xlibpart->AddChild(
node( wxT(
"description" ), lcomp->GetDescription() ) );
1080 if( !lcomp->GetDatasheetField().GetText().IsEmpty() )
1081 xlibpart->AddChild(
node( wxT(
"docs" ), lcomp->GetDatasheetField().GetText() ) );
1084 if( lcomp->GetFPFilters().GetCount() )
1087 xlibpart->AddChild( xfootprints =
node( wxT(
"footprints" ) ) );
1089 for(
unsigned i = 0; i < lcomp->GetFPFilters().GetCount(); ++i )
1091 if( !lcomp->GetFPFilters()[i].IsEmpty() )
1092 xfootprints->AddChild(
node( wxT(
"fp" ), lcomp->GetFPFilters()[i] ) );
1098 lcomp->GetFields( fieldList );
1101 xlibpart->AddChild( xfields =
node(
"fields" ) );
1103 for(
const SCH_FIELD* field : fieldList )
1106 xfields->AddChild( xfield =
node( wxT(
"field" ), field->GetText() ) );
1107 xfield->
AddAttribute( wxT(
"name" ), field->GetUntranslatedName() );
1113 std::vector<SCH_PIN*> pinList = lcomp->GetGraphicalPins( 0, 0 );
1125 for(
int ii = 0; ii < (int)pinList.size()-1; ii++ )
1127 if( pinList[ii]->GetNumber() == pinList[ii+1]->GetNumber() )
1129 pinList.erase(pinList.begin() + ii + 1);
1134 wxLogTrace(
"CVPCB_PINCOUNT",
1135 wxString::Format(
"makeLibParts: lib='%s' part='%s' pinList(size)=%zu",
1136 libNickname, lcomp->GetName(), pinList.size() ) );
1138 if( pinList.size() )
1142 xlibpart->AddChild( pins =
node( wxT(
"pins" ) ) );
1144 for(
unsigned i=0; i<pinList.size(); ++i )
1146 SCH_PIN* basePin = pinList[i];
1148 bool stackedValid =
false;
1152 if( stackedValid && !expandedNums.empty() )
1154 for(
const wxString& num : expandedNums )
1157 pins->AddChild(
pin =
node( wxT(
"pin" ) ) );
1158 pin->AddAttribute( wxT(
"num" ), num );
1162 wxLogTrace(
"CVPCB_PINCOUNT",
1163 wxString::Format(
"makeLibParts: -> pin num='%s' name='%s' (expanded)",
1170 pins->AddChild(
pin =
node( wxT(
"pin" ) ) );
1175 wxLogTrace(
"CVPCB_PINCOUNT",
1176 wxString::Format(
"makeLibParts: -> pin num='%s' name='%s'",
1192 wxString netCodeTxt;
1194 XNODE* xnet =
nullptr;
1216 NET_RECORD(
const wxString& aName ) :
1218 m_HasNoConnect(
false )
1223 bool m_HasNoConnect;
1224 std::vector<NET_NODE> m_Nodes;
1227 std::vector<NET_RECORD*> nets;
1229 std::shared_ptr<NET_SETTINGS> netSettings;
1232 netSettings =
m_schematic->Project().GetProjectFile().NetSettings();
1237 nets.emplace_back(
new NET_RECORD( netName ) );
1238 NET_RECORD* net_record = nets.back();
1239 net_record->m_HasNoConnect = net.hasNoConnect;
1243 if(
const auto netclass = netSettings->GetEffectiveNetClass( net.name ) )
1247 for(
const auto& [
pin, sheet] : net.pins )
1268 net_record->m_Nodes.emplace_back(
pin, sheet );
1273 std::sort( nets.begin(), nets.end(),
1274 [](
const NET_RECORD* a,
const NET_RECORD*b )
1276 return StrNumCmp( a->m_Name, b->m_Name ) < 0;
1279 for(
int i = 0; i < (int) nets.size(); ++i )
1281 NET_RECORD* net_record = nets[i];
1286 std::sort( net_record->m_Nodes.begin(), net_record->m_Nodes.end(),
1289 wxString refA = a.m_Pin->GetParentSymbol()->GetRef( &a.m_Sheet );
1290 wxString refB = b.m_Pin->GetParentSymbol()->GetRef( &b.m_Sheet );
1293 return a.m_Pin->GetShownNumber() < b.m_Pin->GetShownNumber();
1304 wxString refA = a.m_Pin->GetParentSymbol()->GetRef( &a.m_Sheet );
1305 wxString refB = b.m_Pin->GetParentSymbol()->GetRef( &b.m_Sheet );
1307 return refA == refB && a.m_Pin->GetShownNumber() == b.m_Pin->GetShownNumber();
1312 bool allNetPinsStacked =
true;
1314 if( net_record->m_Nodes.size() > 1 )
1316 SCH_PIN* firstPin = net_record->m_Nodes.begin()->m_Pin;
1317 allNetPinsStacked = std::all_of( net_record->m_Nodes.begin() + 1, net_record->m_Nodes.end(),
1320 return firstPin->GetParent() == node.m_Pin->GetParent()
1321 && firstPin->GetPosition() == node.m_Pin->GetPosition()
1322 && firstPin->GetName() == node.m_Pin->GetName();
1326 for(
const NET_NODE& netNode : net_record->m_Nodes )
1328 wxString refText = netNode.m_Pin->GetParentSymbol()->GetRef( &netNode.m_Sheet );
1331 if( refText[0] == wxChar(
'#' ) )
1337 std::vector<wxString> nums =
resolvePadNumbers( netNode.m_Pin, netNode.m_Sheet );
1343 wxString baseName = netNode.m_Pin->GetShownName();
1344 wxString pinType = netNode.m_Pin->GetCanonicalElectricalTypeName();
1348 netCodeTxt.Printf( wxT(
"%d" ), i + 1 );
1350 xnets->AddChild( xnet =
node( wxT(
"net" ) ) );
1352 xnet->
AddAttribute( wxT(
"name" ), net_record->m_Name );
1353 xnet->
AddAttribute( wxT(
"class" ), net_record->m_Class );
1358 for(
const wxString& num : nums )
1360 xnet->AddChild( xnode =
node( wxT(
"node" ) ) );
1364 wxString fullName = baseName.IsEmpty() ? num : baseName + wxT(
"_" ) + num;
1366 if( !baseName.IsEmpty() || nums.size() > 1 )
1369 wxString typeAttr = pinType;
1371 if( net_record->m_HasNoConnect
1372 && ( net_record->m_Nodes.size() == 1 || allNetPinsStacked ) )
1374 typeAttr += wxT(
"+no_connect" );
1382 for( NET_RECORD* record : nets )
1390 const auto& committed =
m_schematic->NetChains().GetCommittedNetChains();
1392 if( committed.empty() )
1395 XNODE* xchains =
node( wxT(
"net_chains" ) );
1397 for(
const std::unique_ptr<SCH_NETCHAIN>&
chain : committed )
1403 xchains->AddChild( xchain =
node( wxT(
"net_chain" ) ) );
1406 if( !
chain->GetNetClass().IsEmpty() )
1415 const std::shared_ptr<NET_SETTINGS>& ns = pf.
NetSettings();
1419 wxString className = ns->GetNetChainClass(
chain->GetName() );
1421 if( !className.IsEmpty() )
1422 xchain->
AddAttribute( wxT(
"net_chain_class" ), className );
1430 wxString::Format( wxT(
"#%02X%02X%02X%02X" ),
1431 (
int) std::clamp(
KiROUND( c.
r * 255.0 ), 0, 255 ),
1432 (
int) std::clamp(
KiROUND( c.
g * 255.0 ), 0, 255 ),
1433 (
int) std::clamp(
KiROUND( c.
b * 255.0 ), 0, 255 ),
1434 (
int) std::clamp(
KiROUND( c.
a * 255.0 ), 0, 255 ) ) );
1438 xchain->AddChild( xmembers =
node( wxT(
"members" ) ) );
1444 for(
const wxString& net :
chain->GetNets() )
1450 xmembers->AddChild( xmember =
node( wxT(
"member" ) ) );
1454 if( !
chain->GetTerminalRef( 0 ).IsEmpty() || !
chain->GetTerminalRef( 1 ).IsEmpty() )
1457 xchain->AddChild( xterms =
node( wxT(
"terminal_pins" ) ) );
1459 for(
int i = 0; i < 2; ++i )
1461 if(
chain->GetTerminalRef( i ).IsEmpty() )
1465 xterms->AddChild( xterm =
node( wxT(
"terminal_pin" ) ) );
1478 XNODE* n =
new XNODE( wxXML_ELEMENT_NODE, aName );
1480 if( aTextualContent.Len() > 0 )
1481 n->AddChild(
new XNODE( wxXML_TEXT_NODE, wxEmptyString, aTextualContent ) );
1500 auto getComponentClassFields =
1501 [&](
const std::vector<SCH_FIELD>& fields,
const SCH_SHEET_PATH* sheetPath )
1503 std::unordered_set<wxString> componentClasses;
1507 if( field.GetUntranslatedName() == wxT(
"Component Class" ) )
1514 return componentClasses;
1522 std::unordered_set<wxString> sheetComponentClasses;
1523 const std::unordered_set<SCH_RULE_AREA*>& sheetRuleAreas = sheetItem->
GetRuleAreaCache();
1529 std::unordered_set<wxString> ruleAreaComponentClasses = getComponentClassFields( label->GetFields(),
1531 sheetComponentClasses.insert( ruleAreaComponentClasses.begin(), ruleAreaComponentClasses.end() );
constexpr BOX2I KiROUND(const BOX2D &aBoxD)
wxString GetBuildVersion()
Get the full KiCad version string.
static const COLOR4D UNSPECIFIED
For legacy support; used as a value to indicate color hasn't been set yet.
A base class for most all the KiCad significant classes used in schematics and boards.
Represents an (ordered) list of JUMPER_GROUP objects.
const std::vector< JUMPER_GROUP > & GetAll() const
Represents a group of jumper pins or pads, keyed by name.
A color representation with 4 components: red, green, blue, alpha.
wxString AsString() const
std::optional< wxString > GetFullURI(LIBRARY_TABLE_TYPE aType, const wxString &aNickname, bool aSubstituted=false)
Return the full location specifying URI for the LIB, either in original UI form or in environment var...
const wxString GetUniStringLibItemName() const
Get strings for display messages in dialogs.
const wxString GetUniStringLibNickname() const
Define a library symbol object.
SCH_SYMBOL * findNextSymbol(EDA_ITEM *aItem, const SCH_SHEET_PATH &aSheetPath)
Check if the given symbol should be processed for netlisting.
std::set< LIB_SYMBOL *, LIB_SYMBOL_LESS_THAN > m_libParts
unique library symbols used. LIB_SYMBOL items are sorted by names
std::vector< wxString > resolvePadNumbers(const SCH_PIN *aPin, const SCH_SHEET_PATH &aSheetPath) const
Resolve aPin to its effective pad number(s) for every netlist path (issue #2282).
UNIQUE_STRINGS m_referencesAlreadyFound
Used for "multiple symbols per package" symbols to avoid processing a lib symbol more than once.
SCH_SHEET_LIST m_exportSheets
std::vector< EXPORT_NET > m_exportNets
wxString m_exportVariant
The schematic we're generating a netlist for.
void getSheetComponentClasses()
std::map< SCH_SHEET_PATH, std::unordered_set< wxString > > m_sheetComponentClasses
Map of all sheets to component classes covering the whole sheet.
XNODE * makeDesignHeader()
Fill out a project "design" header into an XML node.
XNODE * makeLibraries()
Fill out an XML node with a list of used libraries and returns it.
XNODE * node(const wxString &aName, const wxString &aTextualContent=wxEmptyString)
A convenience function that creates a new XNODE with an optional textual child.
XNODE * makeListOfNets(unsigned aCtl)
Fill out an XML node with a list of nets and returns it.
void addSymbolFields(XNODE *aNode, SCH_SYMBOL *aSymbol, const SCH_SHEET_PATH &aSheet, const SCH_SHEET_LIST &aSheetList)
Holder for multi-unit symbol fields.
RESOLUTION_CONTEXT m_resolveTextVars
bool writeNetlist(const wxString &aOutFileName, unsigned aNetlistOptions, REPORTER &aReporter) override
Write generic netlist to aOutFileName.
std::vector< wxString > getComponentClassNamesForAllSymbolUnits(SCH_SYMBOL *aSymbol, const SCH_SHEET_PATH &aSymbolSheet, const SCH_SHEET_LIST &aSheetList)
Finds all component class names attached to any sub-unit of a given symbol.
XNODE * makeSymbols(unsigned aCtl)
XNODE * makeRoot(unsigned aCtl=GNL_ALL)
Build the entire document tree for the generic export.
std::set< wxString > m_libraries
XNODE * makeLibParts()
Fill out an XML node with the unique library parts and returns it.
virtual LIBRARY_MANAGER & GetLibraryManager() const
The backing store for a PROJECT, in JSON format.
std::shared_ptr< NET_SETTINGS > & NetSettings()
Container for project specific data.
A pure virtual class used to derive REPORTER objects from.
wxString GetShownText(const SCH_SHEET_PATH *aPath, RESOLUTION_CONTEXT aContext, const wxString &aVariantName=wxEmptyString, int aDepth=0) const
A set of SCH_ITEMs (i.e., without duplicates).
Base class for any item which can be embedded within the SCHEMATIC container class,...
bool ResolveExcludedFromPosFiles(const SCH_SHEET_PATH *aInstance=nullptr, const wxString &aVariantName=wxEmptyString) const
const std::unordered_set< SCH_RULE_AREA * > & GetRuleAreaCache() const
Get the cache of rule areas enclosing this item.
bool ResolveExcludedFromBOM(const SCH_SHEET_PATH *aInstance=nullptr, const wxString &aVariantName=wxEmptyString) const
wxString ResolveText(const wxString &aText, const SCH_SHEET_PATH *aPath, int aDepth=0) const
bool ResolveExcludedFromBoard(const SCH_SHEET_PATH *aInstance=nullptr, const wxString &aVariantName=wxEmptyString) const
bool ResolveDNP(const SCH_SHEET_PATH *aInstance=nullptr, const wxString &aVariantName=wxEmptyString) const
bool ResolveExcludedFromSim(const SCH_SHEET_PATH *aInstance=nullptr, const wxString &aVariantName=wxEmptyString) const
static bool IsPersistableNet(const wxString &aNet)
Synthetic keys do not survive a reload, so only named nets are written out.
std::vector< wxString > GetStackedPinNumbers(bool *aValid=nullptr) const
wxString GetCanonicalElectricalTypeName() const
const wxString & GetShownName() const
const wxString & GetShownNumber() const
const wxString & GetFileName() const
TITLE_BLOCK & GetTitleBlock()
A container for handling SCH_SHEET_PATH objects in a flattened hierarchy.
void GetSheetsWithinPath(std::vector< SCH_SHEET_PATH > &aSheets, const SCH_SHEET_PATH &aSheetPath) const
Add a SCH_SHEET_PATH object to aSheets for each sheet in the list that are contained within aSheetPat...
Handle access to a stack of flattened SCH_SHEET objects by way of a path for creating a flattened sch...
void push_back(SCH_SHEET *aSheet)
Forwarded method from std::vector.
Sheet symbol placed in a schematic, and is the entry point for a sub schematic.
Variant information for a schematic symbol.
std::optional< LIB_ID > m_SymbolOverride
Alternate library symbol to substitute for the base symbol in this variant, if any.
bool UseLibIdLookup() const
wxString GetFieldText(const wxString &aFieldName, const SCH_SHEET_PATH *aPath=nullptr, const wxString &aVariantName=wxEmptyString) const
wxString GetSchSymbolLibraryName() const
const wxString GetFootprintFieldText(const SCH_SHEET_PATH *aPath, RESOLUTION_CONTEXT aContext, const wxString &aVariantName=wxEmptyString) const
void GetFields(std::vector< SCH_FIELD * > &aVector, bool aVisibleOnly) const override
Populate a std::vector with SCH_FIELDs, sorted in ordinal order.
wxString GetShownDescription(RESOLUTION_CONTEXT aContext, int aDepth=0) const override
std::unordered_set< wxString > GetComponentClassNames(const SCH_SHEET_PATH *aPath, const wxString &aVariantName) const
Return the component classes this symbol belongs in.
const LIB_ID & GetLibId() const override
LIB_SYMBOL * GetVariantLibSymbol(const wxString &aVariantName, const SCH_SHEET_PATH &aPath) const
Resolve the alternate library symbol for a given variant.
bool GetInstance(SCH_SYMBOL_INSTANCE &aInstance, const KIID_PATH &aSheetPath, bool aTestFromEnd=false) const
const wxString GetValue(const SCH_SHEET_PATH *aPath, RESOLUTION_CONTEXT aContext, const wxString &aVariantName=wxEmptyString) const override
int GetUnitSelection(const SCH_SHEET_PATH *aSheet) const
Return the instance-specific unit selection for the given sheet path.
int GetUnitCount() const override
Return the number of units per package of the symbol.
std::unique_ptr< LIB_SYMBOL > & GetLibSymbolRef()
const wxString GetRef(const SCH_SHEET_PATH *aSheet, bool aIncludeUnit=false) const override
SCH_FIELD * GetField(FIELD_T aFieldType)
Return a mandatory field in this symbol.
Hold the information shown in the lower right corner of a plot, printout, or editing view.
const wxString & GetCompany() const
const wxString & GetRevision() const
const wxString & GetDate() const
const wxString & GetComment(int aIdx) const
const wxString & GetTitle() const
std::map< wxString, wxString > m_Fields
An extension of wxXmlNode that can format its contents as KiCad-style s-expressions.
void AddAttribute(const wxString &aName, const wxString &aValue) override
wxString ExpandTextVars(const wxString &aSource, const PROJECT *aProject, RESOLUTION_CONTEXT aContext)
void remove_duplicates(_Container &__c)
Deletes all duplicate values from __c.
static bool sortPinsByNumber(SCH_PIN *aPin1, SCH_PIN *aPin2)
PGM_BASE & Pgm()
The global program "get" accessor.
static const std::vector< std::string > filters
Class to handle a set of SCH_ITEMs.
Definition of the SCH_SHEET_PATH and SCH_SHEET_LIST classes for Eeschema.
int StrNumCmp(const wxString &aString1, const wxString &aString2, bool aIgnoreCase)
Compare two strings with alphanumerical content.
wxString UnescapeString(const wxString &aSource)
wxString GetISO8601CurrentDateTime()
std::vector< wxString > m_pinNumbers
One refdes -> net membership row collected from the NETDEF section.
A simple container for schematic symbol instance information.
std::map< wxString, SCH_SYMBOL_VARIANT > m_Variants
A list of symbol variants.
wxString GetDefaultFieldName(FIELD_T aFieldId, TRANSLATION aTranslation)
Return a default symbol field name for a mandatory field type.
@ DESCRIPTION
Field Description of part, i.e. "1/4W 1% Metal Film Resistor".
@ FOOTPRINT
Field Name Module PCB, i.e. "16DIP300".
@ DATASHEET
name of datasheet
const SHAPE_LINE_CHAIN chain
wxLogTrace helper definitions.