25#include <wx/filename.h>
27#include <wx/xml/xml.h>
43const std::map<CADSTAR_ARCHIVE_PARSER::TEXT_FIELD_NAME, wxString>
45 { { TEXT_FIELD_NAME::DESIGN_TITLE, wxT(
"DESIGN_TITLE" ) },
46 { TEXT_FIELD_NAME::SHORT_JOBNAME, wxT(
"SHORT_JOBNAME" ) },
47 { TEXT_FIELD_NAME::LONG_JOBNAME, wxT(
"LONG_JOBNAME" ) },
48 { TEXT_FIELD_NAME::NUM_OF_SHEETS, wxT(
"##" ) },
49 { TEXT_FIELD_NAME::SHEET_NUMBER, wxT(
"#" ) },
50 { TEXT_FIELD_NAME::SHEET_NAME, wxT(
"SHEETNAME" ) },
51 { TEXT_FIELD_NAME::VARIANT_NAME, wxT(
"VARIANT_NAME" ) },
52 { TEXT_FIELD_NAME::VARIANT_DESCRIPTION, wxT(
"VARIANT_DESCRIPTION" ) },
53 { TEXT_FIELD_NAME::REG_USER, wxT(
"REG_USER" ) },
54 { TEXT_FIELD_NAME::COMPANY_NAME, wxT(
"COMPANY_NAME" ) },
55 { TEXT_FIELD_NAME::CURRENT_USER, wxT(
"CURRENT_USER" ) },
56 { TEXT_FIELD_NAME::DATE, wxT(
"DATE" ) },
57 { TEXT_FIELD_NAME::TIME, wxT(
"TIME" ) },
58 { TEXT_FIELD_NAME::MACHINE_NAME, wxT(
"MACHINE_NAME" ) } };
63 wxASSERT( aNode->GetName() == wxT(
"FORMAT" ) );
73 wxASSERT( aNode->GetName() == wxT(
"TIMESTAMP" ) );
87 wxASSERT( aNode->GetName() == wxT(
"HEADER" ) );
91 for( ; cNode; cNode = cNode->
GetNext() )
93 wxString nodeName = cNode->GetName();
95 if( nodeName == wxT(
"FORMAT" ) )
97 Format.Parse( cNode, aContext );
99 else if( nodeName == wxT(
"JOBFILE" ) )
103 else if( nodeName == wxT(
"JOBTITLE" ) )
107 else if( nodeName == wxT(
"GENERATOR" ) )
111 else if( nodeName == wxT(
"RESOLUTION" ) )
115 if( ( subNode->GetName() == wxT(
"METRIC" ) )
130 else if( nodeName == wxT(
"TIMESTAMP" ) )
132 Timestamp.Parse( cNode, aContext );
144 wxASSERT( aNode->GetName() == wxT(
"VMASTER" ) || aNode->GetName() == wxT(
"VARIANT" ) );
148 if( aNode->GetName() == wxT(
"VMASTER" ) )
164 wxASSERT( aNode->GetName() == wxT(
"VHIERARCHY" ) );
168 for( ; cNode; cNode = cNode->
GetNext() )
170 if( cNode->GetName() == wxT(
"VMASTER" ) || cNode->GetName() == wxT(
"VARIANT" ) )
173 variant.
Parse( cNode, aContext );
174 Variants.insert( std::make_pair( variant.
ID, variant ) );
186 wxASSERT( aNode->GetName() == wxT(
"LINECODE" ) );
196 if( !cNode || cNode->GetName() != wxT(
"STYLE" ) )
201 if( styleStr == wxT(
"SOLID" ) )
205 else if( styleStr == wxT(
"DASH" ) )
209 else if( styleStr == wxT(
"DASHDOT" ) )
213 else if( styleStr == wxT(
"DASHDOTDOT" ) )
217 else if( styleStr == wxT(
"DOT" ) )
224 wxString::Format(
"LINECODE -> %s", Name ) );
231 wxASSERT( aNode->GetName() == wxT(
"HATCH" ) );
238 if( !cNode || cNode->GetName() != wxT(
"ORIENT" ) )
247 wxASSERT( aNode->GetName() == wxT(
"HATCHCODE" ) );
253 wxString
location = wxString::Format(
"HATCHCODE -> %s", Name );
255 for( ; cNode; cNode = cNode->
GetNext() )
257 if( cNode->GetName() != wxT(
"HATCH" ) )
261 hatch.
Parse( cNode, aContext );
262 Hatches.push_back( hatch );
269 wxASSERT( aNode->GetName() == wxT(
"FONT" ) );
277 for( ; cNode; cNode = cNode->
GetNext() )
279 wxString cNodeName = cNode->GetName();
281 if( cNodeName == wxT(
"ITALIC" ) )
283 else if( cNodeName == wxT(
"KERNING" ) )
293 wxASSERT( aNode->GetName() == wxT(
"TEXTCODE" ) );
306 if( cNode->GetName() == wxT(
"FONT" ) )
307 Font.Parse( cNode, aContext );
316 wxASSERT( aNode->GetName() == wxT(
"ROUTEREASSIGN" ) );
323 for( ; cNode; cNode = cNode->
GetNext() )
325 wxString cNodeName = cNode->GetName();
327 if( cNodeName == wxT(
"NECKWIDTH" ) )
329 else if( cNodeName == wxT(
"SROUTEWIDTH" ) )
331 else if( cNodeName == wxT(
"MINWIDTH" ) )
333 else if( cNodeName == wxT(
"MAXWIDTH" ) )
343 wxASSERT( aNode->GetName() == wxT(
"ROUTECODE" ) );
351 for( ; cNode; cNode = cNode->
GetNext() )
353 wxString cNodeName = cNode->GetName();
355 if( cNodeName == wxT(
"NECKWIDTH" ) )
359 else if( cNodeName == wxT(
"SROUTEWIDTH" ) )
363 else if( cNodeName == wxT(
"MINWIDTH" ) )
367 else if( cNodeName == wxT(
"MAXWIDTH" ) )
371 else if( cNodeName == wxT(
"ROUTEREASSIGN" ) )
374 routereassign.
Parse( cNode, aContext );
375 RouteReassigns.push_back( routereassign );
387 return Base * std::pow( 10.0, Exponent );
393 wxASSERT( aNode->GetName() == wxT(
"E" ) );
399 wxString::Format(
"%s->%s", aNode->
GetParent()->GetName(),
407 wxASSERT( aNode->GetName() == wxT(
"PT" ) );
416 wxASSERT( aNode->GetName() == wxT(
"PT" ) );
425 wxString aNodeName = aNode->GetName();
427 if( aNodeName == wxT(
"PT" ) || aNodeName == wxT(
"ACWARC" ) || aNodeName == wxT(
"CWARC" )
428 || aNodeName == wxT(
"CWSEMI" ) || aNodeName == wxT(
"ACWSEMI" ) )
441 wxASSERT( IsVertex( aNode ) );
443 wxString aNodeName = aNode->GetName();
445 if( aNodeName == wxT(
"PT" ) )
450 End.Parse( aNode, aContext );
452 else if( aNodeName == wxT(
"ACWARC" ) || aNodeName == wxT(
"CWARC" ) )
454 if( aNodeName == wxT(
"ACWARC" ) )
464 else if( aNodeName == wxT(
"ACWSEMI" ) || aNodeName == wxT(
"CWSEMI" ) )
466 if( aNodeName == wxT(
"ACWSEMI" ) )
480 wxASSERT_MSG(
true, wxT(
"Unknown VERTEX type" ) );
486 const std::function<
VECTOR2I(
const VECTOR2I& )> aCadstarToKicadPointCallback,
487 double aAccuracy )
const
491 aChainToAppendTo->
Append( aCadstarToKicadPointCallback( End ) );
495 wxCHECK_MSG( aChainToAppendTo->
PointCount() > 0, ,
496 "Can't append an arc to vertex to an empty chain" );
498 aChainToAppendTo->
Append( BuildArc( aChainToAppendTo->
GetPoint( -1 ),
499 aCadstarToKicadPointCallback ),
505 const std::function<
VECTOR2I(
const VECTOR2I& )> aCadstarToKicadPointCallback )
const
508 "Can't build an arc for a straight segment!" );
511 VECTOR2I endPoint = aCadstarToKicadPointCallback( End );
515 centerPoint = ( startPoint / 2 ) + ( endPoint / 2 );
517 centerPoint = aCadstarToKicadPointCallback( Center );
523 VECTOR2I transform = aCadstarToKicadPointCallback( { 500, 500 } )
524 - aCadstarToKicadPointCallback( { 0, 0 } );
526 if( ( transform.
x > 0 && transform.
y < 0 ) || ( transform.
x < 0 && transform.
y > 0 ) )
527 clockwise = !clockwise;
537 wxASSERT( aNode->GetName() == wxT(
"CUTOUT" ) );
545 wxString aNodeName = aNode->GetName();
547 if( aNodeName == wxT(
"OPENSHAPE" ) || aNodeName == wxT(
"OUTLINE" )
548 || aNodeName == wxT(
"SOLID" ) || aNodeName == wxT(
"HATCHED" ) )
561 wxASSERT( IsShape( aNode ) );
563 wxString aNodeName = aNode->GetName();
565 if( aNodeName == wxT(
"OPENSHAPE" ) )
570 HatchCodeID = wxEmptyString;
572 else if( aNodeName == wxT(
"OUTLINE" ) )
577 HatchCodeID = wxEmptyString;
579 else if( aNodeName == wxT(
"SOLID" ) )
584 HatchCodeID = wxEmptyString;
586 else if( aNodeName == wxT(
"HATCHED" ) )
595 wxASSERT_MSG(
true, wxT(
"Unknown SHAPE type" ) );
600 const std::function<
VECTOR2I(
const VECTOR2I& )> aCadstarToKicadPointCallback,
601 double aAccuracy )
const
605 if( Vertices.size() == 0 )
608 for(
const auto& vertex : Vertices )
609 vertex.AppendToChain( &outline, aCadstarToKicadPointCallback, aAccuracy );
624 const std::function<
VECTOR2I(
const VECTOR2I& )> aCadstarToKicadPointCallback,
625 double aAccuracy )
const
632 polyset.
AddOutline( OutlineAsChain( aCadstarToKicadPointCallback, aAccuracy ) );
634 for(
const auto& cutout : Cutouts )
638 if( cutout.Vertices.size() == 0 )
641 for(
const auto& cutoutVertex : cutout.Vertices )
642 cutoutVertex.AppendToChain( &hole, aCadstarToKicadPointCallback, aAccuracy );
647 cutout.Vertices.at( 0 ).AppendToChain( &hole, aCadstarToKicadPointCallback, aAccuracy );
658 wxASSERT( aNode->GetName() == wxT(
"UNITS" ) );
662 if( unit == wxT(
"CENTIMETER" ) )
664 else if( unit == wxT(
"INCH" ) )
666 else if( unit == wxT(
"METER" ) )
668 else if( unit == wxT(
"MICROMETRE" ) )
670 else if( unit == wxT(
"MM" ) )
672 else if( unit == wxT(
"THOU" ) )
674 else if( unit == wxT(
"DESIGN" ) )
685 wxASSERT( aNode->GetName() == wxT(
"ANGUNITS" ) );
689 if( angUnitStr == wxT(
"DEGREES" ) )
691 else if( angUnitStr == wxT(
"RADIANS" ) )
702 wxString aNodeName = aNode->GetName();
704 if( aNodeName == wxT(
"FRACTIONALGRID" ) || aNodeName == wxT(
"STEPGRID" ) )
713 wxASSERT( IsGrid( aNode ) );
715 wxString aNodeName = aNode->GetName();
717 if( aNodeName == wxT(
"FRACTIONALGRID" ) )
719 else if( aNodeName == wxT(
"STEPGRID" ) )
722 wxASSERT_MSG(
true, wxT(
"Unknown Grid Type" ) );
732 wxASSERT( aNode->GetName() == wxT(
"GRIDS" ) );
736 for( ; cNode; cNode = cNode->
GetNext() )
738 wxString cNodeName = cNode->GetName();
740 if( cNodeName == wxT(
"WORKINGGRID" ) )
747 workingGridNode->GetName(), wxT(
"GRIDS -> WORKINGGRID" ) );
751 WorkingGrid.Parse( workingGridNode, aContext );
754 else if( cNodeName == wxT(
"SCREENGRID" ) )
761 screenGridNode->GetName(), wxT(
"GRIDS -> SCREENGRID" ) );
765 ScreenGrid.Parse( screenGridNode, aContext );
771 userGrid.
Parse( cNode, aContext );
772 UserGrids.push_back( userGrid );
780 wxString cNodeName = aChildNode->GetName();
782 if( cNodeName == wxT(
"UNITS" ) )
786 else if( cNodeName == wxT(
"UNITSPRECISION" ) )
790 else if( cNodeName == wxT(
"INTERLINEGAP" ) )
794 else if( cNodeName == wxT(
"BARLINEGAP" ) )
798 else if( cNodeName == wxT(
"ALLOWBARTEXT" ) )
800 AllowBarredText =
true;
802 else if( cNodeName == wxT(
"ANGULARPRECISION" ) )
806 else if( cNodeName == wxT(
"DESIGNORIGIN" ) )
808 DesignOrigin.Parse( aChildNode->
GetChildren(), aContext );
810 else if( cNodeName == wxT(
"DESIGNAREA" ) )
813 DesignArea = std::make_pair( pts[0], pts[1] );
815 else if( cNodeName == wxT(
"DESIGNREF" ) )
817 DesignOrigin.Parse( aChildNode->
GetChildren(), aContext );
819 else if( cNodeName == wxT(
"DESIGNLIMIT" ) )
821 DesignLimit.Parse( aChildNode->
GetChildren(), aContext );
823 else if( cNodeName == wxT(
"PINNOOFFSET" ) )
827 else if( cNodeName == wxT(
"PINNOANGLE" ) )
842 wxASSERT( aNode->GetName() == wxT(
"SETTINGS" ) );
846 for( ; cNode; cNode = cNode->
GetNext() )
848 wxString cNodeName = cNode->GetName();
850 if( ParseSubNode( cNode, aContext ) )
861 static const std::map<TEXT_FIELD_NAME, wxString> txtTokens =
885 wxString remainingStr = aTextString;
888 while( remainingStr.size() > 0 )
891 size_t startpos = remainingStr.Find( wxT(
"<@" ) );
893 if(
static_cast<int>( startpos ) == wxNOT_FOUND )
896 returnStr += remainingStr;
901 returnStr += remainingStr.SubString( 0, startpos - 1 );
903 if( ( startpos + 2 ) >= remainingStr.size() )
906 remainingStr = remainingStr.Mid( startpos + 2 );
911 for( std::pair<TEXT_FIELD_NAME, wxString> txtF : txtTokens )
913 if( remainingStr.StartsWith( txtF.second ) )
915 foundField = txtF.first;
923 returnStr += wxT(
"<@" );
928 size_t endpos = remainingStr.Find( wxT(
"@>" ) );
930 if(
static_cast<int>( endpos ) == wxNOT_FOUND )
934 returnStr += wxT(
"<@" ) + remainingStr;
938 size_t valueStart = txtTokens.at( foundField ).size();
939 wxString fieldValue = remainingStr.SubString( valueStart, endpos - 1 );
945 wxASSERT_MSG( fieldValue.at( 0 ) ==
'"',
"Expected '\"' as the first character" );
947 size_t splitPos = fieldValue.find_first_of(
'"', 1 );
948 address = fieldValue.SubString( 1, splitPos - 1 );
953 wxASSERT_MSG( remainingStr.EndsWith( wxT(
"@>" ) ),
954 "Expected '@>' at the end of a hyperlink" );
956 fieldValue = remainingStr.SubString( valueStart + splitPos + 1,
957 remainingStr.Length() - 3 );
959 remainingStr = wxEmptyString;
963 fieldValue = fieldValue.Mid( splitPos + 1 );
1004 returnStr += fieldValue;
1009 wxFileName fn( address );
1010 wxString fieldFmt = wxT(
"FROM_FILE_%s_%s" );
1011 wxString fieldName = wxString::Format( fieldFmt, fn.GetName(), fn.GetExt() );
1020 fieldName = wxString::Format( fieldFmt, fn.GetName(), fn.GetExt() )
1021 + wxString::Format( wxT(
"_%d" ), version++ );
1025 returnStr += wxT(
"${" ) + fieldName + wxT(
"}" );
1037 wxFAIL_MSG(
"We should have already covered this scenario above" );
1042 if( ( endpos + 2 ) >= remainingStr.size() )
1045 remainingStr = remainingStr.Mid( endpos + 2 );
1054 wxASSERT( aNode->GetName() == wxT(
"ALIGN" ) );
1058 if( alignmentStr == wxT(
"BOTTOMCENTER" ) )
1060 else if( alignmentStr == wxT(
"BOTTOMLEFT" ) )
1062 else if( alignmentStr == wxT(
"BOTTOMRIGHT" ) )
1064 else if( alignmentStr == wxT(
"CENTERCENTER" ) )
1066 else if( alignmentStr == wxT(
"CENTERLEFT" ) )
1068 else if( alignmentStr == wxT(
"CENTERRIGHT" ) )
1070 else if( alignmentStr == wxT(
"TOPCENTER" ) )
1072 else if( alignmentStr == wxT(
"TOPLEFT" ) )
1074 else if( alignmentStr == wxT(
"TOPRIGHT" ) )
1086 wxASSERT( aNode->GetName() == wxT(
"JUSTIFICATION" ) );
1090 if( justificationStr == wxT(
"LEFT" ) )
1092 else if( justificationStr == wxT(
"RIGHT" ) )
1094 else if( justificationStr == wxT(
"CENTER" ) )
1105 wxASSERT( aNode->GetName() == wxT(
"READABILITY" ) );
1109 if( readabilityStr == wxT(
"BOTTOM_TO_TOP" ) )
1111 else if( readabilityStr == wxT(
"TOP_TO_BOTTOM" ) )
1131 wxString cNodeName = aChildNode->GetName();
1133 if( cNodeName == wxT(
"PT" ) )
1134 Position.Parse( aChildNode, aContext );
1135 else if( cNodeName == wxT(
"ORIENT" ) )
1137 else if( cNodeName == wxT(
"MIRROR" ) )
1139 else if( cNodeName == wxT(
"FIX" ) )
1141 else if( cNodeName == wxT(
"ALIGN" ) )
1143 else if( cNodeName == wxT(
"JUSTIFICATION" ) )
1154 wxASSERT( aNode->GetName() == wxT(
"ATTRLOC" ) );
1156 ParseIdentifiers( aNode, aContext );
1161 for( ; cNode; cNode = cNode->
GetNext() )
1163 if( ParseSubNode( cNode, aContext ) )
1176 wxASSERT( aNode->GetName() == wxT(
"COLUMNORDER" ) );
1187 wxASSERT( aNode->GetName() == wxT(
"COLUMNWIDTH" ) );
1198 wxASSERT( aNode->GetName() == wxT(
"ATTRNAME" ) );
1204 wxString
location = wxString::Format(
"ATTRNAME -> %s", Name );
1206 for( ; cNode; cNode = cNode->
GetNext() )
1208 wxString cNodeName = cNode->GetName();
1210 if( cNodeName == wxT(
"ATTROWNER" ) )
1214 if( attOwnerVal == wxT(
"ALL_ITEMS" ) )
1216 else if( attOwnerVal == wxT(
"AREA" ) )
1218 else if( attOwnerVal == wxT(
"BOARD" ) )
1220 else if( attOwnerVal == wxT(
"COMPONENT" ) )
1222 else if( attOwnerVal == wxT(
"CONNECTION" ) )
1224 else if( attOwnerVal == wxT(
"COPPER" ) )
1226 else if( attOwnerVal == wxT(
"DOCSYMBOL" ) )
1228 else if( attOwnerVal == wxT(
"FIGURE" ) )
1230 else if( attOwnerVal == wxT(
"NET" ) )
1232 else if( attOwnerVal == wxT(
"NETCLASS" ) )
1234 else if( attOwnerVal == wxT(
"PART" ) )
1236 else if( attOwnerVal == wxT(
"PART_DEFINITION" ) )
1238 else if( attOwnerVal == wxT(
"PIN" ) )
1240 else if( attOwnerVal == wxT(
"SIGNALREF" ) )
1242 else if( attOwnerVal == wxT(
"SYMBOL" ) )
1244 else if( attOwnerVal == wxT(
"SYMDEF" ) )
1246 else if( attOwnerVal == wxT(
"TEMPLATE" ) )
1248 else if( attOwnerVal == wxT(
"TESTPOINT" ) )
1253 else if( cNodeName == wxT(
"ATTRUSAGE" ) )
1257 if( attUsageVal == wxT(
"BOTH" ) )
1259 else if( attUsageVal == wxT(
"COMPONENT" ) )
1261 else if( attUsageVal == wxT(
"PART_DEFINITION" ) )
1263 else if( attUsageVal == wxT(
"PART_LIBRARY" ) )
1265 else if( attUsageVal == wxT(
"SYMBOL" ) )
1270 else if( cNodeName == wxT(
"NOTRANSFER" ) )
1274 else if( cNodeName == wxT(
"COLUMNORDER" ) )
1277 cOrder.
Parse( cNode, aContext );
1278 ColumnOrders.push_back( cOrder );
1280 else if( cNodeName == wxT(
"COLUMNWIDTH" ) )
1283 cWidth.
Parse( cNode, aContext );
1284 ColumnWidths.push_back( cWidth );
1286 else if( cNodeName == wxT(
"COLUMNINVISIBLE" ) )
1288 ColumnInvisible =
true;
1300 wxASSERT( aNode->GetName() == wxT(
"ATTR" ) );
1307 for( ; cNode; cNode = cNode->
GetNext() )
1309 if( cNode->GetName() == wxT(
"READONLY" ) )
1313 else if( cNode->GetName() == wxT(
"ATTRLOC" ) )
1315 AttributeLocation.Parse( cNode, aContext );
1328 wxASSERT( aNode->GetName() == wxT(
"TEXTLOC" ) );
1331 bool attributeIDisSet =
false;
1333 if( attributeStr == wxT(
"PART_NAME" ) )
1336 attributeIDisSet =
true;
1338 else if( attributeStr == wxT(
"COMP_NAME" ) )
1341 attributeIDisSet =
true;
1343 else if( attributeStr == wxT(
"COMP_NAME2" ) )
1346 attributeIDisSet =
true;
1348 else if( attributeStr == wxT(
"SYMBOL_NAME" ) )
1351 attributeIDisSet =
true;
1353 else if( attributeStr == wxT(
"LINK_ORIGIN" ) )
1356 attributeIDisSet =
true;
1358 else if( attributeStr == wxT(
"SIGNALNAME_ORIGIN" ) )
1361 attributeIDisSet =
true;
1363 else if( attributeStr == wxT(
"ATTRREF" ) )
1366 attributeIDisSet =
false;
1379 for( ; cNode; cNode = cNode->
GetNext() )
1381 wxString cNodeName = cNode->GetName();
1383 if( ParseSubNode( cNode, aContext ) )
1387 else if( !attributeIDisSet && cNodeName == wxT(
"ATTRREF" ) )
1390 attributeIDisSet =
true;
1392 else if( cNodeName == wxT(
"ORIENT" ) )
1396 else if( cNodeName == wxT(
"MIRROR" ) )
1400 else if( cNodeName == wxT(
"FIX" ) )
1404 else if( cNodeName == wxT(
"ALIGN" ) )
1408 else if( cNodeName == wxT(
"JUSTIFICATION" ) )
1425 wxASSERT( aNode->GetName() == wxT(
"NETCLASS" ) );
1431 wxString
location = wxString::Format(
"NETCLASS -> %s", Name );
1433 for( ; cNode; cNode = cNode->
GetNext() )
1435 wxString cNodeName = cNode->GetName();
1437 if( cNodeName == wxT(
"ATTR" ) )
1440 attribute_val.
Parse( cNode, aContext );
1441 Attributes.push_back( attribute_val );
1453 wxASSERT( aNode->GetName() == wxT(
"SPCCLASSNAME" ) );
1462 wxString nodeName = aChildNode->GetName();
1464 if( nodeName == wxT(
"LINECODE" ) )
1467 linecode.
Parse( aChildNode, aContext );
1468 LineCodes.insert( std::make_pair( linecode.
ID, linecode ) );
1470 else if( nodeName == wxT(
"HATCHCODE" ) )
1473 hatchcode.
Parse( aChildNode, aContext );
1474 HatchCodes.insert( std::make_pair( hatchcode.
ID, hatchcode ) );
1476 else if( nodeName == wxT(
"TEXTCODE" ) )
1479 textcode.
Parse( aChildNode, aContext );
1480 TextCodes.insert( std::make_pair( textcode.
ID, textcode ) );
1482 else if( nodeName == wxT(
"ROUTECODE" ) )
1485 routecode.
Parse( aChildNode, aContext );
1486 RouteCodes.insert( std::make_pair( routecode.
ID, routecode ) );
1488 else if( nodeName == wxT(
"ATTRNAME" ) )
1491 attrname.
Parse( aChildNode, aContext );
1492 AttributeNames.insert( std::make_pair( attrname.
ID, attrname ) );
1494 else if( nodeName == wxT(
"NETCLASS" ) )
1497 netclass.
Parse( aChildNode, aContext );
1498 NetClasses.insert( std::make_pair( netclass.
ID, netclass ) );
1500 else if( nodeName == wxT(
"SPCCLASSNAME" ) )
1503 spcclassname.
Parse( aChildNode, aContext );
1504 SpacingClassNames.insert( std::make_pair( spcclassname.
ID, spcclassname ) );
1517 wxASSERT( aNode->GetName() == wxT(
"SWAPRULE" ) );
1522 if( swapRuleStr == wxT(
"NO_SWAP" ) )
1524 else if( swapRuleStr == wxT(
"USE_SWAP_LAYER" ) )
1535 wxASSERT( aNode->GetName() == wxT(
"REUSEBLOCK" ) );
1543 for( ; cNode; cNode = cNode->
GetNext() )
1545 wxString cNodeName = cNode->GetName();
1547 if( cNodeName == wxT(
"MIRROR" ) )
1549 else if( cNodeName == wxT(
"ORIENT" ) )
1559 return ReuseBlockID == wxEmptyString && ItemReference == wxEmptyString;
1565 wxASSERT( aNode->GetName() == wxT(
"REUSEBLOCKREF" ) );
1576 wxASSERT( aNode->GetName() == wxT(
"GROUP" ) );
1583 for( ; cNode; cNode = cNode->
GetNext() )
1585 wxString cNodeName = cNode->GetName();
1587 if( cNodeName == wxT(
"FIX" ) )
1589 else if( cNodeName == wxT(
"TRANSFER" ) )
1591 else if( cNodeName == wxT(
"GROUPREF" ) )
1593 else if( cNodeName == wxT(
"REUSEBLOCKREF" ) )
1594 ReuseBlockRef.Parse( cNode, aContext );
1603 wxASSERT( aNode->GetName() == wxT(
"FIGURE" ) );
1610 bool shapeIsInitialised =
false;
1611 wxString
location = wxString::Format(
"Figure %s",
ID );
1616 for( ; cNode; cNode = cNode->
GetNext() )
1618 wxString cNodeName = cNode->GetName();
1620 if( !shapeIsInitialised && Shape.IsShape( cNode ) )
1622 Shape.Parse( cNode, aContext );
1623 shapeIsInitialised =
true;
1625 else if( cNodeName == wxT(
"SWAPRULE" ) )
1629 else if( cNodeName == wxT(
"FIX" ) )
1633 else if( cNodeName == wxT(
"GROUPREF" ) )
1638 else if( cNodeName == wxT(
"REUSEBLOCKREF" ) )
1640 ReuseBlockRef.Parse( cNode, aContext );
1642 else if( cNodeName == wxT(
"ATTR" ) )
1645 attr.
Parse( cNode, aContext );
1646 AttributeValues.insert( std::make_pair( attr.
AttributeID, attr ) );
1658 Parse( aNode, aContext,
true );
1665 wxASSERT( aNode->GetName() == wxT(
"TEXT" ) );
1681 for( ; cNode; cNode = cNode->
GetNext() )
1683 wxString cNodeName = cNode->GetName();
1685 if( cNodeName == wxT(
"PT" ) )
1686 Position.Parse( cNode, aContext );
1687 else if( cNodeName == wxT(
"ORIENT" ) )
1689 else if( cNodeName == wxT(
"MIRROR" ) )
1691 else if( cNodeName == wxT(
"FIX" ) )
1693 else if( cNodeName == wxT(
"SWAPRULE" ) )
1695 else if( cNodeName == wxT(
"ALIGN" ) )
1697 else if( cNodeName == wxT(
"JUSTIFICATION" ) )
1699 else if( cNodeName == wxT(
"GROUPREF" ) )
1701 else if( cNodeName == wxT(
"REUSEBLOCKREF" ) )
1702 ReuseBlockRef.Parse( cNode, aContext );
1717 wxASSERT( aNode->GetName() == wxT(
"SYMDEF" ) );
1727 wxString cNodeName = aChildNode->GetName();
1729 if( cNodeName == wxT(
"PT" ) )
1731 Origin.Parse( aChildNode, aContext );
1733 else if( cNodeName == wxT(
"STUB" ) )
1737 else if( cNodeName == wxT(
"VERSION" ) )
1741 else if( cNodeName == wxT(
"FIGURE" ) )
1744 figure.
Parse( aChildNode, aContext );
1745 Figures.insert( std::make_pair( figure.
ID, figure ) );
1747 else if( cNodeName == wxT(
"TEXT" ) )
1750 txt.
Parse( aChildNode, aContext );
1751 Texts.insert( std::make_pair( txt.
ID, txt ) );
1753 else if( cNodeName == wxT(
"TEXTLOC" ) )
1756 textloc.
Parse( aChildNode, aContext );
1757 TextLocations.insert( std::make_pair( textloc.
AttributeID, textloc ) );
1759 else if( cNodeName == wxT(
"ATTR" ) )
1762 attrVal.
Parse( aChildNode, aContext );
1763 AttributeValues.insert( std::make_pair( attrVal.
AttributeID, attrVal ) );
1776 wxASSERT( aNode->GetName() == wxT(
"GATEDEFINITION" ) );
1789 wxASSERT( aNode->GetName() == wxT(
"PINTYPE" ) );
1793 std::map<wxString, CADSTAR_PIN_TYPE> pinTypeMap = {
1794 { wxT(
"INPUT" ), CADSTAR_PIN_TYPE::INPUT },
1795 { wxT(
"OUTPUT_OR" ), CADSTAR_PIN_TYPE::OUTPUT_OR },
1796 { wxT(
"OUTPUT_NOT_OR" ), CADSTAR_PIN_TYPE::OUTPUT_NOT_OR },
1797 { wxT(
"OUTPUT_NOT_NORM_OR" ), CADSTAR_PIN_TYPE::OUTPUT_NOT_NORM_OR },
1798 { wxT(
"POWER" ), CADSTAR_PIN_TYPE::POWER },
1799 { wxT(
"GROUND" ), CADSTAR_PIN_TYPE::GROUND },
1800 { wxT(
"TRISTATE_BIDIR" ), CADSTAR_PIN_TYPE::TRISTATE_BIDIR },
1801 { wxT(
"TRISTATE_INPUT" ), CADSTAR_PIN_TYPE::TRISTATE_INPUT },
1802 { wxT(
"TRISTATE_DRIVER" ), CADSTAR_PIN_TYPE::TRISTATE_DRIVER } };
1804 if( pinTypeMap.find( pinTypeStr ) == pinTypeMap.end() )
1807 return pinTypeMap[pinTypeStr];
1813 wxASSERT( aNode->GetName() == wxT(
"PARTDEFINITIONPIN" ) );
1819 for( ; cNode; cNode = cNode->
GetNext() )
1821 wxString cNodeName = cNode->GetName();
1823 if( cNodeName == wxT(
"PINNAME" ) )
1827 else if( cNodeName == wxT(
"PINLABEL" ) )
1831 else if( cNodeName == wxT(
"PINSIGNAL" ) )
1835 else if( cNodeName == wxT(
"PINTERM" ) )
1840 else if( cNodeName == wxT(
"PINTYPE" ) )
1842 Type = GetPinType( cNode );
1844 else if( cNodeName == wxT(
"PINLOAD" ) )
1848 else if( cNodeName == wxT(
"PINPOSITION" ) )
1852 else if( cNodeName == wxT(
"PINIDENTIFIER" ) )
1866 wxASSERT( aNode->GetName() == wxT(
"PARTPIN" ) );
1872 for( ; cNode; cNode = cNode->
GetNext() )
1874 wxString cNodeName = cNode->GetName();
1876 if( cNodeName == wxT(
"PINNAME" ) )
1878 else if( cNodeName == wxT(
"PINTYPE" ) )
1879 Type = GetPinType( cNode );
1880 else if( cNodeName == wxT(
"PINIDENTIFIER" ) )
1891 wxASSERT( aNode->GetName() == wxT(
"PINEQUIVALENCE" ) );
1893 wxXmlAttribute* xmlAttribute = aNode->GetAttributes();
1895 for( ; xmlAttribute; xmlAttribute = xmlAttribute->GetNext() )
1902 if( !xmlAttribute->GetValue().ToLong( &pinId ) )
1915 wxASSERT( aNode->GetName() == wxT(
"SWAPGATE" ) );
1917 wxXmlAttribute* xmlAttribute = aNode->GetAttributes();
1919 for( ; xmlAttribute; xmlAttribute = xmlAttribute->GetNext() )
1926 if( !xmlAttribute->GetValue().ToLong( &pinId ) )
1939 wxASSERT( aNode->GetName() == wxT(
"SWAPGROUP" ) );
1945 for( ; cNode; cNode = cNode->
GetNext() )
1947 wxString cNodeName = cNode->GetName();
1949 if( cNodeName == wxT(
"EXTERNAL" ) )
1953 else if( cNodeName == wxT(
"SWAPGATE" ) )
1956 swapGate.
Parse( cNode, aContext );
1957 SwapGates.push_back( swapGate );
1969 wxASSERT( aNode->GetName() == wxT(
"PARTDEFINITION" ) );
1975 for( ; cNode; cNode = cNode->
GetNext() )
1977 wxString cNodeName = cNode->GetName();
1979 if( cNodeName == wxT(
"HIDEPINNAMES" ) )
1981 HidePinNames =
true;
1983 else if( cNodeName == wxT(
"MAXPIN" ) )
1987 else if( cNodeName == wxT(
"GATEDEFINITION" ) )
1990 gate.
Parse( cNode, aContext );
1991 GateSymbols.insert( std::make_pair( gate.
ID, gate ) );
1993 else if( cNodeName == wxT(
"PARTDEFINITIONPIN" ) )
1996 pin.Parse( cNode, aContext );
1997 Pins.insert( std::make_pair(
pin.ID,
pin ) );
1999 else if( cNodeName == wxT(
"ATTR" ) )
2002 attr.
Parse( cNode, aContext );
2003 AttributeValues.insert( std::make_pair( attr.
AttributeID, attr ) );
2005 else if( cNodeName == wxT(
"PINEQUIVALENCE" ) )
2008 pinEq.
Parse( cNode, aContext );
2009 PinEquivalences.push_back( pinEq );
2011 else if( cNodeName == wxT(
"SWAPGROUP" ) )
2014 swapGroup.
Parse( cNode, aContext );
2015 SwapGroups.push_back( swapGroup );
2027 wxASSERT( aNode->GetName() == wxT(
"PART" ) );
2034 for( ; cNode; cNode = cNode->
GetNext() )
2036 wxString cNodeName = cNode->GetName();
2038 if( cNodeName == wxT(
"VERSION" ) )
2042 else if( cNodeName == wxT(
"HIDEPINNAMES" ) )
2044 HidePinNames =
true;
2046 else if( cNodeName == wxT(
"PARTDEFINITION" ) )
2048 Definition.Parse( cNode, aContext );
2050 else if( cNodeName == wxT(
"PARTPIN" ) )
2053 pin.Parse( cNode, aContext );
2054 PartPins.insert( std::make_pair(
pin.ID,
pin ) );
2056 else if( cNodeName == wxT(
"ATTR" ) )
2059 attr.
Parse( cNode, aContext );
2060 AttributeValues.insert( std::make_pair( attr.
AttributeID, attr ) );
2072 wxASSERT( aNode->GetName() == wxT(
"PARTS" ) );
2076 for( ; cNode; cNode = cNode->
GetNext() )
2078 wxString cNodeName = cNode->GetName();
2080 if( cNodeName == wxT(
"PART" ) )
2083 part.
Parse( cNode, aContext );
2084 PartDefinitions.insert( std::make_pair( part.
ID, part ) );
2099 wxASSERT( aNode->GetName() == wxT(
"JPT" ) );
2109 wxString cNodeName = aChildNode->GetName();
2111 if( cNodeName == wxT(
"PT" ) )
2112 Location.Parse( aChildNode, aContext );
2113 else if( cNodeName == wxT(
"FIX" ) )
2115 else if( cNodeName == wxT(
"GROUPREF" ) )
2117 else if( cNodeName == wxT(
"REUSEBLOCKREF" ) )
2118 ReuseBlockRef.Parse( aChildNode, aContext );
2128 ParseIdentifiers( aNode, aContext );
2131 for( ; cNode; cNode = cNode->
GetNext() )
2133 if( ParseSubNode( cNode, aContext ) )
2144 wxASSERT( aNode->GetName() == wxT(
"CONN" ) );
2155 wxString cNodeName = aChildNode->GetName();
2157 if( cNodeName == wxT(
"FIX" ) )
2161 else if( cNodeName == wxT(
"HIDDEN" ) )
2165 else if( cNodeName == wxT(
"GROUPREF" ) )
2169 else if( cNodeName == wxT(
"REUSEBLOCKREF" ) )
2171 ReuseBlockRef.Parse( aChildNode, aContext );
2173 else if( cNodeName == wxT(
"ATTR" ) )
2176 attrVal.
Parse( aChildNode, aContext );
2177 AttributeValues.insert( std::make_pair( attrVal.
AttributeID, attrVal ) );
2190 wxASSERT( aNode->GetName() == wxT(
"NET" ) );
2198 wxString cNodeName = aChildNode->GetName();
2200 if( cNodeName == wxT(
"NETCODE" ) )
2204 else if( cNodeName == wxT(
"SIGNAME" ) )
2208 else if( cNodeName == wxT(
"SIGNUM" ) )
2212 else if( cNodeName == wxT(
"HIGHLIT" ) )
2216 else if( cNodeName == wxT(
"JPT" ) )
2219 jpt.
Parse( aChildNode, aContext );
2220 Junctions.insert( std::make_pair( jpt.
ID, jpt ) );
2222 else if( cNodeName == wxT(
"NETCLASSREF" ) )
2226 else if( cNodeName == wxT(
"SPACINGCLASS" ) )
2230 else if( cNodeName == wxT(
"ATTR" ) )
2233 attrVal.
Parse( aChildNode, aContext );
2234 AttributeValues.insert( std::make_pair( attrVal.
AttributeID, attrVal ) );
2247 wxASSERT( aNode->GetName() == wxT(
"DOCSYMBOL" ) );
2254 bool originParsed =
false;
2256 for( ; cNode; cNode = cNode->
GetNext() )
2258 wxString cNodeName = cNode->GetName();
2260 if( !originParsed && cNodeName == wxT(
"PT" ) )
2262 Origin.Parse( cNode, aContext );
2263 originParsed =
true;
2265 else if( cNodeName == wxT(
"GROUPREF" ) )
2269 else if( cNodeName == wxT(
"REUSEBLOCKREF" ) )
2271 ReuseBlockRef.Parse( cNode, aContext );
2273 else if( cNodeName == wxT(
"FIX" ) )
2277 else if( cNodeName == wxT(
"MIRROR" ) )
2281 else if( cNodeName == wxT(
"READABILITY" ) )
2285 else if( cNodeName == wxT(
"ORIENT" ) )
2289 else if( cNodeName == wxT(
"ATTR" ) )
2292 attr.
Parse( cNode, aContext );
2293 AttributeValues.insert( std::make_pair( attr.
AttributeID, attr ) );
2295 else if( cNodeName == wxT(
"SCALE" ) )
2313 wxASSERT( aNode->GetName() == wxT(
"DFLTSETTINGS" ) );
2319 for( ; cNode; cNode = cNode->
GetNext() )
2321 wxString cNodeName = cNode->GetName();
2323 if( cNodeName == wxT(
"INVISIBLE" ) )
2337 wxASSERT( aNode->GetName() == wxT(
"ATTRCOL" ) );
2344 for( ; cNode; cNode = cNode->
GetNext() )
2346 wxString cNodeName = cNode->GetName();
2348 if( cNodeName == wxT(
"INVISIBLE" ) )
2352 else if( cNodeName == wxT(
"NOTPICKABLE" ) )
2366 wxASSERT( aNode->GetName() == wxT(
"ATTRCOLORS" ) );
2370 for( ; cNode; cNode = cNode->
GetNext() )
2372 wxString cNodeName = cNode->GetName();
2374 if( cNodeName == wxT(
"DFLTSETTINGS" ) )
2376 DefaultSettings.Parse( cNode, aContext );
2378 else if( cNodeName == wxT(
"ATTRCOL" ) )
2381 attrcol.
Parse( cNode, aContext );
2382 AttributeColors.insert( { attrcol.
AttributeID, attrcol } );
2384 else if( cNodeName == wxT(
"INVISIBLE" ) )
2398 wxASSERT( aNode->GetName() == wxT(
"PARTNAMECOL" ) );
2404 for( ; cNode; cNode = cNode->
GetNext() )
2406 wxString cNodeName = cNode->GetName();
2408 if( cNodeName == wxT(
"INVISIBLE" ) )
2412 else if( cNodeName == wxT(
"NOTPICKABLE" ) )
2426 static const wxString c_numAttributes = wxT(
"numAttributes" );
2429 long numAttributes = 0;
2431 if( aNode->GetAttribute( c_numAttributes, &result ) )
2433 numAttributes = wxAtol( result );
2434 aNode->DeleteAttribute( c_numAttributes );
2438#if wxUSE_UNICODE_WCHAR
2439 std::wstring numAttrStr = std::to_wstring( numAttributes );
2441 std::string numAttrStr = std::to_string( numAttributes );
2444 aNode->AddAttribute( c_numAttributes, numAttrStr );
2446 wxString paramName = wxT(
"attr" );
2447 paramName << numAttrStr;
2449 aNode->AddAttribute( paramName, aValue );
2454 const wxString& aFileTypeIdentifier,
2457 KEYWORD emptyKeywords[1] = {};
2458 XNODE* rootNode =
nullptr;
2459 XNODE* cNode =
nullptr;
2460 XNODE* iNode =
nullptr;
2462 bool cadstarFileCheckDone =
false;
2464 wxCSConv win1252( wxT(
"windows-1252" ) );
2465 wxMBConv* conv = &win1252;
2469 FILE* fp = wxFopen( aFileName, wxT(
"rt" ) );
2472 THROW_IO_ERROR( wxString::Format(
_(
"Cannot open file '%s'" ), aFileName ) );
2474 fseek( fp, 0L, SEEK_END );
2475 long fileSize = ftell( fp );
2478 DSNLEXER lexer( emptyKeywords, 0,
nullptr, fp, aFileName );
2480 auto currentProgress = [&]() ->
double
2482 return static_cast<double>( ftell( fp ) ) / fileSize;
2485 double previousReportedProgress = -1.0;
2489 if( aProgressReporter && ( currentProgress() - previousReportedProgress ) > 0.01 )
2500 previousReportedProgress = currentProgress();
2514 THROW_IO_ERROR(
_(
"The selected file is not valid or might be corrupt!" ) );
2520 str = wxString( lexer.
CurText(), *conv );
2521 cNode =
new XNODE( wxXML_ELEMENT_NODE, str );
2530 iNode->AddChild( cNode );
2532 else if( !cadstarFileCheckDone )
2534 if( cNode->GetName() != aFileTypeIdentifier )
2537 THROW_IO_ERROR(
_(
"The selected file is not valid or might be corrupt!" ) );
2540 cadstarFileCheckDone =
true;
2547 str = wxString( lexer.
CurText(), *conv );
2555 THROW_IO_ERROR(
_(
"The selected file is not valid or might be corrupt!" ) );
2560 if( iNode !=
nullptr )
2563 THROW_IO_ERROR(
_(
"The selected file is not valid or might be corrupt!" ) );
2574 THROW_IO_ERROR(
_(
"The selected file is not valid or might be corrupt!" ) );
2583 return aAttribute->GetName() != wxT(
"numAttributes" );
2590#if wxUSE_UNICODE_WCHAR
2591 std::wstring idStr = std::to_wstring( aID );
2593 std::string idStr = std::to_string( aID );
2596 wxString attrName = wxS(
"attr" );
2601 if( !aNode->GetAttribute( attrName, &retVal ) )
2606 return wxEmptyString;
2640 if( aNode && aNode->
GetNext() )
2648 if( aNode->
GetChildren()->GetName() == wxT(
"E" ) )
2658 std::vector<POINT> retVal;
2662 for( ; cNode; cNode = cNode->
GetNext() )
2664 if( cNode->GetName() == wxT(
"PT" ) )
2668 pt.
Parse( cNode, aContext );
2669 retVal.push_back( pt );
2671 else if( aTestAllChildNodes )
2678 && retVal.size() !=
static_cast<size_t>( aExpectedNumPoints ) )
2681 _(
"Unexpected number of points in '%s'. Found %d but expected %d." ),
2682 aNode->GetName(), retVal.size(), aExpectedNumPoints ) );
2692 std::vector<VERTEX> retVal;
2696 for( ; cNode; cNode = cNode->
GetNext() )
2702 vertex.
Parse( cNode, aContext );
2703 retVal.push_back( vertex );
2705 else if( aTestAllChildNodes )
2718 std::vector<CUTOUT> retVal;
2722 for( ; cNode; cNode = cNode->
GetNext() )
2724 if( cNode->GetName() == wxT(
"CUTOUT" ) )
2728 cutout.
Parse( cNode, aContext );
2729 retVal.push_back( cutout );
2731 else if( aTestAllChildNodes )
2746 for( ; childNodes; childNodes = childNodes->
GetNext() )
2754 XNODE* aRootNode, std::vector<wxString> aSubNodeChildrenToCount )
2759 for( ; level1Node; level1Node = level1Node->
GetNext() )
2761 for( wxString childNodeName : aSubNodeChildrenToCount )
2763 if( level1Node->GetName() == childNodeName )
2776 wxString escapedText = aCadstarString;
2778 escapedText.Replace( wxT(
"'" ), wxT(
"~" ) );
2786 if( !aKiCadTextItem->
GetText().IsEmpty() )
2793 int numExtraLines =
text.Replace(
"\n",
"\n" );
2794 numExtraLines -=
text.at(
text.size() - 1 ) ==
'\n';
2795 positionOffset.
x *= numExtraLines;
2796 positionOffset.
y *= numExtraLines;
2798 aKiCadTextItem->
Offset( positionOffset );
2804 const wxString& aAlternateName )
2806 if( aAlternateName.IsEmpty() )
KICAD_PLUGIN_EXPORT SCENEGRAPH * Load(char const *aFileName)
Read a model file and creates a generic display structure.
CADSTAR_PIN_POSITION
Positioning of pin names can be in one of four quadrants.
CADSTAR_PIN_TYPE
file: cadstar_archive_objects.h Contains common object definitions
Helper functions and common defines between schematic and PCB Archive files.
#define SYMBOL_NAME_ATTRID
Symbol Name attribute ID - used for placement of designators on the schematic.
#define SIGNALNAME_ORIGIN_ATTRID
#define THROW_MISSING_NODE_IO_ERROR(nodename, location)
#define THROW_UNKNOWN_NODE_IO_ERROR(nodename, location)
#define LINK_ORIGIN_ATTRID
#define COMPONENT_NAME_2_ATTRID
Component Name 2 Attribute ID - typically used for indicating the placement of designators in placeme...
#define THROW_UNKNOWN_PARAMETER_IO_ERROR(param, location)
#define COMPONENT_NAME_ATTRID
Component Name Attribute ID - typically used for placement of designators on silk screen.
#define THROW_MISSING_PARAMETER_IO_ERROR(param, location)
#define THROW_PARSING_IO_ERROR(param, location)
READABILITY
Sets the readability direction of text.
@ BOTTOM_TO_TOP
When text is vertical, show it rotated 90 degrees anticlockwise.
@ TOP_TO_BOTTOM
When text is vertical, show it rotated 90 degrees clockwise.
@ ANTICLOCKWISE_SEMICIRCLE
@ STEPGRID
Param1 = X Step, Param2 = Y Step. A standard x,y grid.
@ FRACTIONALGRID
Param1 = Units, Param2 = Divisor.
SWAP_RULE
Corresponds to "Display when" Item property.
@ USE_SWAP_LAYER
Display when Mirrored.
@ NO_SWAP
Display when Unmirrored.
static UNITS ParseUnits(XNODE *aNode)
static ALIGNMENT ParseAlignment(XNODE *aNode)
static const std::map< TEXT_FIELD_NAME, wxString > CADSTAR_TO_KICAD_FIELDS
Map between CADSTAR fields and KiCad text variables.
TEXT_FIELD_NAME
These are special fields in text objects enclosed between the tokens '<@' and '>' such as <@[FIELD_NA...
@ NONE
Synthetic for flagging.
static SWAP_RULE ParseSwapRule(XNODE *aNode)
ALIGNMENT
From CADSTAR Help: "Text Alignment enables you to define the position of an alignment origin for all ...
@ NO_ALIGNMENT
NO_ALIGNMENT has different meaning depending on the object type.
static const long UNDEFINED_VALUE
static wxString generateLibName(const wxString &aRefName, const wxString &aAlternateName)
static void CheckNoNextNodes(XNODE *aNode)
static std::vector< CUTOUT > ParseAllChildCutouts(XNODE *aNode, PARSER_CONTEXT *aContext, bool aTestAllChildNodes=false)
If no children are present, it just returns an empty vector (without throwing an exception).
static XNODE * LoadArchiveFile(const wxString &aFileName, const wxString &aFileTypeIdentifier, PROGRESS_REPORTER *aProgressReporter=nullptr)
Reads a CADSTAR Archive file (S-parameter format).
static JUSTIFICATION ParseJustification(XNODE *aNode)
static wxString ParseTextFields(const wxString &aTextString, PARSER_CONTEXT *aParserContext)
Replaces CADSTAR fields for the equivalent in KiCad and stores the field values in aParserContext.
@ PART_DEFINITION
From CADSTAR Help: Assigned to Parts library Definitions and displayed by the Library searcher.
@ BOTH
From CADSTAR Help: Assigned to both Schematic symbols and PCB components, and displayed on Schematic ...
@ COMPONENT
From CADSTAR Help: Assigned to PCB components and displayed on PCB designs.
@ SYMBOL
From CADSTAR Help: Assigned to Schematic Symbols and displayed on Schematic Designs.
@ PART_LIBRARY
From CADSTAR Help: Only used by non-Cadstar applications.
static std::vector< VERTEX > ParseAllChildVertices(XNODE *aNode, PARSER_CONTEXT *aContext, bool aTestAllChildNodes=false)
If no children are present, it just returns an empty vector (without throwing an exception).
static void FixTextPositionNoAlignment(EDA_TEXT *aKiCadTextItem)
Correct the position of a text element that had NO_ALIGNMENT in CADSTAR.
static ANGUNITS ParseAngunits(XNODE *aNode)
long PART_DEFINITION_PIN_ID
Pin identifier in the part definition.
@ OUTLINE
Unfilled closed shape.
@ OPENSHAPE
Unfilled open shape. Cannot have cutouts.
@ SOLID
Filled closed shape (solid fill).
@ HATCHED
Filled closed shape (hatch fill).
static const double TXT_HEIGHT_RATIO
CADSTAR fonts are drawn on a 24x24 integer matrix, where the each axis goes from 0 to 24.
static wxString GetXmlAttributeIDString(XNODE *aNode, unsigned int aID, bool aIsRequired=true)
void checkPoint()
Updates m_progressReporter or throws if user canceled.
static bool IsValidAttribute(wxXmlAttribute *aAttribute)
static READABILITY ParseReadability(XNODE *aNode)
static std::vector< POINT > ParseAllChildPoints(XNODE *aNode, PARSER_CONTEXT *aContext, bool aTestAllChildNodes=false, int aExpectedNumPoints=UNDEFINED_VALUE)
If no children are present, it just returns an empty vector (without throwing an exception).
@ DESIGN
Inherits from design units (assumed Assignments->Technology->Units)
static wxString HandleTextOverbar(wxString aCadstarString)
Convert a string with CADSTAR overbar characters to equivalent in KiCad.
static void CheckNoChildNodes(XNODE *aNode)
static long GetXmlAttributeIDLong(XNODE *aNode, unsigned int aID, bool aIsRequired=true)
JUSTIFICATION
From CADSTAR Help: "Multi Line Text can also be justified as Left, Centre or Right.
static void ParseChildEValue(XNODE *aNode, PARSER_CONTEXT *aContext, EVALUE &aValueToParse)
static long GetNumberOfStepsForReporting(XNODE *aRootNode, std::vector< wxString > aSubNodeChildrenToCount)
PROGRESS_REPORTER * m_progressReporter
static long GetNumberOfChildNodes(XNODE *aNode)
static void InsertAttributeAtEnd(XNODE *aNode, wxString aValue)
@ PART_DEFINITION
Only library Attributes.
@ PART
Only library Attributes.
Implement a lexical analyzer for the SPECCTRA DSN file format.
const char * CurText() const
Return a pointer to the current token's text.
int NextTok()
Return the next token found in the input file or DSN_EOF when reaching the end of file.
A mix-in class (via multiple inheritance) that handles texts such as labels, parts,...
const EDA_ANGLE & GetTextAngle() const
virtual const wxString & GetText() const
Return the string associated with the text object.
int GetInterline() const
Return the distance between two lines of text.
void Offset(const VECTOR2I &aOffset)
A progress reporter interface for use in multi-threaded environments.
virtual bool KeepRefreshing(bool aWait=false)=0
Update the UI (if any).
virtual void AdvanceProgress()=0
Increment the progress bar length (inside the current virtual zone).
virtual void SetCurrentProgress(double aProgress)=0
Set the progress value to aProgress (0..1).
SHAPE_ARC & ConstructFromStartEndCenter(const VECTOR2I &aStart, const VECTOR2I &aEnd, const VECTOR2I &aCenter, bool aClockwise=false, double aWidth=0)
Constructs this arc from the given start, end and center.
Represent a polyline containing arcs as well as line segments: A chain of connected line and/or arc s...
virtual const VECTOR2I GetPoint(int aIndex) const override
void SetClosed(bool aClosed)
Mark the line chain as closed (i.e.
int PointCount() const
Return the number of points (vertices) in this line chain.
void Append(int aX, int aY, bool aAllowDuplication=false)
Append a new point at the end of the line chain.
const VECTOR2I & CPoint(int aIndex) const
Return a reference to a given point in the line chain.
Represent a set of closed polygons.
int AddOutline(const SHAPE_LINE_CHAIN &aOutline)
Adds a new outline to the set and returns its index.
int AddHole(const SHAPE_LINE_CHAIN &aHole, int aOutline=-1)
Adds a new hole to the given outline (default: last) and returns its index.
Hold an XML or S-expression element.
XNODE * GetParent() const
XNODE * GetChildren() const
#define THROW_IO_ERROR(msg)
This file contains miscellaneous commonly used macros and functions.
#define KI_FALLTHROUGH
The KI_FALLTHROUGH macro is to be used when switch statement cases should purposely fallthrough from ...
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
wxString ConvertToNewOverbarNotation(const wxString &aOldStr)
Convert the old ~...~ overbar notation to the new ~{...} one.
wxString EscapeString(const wxString &aSource, ESCAPE_CONTEXT aContext)
The Escape/Unescape routines use HTML-entity-reference-style encoding to handle characters which are:...
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void ParseIdentifiers(XNODE *aNode, PARSER_CONTEXT *aContext)
virtual void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
NOTE from CADSTAR help: To convert a Part Definition Attribute into a hyperlink, prefix the attribute...
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
Represent a cutout in a closed shape (e.g.
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
Represent a floating value in E notation.
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
static bool IsGrid(XNODE *aNode)
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void ParseIdentifiers(XNODE *aNode, PARSER_CONTEXT *aContext)
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
virtual void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void ParseIdentifiers(XNODE *aNode, PARSER_CONTEXT *aContext)
NETELEMENT_ID ID
First character is "J".
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
void ParseIdentifiers(XNODE *aNode, PARSER_CONTEXT *aContext)
std::map< TEXT_FIELD_NAME, wxString > TextFieldToValuesMap
Values for the text field elements used in the CADSTAR design extracted from the text element instanc...
std::map< wxString, wxString > FilenamesToTextMap
CADSTAR doesn't have user defined text fields but does allow loading text from a file.
std::map< wxString, wxString > TextToHyperlinksMap
KiCad doesn't support hyperlinks but we use this map to display warning messages after import.
std::set< TEXT_FIELD_NAME > InconsistentTextFields
Text fields need to be updated in CADSTAR and it is possible that they are not consistent across text...
std::function< void()> CheckPointCallback
Callback function to report progress.
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
< "GATEDEFINITION" node name
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
GATE_ID ID
Usually "A", "B", "C", etc.
< "PINEQUIVALENCE" Node name
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
< "PARTDEFINITIONPIN" node name
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
< "SWAPGATE" Node name (represents an "Element")
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
static CADSTAR_PIN_TYPE GetPinType(XNODE *aNode)
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
Represent a point in x,y coordinates.
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
bool IsEmpty()
Determines if this is empty (i.e. no design reuse associated)
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
virtual void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
SHAPE_POLY_SET ConvertToPolySet(const std::function< VECTOR2I(const VECTOR2I &)> aCadstarToKicadPointCallback, double aAccuracy) const
SHAPE_LINE_CHAIN OutlineAsChain(const std::function< VECTOR2I(const VECTOR2I &)> aCadstarToKicadPointCallback, double aAccuracy) const
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
static bool IsShape(XNODE *aNode)
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
bool ParseSubNode(XNODE *aChildNode, PARSER_CONTEXT *aContext)
void ParseIdentifiers(XNODE *aNode, PARSER_CONTEXT *aContext)
wxString BuildLibName() const
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
Corresponds to CADSTAR "origin".
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
< Nodename = "VARIANT" or "VMASTER" (master variant
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
Represents a vertex in a shape.
static bool IsVertex(XNODE *aNode)
SHAPE_ARC BuildArc(const VECTOR2I &aPrevPoint, const std::function< VECTOR2I(const VECTOR2I &)> aCadstarToKicadPointCallback) const
void AppendToChain(SHAPE_LINE_CHAIN *aChainToAppendTo, const std::function< VECTOR2I(const VECTOR2I &)> aCadstarToKicadPointCallback, double aAccuracy) const
void Parse(XNODE *aNode, PARSER_CONTEXT *aContext) override
Hold a keyword string and its unique integer token.
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.
VECTOR2< int32_t > VECTOR2I