Eagle Schematics Importer: support for UTF-8

Fixes: lp:1736083
* https://bugs.launchpad.net/kicad/+bug/1736083
This commit is contained in:
Maciej Suminski 2017-12-14 10:37:32 +01:00
parent 812b8b081d
commit 378846c2e3
7 changed files with 199 additions and 203 deletions

View File

@ -34,6 +34,16 @@
constexpr auto DEFAULT_ALIGNMENT = ETEXT::BOTTOM_LEFT;
template<> template<>
OPTIONAL_XML_ATTRIBUTE<wxString>::OPTIONAL_XML_ATTRIBUTE( wxString aData )
{
m_isAvailable = !aData.IsEmpty();
if( m_isAvailable )
Set( aData );
}
ECOORD::ECOORD( const wxString& aValue, enum ECOORD::EAGLE_UNIT aUnit )
{
// this array is used to adjust the fraction part value basing on the number of digits in the fraction
@ -94,6 +104,7 @@ long long int ECOORD::ToNanoMeters( int aValue, enum EAGLE_UNIT aUnit )
// Template specializations below parse wxString to the used types:
// - wxString (preferred)
// - string
// - double
// - int
@ -101,10 +112,17 @@ long long int ECOORD::ToNanoMeters( int aValue, enum EAGLE_UNIT aUnit )
// - EROT
// - ECOORD
template<>
string Convert<string>( const wxString& aValue )
template <>
wxString Convert<wxString>( const wxString& aValue )
{
return string( aValue.ToUTF8() );
return aValue;
}
template <>
std::string Convert<std::string>( const wxString& aValue )
{
return std::string( aValue.ToUTF8() );
}
@ -179,7 +197,7 @@ ECOORD Convert<ECOORD>( const wxString& aCoord )
* @return T - the attributed parsed as the specified type.
*/
template<typename T>
T parseRequiredAttribute( wxXmlNode* aNode, const string& aAttribute )
T parseRequiredAttribute( wxXmlNode* aNode, const wxString& aAttribute )
{
wxString value;
@ -189,6 +207,7 @@ T parseRequiredAttribute( wxXmlNode* aNode, const string& aAttribute )
throw XML_PARSER_ERROR( "The required attribute " + aAttribute + " is missing." );
}
/**
* Function parseOptionalAttribute
* parses the aAttribute of the XML node aNode.
@ -198,7 +217,7 @@ T parseRequiredAttribute( wxXmlNode* aNode, const string& aAttribute )
* found.
*/
template<typename T>
OPTIONAL_XML_ATTRIBUTE<T> parseOptionalAttribute( wxXmlNode* aNode, const string& aAttribute )
OPTIONAL_XML_ATTRIBUTE<T> parseOptionalAttribute( wxXmlNode* aNode, const wxString& aAttribute )
{
return OPTIONAL_XML_ATTRIBUTE<T>( aNode->GetAttribute( aAttribute ) );
}
@ -218,7 +237,7 @@ NODE_MAP MapChildren( wxXmlNode* aCurrentNode )
// Create a new pair in the map
// key: current node name
// value: current node pointer
nodesMap[aCurrentNode->GetName().ToStdString()] = aCurrentNode;
nodesMap[aCurrentNode->GetName()] = aCurrentNode;
// Get next child
aCurrentNode = aCurrentNode->GetNext();
@ -235,10 +254,10 @@ unsigned long EagleTimeStamp( wxXmlNode* aTree )
}
time_t EagleModuleTstamp( const string& aName, const string& aValue, int aUnit )
time_t EagleModuleTstamp( const wxString& aName, const wxString& aValue, int aUnit )
{
std::size_t h1 = std::hash<string>{}( aName );
std::size_t h2 = std::hash<string>{}( aValue );
std::size_t h1 = std::hash<wxString>{}( aName );
std::size_t h2 = std::hash<wxString>{}( aValue );
std::size_t h3 = std::hash<int>{}( aUnit );
return h1 ^ (h2 << 1) ^ (h3 << 2);
@ -319,7 +338,7 @@ EWIRE::EWIRE( wxXmlNode* aWire )
layer = parseRequiredAttribute<int>( aWire, "layer" );
curve = parseOptionalAttribute<double>( aWire, "curve" );
opt_string s = parseOptionalAttribute<string>( aWire, "style" );
opt_wxString s = parseOptionalAttribute<wxString>( aWire, "style" );
if( s == "continuous" )
style = EWIRE::CONTINUOUS;
@ -330,7 +349,7 @@ EWIRE::EWIRE( wxXmlNode* aWire )
else if( s == "dashdot" )
style = EWIRE::DASHDOT;
s = parseOptionalAttribute<string>( aWire, "cap" );
s = parseOptionalAttribute<wxString>( aWire, "cap" );
if( s == "round" )
cap = EWIRE::ROUND;
@ -375,7 +394,7 @@ ELABEL::ELABEL( wxXmlNode* aLabel, const wxString& aNetName )
size = parseRequiredAttribute<ECOORD>( aLabel, "size" );
layer = parseRequiredAttribute<int>( aLabel, "layer" );
rot = parseOptionalAttribute<EROT>( aLabel, "rot" );
xref = parseOptionalAttribute<string>( aLabel, "xref" );
xref = parseOptionalAttribute<wxString>( aLabel, "xref" );
netname = aNetName;
}
@ -398,13 +417,12 @@ EVIA::EVIA( wxXmlNode* aVia )
x = parseRequiredAttribute<ECOORD>( aVia, "x" );
y = parseRequiredAttribute<ECOORD>( aVia, "y" );
string ext = parseRequiredAttribute<string>( aVia, "extent" );
wxString ext = parseRequiredAttribute<wxString>( aVia, "extent" );
sscanf( ext.c_str(), "%d-%d", &layer_front_most, &layer_back_most );
drill = parseRequiredAttribute<ECOORD>( aVia, "drill" );
diam = parseOptionalAttribute<ECOORD>( aVia, "diameter" );
shape = parseOptionalAttribute<string>( aVia, "shape" );
shape = parseOptionalAttribute<wxString>( aVia, "shape" );
}
@ -471,8 +489,8 @@ EATTR::EATTR( wxXmlNode* aTree )
>
*/
name = parseRequiredAttribute<string>( aTree, "name" );
value = parseOptionalAttribute<string>( aTree, "value" );
name = parseRequiredAttribute<wxString>( aTree, "name" );
value = parseOptionalAttribute<wxString>( aTree, "value" );
x = parseOptionalAttribute<ECOORD>( aTree, "x" );
y = parseOptionalAttribute<ECOORD>( aTree, "y" );
@ -484,7 +502,7 @@ EATTR::EATTR( wxXmlNode* aTree )
ratio = parseOptionalAttribute<double>( aTree, "ratio" );
rot = parseOptionalAttribute<EROT>( aTree, "rot" );
opt_string stemp = parseOptionalAttribute<string>( aTree, "display" );
opt_wxString stemp = parseOptionalAttribute<wxString>( aTree, "display" );
// (off | value | name | both)
if( stemp == "off" )
@ -496,7 +514,7 @@ EATTR::EATTR( wxXmlNode* aTree )
else if( stemp == "both" )
display = EATTR::BOTH;
stemp = parseOptionalAttribute<string>( aTree, "align" );
stemp = parseOptionalAttribute<wxString>( aTree, "align" );
align = stemp ? parseAlignment( *stemp ) : DEFAULT_ALIGNMENT;
}
@ -525,7 +543,7 @@ EDIMENSION::EDIMENSION( wxXmlNode* aDimension )
x3 = parseRequiredAttribute<ECOORD>( aDimension, "x3" );
y3 = parseRequiredAttribute<ECOORD>( aDimension, "y3" );
layer = parseRequiredAttribute<int>( aDimension, "layer" );
dimensionType = parseOptionalAttribute<string>( aDimension, "dtype" );
dimensionType = parseOptionalAttribute<wxString>( aDimension, "dtype" );
}
@ -551,11 +569,11 @@ ETEXT::ETEXT( wxXmlNode* aText )
size = parseRequiredAttribute<ECOORD>( aText, "size" );
layer = parseRequiredAttribute<int>( aText, "layer" );
font = parseOptionalAttribute<string>( aText, "font" );
font = parseOptionalAttribute<wxString>( aText, "font" );
ratio = parseOptionalAttribute<double>( aText, "ratio" );
rot = parseOptionalAttribute<EROT>( aText, "rot" );
opt_string stemp = parseOptionalAttribute<string>( aText, "align" );
opt_wxString stemp = parseOptionalAttribute<wxString>( aText, "align" );
align = stemp ? parseAlignment( *stemp ) : DEFAULT_ALIGNMENT;
}
@ -611,7 +629,7 @@ EPAD::EPAD( wxXmlNode* aPad )
*/
// #REQUIRED says DTD, throw exception if not found
name = parseRequiredAttribute<string>( aPad, "name" );
name = parseRequiredAttribute<wxString>( aPad, "name" );
x = parseRequiredAttribute<ECOORD>( aPad, "x" );
y = parseRequiredAttribute<ECOORD>( aPad, "y" );
drill = parseRequiredAttribute<ECOORD>( aPad, "drill" );
@ -619,7 +637,7 @@ EPAD::EPAD( wxXmlNode* aPad )
// Optional attributes
diameter = parseOptionalAttribute<ECOORD>( aPad, "diameter" );
opt_string s = parseOptionalAttribute<string>( aPad, "shape" );
opt_wxString s = parseOptionalAttribute<wxString>( aPad, "shape" );
// (square | round | octagon | long | offset)
if( s == "square" )
@ -659,7 +677,7 @@ ESMD::ESMD( wxXmlNode* aSMD )
*/
// DTD #REQUIRED, throw exception if not found
name = parseRequiredAttribute<string>( aSMD, "name" );
name = parseRequiredAttribute<wxString>( aSMD, "name" );
x = parseRequiredAttribute<ECOORD>( aSMD, "x" );
y = parseRequiredAttribute<ECOORD>( aSMD, "y" );
dx = parseRequiredAttribute<ECOORD>( aSMD, "dx" );
@ -693,14 +711,14 @@ EPIN::EPIN( wxXmlNode* aPin )
*/
// DTD #REQUIRED, throw exception if not found
name = parseRequiredAttribute<string>( aPin, "name" );
name = parseRequiredAttribute<wxString>( aPin, "name" );
x = parseRequiredAttribute<ECOORD>( aPin, "x" );
y = parseRequiredAttribute<ECOORD>( aPin, "y" );
visible = parseOptionalAttribute<string>( aPin, "visible" );
length = parseOptionalAttribute<string>( aPin, "length" );
direction = parseOptionalAttribute<string>( aPin, "direction" );
function = parseOptionalAttribute<string>( aPin, "function" );
visible = parseOptionalAttribute<wxString>( aPin, "visible" );
length = parseOptionalAttribute<wxString>( aPin, "length" );
direction = parseOptionalAttribute<wxString>( aPin, "direction" );
function = parseOptionalAttribute<wxString>( aPin, "function" );
swaplevel = parseOptionalAttribute<int>( aPin, "swaplevel" );
rot = parseOptionalAttribute<EROT>( aPin, "rot" );
}
@ -742,7 +760,7 @@ EPOLYGON::EPOLYGON( wxXmlNode* aPolygon )
spacing = parseOptionalAttribute<ECOORD>( aPolygon, "spacing" );
isolate = parseOptionalAttribute<ECOORD>( aPolygon, "isolate" );
opt_string s = parseOptionalAttribute<string>( aPolygon, "pour" );
opt_wxString s = parseOptionalAttribute<wxString>( aPolygon, "pour" );
// default pour to solid fill
pour = EPOLYGON::SOLID;
@ -795,11 +813,12 @@ EELEMENT::EELEMENT( wxXmlNode* aElement )
*/
// #REQUIRED
name = parseRequiredAttribute<string>( aElement, "name" );
library = parseRequiredAttribute<string>( aElement, "library" );
value = parseRequiredAttribute<string>( aElement, "value" );
package = parseRequiredAttribute<string>( aElement, "package" );
ReplaceIllegalFileNameChars( &package );
name = parseRequiredAttribute<wxString>( aElement, "name" );
library = parseRequiredAttribute<wxString>( aElement, "library" );
value = parseRequiredAttribute<wxString>( aElement, "value" );
std::string p = parseRequiredAttribute<std::string>( aElement, "package" );
ReplaceIllegalFileNameChars( &p );
package = wxString::FromUTF8( p.c_str() );
x = parseRequiredAttribute<ECOORD>( aElement, "x" );
y = parseRequiredAttribute<ECOORD>( aElement, "y" );
@ -826,7 +845,7 @@ ELAYER::ELAYER( wxXmlNode* aLayer )
*/
number = parseRequiredAttribute<int>( aLayer, "number" );
name = parseRequiredAttribute<string>( aLayer, "name" );
name = parseRequiredAttribute<wxString>( aLayer, "name" );
color = parseRequiredAttribute<int>( aLayer, "color" );
fill = 1; // Temporary value.
visible = parseOptionalAttribute<bool>( aLayer, "visible" );
@ -848,12 +867,12 @@ EPART::EPART( wxXmlNode* aPart )
* >
*/
// #REQUIRED
name = parseRequiredAttribute<string>( aPart, "name" );
library = parseRequiredAttribute<string>( aPart, "library" );
deviceset = parseRequiredAttribute<string>( aPart, "deviceset" );
device = parseRequiredAttribute<string>( aPart, "device" );
technology = parseOptionalAttribute<string>( aPart, "technology" );
value = parseOptionalAttribute<string>( aPart, "value" );
name = parseRequiredAttribute<wxString>( aPart, "name" );
library = parseRequiredAttribute<wxString>( aPart, "library" );
deviceset = parseRequiredAttribute<wxString>( aPart, "deviceset" );
device = parseRequiredAttribute<wxString>( aPart, "device" );
technology = parseOptionalAttribute<wxString>( aPart, "technology" );
value = parseOptionalAttribute<wxString>( aPart, "value" );
}
@ -870,8 +889,8 @@ EINSTANCE::EINSTANCE( wxXmlNode* aInstance )
* rot %Rotation; "R0"
* >
*/
part = parseRequiredAttribute<string>( aInstance, "part" );
gate = parseRequiredAttribute<string>( aInstance, "gate" );
part = parseRequiredAttribute<wxString>( aInstance, "part" );
gate = parseRequiredAttribute<wxString>( aInstance, "gate" );
x = parseRequiredAttribute<ECOORD>( aInstance, "x" );
y = parseRequiredAttribute<ECOORD>( aInstance, "y" );
@ -896,13 +915,13 @@ EGATE::EGATE( wxXmlNode* aGate )
* >
*/
name = parseRequiredAttribute<string>( aGate, "name" );
symbol = parseRequiredAttribute<string>( aGate, "symbol" );
name = parseRequiredAttribute<wxString>( aGate, "name" );
symbol = parseRequiredAttribute<wxString>( aGate, "symbol" );
x = parseRequiredAttribute<ECOORD>( aGate, "x" );
y = parseRequiredAttribute<ECOORD>( aGate, "y" );
opt_string stemp = parseOptionalAttribute<string>( aGate, "addlevel" );
opt_wxString stemp = parseOptionalAttribute<wxString>( aGate, "addlevel" );
// (off | value | name | both)
if( stemp == "must" )
@ -931,9 +950,9 @@ ECONNECT::ECONNECT( wxXmlNode* aConnect )
* route %ContactRoute; "all"
* >
*/
gate = parseRequiredAttribute<string>( aConnect, "gate" );
pin = parseRequiredAttribute<string>( aConnect, "pin" );
pad = parseRequiredAttribute<string>( aConnect, "pad" );
gate = parseRequiredAttribute<wxString>( aConnect, "gate" );
pin = parseRequiredAttribute<wxString>( aConnect, "pin" );
pad = parseRequiredAttribute<wxString>( aConnect, "pad" );
}
@ -946,8 +965,8 @@ EDEVICE::EDEVICE( wxXmlNode* aDevice )
package %String; #IMPLIED
>
*/
name = parseRequiredAttribute<string>( aDevice, "name" );
package = parseOptionalAttribute<string>( aDevice, "package" );
name = parseRequiredAttribute<wxString>( aDevice, "name" );
package = parseOptionalAttribute<wxString>( aDevice, "package" );
NODE_MAP aDeviceChildren = MapChildren(aDevice);
wxXmlNode* connectNode = getChildrenNodes(aDeviceChildren, "connects");
@ -971,9 +990,9 @@ EDEVICE_SET::EDEVICE_SET( wxXmlNode* aDeviceSet )
>
*/
name = parseRequiredAttribute<string>(aDeviceSet, "name");
prefix = parseOptionalAttribute<string>( aDeviceSet, "prefix" );
uservalue = parseOptionalAttribute<bool>( aDeviceSet, "uservalue" );
name = parseRequiredAttribute<wxString>(aDeviceSet, "name");
prefix = parseOptionalAttribute<wxString>( aDeviceSet, "prefix" );
uservalue = parseOptionalAttribute<bool>( aDeviceSet, "uservalue" );
/* Russell: Parsing of devices and gates moved to sch_eagle_plugin.cpp
*

View File

@ -385,8 +385,9 @@ UTF8 LIB_ID::FixIllegalChars( const UTF8& aLibItemName )
{
UTF8 fixedName;
for( auto ch : aLibItemName )
for( UTF8::uni_iter chIt = aLibItemName.ubegin(); chIt < aLibItemName.uend(); ++chIt )
{
auto ch = *chIt;
if( !wxIsascii( ch ) )
{

View File

@ -25,7 +25,6 @@
#include <wx/filename.h>
#include <memory>
#include <string>
#include <unordered_map>
#include <sch_junction.h>
@ -55,8 +54,6 @@
#include <sch_eagle_plugin.h>
using std::string;
// Eagle schematic axes are aligned with x increasing left to right and Y increasing bottom to top
// Kicad schematic axes are aligned with x increasing left to right and Y increasing top to bottom.
@ -69,7 +66,7 @@ using namespace std;
* @param aName the name of the specific child names to be counted.
* @return number of children with the give node name.
*/
static int countChildren( wxXmlNode* aCurrentNode, const std::string& aName )
static int countChildren( wxXmlNode* aCurrentNode, const wxString& aName )
{
// Map node_name -> node_pointer
int count = 0;
@ -79,7 +76,7 @@ static int countChildren( wxXmlNode* aCurrentNode, const std::string& aName )
while( aCurrentNode )
{
if( aCurrentNode->GetName().ToStdString() == aName )
if( aCurrentNode->GetName() == aName )
count++;
// Get next child
@ -325,13 +322,13 @@ SCH_EAGLE_PLUGIN::~SCH_EAGLE_PLUGIN()
const wxString SCH_EAGLE_PLUGIN::GetName() const
{
return wxT( "EAGLE" );
return "EAGLE";
}
const wxString SCH_EAGLE_PLUGIN::GetFileExtension() const
{
return wxT( "sch" );
return "sch";
}
@ -391,8 +388,8 @@ SCH_SHEET* SCH_EAGLE_PLUGIN::Load( const wxString& aFileName, KIWAY* aKiway,
{
// Create a new empty symbol library.
m_pi->CreateSymbolLib( getLibFileName().GetFullPath() );
wxString libTableUri = "${KIPRJMOD}/" + getLibFileName().GetFullName();
// Add the new library to the project symbol library table.
libTable->InsertRow( new SYMBOL_LIB_TABLE_ROW( getLibName(), libTableUri,
wxString( "Legacy" ) ) );
@ -471,7 +468,7 @@ void SCH_EAGLE_PLUGIN::countNets( wxXmlNode* aSchematicNode )
while( netNode )
{
std::string netName = netNode->GetAttribute( "name" ).ToStdString();
wxString netName = netNode->GetAttribute( "name" );
if( m_netCounts.count( netName ) )
m_netCounts[netName] = m_netCounts[netName] + 1;
@ -497,8 +494,7 @@ void SCH_EAGLE_PLUGIN::loadSchematic( wxXmlNode* aSchematicNode )
while( partNode )
{
std::unique_ptr<EPART> epart( new EPART( partNode ) );
string name = epart->name;
m_partlist[name] = std::move( epart );
m_partlist[epart->name] = std::move( epart );
partNode = partNode->GetNext();
}
@ -511,10 +507,10 @@ void SCH_EAGLE_PLUGIN::loadSchematic( wxXmlNode* aSchematicNode )
// Read the library name
wxString libName = libraryNode->GetAttribute( "name" );
EAGLE_LIBRARY* elib = &m_eagleLibs[libName.ToStdString()];
elib->name = libName.ToStdString();
EAGLE_LIBRARY* elib = &m_eagleLibs[libName];
elib->name = libName;
loadLibrary( libraryNode, &m_eagleLibs[libName.ToStdString()] );
loadLibrary( libraryNode, &m_eagleLibs[libName] );
libraryNode = libraryNode->GetNext();
}
@ -594,7 +590,7 @@ void SCH_EAGLE_PLUGIN::loadSheet( wxXmlNode* aSheetNode, int aSheetIndex )
}
else
{
filename = m_filename.GetName().ToStdString() + "_" + std::to_string( aSheetIndex );
filename = wxString::Format( "%s_%d", m_filename.GetName(), aSheetIndex );
m_currentSheet->SetName( filename );
}
@ -631,8 +627,8 @@ void SCH_EAGLE_PLUGIN::loadSheet( wxXmlNode* aSheetNode, int aSheetIndex )
while( netNode )
{
// Get the net name and class
wxString netName = netNode->GetAttribute( "name" );
wxString netClass = netNode->GetAttribute( "class" );
wxString netName = netNode->GetAttribute( "name" );
wxString netClass = netNode->GetAttribute( "class" );
// Load segments of this net
loadSegments( netNode, netName, netClass );
@ -894,7 +890,7 @@ SCH_TEXT* SCH_EAGLE_PLUGIN::loadLabel( wxXmlNode* aLabelNode,
// Determine if the Label is a local and global label based on the number of sheets the net appears on.
if( m_netCounts[aNetName.ToStdString()] > 1 )
if( m_netCounts[aNetName] > 1 )
{
std::unique_ptr<SCH_GLOBALLABEL> glabel( new SCH_GLOBALLABEL );
glabel->SetPosition( elabelpos );
@ -1054,16 +1050,14 @@ void SCH_EAGLE_PLUGIN::loadInstance( wxXmlNode* aInstanceNode )
EPART* epart = m_partlist[einstance.part].get();
std::string libraryname = epart->library;
std::string gatename = epart->deviceset + epart->device + einstance.gate;
wxString sntemp = wxString( epart->deviceset + epart->device );
sntemp.Replace( "*", "" );
std::string symbolname = sntemp.ToStdString();
wxString libraryname = epart->library;
wxString gatename = epart->deviceset + epart->device + einstance.gate;
wxString symbolname = wxString( epart->deviceset + epart->device );
symbolname.Replace( "*", "" );
int unit = m_eagleLibs[libraryname].GateUnit[gatename];
std::string package;
wxString package;
EAGLE_LIBRARY* elib = &m_eagleLibs[libraryname];
auto p = elib->package.find( symbolname );
@ -1073,10 +1067,7 @@ void SCH_EAGLE_PLUGIN::loadInstance( wxXmlNode* aInstanceNode )
package = p->second;
}
std::string kisymbolname = LIB_ID::FixIllegalChars( symbolname );
// std::replace( kisymbolname.begin(), kisymbolname.end(), ':', '_' );
// std::replace( kisymbolname.begin(), kisymbolname.end(), '/', '_' );
// std::replace( kisymbolname.begin(), kisymbolname.end(), '"', '_' );
wxString kisymbolname = LIB_ID::FixIllegalChars( symbolname );
LIB_ALIAS* alias = m_pi->LoadSymbol( getLibFileName().GetFullPath(), kisymbolname,
m_properties.get() );
@ -1090,7 +1081,7 @@ void SCH_EAGLE_PLUGIN::loadInstance( wxXmlNode* aInstanceNode )
component->SetLibId( libId );
component->SetUnit( unit );
component->SetPosition( wxPoint( einstance.x.ToSchUnits(), -einstance.y.ToSchUnits() ) );
component->GetField( FOOTPRINT )->SetText( wxString( package ) );
component->GetField( FOOTPRINT )->SetText( package );
component->SetTimeStamp( EagleModuleTstamp( einstance.part, epart->value ? *epart->value : "",
unit ) );
@ -1128,7 +1119,7 @@ void SCH_EAGLE_PLUGIN::loadInstance( wxXmlNode* aInstanceNode )
component->AddHierarchicalReference( current_sheetpath, wxString( einstance.part ), unit );
if( epart->value )
component->GetField( VALUE )->SetText( wxString::FromUTF8( epart->value->c_str() ) );
component->GetField( VALUE )->SetText( *epart->value );
else
component->GetField( VALUE )->SetText( symbolname );
@ -1214,7 +1205,7 @@ EAGLE_LIBRARY* SCH_EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLibraryNode,
while( symbolNode )
{
string symbolName = symbolNode->GetAttribute( "name" ).ToStdString();
wxString symbolName = symbolNode->GetAttribute( "name" );
aEagleLibrary->SymbolNodes[symbolName] = symbolNode;
symbolNode = symbolNode->GetNext();
}
@ -1239,11 +1230,12 @@ EAGLE_LIBRARY* SCH_EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLibraryNode,
EDEVICE edevice = EDEVICE( deviceNode );
// Create symbol name from deviceset and device names.
wxString symbolName = wxString( edeviceset.name + edevice.name );
wxString symbolName = edeviceset.name + edevice.name;
symbolName.Replace( "*", "" );
wxASSERT( !symbolName.IsEmpty() );
if( edevice.package )
aEagleLibrary->package[symbolName.ToStdString()] = edevice.package.Get();
aEagleLibrary->package[symbolName] = edevice.package.Get();
// Create KiCad symbol.
unique_ptr<LIB_PART> kpart( new LIB_PART( symbolName ) );
@ -1281,10 +1273,7 @@ EAGLE_LIBRARY* SCH_EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLibraryNode,
if( gates_count == 1 && ispower )
kpart->SetPower();
string name = LIB_ID::FixIllegalChars( kpart->GetName().ToStdString() );
// std::replace( name.begin(), name.end(), ':', '_' );
// std::replace( name.begin(), name.end(), '/', '_' );
// std::replace( name.begin(), name.end(), '"', '_' );
wxString name = LIB_ID::FixIllegalChars( kpart->GetName() );
kpart->SetName( name );
m_pi->SaveSymbol( getLibFileName().GetFullPath(), new LIB_PART( *kpart.get() ),
m_properties.get() );
@ -1300,11 +1289,8 @@ EAGLE_LIBRARY* SCH_EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLibraryNode,
}
bool SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode,
std::unique_ptr<LIB_PART>& aPart,
EDEVICE* aDevice,
int aGateNumber,
string aGateName )
bool SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode, std::unique_ptr<LIB_PART>& aPart,
EDEVICE* aDevice, int aGateNumber, const wxString& aGateName )
{
wxString symbolName = aSymbolNode->GetAttribute( "name" );
std::vector<LIB_ITEM*> items;
@ -1376,7 +1362,7 @@ bool SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode,
{
for( auto connect : aDevice->connects )
{
if( connect.gate == aGateName and pin->GetName().ToStdString() == connect.pin )
if( connect.gate == aGateName && pin->GetName() == connect.pin )
{
wxArrayString pads = wxSplit( wxString( connect.pad ), ' ');
@ -1405,8 +1391,7 @@ bool SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode,
{
pin->SetPartNumber( aGateNumber );
pin->SetUnit( aGateNumber );
wxString stringPinNum = wxString::Format( wxT( "%i" ), pincount );
pin->SetNumber( stringPinNum );
pin->SetNumber( wxString::Format( "%i", pincount ) );
aPart->AddDrawItem( pin.release() );
}
}

View File

@ -62,14 +62,14 @@ class LIB_TEXT;
typedef struct EAGLE_LIBRARY
{
std::string name;
boost::ptr_map<std::string, LIB_PART> KiCadSymbols;
std::unordered_map<std::string, wxXmlNode*> SymbolNodes;
std::unordered_map<std::string, int> GateUnit;
std::unordered_map<std::string, std::string> package;
wxString name;
boost::ptr_map<wxString, LIB_PART> KiCadSymbols;
std::unordered_map<wxString, wxXmlNode*> SymbolNodes;
std::unordered_map<wxString, int> GateUnit;
std::unordered_map<wxString, wxString> package;
} EAGLE_LIBRARY;
typedef boost::ptr_map<std::string, EPART> EPART_LIST;
typedef boost::ptr_map<wxString, EPART> EPART_LIST;
/**
@ -161,7 +161,7 @@ private:
SCH_JUNCTION* loadJunction( wxXmlNode* aJunction );
SCH_TEXT* loadPlainText( wxXmlNode* aSchText );
bool loadSymbol( wxXmlNode* aSymbolNode, std::unique_ptr<LIB_PART>& aPart, EDEVICE* aDevice, int aGateNumber, string aGateName );
bool loadSymbol( wxXmlNode* aSymbolNode, std::unique_ptr<LIB_PART>& aPart, EDEVICE* aDevice, int aGateNumber, const wxString& aGateName );
LIB_CIRCLE* loadSymbolCircle( std::unique_ptr<LIB_PART>& aPart, wxXmlNode* aCircleNode, int aGateNumber );
LIB_RECTANGLE* loadSymbolRectangle( std::unique_ptr<LIB_PART>& aPart, wxXmlNode* aRectNode, int aGateNumber );
LIB_POLYLINE* loadSymbolPolyLine( std::unique_ptr<LIB_PART>& aPart, wxXmlNode* aPolygonNode, int aGateNumber );
@ -183,12 +183,12 @@ private:
wxString m_libName; ///< Library name to save symbols
EPART_MAP m_partlist;
std::map<std::string, EAGLE_LIBRARY> m_eagleLibs;
std::map<wxString, EAGLE_LIBRARY> m_eagleLibs;
SCH_PLUGIN::SCH_PLUGIN_RELEASER m_pi; ///< Plugin to create the KiCad symbol library.
std::unique_ptr< PROPERTIES > m_properties; ///< Library plugin properties.
std::map<std::string, int> m_netCounts;
std::map<wxString, int> m_netCounts;
std::map<int, SCH_LAYER_ID> m_layerMap;
};

View File

@ -40,20 +40,19 @@
#include <macros.h>
#include <trigo.h>
#include <kicad_string.h>
using std::string;
#include <common.h>
class MODULE;
struct EINSTANCE;
struct EPART;
struct ETEXT;
typedef std::unordered_map<string, wxXmlNode*> NODE_MAP;
typedef std::map<string, MODULE*> MODULE_MAP;
typedef std::map<string, EINSTANCE*> EINSTANCE_MAP;
typedef std::map<string, std::unique_ptr<EPART>> EPART_MAP;
typedef std::unordered_map<wxString, wxXmlNode*> NODE_MAP;
typedef std::map<wxString, MODULE*> MODULE_MAP;
typedef std::map<wxString, EINSTANCE*> EINSTANCE_MAP;
typedef std::map<wxString, std::unique_ptr<EPART>> EPART_MAP;
static inline wxXmlNode* getChildrenNodes( NODE_MAP& aMap, const string& aName )
static inline wxXmlNode* getChildrenNodes( NODE_MAP& aMap, const wxString& aName )
{
auto it = aMap.find( aName );
return it == aMap.end() ? nullptr : it->second->GetChildren();
@ -73,7 +72,7 @@ struct XML_PARSER_ERROR : std::runtime_error
* the passed message.
* @param aMessage is an explanatory error message.
*/
XML_PARSER_ERROR( const string& aMessage ) noexcept :
XML_PARSER_ERROR( const wxString& aMessage ) noexcept :
std::runtime_error( "XML parser failed - " + aMessage )
{}
};
@ -134,11 +133,11 @@ public:
}
/// return the contents of the XPATH as a single string
string Contents()
wxString Contents()
{
typedef std::vector<TRIPLET>::const_iterator CITER_TRIPLET;
string ret;
wxString ret;
for( CITER_TRIPLET it = p.begin(); it != p.end(); ++it )
{
@ -182,7 +181,7 @@ T Convert( const wxString& aValue )
* This was implemented as an alternative to OPT. This class should be replaced with a
* simple typedef per type using std::optional when C++17 is published.
*/
template <class T>
template <typename T>
class OPTIONAL_XML_ATTRIBUTE
{
private:
@ -220,6 +219,7 @@ public:
* @param aData is the value of the XML attribute. If this constructor is called, the
* attribute is available.
*/
template<typename V = T>
OPTIONAL_XML_ATTRIBUTE( T aData ) :
m_isAvailable( true ),
m_data( aData )
@ -361,7 +361,7 @@ NODE_MAP MapChildren( wxXmlNode* aCurrentNode );
unsigned long EagleTimeStamp( wxXmlNode* aTree );
/// Computes module timestamp basing on its name, value and unit
time_t EagleModuleTstamp( const string& aName, const string& aValue, int aUnit );
time_t EagleModuleTstamp( const wxString& aName, const wxString& aValue, int aUnit );
/// Convert an Eagle curve end to a KiCad center for S_ARC
wxPoint ConvertArcCenter( const wxPoint& aStart, const wxPoint& aEnd, double aAngle );
@ -369,7 +369,7 @@ wxPoint ConvertArcCenter( const wxPoint& aStart, const wxPoint& aEnd, double aAn
// Pre-declare for typedefs
struct EROT;
struct ECOORD;
typedef OPTIONAL_XML_ATTRIBUTE<string> opt_string;
typedef OPTIONAL_XML_ATTRIBUTE<wxString> opt_wxString;
typedef OPTIONAL_XML_ATTRIBUTE<int> opt_int;
typedef OPTIONAL_XML_ATTRIBUTE<double> opt_double;
typedef OPTIONAL_XML_ATTRIBUTE<bool> opt_bool;
@ -452,9 +452,9 @@ struct ECOORD
struct ENET
{
int netcode;
string netname;
wxString netname;
ENET( int aNetCode, const string& aNetName ) :
ENET( int aNetCode, const wxString& aNetName ) :
netcode( aNetCode ),
netname( aNetName )
{}
@ -535,7 +535,7 @@ struct ELABEL
ECOORD size;
LAYER_NUM layer;
opt_erot rot;
opt_string xref;
opt_wxString xref;
wxString netname;
ELABEL( wxXmlNode* aLabel, const wxString& aNetName );
@ -551,7 +551,7 @@ struct EVIA
int layer_back_most; /// < inclusive
ECOORD drill;
opt_ecoord diam;
opt_string shape;
opt_wxString shape;
EVIA( wxXmlNode* aVia );
};
@ -592,8 +592,8 @@ struct ERECT
*/
struct EATTR
{
string name;
opt_string value;
wxString name;
opt_wxString value;
opt_ecoord x;
opt_ecoord y;
opt_ecoord size;
@ -626,7 +626,7 @@ struct EDIMENSION
ECOORD y3;
int layer;
opt_string dimensionType;
opt_wxString dimensionType;
EDIMENSION( wxXmlNode* aDimension );
};
@ -635,12 +635,12 @@ struct EDIMENSION
/// Eagle text element
struct ETEXT
{
string text;
wxString text;
ECOORD x;
ECOORD y;
ECOORD size;
int layer;
opt_string font;
opt_wxString font;
opt_double ratio;
opt_erot rot;
@ -670,7 +670,7 @@ struct ETEXT
/// Eagle thru hol pad
struct EPAD
{
string name;
wxString name;
ECOORD x;
ECOORD y;
ECOORD drill;
@ -697,7 +697,7 @@ struct EPAD
/// Eagle SMD pad
struct ESMD
{
string name;
wxString name;
ECOORD x;
ECOORD y;
ECOORD dx;
@ -716,14 +716,14 @@ struct ESMD
/// Eagle pin element
struct EPIN
{
string name;
wxString name;
ECOORD x;
ECOORD y;
opt_string visible;
opt_string length;
opt_string direction;
opt_string function;
opt_wxString visible;
opt_wxString length;
opt_wxString direction;
opt_wxString function;
opt_int swaplevel;
opt_erot rot;
@ -784,10 +784,10 @@ struct EHOLE
/// Eagle element element
struct EELEMENT
{
string name;
string library;
string package;
string value;
wxString name;
wxString library;
wxString package;
wxString value;
ECOORD x;
ECOORD y;
opt_bool locked;
@ -801,7 +801,7 @@ struct EELEMENT
struct ELAYER
{
int number;
string name;
wxString name;
int color;
int fill;
opt_bool visible;
@ -895,12 +895,12 @@ struct EPART
* >
*/
string name;
string library;
string deviceset;
string device;
opt_string technology;
opt_string value;
wxString name;
wxString library;
wxString deviceset;
wxString device;
opt_wxString technology;
opt_wxString value;
EPART( wxXmlNode* aPart );
};
@ -920,8 +920,8 @@ struct EINSTANCE
* >
*/
string part;
string gate;
wxString part;
wxString gate;
ECOORD x;
ECOORD y;
opt_bool smashed;
@ -945,8 +945,8 @@ struct EGATE
* >
*/
string name;
string symbol;
wxString name;
wxString symbol;
ECOORD x;
ECOORD y;
@ -978,9 +978,9 @@ struct ECONNECT
* route %ContactRoute; "all"
* >
*/
string gate;
string pin;
string pad;
wxString gate;
wxString pin;
wxString pad;
//int contactroute; // TODO
ECONNECT( wxXmlNode* aConnect );
@ -996,8 +996,8 @@ struct EDEVICE
package %String; #IMPLIED
>
*/
string name;
opt_string package;
wxString name;
opt_wxString package;
std::vector<ECONNECT> connects;
@ -1016,8 +1016,8 @@ struct EDEVICE_SET
>
*/
string name;
opt_string prefix;
wxString name;
opt_wxString prefix;
opt_bool uservalue;
//std::vector<EDEVICE> devices;
//std::vector<EGATE> gates;

View File

@ -96,9 +96,9 @@ static int parseEagle( const wxString& aDistance )
/// Assemble a two part key as a simple concatenation of aFirst and aSecond parts,
/// using a separator.
static string makeKey( const string& aFirst, const string& aSecond )
static wxString makeKey( const wxString& aFirst, const wxString& aSecond )
{
string key = aFirst + '\x02' + aSecond;
wxString key = aFirst + '\x02' + aSecond;
return key;
}
@ -237,7 +237,7 @@ BOARD* EAGLE_PLUGIN::Load( const wxString& aFileName, BOARD* aAppendToMe, const
// Catch all exceptions thrown from the parser.
catch( const XML_PARSER_ERROR &exc )
{
string errmsg = exc.what();
wxString errmsg = exc.what();
errmsg += "\n@ ";
errmsg += m_xpath->Contents();
@ -746,7 +746,7 @@ void EAGLE_PLUGIN::loadPlain( wxXmlNode* aGraphics )
}
void EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLib, const string* aLibName )
void EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLib, const wxString* aLibName )
{
m_xpath->push( "packages" );
@ -766,14 +766,12 @@ void EAGLE_PLUGIN::loadLibrary( wxXmlNode* aLib, const string* aLibName )
m_xpath->push( "package", "name" );
const wxString& pack_ref = package->GetAttribute( "name" );
string pack_name( pack_ref.ToStdString() );
std::string pack_name( pack_ref );
ReplaceIllegalFileNameChars( &pack_name );
m_xpath->Value( pack_name.c_str() );
string key = aLibName ? makeKey( *aLibName, pack_name ) : pack_name;
wxString key = aLibName ? makeKey( *aLibName, pack_name ) : pack_name;
MODULE* m = makeModule( package, pack_name );
@ -813,12 +811,10 @@ void EAGLE_PLUGIN::loadLibraries( wxXmlNode* aLibs )
while( library )
{
const string& lib_name = library->GetAttribute( "name" ).ToStdString();
const wxString& lib_name = library->GetAttribute( "name" );
m_xpath->Value( lib_name.c_str() );
loadLibrary( library, &lib_name );
library = library->GetNext();
}
@ -856,7 +852,7 @@ void EAGLE_PLUGIN::loadElements( wxXmlNode* aElements )
m_xpath->Value( e.name.c_str() );
string pkg_key = makeKey( e.library, e.package );
wxString pkg_key = makeKey( e.library, e.package );
MODULE_CITER mi = m_templates.find( pkg_key );
@ -875,7 +871,7 @@ void EAGLE_PLUGIN::loadElements( wxXmlNode* aElements )
// update the nets within the pads of the clone
for( D_PAD* pad = m->PadsList(); pad; pad = pad->Next() )
{
string pn_key = makeKey( e.name, TO_UTF8( pad->GetName() ) );
wxString pn_key = makeKey( e.name, pad->GetName() );
NET_MAP_CITER ni = m_pads_to_nets.find( pn_key );
if( ni != m_pads_to_nets.end() )
@ -1001,7 +997,7 @@ void EAGLE_PLUGIN::loadElements( wxXmlNode* aElements )
switch( *a.display )
{
case EATTR::VALUE :
valueAttr->value = e.value;
valueAttr->value = opt_wxString( e.value );
m->SetValue( e.value );
if( valueNamePresetInPackageLayout )
m->Value().SetVisible( true );
@ -1016,7 +1012,7 @@ void EAGLE_PLUGIN::loadElements( wxXmlNode* aElements )
case EATTR::BOTH :
if( valueNamePresetInPackageLayout )
m->Value().SetVisible( true );
valueAttr->value = "VALUE = " + e.value;
valueAttr->value = opt_wxString( "VALUE = " + e.value );
m->SetValue( "VALUE = " + e.value );
break;
@ -1025,7 +1021,7 @@ void EAGLE_PLUGIN::loadElements( wxXmlNode* aElements )
break;
default:
valueAttr->value = e.value;
valueAttr->value = opt_wxString( e.value );
if( valueNamePresetInPackageLayout )
m->Value().SetVisible( true );
}
@ -1182,7 +1178,7 @@ void EAGLE_PLUGIN::orientModuleText( MODULE* m, const EELEMENT& e,
}
MODULE* EAGLE_PLUGIN::makeModule( wxXmlNode* aPackage, const string& aPkgName ) const
MODULE* EAGLE_PLUGIN::makeModule( wxXmlNode* aPackage, const wxString& aPkgName ) const
{
std::unique_ptr<MODULE> m( new MODULE( m_board ) );
@ -1722,11 +1718,10 @@ void EAGLE_PLUGIN::loadSignals( wxXmlNode* aSignals )
zones.clear();
const string& nname = net->GetAttribute( "name" ).ToStdString();
wxString netName = FROM_UTF8( nname.c_str() );
const wxString& netName = net->GetAttribute( "name" );
m_board->Add( new NETINFO_ITEM( m_board, netName, netCode ) );
m_xpath->Value( nname.c_str() );
m_xpath->Value( netName );
// Get the first net item and iterate
wxXmlNode* netItem = net->GetChildren();
@ -1735,6 +1730,7 @@ void EAGLE_PLUGIN::loadSignals( wxXmlNode* aSignals )
while( netItem )
{
const wxString& itemName = netItem->GetName();
if( itemName == "wire" )
{
m_xpath->push( "wire" );
@ -1842,14 +1838,13 @@ void EAGLE_PLUGIN::loadSignals( wxXmlNode* aSignals )
m_xpath->push( "contactref" );
// <contactref element="RN1" pad="7"/>
const string& reference = netItem->GetAttribute( "element" ).ToStdString();
const string& pad = netItem->GetAttribute( "pad" ).ToStdString();
const wxString& reference = netItem->GetAttribute( "element" );
const wxString& pad = netItem->GetAttribute( "pad" );
wxString key = makeKey( reference, pad ) ;
string key = makeKey( reference, pad ) ;
// D(printf( "adding refname:'%s' pad:'%s' netcode:%d netname:'%s'\n", reference.c_str(), pad.c_str(), netCode, netName.c_str() );)
// D(printf( "adding refname:'%s' pad:'%s' netcode:%d netname:'%s'\n", reference.c_str(), pad.c_str(), netCode, nname.c_str() );)
m_pads_to_nets[ key ] = ENET( netCode, nname );
m_pads_to_nets[ key ] = ENET( netCode, netName );
m_xpath->pop();
@ -2030,9 +2025,9 @@ PCB_LAYER_ID EAGLE_PLUGIN::kicad_layer( int aEagleLayer ) const
}
const string& EAGLE_PLUGIN::eagle_layer_name( int aLayer ) const
const wxString& EAGLE_PLUGIN::eagle_layer_name( int aLayer ) const
{
static const string unknown( "unknown" );
static const wxString unknown( "unknown" );
auto it = m_eagleLayers.find( aLayer );
return it == m_eagleLayers.end() ? unknown : it->second.name;
}
@ -2193,12 +2188,8 @@ MODULE* EAGLE_PLUGIN::FootprintLoad( const wxString& aLibraryPath, const wxStrin
const PROPERTIES* aProperties )
{
init( aProperties );
cacheLib( aLibraryPath );
string key = TO_UTF8( aFootprintName );
MODULE_CITER mi = m_templates.find( key );
MODULE_CITER mi = m_templates.find( aFootprintName );
if( mi == m_templates.end() )
return NULL;

View File

@ -33,9 +33,9 @@
#include <wx/xml/xml.h>
typedef std::map< std::string, MODULE* > MODULE_MAP;
typedef std::map< std::string, ENET > NET_MAP;
typedef NET_MAP::const_iterator NET_MAP_CITER;
typedef std::map<wxString, MODULE*> MODULE_MAP;
typedef std::map<wxString, ENET> NET_MAP;
typedef NET_MAP::const_iterator NET_MAP_CITER;
/// subset of eagle.drawing.board.designrules in the XML document
@ -170,7 +170,7 @@ private:
PCB_LAYER_ID kicad_layer( int aLayer ) const;
/// Get Eagle layer name by its number
const std::string& eagle_layer_name( int aLayer ) const;
const wxString& eagle_layer_name( int aLayer ) const;
/// This PLUGIN only caches one footprint library, this determines which one.
void cacheLib( const wxString& aLibraryPath );
@ -197,7 +197,7 @@ private:
* we are loading a *.lbr not a *.brd file and the key used in m_templates is to exclude
* the library name.
*/
void loadLibrary( wxXmlNode* aLib, const std::string* aLibName );
void loadLibrary( wxXmlNode* aLib, const wxString* aLibName );
void loadLibraries( wxXmlNode* aLibs );
void loadElements( wxXmlNode* aElements );
@ -215,13 +215,13 @@ private:
* is the opposite or complement of degParse(). One has to know what the
* other is doing.
*/
std::string fmtDEG( double aAngle ) const;
wxString fmtDEG( double aAngle ) const;
/**
* Function makeModule
* creates a MODULE from an Eagle package.
*/
MODULE* makeModule( wxXmlNode* aPackage, const std::string& aPkgName ) const;
MODULE* makeModule( wxXmlNode* aPackage, const wxString& aPkgName ) const;
void packageWire( MODULE* aModule, wxXmlNode* aTree ) const;
void packagePad( MODULE* aModule, wxXmlNode* aTree ) const;