Eeschema: Eagle plugin> work on schematic and symbol elements

This commit is contained in:
Russell Oliver 2017-06-18 21:31:11 +10:00 committed by Maciej Suminski
parent e92c8c1d6c
commit ea8f7ed02d
4 changed files with 234 additions and 59 deletions

View File

@ -181,6 +181,47 @@ EWIRE::EWIRE( wxXmlNode* aWire )
cap = EWIRE::FLAT; cap = EWIRE::FLAT;
} }
EJUNCTION::EJUNCTION( wxXmlNode* aJunction)
{
/*
<!ELEMENT junction EMPTY>
<!ATTLIST junction
x %Coord; #REQUIRED
y %Coord; #REQUIRED
>
*/
x = parseRequiredAttribute<double>( aJunction, "x" );
y = parseRequiredAttribute<double>( aJunction, "y" );
}
ELABEL::ELABEL( wxXmlNode* aLabel, wxString aNetName)
{
/*
<!ELEMENT label EMPTY>
<!ATTLIST label
x %Coord; #REQUIRED
y %Coord; #REQUIRED
size %Dimension; #REQUIRED
layer %Layer; #REQUIRED
font %TextFont; "proportional"
ratio %Int; "8"
rot %Rotation; "R0"
xref %Bool; "no"
>
*/
x = parseRequiredAttribute<double>( aLabel, "x" );
y = parseRequiredAttribute<double>( aLabel, "y" );
size = parseRequiredAttribute<double>( aLabel, "size" );
layer = parseRequiredAttribute<int>( aLabel, "layer" );
rot = parseOptionalAttribute<EROT>( aLabel, "rot" );
xref = parseOptionalAttribute<string>(aLabel, "xref");
netname = aNetName;
}
EVIA::EVIA( wxXmlNode* aVia ) EVIA::EVIA( wxXmlNode* aVia )
{ {
@ -466,6 +507,36 @@ ESMD::ESMD( wxXmlNode* aSMD )
cream = parseOptionalAttribute<bool>( aSMD, "cream" ); cream = parseOptionalAttribute<bool>( aSMD, "cream" );
} }
EPIN::EPIN( wxXmlNode* aPin ){
/*
<!ELEMENT pin EMPTY>
<!ATTLIST pin
name %String; #REQUIRED
x %Coord; #REQUIRED
y %Coord; #REQUIRED
visible %PinVisible; "both"
length %PinLength; "long"
direction %PinDirection; "io"
function %PinFunction; "none"
swaplevel %Int; "0"
rot %Rotation; "R0"
>
*/
// DTD #REQUIRED, throw exception if not found
name = parseRequiredAttribute<string>( aPin, "name" );
x = parseRequiredAttribute<double>( aPin, "x" );
y = parseRequiredAttribute<double>( aPin, "y" );
visible = parseOptionalAttribute<string>( aPin, "visible" );
length = parseOptionalAttribute<string>( aPin, "length" );
direction = parseOptionalAttribute<string>( aPin, "direction" );
function = parseOptionalAttribute<string>( aPin, "function" );
swaplevel = parseOptionalAttribute<int>(aPin, "swaplevel");
rot = parseOptionalAttribute<EROT>(aPin, "rot");
}
EVERTEX::EVERTEX( wxXmlNode* aVertex ) EVERTEX::EVERTEX( wxXmlNode* aVertex )
{ {

View File

@ -25,6 +25,7 @@
#include <string> #include <string>
#include <unordered_map> #include <unordered_map>
#include <sch_junction.h>
#include <sch_sheet.h> #include <sch_sheet.h>
#include <sch_eagle_plugin.h> #include <sch_eagle_plugin.h>
@ -33,9 +34,17 @@
#include <lib_circle.h> #include <lib_circle.h>
#include <lib_rectangle.h> #include <lib_rectangle.h>
#include <lib_polyline.h> #include <lib_polyline.h>
#include <lib_pin.h>
#include <eagle_parser.h> #include <eagle_parser.h>
// Eagle schematic internal units are millimeters
// Kicad schematic units are thousandths of an inch
#define EUNIT_TO_MIL 1000.0/25.4
// Eagle schematic axes are aligned with x increasing left to right and Y increasing bottom to top
// Kicad schematic axes are algigned with x increasing left to rigth and Y increasing top to bottom.
using namespace std; using namespace std;
NODE_MAP mapChildren( wxXmlNode* aCurrentNode ) NODE_MAP mapChildren( wxXmlNode* aCurrentNode )
@ -349,7 +358,7 @@ void SCH_EAGLE_PLUGIN::loadSheet( wxXmlNode* aSheetNode )
wxString busName = busNode->GetAttribute( "name" ); wxString busName = busNode->GetAttribute( "name" );
// Load segments of this bus // Load segments of this bus
loadSegments( busNode ); // loadSegments( busNode );
// Get next bus // Get next bus
busNode = busNode->GetNext(); busNode = busNode->GetNext();
@ -366,7 +375,7 @@ void SCH_EAGLE_PLUGIN::loadSheet( wxXmlNode* aSheetNode )
wxString netClass = netNode->GetAttribute( "class" ); wxString netClass = netNode->GetAttribute( "class" );
// Load segments of this net // Load segments of this net
loadSegments( netNode ); loadSegments( netNode , netName, netClass);
// Get next net // Get next net
netNode = netNode->GetNext(); netNode = netNode->GetNext();
@ -400,19 +409,18 @@ void SCH_EAGLE_PLUGIN::loadSheet( wxXmlNode* aSheetNode )
while( plainNode ) while( plainNode )
{ {
loadSegments( plainNode ); //loadSegments( plainNode );
plainNode = plainNode->GetNext(); plainNode = plainNode->GetNext();
} }
} }
void SCH_EAGLE_PLUGIN::loadSegments( wxXmlNode* aSegmentsNode ) void SCH_EAGLE_PLUGIN::loadSegments( wxXmlNode* aSegmentsNode, wxString netName, wxString netClass)
{ {
// Loop through all segments // Loop through all segments
wxXmlNode* currentSegment = aSegmentsNode->GetChildren(); wxXmlNode* currentSegment = aSegmentsNode->GetChildren();
SCH_SCREEN* screen = m_rootSheet->GetScreen(); SCH_SCREEN* screen = m_currentSheet->GetScreen();
//wxCHECK( screen, [>void<] ); //wxCHECK( screen, [>void<] );
while( currentSegment ) while( currentSegment )
{ {
// Loop through all segment children // Loop through all segment children
@ -427,6 +435,7 @@ void SCH_EAGLE_PLUGIN::loadSegments( wxXmlNode* aSegmentsNode )
// TODO: handle junctions attributes // TODO: handle junctions attributes
segmentAttribute->GetAttribute( "x" ); segmentAttribute->GetAttribute( "x" );
segmentAttribute->GetAttribute( "y" ); segmentAttribute->GetAttribute( "y" );
screen->Append(loadJunction(segmentAttribute));
} }
else if( nodeName == "label" ) else if( nodeName == "label" )
{ {
@ -439,6 +448,9 @@ void SCH_EAGLE_PLUGIN::loadSegments( wxXmlNode* aSegmentsNode )
segmentAttribute->GetAttribute( "ratio" ); // Defaults to "8" segmentAttribute->GetAttribute( "ratio" ); // Defaults to "8"
segmentAttribute->GetAttribute( "rot" ); // Defaults to "R0" segmentAttribute->GetAttribute( "rot" ); // Defaults to "R0"
segmentAttribute->GetAttribute( "xref" ); // Defaults to "no" segmentAttribute->GetAttribute( "xref" ); // Defaults to "no"
screen->Append(loadLabel(segmentAttribute, netName));
} }
else if( nodeName == "pinref" ) else if( nodeName == "pinref" )
{ {
@ -455,11 +467,11 @@ void SCH_EAGLE_PLUGIN::loadSegments( wxXmlNode* aSegmentsNode )
} }
else if( nodeName == "wire" ) else if( nodeName == "wire" )
{ {
screen->Append( loadWire( segmentAttribute ) ); screen->Append( loadSignalWire( segmentAttribute ) );
} }
else if( nodeName == "segment" ) else if( nodeName == "segment" )
{ {
loadSegments( segmentAttribute ); //loadSegments( segmentAttribute );
} }
else if( nodeName == "text" ) else if( nodeName == "text" )
{ {
@ -481,30 +493,20 @@ void SCH_EAGLE_PLUGIN::loadSegments( wxXmlNode* aSegmentsNode )
} }
SCH_LINE* SCH_EAGLE_PLUGIN::loadWire( wxXmlNode* aWireNode ) SCH_LINE* SCH_EAGLE_PLUGIN::loadSignalWire( wxXmlNode* aWireNode )
{ {
std::unique_ptr<SCH_LINE> wire( new SCH_LINE ); std::unique_ptr<SCH_LINE> wire( new SCH_LINE );
auto ewire = EWIRE( aWireNode ); auto ewire = EWIRE( aWireNode );
// TODO: layer map? wire->SetLayer( LAYER_WIRE );
// wire->SetLayer( layerMap( layer ) );
// if( strCompare( "Wire", line, &line ) )
wire->SetLayer( LAYER_WIRE );
// else if( strCompare( "Bus", line, &line ) )
// wire->SetLayer( LAYER_BUS );
// else if( strCompare( "Notes", line, &line ) )
// wire->SetLayer( LAYER_NOTES );
// else
// SCH_PARSE_ERROR( "invalid line type", aReader, line );
wxPoint begin, end; wxPoint begin, end;
begin.x = ewire.x1; begin.x = ewire.x1*EUNIT_TO_MIL;
begin.y = ewire.y1; begin.y = -ewire.y1*EUNIT_TO_MIL;
end.x = ewire.x2; end.x = ewire.x2*EUNIT_TO_MIL;
end.y = ewire.y2; end.y = -ewire.y2*EUNIT_TO_MIL;
wire->SetStartPoint( begin ); wire->SetStartPoint( begin );
wire->SetEndPoint( end ); wire->SetEndPoint( end );
@ -513,6 +515,34 @@ SCH_LINE* SCH_EAGLE_PLUGIN::loadWire( wxXmlNode* aWireNode )
} }
SCH_JUNCTION* SCH_EAGLE_PLUGIN::loadJunction(wxXmlNode* aJunction){
std::unique_ptr<SCH_JUNCTION> junction( new SCH_JUNCTION );
auto ejunction = EJUNCTION(aJunction);
junction->SetPosition( wxPoint( ejunction.x*EUNIT_TO_MIL, -ejunction.y*EUNIT_TO_MIL ) );
return junction.release();
}
SCH_GLOBALLABEL* SCH_EAGLE_PLUGIN::loadLabel(wxXmlNode* aLabelNode, wxString aNetName){
std::unique_ptr<SCH_GLOBALLABEL> glabel( new SCH_GLOBALLABEL );
auto elabel = ELABEL(aLabelNode, aNetName);
glabel->SetPosition( wxPoint( elabel.x*EUNIT_TO_MIL, -elabel.y*EUNIT_TO_MIL ) );
glabel->SetText(elabel.netname);
glabel->SetTextSize( wxSize( GetDefaultTextSize(), GetDefaultTextSize() ) );
EROT rot = elabel.rot.Get();
glabel->SetLabelSpinStyle( int(rot.degrees/90+2)%4 );
return glabel.release();
}
void SCH_EAGLE_PLUGIN::loadInstance( wxXmlNode* aInstanceNode ) void SCH_EAGLE_PLUGIN::loadInstance( wxXmlNode* aInstanceNode )
{ {
} }
@ -588,11 +618,11 @@ LIB_PART* SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode )
} }
else if( nodeName == "circle" ) else if( nodeName == "circle" )
{ {
part->AddDrawItem( loadCircle( part.get(), currentNode ) ); part->AddDrawItem( loadSymbolCircle( part.get(), currentNode ) );
} }
else if( nodeName == "pin" ) else if( nodeName == "pin" )
{ {
// part->AddDrawItem( loadPin( part, currentNode ) ); part->AddDrawItem( loadPin( part.get(), currentNode ) );
} }
else if( nodeName == "polygon" ) else if( nodeName == "polygon" )
{ {
@ -600,7 +630,7 @@ LIB_PART* SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode )
} }
else if( nodeName == "rectangle" ) else if( nodeName == "rectangle" )
{ {
part->AddDrawItem( loadRectangle( part.get(), currentNode ) ); part->AddDrawItem( loadSymbolRectangle( part.get(), currentNode ) );
} }
else if( nodeName == "text" ) else if( nodeName == "text" )
{ {
@ -608,7 +638,7 @@ LIB_PART* SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode )
} }
else if( nodeName == "wire" ) else if( nodeName == "wire" )
{ {
// part->AddDrawItem( loadPolyline( part, currentNode ) ); part->AddDrawItem( loadSymbolWire( part.get(), currentNode ) );
} }
currentNode = currentNode->GetNext(); currentNode = currentNode->GetNext();
@ -618,60 +648,90 @@ LIB_PART* SCH_EAGLE_PLUGIN::loadSymbol( wxXmlNode* aSymbolNode )
} }
LIB_CIRCLE* SCH_EAGLE_PLUGIN::loadCircle( LIB_PART* aPart, wxXmlNode* aCircleNode ) LIB_CIRCLE* SCH_EAGLE_PLUGIN::loadSymbolCircle( LIB_PART* aPart, wxXmlNode* aCircleNode )
{ {
// Parse the circle properties // Parse the circle properties
ECIRCLE c( aCircleNode ); ECIRCLE c( aCircleNode );
unique_ptr<LIB_CIRCLE> circle( new LIB_CIRCLE( aPart ) ); unique_ptr<LIB_CIRCLE> circle( new LIB_CIRCLE( aPart ) );
circle->SetPosition( wxPoint( c.x, c.y ) ); circle->SetPosition( wxPoint( c.x*EUNIT_TO_MIL, -c.y*EUNIT_TO_MIL ) );
circle->SetRadius( c.radius ); circle->SetRadius( c.radius*EUNIT_TO_MIL );
circle->SetWidth( c.width ); circle->SetWidth( c.width*EUNIT_TO_MIL );
return circle.release(); return circle.release();
} }
LIB_RECTANGLE* SCH_EAGLE_PLUGIN::loadRectangle( LIB_PART* aPart, wxXmlNode* aRectNode ) LIB_RECTANGLE* SCH_EAGLE_PLUGIN::loadSymbolRectangle( LIB_PART* aPart, wxXmlNode* aRectNode )
{ {
ERECT rect( aRectNode ); ERECT rect( aRectNode );
unique_ptr<LIB_RECTANGLE> rectangle( new LIB_RECTANGLE( aPart ) ); unique_ptr<LIB_RECTANGLE> rectangle( new LIB_RECTANGLE( aPart ) );
rectangle->SetPosition( wxPoint( rect.x1, rect.y1 ) ); rectangle->SetPosition( wxPoint( rect.x1*EUNIT_TO_MIL, -rect.y1*EUNIT_TO_MIL ) );
rectangle->SetEnd( wxPoint( rect.x2, rect.y2 ) ); rectangle->SetEnd( wxPoint( rect.x2*EUNIT_TO_MIL, -rect.y2*EUNIT_TO_MIL ) );
// TODO: Manage rotation // TODO: Manage rotation
return rectangle.release(); return rectangle.release();
} }
LIB_POLYLINE* SCH_EAGLE_PLUGIN::loadSymbolWire( LIB_PART* aPart, wxXmlNode* aWireNode )
LIB_POLYLINE* SCH_EAGLE_PLUGIN::loadPolyLine( LIB_PART* aPart, wxXmlNode* aRectNode )
{ {
// TODO: Layer map
std::unique_ptr< LIB_POLYLINE > polyLine( new LIB_POLYLINE( aPart ) ); std::unique_ptr< LIB_POLYLINE > polyLine( new LIB_POLYLINE( aPart ) );
/*int points = parseInt( aReader, line, &line ); auto ewire = EWIRE(aWireNode);
polyLine->SetUnit( parseInt( aReader, line, &line ) ); wxPoint begin, end;
polyLine->SetConvert( parseInt( aReader, line, &line ) );
polyLine->SetWidth( parseInt( aReader, line, &line ) );
wxPoint pt; begin.x = ewire.x1*EUNIT_TO_MIL;
begin.y = -ewire.y1*EUNIT_TO_MIL;
end.x = ewire.x2*EUNIT_TO_MIL;
end.y = -ewire.y2*EUNIT_TO_MIL;
for( int i = 0; i < points; i++ ) polyLine->AddPoint( begin );
{ polyLine->AddPoint( end );
pt.x = parseInt( aReader, line, &line );
pt.y = parseInt( aReader, line, &line );
polyLine->AddPoint( pt );
}
if( *line != 0 )
polyLine->SetFillMode( parseFillMode( aReader, line, &line ) );*/
return polyLine.release(); return polyLine.release();
} }
LIB_POLYLINE* SCH_EAGLE_PLUGIN::loadSymbolPolyLine( LIB_PART* aPart, wxXmlNode* aPolygonNode )
{
// TODO: Layer map
std::unique_ptr< LIB_POLYLINE > polyLine( new LIB_POLYLINE( aPart ) );
NODE_MAP polygonChildren = mapChildren( aPolygonNode );
wxXmlNode* vertex = getChildrenNodes( polygonChildren, "vertex" );
while(vertex) {
auto evertex = EVERTEX( vertex);
auto v = wxPoint(evertex.x*EUNIT_TO_MIL, -evertex.y*EUNIT_TO_MIL);
polyLine->AddPoint( v );
vertex->GetNext();
}
return polyLine.release();
}
LIB_PIN* SCH_EAGLE_PLUGIN::loadPin( LIB_PART* aPart, wxXmlNode* aPin)
{
std::unique_ptr< LIB_PIN > pin( new LIB_PIN( aPart ) );
auto epin = EPIN(aPin);
pin->SetPosition(wxPoint(epin.x*EUNIT_TO_MIL, -epin.y*EUNIT_TO_MIL));
pin->SetName(epin.name);
EROT rot = epin.rot.Get();
pin->SetOrientation( int(rot.degrees/90+2)%4 );
return pin.release();
}
void SCH_EAGLE_PLUGIN::Save( const wxString& aFileName, SCH_SCREEN* aSchematic, KIWAY* aKiway, void SCH_EAGLE_PLUGIN::Save( const wxString& aFileName, SCH_SCREEN* aSchematic, KIWAY* aKiway,
const PROPERTIES* aProperties ) const PROPERTIES* aProperties )
@ -753,8 +813,6 @@ void SCH_EAGLE_PLUGIN::SymbolLibOptions( PROPERTIES* aListToAppendTo ) const
// gate // gate
// grid // grid
// hole // hole
// junction
// label
// layer // layer
// note // note
// pad // pad

