25#include <unordered_map>
38 static const std::unordered_map<std::string, ALTIUM_LAYER> hash_map = {
130 auto it = hash_map.find( std::string( aName.c_str() ) );
132 if( it == hash_map.end() )
134 wxLogError(
_(
"Unknown mapping of the Altium layer '%s'." ), aName );
144 std::vector<ALTIUM_VERTICE>& aVertices )
146 for(
size_t i = 0; i < std::numeric_limits<size_t>::max(); i++ )
148 const wxString si = std::to_string( i );
150 const wxString vxi = wxT(
"VX" ) + si;
151 const wxString vyi = wxT(
"VY" ) + si;
153 if( aProps.find( vxi ) == aProps.end() || aProps.find( vyi ) == aProps.end() )
165 aVertices.emplace_back( isRound, radius, sa, ea, vp, cp );
175 if( mode == wxT(
"None" ) )
177 else if( mode == wxT(
"Rule" ) )
179 else if( mode == wxT(
"Manual" ) )
182 wxLogError(
_(
"Unknown Mode string: '%s'." ), mode );
192 if( record == wxT(
"Arc" ) )
194 else if( record == wxT(
"Pad" ) )
196 else if( record == wxT(
"Via" ) )
198 else if( record == wxT(
"Track" ) )
200 else if( record == wxT(
"Text" ) )
202 else if( record == wxT(
"Fill" ) )
204 else if( record == wxT(
"Region" ) )
206 else if( record == wxT(
"Model" ) )
209 wxLogError(
_(
"Unknown Record name string: '%s'." ), record );
216 const std::map<wxString, wxString>& aProps, wxString aKey )
220 if( parsedType == wxT(
"Mask" ) )
223 wxLogError(
_(
"Unknown Extended Primitive Information type: '%s'." ), parsedType );
230 const std::map<wxString, wxString> props = aReader.
ReadProperties();
233 THROW_IO_ERROR( wxT(
"ExtendedPrimitiveInformation stream has no properties!" ) );
241 props, wxT(
"PASTEMASKEXPANSION_MANUAL" ), wxT(
"0mil" ) );
245 props, wxT(
"SOLDERMASKEXPANSION_MANUAL" ), wxT(
"0mil" ) );
263 for(
size_t i = 1; i < std::numeric_limits<size_t>::max(); i++ )
265 const wxString layeri = wxT(
"LAYER" ) + std::to_string( i );
266 const wxString layername = layeri + wxT(
"NAME" );
268 auto layernameit = props.find( layername );
270 if( layernameit == props.end() )
290 THROW_IO_ERROR( wxT(
"Board6 stream was not parsed correctly!" ) );
295 std::map<wxString, wxString> properties = aReader.
ReadProperties();
297 if( properties.empty() )
304 for(
size_t i = 0; i < std::numeric_limits<size_t>::max(); i++ )
306 auto mit = properties.find( wxT(
"M" ) + std::to_string( i ) );
308 if( mit == properties.end() )
311 names.push_back( mit->second );
315 THROW_IO_ERROR( wxT(
"Classes6 stream was not parsed correctly" ) );
345 THROW_IO_ERROR( wxT(
"Components6 stream was not parsed correctly" ) );
384 for(
int i = 0; i < refcount; i++ )
386 const std::string refi =
"REFERENCE" + std::to_string( i ) +
"POINT";
391 for(
size_t i = 1; i < std::numeric_limits<size_t>::max(); i++ )
393 const std::string texti =
"TEXT" + std::to_string( i );
394 const std::string textix = texti +
"X";
395 const std::string textiy = texti +
"Y";
397 if( props.find( textix ) == props.end() || props.find( textiy ) == props.end() )
413 THROW_IO_ERROR( wxT(
"Dimensions6 stream was not parsed correctly" ) );
418 std::map<wxString, wxString> properties = aReader.
ReadProperties();
420 if( properties.empty() )
437 std::map<wxString, wxString> properties = aReader.
ReadProperties();
439 if( properties.empty() )
450 std::map<wxString, wxString> properties = aReader.
ReadProperties();
452 if( properties.empty() )
481 THROW_IO_ERROR( wxT(
"Polygons6 stream was not parsed correctly" ) );
508 if( rulekind == wxT(
"Clearance" ) )
513 else if( rulekind == wxT(
"DiffPairsRouting" ) )
517 else if( rulekind == wxT(
"Height" ) )
521 else if( rulekind == wxT(
"HoleSize" ) )
525 else if( rulekind == wxT(
"HoleToHoleClearance" ) )
529 else if( rulekind == wxT(
"Width" ) )
533 else if( rulekind == wxT(
"PasteMaskExpansion" ) )
537 else if( rulekind == wxT(
"PlaneClearance" ) )
542 else if( rulekind == wxT(
"PolygonConnect" ) )
562 THROW_IO_ERROR( wxT(
"Rules6 stream was not parsed correctly" ) );
578 uint8_t flags1 = aReader.
Read<uint8_t>();
582 uint8_t flags2 = aReader.
Read<uint8_t>();
585 net = aReader.
Read<uint16_t>();
618 THROW_IO_ERROR( wxT(
"ComponentsBodies6 stream has invalid recordtype" ) );
626 std::map<wxString, wxString> properties = aReader.
ReadProperties();
628 if( properties.empty() )
629 THROW_IO_ERROR( wxT(
"ComponentsBodies6 stream has no properties" ) );
650 THROW_IO_ERROR( wxT(
"Components6 stream was not parsed correctly" ) );
663 if( subrecord1 == 0 )
669 THROW_IO_ERROR( wxT(
"Pads6 stream has invalid subrecord1 length" ) );
688 if( subrecord5 < 114 )
689 THROW_IO_ERROR( wxT(
"Pads6 stream subrecord has length < 114, which is unexpected" ) );
695 uint8_t flags1 = aReader.
Read<uint8_t>();
701 uint8_t flags2 = aReader.
Read<uint8_t>();
704 net = aReader.
Read<uint16_t>();
732 if( subrecord5 >= 120 )
739 else if( subrecord5 == 171 )
749 if( subrecord6 >= 596 )
751 sizeAndShape = std::make_unique<APAD6_SIZE_AND_SHAPE>();
780 radius = aReader.
Read<uint8_t>();
782 else if( subrecord6 != 0 )
784 wxLogError(
_(
"Pads6 stream has unexpected length for subrecord 6: %d." ), subrecord6 );
805 uint8_t flags1 = aReader.
Read<uint8_t>();
811 uint8_t flags2 = aReader.
Read<uint8_t>();
814 net = aReader.
Read<uint16_t>();
823 if( subrecord1 <= 74 )
851 uint8_t flags1 = aReader.
Read<uint8_t>();
855 uint8_t flags2 = aReader.
Read<uint8_t>();
858 net = aReader.
Read<uint16_t>();
879 THROW_IO_ERROR( wxT(
"Tracks6 stream was not parsed correctly" ) );
910 uint32_t stringIndex = aReader.
Read<uint32_t>();
917 if( subrecord1 <= 230 )
928 auto entry = aStringTable.find( stringIndex );
930 if( entry != aStringTable.end() )
931 text = entry->second;
936 text.Replace( wxT(
"\r\n" ), wxT(
"\n" ) );
941 THROW_IO_ERROR( wxT(
"Texts6 stream was not parsed correctly" ) );
956 uint8_t flags1 = aReader.
Read<uint8_t>();
959 uint8_t flags2 = aReader.
Read<uint8_t>();
962 net = aReader.
Read<uint16_t>();
983 THROW_IO_ERROR( wxT(
"Fills6 stream was not parsed correctly" ) );
991 THROW_IO_ERROR( wxT(
"Regions6 stream has invalid recordtype" ) );
998 uint8_t flags1 = aReader.
Read<uint8_t>();
1001 uint8_t flags2 = aReader.
Read<uint8_t>();
1004 net = aReader.
Read<uint16_t>();
1011 std::map<wxString, wxString> properties = aReader.
ReadProperties();
1013 if( properties.empty() )
1056 uint32_t num_outline_vertices = aReader.
Read<uint32_t>();
1058 for( uint32_t i = 0; i < num_outline_vertices; i++ )
1060 if( aExtendedVertices )
1062 bool isRound = aReader.
Read<uint8_t>() != 0;
1066 double angle1 = aReader.
Read<
double>();
1067 double angle2 = aReader.
Read<
double>();
1068 outline.emplace_back( isRound, radius, angle1, angle2, position, center );
1080 if( !aExtendedVertices )
1083 for( uint16_t k = 0; k <
holecount; k++ )
1085 uint32_t num_hole_vertices = aReader.
Read<uint32_t>();
1086 holes.at( k ).reserve( num_hole_vertices );
1088 for( uint32_t i = 0; i < num_hole_vertices; i++ )
1100 THROW_IO_ERROR( wxT(
"Regions6 stream was not parsed correctly" ) );
void altium_parse_polygons(std::map< wxString, wxString > &aProps, std::vector< ALTIUM_VERTICE > &aVertices)
ALTIUM_LAYER altium_layer_from_name(const wxString &aName)
static AEXTENDED_PRIMITIVE_INFORMATION_TYPE ReadAltiumExtendedPrimitiveInformationTypeFromProperties(const std::map< wxString, wxString > &aProps, wxString aKey)
static ALTIUM_MODE ReadAltiumModeFromProperties(const std::map< wxString, wxString > &aProps, wxString aKey)
static ALTIUM_RECORD ReadAltiumRecordFromProperties(const std::map< wxString, wxString > &aProps, wxString aKey)
const uint16_t ALTIUM_NET_UNCONNECTED
AEXTENDED_PRIMITIVE_INFORMATION_TYPE
static int ReadInt(const std::map< wxString, wxString > &aProps, const wxString &aKey, int aDefault)
std::map< wxString, wxString > ReadProperties()
size_t GetRemainingSubrecordBytes() const
static wxString ReadString(const std::map< wxString, wxString > &aProps, const wxString &aKey, const wxString &aDefault)
size_t ReadAndSetSubrecordLength()
static double ReadDouble(const std::map< wxString, wxString > &aProps, const wxString &aKey, double aDefault)
VECTOR2I ReadVector2ISize()
static int32_t ConvertToKicadUnit(const double aValue)
static bool ReadBool(const std::map< wxString, wxString > &aProps, const wxString &aKey, bool aDefault)
VECTOR2I ReadVector2IPos()
void Skip(size_t aLength)
#define THROW_IO_ERROR(msg)
AARC6(ALTIUM_PARSER &aReader)
uint8_t keepoutrestrictions
wxString dielectricmaterial
ABOARD6(ALTIUM_PARSER &aReader)
std::vector< ABOARD6_LAYER_STACKUP > stackup
std::vector< ALTIUM_VERTICE > board_vertices
std::vector< wxString > names
ACLASS6(ALTIUM_PARSER &aReader)
ALTIUM_TEXT_POSITION commentautoposition
ALTIUM_TEXT_POSITION nameautoposition
ACOMPONENT6(ALTIUM_PARSER &aReader)
wxString sourcefootprintlibrary
wxString sourcelibreference
wxString sourcedesignator
wxString sourcecomponentlibrary
ACOMPONENTBODY6(ALTIUM_PARSER &aReader)
ADIMENSION6(ALTIUM_PARSER &aReader)
std::vector< VECTOR2I > textPoint
ALTIUM_DIMENSION_KIND kind
std::vector< VECTOR2I > referencePoint
uint8_t keepoutrestrictions
AFILL6(ALTIUM_PARSER &aReader)
AMODEL(ALTIUM_PARSER &aReader)
ANET6(ALTIUM_PARSER &aReader)
int32_t soldermaskexpansionmanual
std::unique_ptr< APAD6_SIZE_AND_SHAPE > sizeAndShape
ALTIUM_PAD_SHAPE topshape
ALTIUM_MODE pastemaskexpansionmode
ALTIUM_MODE soldermaskexpansionmode
ALTIUM_PAD_SHAPE botshape
ALTIUM_PAD_SHAPE midshape
int32_t pastemaskexpansionmanual
APAD6(ALTIUM_PARSER &aReader)
APOLYGON6(ALTIUM_PARSER &aReader)
std::vector< ALTIUM_VERTICE > vertices
ALTIUM_POLYGON_HATCHSTYLE hatchstyle
uint8_t keepoutrestrictions
AREGION6(ALTIUM_PARSER &aReader, bool aExtendedVertices)
std::vector< ALTIUM_VERTICE > outline
std::vector< std::vector< ALTIUM_VERTICE > > holes
ALTIUM_CONNECT_STYLE polygonconnectStyle
int planeclearanceClearance
int32_t polygonconnectReliefconductorwidth
ARULE6(ALTIUM_PARSER &aReader)
int32_t polygonconnectAirgapwidth
int polygonconnectReliefentries
ALTIUM_TEXT_POSITION textposition
ATEXT6(ALTIUM_PARSER &aReader, std::map< uint32_t, wxString > &aStringTable)
ALTIUM_TEXT_TYPE fonttype
uint8_t keepoutrestrictions
ATRACK6(ALTIUM_PARSER &aReader)
AVIA6(ALTIUM_PARSER &aReader)