View File

@ -36,6 +36,7 @@ class SCH_NO_CONNECT;
class SCH_LINE; class SCH_LINE;
class SCH_BUS_ENTRY_BASE; class SCH_BUS_ENTRY_BASE;
class SCH_TEXT; class SCH_TEXT;
class SCH_GLOBALLABEL;
class SCH_COMPONENT; class SCH_COMPONENT;
class SCH_FIELD; class SCH_FIELD;
class PROPERTIES; class PROPERTIES;
@ -46,6 +47,7 @@ class LIB_ALIAS;
class LIB_CIRCLE; class LIB_CIRCLE;
class LIB_RECTANGLE; class LIB_RECTANGLE;
class LIB_POLYLINE; class LIB_POLYLINE;
class LIB_PIN;
/** /**
@ -110,17 +112,21 @@ private:
void loadDrawing( wxXmlNode* aDrawingNode ); void loadDrawing( wxXmlNode* aDrawingNode );
void loadSchematic( wxXmlNode* aSchematicNode ); void loadSchematic( wxXmlNode* aSchematicNode );
void loadSheet( wxXmlNode* aSheetNode ); void loadSheet( wxXmlNode* aSheetNode );
void loadSegments( wxXmlNode* aSegmentsNode );
SCH_LINE* loadWire( wxXmlNode* aWireNode );
void loadInstance( wxXmlNode* aInstanceNode ); void loadInstance( wxXmlNode* aInstanceNode );
void loadModuleinst( wxXmlNode* aModuleinstNode ); void loadModuleinst( wxXmlNode* aModuleinstNode );
void loadLibrary( wxXmlNode* aLibraryNode ); void loadLibrary( wxXmlNode* aLibraryNode );
LIB_PART* loadSymbol( wxXmlNode* aSymbolNode );
LIB_CIRCLE* loadCircle( LIB_PART* aPart, wxXmlNode* aCircleNode ); void loadSegments( wxXmlNode* aSegmentsNode, wxString aNetName, wxString aNetClass );
LIB_RECTANGLE* loadRectangle( LIB_PART* aPart, wxXmlNode* aRectNode ); SCH_LINE* loadSignalWire( wxXmlNode* aWireNode );
LIB_POLYLINE* loadPolyLine( LIB_PART* aPart, wxXmlNode* aRectNode ); SCH_GLOBALLABEL* loadLabel( wxXmlNode* aLabelNode, wxString aNetName );
SCH_JUNCTION* loadJunction( wxXmlNode* aJunction );
LIB_PART* loadSymbol( wxXmlNode* aSymbolNode );
LIB_CIRCLE* loadSymbolCircle( LIB_PART* aPart, wxXmlNode* aCircleNode );
LIB_RECTANGLE* loadSymbolRectangle( LIB_PART* aPart, wxXmlNode* aRectNode );
LIB_POLYLINE* loadSymbolPolyLine( LIB_PART* aPart, wxXmlNode* aRectNode );
LIB_POLYLINE* loadSymbolWire( LIB_PART* aPart, wxXmlNode* aWireNode );
LIB_PIN* loadPin( LIB_PART*, wxXmlNode* );
KIWAY* m_kiway; ///< For creating sub sheets. KIWAY* m_kiway; ///< For creating sub sheets.
SCH_SHEET* m_rootSheet; ///< The root sheet of the schematic being loaded.. SCH_SHEET* m_rootSheet; ///< The root sheet of the schematic being loaded..

View File

@ -427,6 +427,30 @@ struct EWIRE
EWIRE( wxXmlNode* aWire ); EWIRE( wxXmlNode* aWire );
}; };
/// Eagle Junction
struct EJUNCTION
{
double x;
double y;
EJUNCTION( wxXmlNode* aJunction);
};
/// Eagle label
struct ELABEL
{
double x;
double y;
double size;
LAYER_NUM layer;
opt_erot rot;
opt_string xref;
wxString netname;
ELABEL( wxXmlNode* aLabel, wxString aNetName );
};
/// Eagle via /// Eagle via
struct EVIA struct EVIA
@ -594,6 +618,22 @@ struct ESMD
ESMD( wxXmlNode* aSMD ); ESMD( wxXmlNode* aSMD );
}; };
/// Eagle pin element
struct EPIN
{
string name;
double x;
double y;
opt_string visible;
opt_string length;
opt_string direction;
opt_string function;
opt_int swaplevel;
opt_erot rot;
EPIN( wxXmlNode* aPin );
};
/// Eagle vertex /// Eagle vertex
struct EVERTEX struct EVERTEX