Pcbnew s-expression file parser bug fixes and file size improvements.
* Use index when saving layers to handle translated layer names. * Add LOCALE_IO switcher when loading s-expression format. * Make SEGVIA default to through hole to improve file size. * Don't save default orientation of 0 degrees in TEXTE_MODULE and TEXTE_PCB. * Don't save default zone configuration parameters. * Save multiple zone corners on a single line. * Fixed missing ( check in graphic and module arc parsers. * Consistency improvements for DRAWSEGMENT and EDGE_MODULE objects. * Minor tweaks to D_PAD formatting.
This commit is contained in:
parent
d9ed8a3085
commit
8c72db6631
|
@ -129,8 +129,8 @@ priority
|
|||
pts
|
||||
radius
|
||||
rev
|
||||
rect
|
||||
rect_delta
|
||||
rectangle
|
||||
reference
|
||||
right
|
||||
rotate
|
||||
|
@ -165,7 +165,6 @@ trapezoid
|
|||
thru
|
||||
thru_hole
|
||||
tstamp
|
||||
use_thermal
|
||||
user
|
||||
user_trace_width
|
||||
user_via
|
||||
|
|
|
@ -74,10 +74,14 @@ BOARD::BOARD() :
|
|||
|
||||
BuildListOfNets(); // prepare pad and netlist containers.
|
||||
|
||||
for( int layer = 0; layer < NB_COPPER_LAYERS; ++layer )
|
||||
for( int layer = 0; layer < LAYER_COUNT; ++layer )
|
||||
{
|
||||
m_Layer[layer].m_Name = GetDefaultLayerName( layer );
|
||||
m_Layer[layer].m_Type = LT_SIGNAL;
|
||||
|
||||
if( layer <= LAST_COPPER_LAYER )
|
||||
m_Layer[layer].m_Type = LT_SIGNAL;
|
||||
else
|
||||
m_Layer[layer].m_Type = LT_UNDEFINED;
|
||||
}
|
||||
|
||||
m_NetClasses.GetDefault()->SetDescription( _( "This is the default net class." ) );
|
||||
|
@ -356,8 +360,8 @@ wxString BOARD::GetLayerName( int aLayerIndex ) const
|
|||
if( !IsValidLayerIndex( aLayerIndex ) )
|
||||
return wxEmptyString;
|
||||
|
||||
// copper layer names are stored in the BOARD.
|
||||
if( IsValidCopperLayerIndex( aLayerIndex ) && IsLayerEnabled( aLayerIndex ) )
|
||||
// All layer names are stored in the BOARD.
|
||||
if( IsLayerEnabled( aLayerIndex ) )
|
||||
{
|
||||
// default names were set in BOARD::BOARD() but they may be
|
||||
// over-ridden by BOARD::SetLayerName()
|
||||
|
|
|
@ -199,7 +199,7 @@ private:
|
|||
/// edge zone descriptors, owned by pointer.
|
||||
ZONE_CONTAINERS m_ZoneDescriptorList;
|
||||
|
||||
LAYER m_Layer[NB_COPPER_LAYERS];
|
||||
LAYER m_Layer[LAYER_COUNT];
|
||||
// if true m_highLight_NetCode is used
|
||||
HIGH_LIGHT_INFO m_highLight; // current high light data
|
||||
HIGH_LIGHT_INFO m_highLightPrevious; // a previously stored high light data
|
||||
|
|
|
@ -186,6 +186,7 @@ wxString SEGZONE::GetSelectMenuText() const
|
|||
SEGVIA::SEGVIA( BOARD_ITEM* aParent ) :
|
||||
TRACK( aParent, PCB_VIA_T )
|
||||
{
|
||||
SetShape( VIA_THROUGH );
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -134,7 +134,7 @@ void PCB_IO::Format( BOARD_ITEM* aItem, int aNestLevel ) const
|
|||
|
||||
void PCB_IO::formatLayer( const BOARD_ITEM* aItem ) const
|
||||
{
|
||||
#if USE_LAYER_NAMES
|
||||
#if 1
|
||||
m_out->Print( 0, " (layer %s)", m_out->Quotew( aItem->GetLayerName() ).c_str() );
|
||||
#else
|
||||
m_out->Print( 0, " (layer %d)", aItem->GetLayer() );
|
||||
|
@ -182,7 +182,7 @@ void PCB_IO::format( BOARD* aBoard, int aNestLevel ) const
|
|||
if( mask & aBoard->GetEnabledLayers() )
|
||||
{
|
||||
#if USE_LAYER_NAMES
|
||||
m_out->Print( aNestLevel+1, "(%s %s",
|
||||
m_out->Print( aNestLevel+1, "(%d %s %s", layer,
|
||||
m_out->Quotew( aBoard->GetLayerName( layer ) ).c_str(),
|
||||
LAYER::ShowType( aBoard->GetLayerType( layer ) ) );
|
||||
#else
|
||||
|
@ -210,7 +210,7 @@ void PCB_IO::format( BOARD* aBoard, int aNestLevel ) const
|
|||
if( mask & aBoard->GetEnabledLayers() )
|
||||
{
|
||||
#if USE_LAYER_NAMES
|
||||
m_out->Print( aNestLevel+1, "(%s user",
|
||||
m_out->Print( aNestLevel+1, "(%d %s user", layer,
|
||||
m_out->Quotew( aBoard->GetLayerName( layer ) ).c_str() );
|
||||
#else
|
||||
m_out->Print( aNestLevel+1, "(%d %s user", layer,
|
||||
|
@ -454,20 +454,23 @@ void PCB_IO::format( DRAWSEGMENT* aSegment, int aNestLevel ) const
|
|||
switch( aSegment->GetShape() )
|
||||
{
|
||||
case S_SEGMENT: // Line
|
||||
m_out->Print( aNestLevel, "(gr_line (pts (xy %s) (xy %s)) (angle %s)",
|
||||
m_out->Print( aNestLevel, "(gr_line (start %s) (end %s)",
|
||||
FMT_IU( aSegment->GetStart() ).c_str(),
|
||||
FMT_IU( aSegment->GetEnd() ).c_str(),
|
||||
FMT_ANGLE( aSegment->GetAngle() ).c_str() );
|
||||
FMT_IU( aSegment->GetEnd() ).c_str() );
|
||||
|
||||
if( aSegment->GetAngle() != 0.0 )
|
||||
m_out->Print( 0, " (angle %s)", FMT_ANGLE( aSegment->GetAngle() ).c_str() );
|
||||
|
||||
break;
|
||||
|
||||
case S_CIRCLE: // Circle
|
||||
m_out->Print( aNestLevel, "(gr_circle (center (xy %s)) (end (xy %s))",
|
||||
m_out->Print( aNestLevel, "(gr_circle (center %s) (end %s)",
|
||||
FMT_IU( aSegment->GetStart() ).c_str(),
|
||||
FMT_IU( aSegment->GetEnd() ).c_str() );
|
||||
break;
|
||||
|
||||
case S_ARC: // Arc
|
||||
m_out->Print( aNestLevel, "(gr_arc (start (xy %s)) (end (xy %s)) (angle %s)",
|
||||
m_out->Print( aNestLevel, "(gr_arc (start %s) (end %s) (angle %s)",
|
||||
FMT_IU( aSegment->GetStart() ).c_str(),
|
||||
FMT_IU( aSegment->GetEnd() ).c_str(),
|
||||
FMT_ANGLE( aSegment->GetAngle() ).c_str() );
|
||||
|
@ -515,19 +518,19 @@ void PCB_IO::format( EDGE_MODULE* aModuleDrawing, int aNestLevel ) const
|
|||
switch( aModuleDrawing->GetShape() )
|
||||
{
|
||||
case S_SEGMENT: // Line
|
||||
m_out->Print( aNestLevel, "(fp_line (pts (xy %s) (xy %s))",
|
||||
m_out->Print( aNestLevel, "(fp_line (start %s) (end %s)",
|
||||
FMT_IU( aModuleDrawing->GetStart0() ).c_str(),
|
||||
FMT_IU( aModuleDrawing->GetEnd0() ).c_str() );
|
||||
break;
|
||||
|
||||
case S_CIRCLE: // Circle
|
||||
m_out->Print( aNestLevel, "(fp_circle (center (xy %s)) (end (xy %s))",
|
||||
m_out->Print( aNestLevel, "(fp_circle (center %s) (end %s)",
|
||||
FMT_IU( aModuleDrawing->GetStart0() ).c_str(),
|
||||
FMT_IU( aModuleDrawing->GetEnd0() ).c_str() );
|
||||
break;
|
||||
|
||||
case S_ARC: // Arc
|
||||
m_out->Print( aNestLevel, "(fp_arc (start (xy %s)) (end (xy %s)) (angle %s)",
|
||||
m_out->Print( aNestLevel, "(fp_arc (start %s) (end %s) (angle %s)",
|
||||
FMT_IU( aModuleDrawing->GetStart0() ).c_str(),
|
||||
FMT_IU( aModuleDrawing->GetEnd0() ).c_str(),
|
||||
FMT_ANGLE( aModuleDrawing->GetAngle() ).c_str() );
|
||||
|
@ -722,7 +725,7 @@ void PCB_IO::format( D_PAD* aPad, int aNestLevel ) const
|
|||
switch( aPad->GetShape() )
|
||||
{
|
||||
case PAD_CIRCLE: shape = "circle"; break;
|
||||
case PAD_RECT: shape = "rectangle"; break;
|
||||
case PAD_RECT: shape = "rect"; break;
|
||||
case PAD_OVAL: shape = "oval"; break;
|
||||
case PAD_TRAPEZOID: shape = "trapezoid"; break;
|
||||
|
||||
|
@ -744,27 +747,25 @@ void PCB_IO::format( D_PAD* aPad, int aNestLevel ) const
|
|||
aPad->GetAttribute() ) );
|
||||
}
|
||||
|
||||
m_out->Print( aNestLevel, "(pad %s %s %s (size %s)",
|
||||
m_out->Print( aNestLevel, "(pad %s %s %s",
|
||||
m_out->Quotew( aPad->GetPadName() ).c_str(),
|
||||
type.c_str(), shape.c_str(),
|
||||
FMT_IU( aPad->GetSize() ).c_str() );
|
||||
m_out->Print( aNestLevel+1, " (at %s", FMT_IU( aPad->GetPos0() ).c_str() );
|
||||
type.c_str(), shape.c_str() );
|
||||
m_out->Print( 0, " (at %s", FMT_IU( aPad->GetPos0() ).c_str() );
|
||||
|
||||
if( aPad->GetOrientation() != 0.0 )
|
||||
m_out->Print( 0, " %s", FMT_ANGLE( aPad->GetOrientation() ).c_str() );
|
||||
|
||||
m_out->Print( 0, ")" );
|
||||
m_out->Print( 0, " (size %s)", FMT_IU( aPad->GetSize() ).c_str() );
|
||||
|
||||
if( (aPad->GetDelta().GetWidth()) != 0 || (aPad->GetDelta().GetHeight() != 0 ) )
|
||||
m_out->Print( 0, " (rect_delta %s )", FMT_IU( aPad->GetDelta() ).c_str() );
|
||||
|
||||
m_out->Print( 0, "\n" );
|
||||
|
||||
wxSize sz = aPad->GetDrillSize();
|
||||
|
||||
if( (sz.GetWidth() > 0) || (sz.GetHeight() > 0) )
|
||||
{
|
||||
m_out->Print( aNestLevel+1, "(drill" );
|
||||
m_out->Print( 0, " (drill" );
|
||||
|
||||
if( aPad->GetDrillShape() == PAD_OVAL )
|
||||
m_out->Print( 0, " oval" );
|
||||
|
@ -775,9 +776,10 @@ void PCB_IO::format( D_PAD* aPad, int aNestLevel ) const
|
|||
if( (aPad->GetOffset().x != 0) || (aPad->GetOffset().y != 0) )
|
||||
m_out->Print( 0, " (offset %s)", FMT_IU( aPad->GetOffset() ).c_str() );
|
||||
|
||||
m_out->Print( 0, ")\n" );
|
||||
m_out->Print( 0, ")" );
|
||||
}
|
||||
|
||||
m_out->Print( 0, "\n" );
|
||||
|
||||
m_out->Print( aNestLevel+1, "(layers" );
|
||||
|
||||
|
@ -787,7 +789,7 @@ void PCB_IO::format( D_PAD* aPad, int aNestLevel ) const
|
|||
{
|
||||
if( layerMask & 1 )
|
||||
{
|
||||
#if USE_LAYER_NAMES
|
||||
#if 1
|
||||
m_out->Print( 0, " %s", m_out->Quotew( m_board->GetLayerName( layer ) ).c_str() );
|
||||
#else
|
||||
m_out->Print( 0, " %d", layer );
|
||||
|
@ -838,10 +840,14 @@ void PCB_IO::format( D_PAD* aPad, int aNestLevel ) const
|
|||
void PCB_IO::format( TEXTE_PCB* aText, int aNestLevel ) const
|
||||
throw( IO_ERROR )
|
||||
{
|
||||
m_out->Print( aNestLevel, "(gr_text %s (at %s %s)",
|
||||
m_out->Print( aNestLevel, "(gr_text %s (at %s",
|
||||
m_out->Quotew( aText->GetText() ).c_str(),
|
||||
FMT_IU( aText->GetPosition() ).c_str(),
|
||||
FMT_ANGLE( aText->GetOrientation() ).c_str() );
|
||||
FMT_IU( aText->GetPosition() ).c_str() );
|
||||
|
||||
if( aText->GetOrientation() != 0.0 )
|
||||
m_out->Print( 0, " %s", FMT_ANGLE( aText->GetOrientation() ).c_str() );
|
||||
|
||||
m_out->Print( 0, ")" );
|
||||
|
||||
formatLayer( aText );
|
||||
|
||||
|
@ -875,11 +881,15 @@ void PCB_IO::format( TEXTE_MODULE* aText, int aNestLevel ) const
|
|||
if( parent )
|
||||
orient += parent->GetOrientation();
|
||||
|
||||
m_out->Print( aNestLevel, "(fp_text %s %s (at %s %s)",
|
||||
m_out->Print( aNestLevel, "(fp_text %s %s (at %s",
|
||||
m_out->Quotew( type ).c_str(),
|
||||
m_out->Quotew( aText->GetText() ).c_str(),
|
||||
FMT_IU( aText->GetPos0() ).c_str(), FMT_ANGLE( orient ).c_str() );
|
||||
FMT_IU( aText->GetPos0() ).c_str() );
|
||||
|
||||
if( orient != 0.0 )
|
||||
m_out->Print( 0, " %s", FMT_ANGLE( orient ).c_str() );
|
||||
|
||||
m_out->Print( 0, ")" );
|
||||
formatLayer( aText );
|
||||
|
||||
if( !aText->IsVisible() )
|
||||
|
@ -898,7 +908,6 @@ void PCB_IO::format( TRACK* aTrack, int aNestLevel ) const
|
|||
{
|
||||
if( aTrack->Type() == PCB_VIA_T )
|
||||
{
|
||||
std::string type;
|
||||
int layer1, layer2;
|
||||
|
||||
SEGVIA* via = (SEGVIA*) aTrack;
|
||||
|
@ -907,25 +916,35 @@ void PCB_IO::format( TRACK* aTrack, int aNestLevel ) const
|
|||
wxCHECK_RET( board != 0, wxT( "Via " ) + via->GetSelectMenuText() +
|
||||
wxT( " has no parent." ) );
|
||||
|
||||
m_out->Print( aNestLevel, "(via" );
|
||||
|
||||
via->ReturnLayerPair( &layer1, &layer2 );
|
||||
|
||||
switch( aTrack->GetShape() )
|
||||
{
|
||||
case VIA_THROUGH: type = "thru"; break;
|
||||
case VIA_BLIND_BURIED: type = "blind"; break;
|
||||
case VIA_MICROVIA: type = "micro"; break;
|
||||
case VIA_THROUGH: // Default shape not saved.
|
||||
break;
|
||||
|
||||
case VIA_BLIND_BURIED:
|
||||
m_out->Print( 0, " blind" );
|
||||
break;
|
||||
|
||||
case VIA_MICROVIA:
|
||||
m_out->Print( 0, " micro" );
|
||||
break;
|
||||
|
||||
default:
|
||||
THROW_IO_ERROR( wxString::Format( _( "unknown via type %d" ), aTrack->GetShape() ) );
|
||||
}
|
||||
|
||||
m_out->Print( aNestLevel, "(via %s (at %s) (size %s)", type.c_str(),
|
||||
m_out->Print( 0, " (at %s) (size %s)",
|
||||
FMT_IU( aTrack->GetStart() ).c_str(),
|
||||
FMT_IU( aTrack->GetWidth() ).c_str() );
|
||||
|
||||
if( aTrack->GetDrill() != UNDEFINED_DRILL_DIAMETER )
|
||||
m_out->Print( 0, " (drill %s)", FMT_IU( aTrack->GetDrill() ).c_str() );
|
||||
|
||||
#if USE_LAYER_NAMES
|
||||
#if 1
|
||||
m_out->Print( 0, " (layers %s %s)",
|
||||
m_out->Quotew( m_board->GetLayerName( layer1 ) ).c_str(),
|
||||
m_out->Quotew( m_board->GetLayerName( layer2 ) ).c_str() );
|
||||
|
@ -939,7 +958,7 @@ void PCB_IO::format( TRACK* aTrack, int aNestLevel ) const
|
|||
FMT_IU( aTrack->GetStart() ).c_str(), FMT_IU( aTrack->GetEnd() ).c_str(),
|
||||
FMT_IU( aTrack->GetWidth() ).c_str() );
|
||||
|
||||
#if USE_LAYER_NAMES
|
||||
#if 1
|
||||
m_out->Print( 0, " (layer %s)", m_out->Quotew( aTrack->GetLayerName() ).c_str() );
|
||||
#else
|
||||
m_out->Print( 0, " (layer %d)", aTrack->GetLayer() );
|
||||
|
@ -985,47 +1004,72 @@ void PCB_IO::format( ZONE_CONTAINER* aZone, int aNestLevel ) const
|
|||
if( aZone->GetPriority() > 0 )
|
||||
m_out->Print( aNestLevel+1, " (priority %d)\n", aZone->GetPriority() );
|
||||
|
||||
// Save pad option and clearance
|
||||
std::string padoption;
|
||||
m_out->Print( aNestLevel+1, "(connect_pads" );
|
||||
|
||||
switch( aZone->GetPadConnection() )
|
||||
{
|
||||
default:
|
||||
case PAD_IN_ZONE: padoption = "yes"; break;
|
||||
case THERMAL_PAD: padoption = "use_thermal"; break;
|
||||
case PAD_NOT_IN_ZONE: padoption = "no"; break;
|
||||
case THERMAL_PAD: // Default option not saved or loaded.
|
||||
break;
|
||||
|
||||
case PAD_IN_ZONE:
|
||||
m_out->Print( 0, " yes" );
|
||||
break;
|
||||
|
||||
case PAD_NOT_IN_ZONE:
|
||||
m_out->Print( 0, " no" );
|
||||
break;
|
||||
}
|
||||
|
||||
m_out->Print( aNestLevel+1, "(connect_pads %s (clearance %s))\n",
|
||||
padoption.c_str(), FMT_IU( aZone->GetZoneClearance() ).c_str() );
|
||||
m_out->Print( 0, " (clearance %s))\n",
|
||||
FMT_IU( aZone->GetZoneClearance() ).c_str() );
|
||||
|
||||
m_out->Print( aNestLevel+1, "(min_thickness %s)\n",
|
||||
FMT_IU( aZone->GetMinThickness() ).c_str() );
|
||||
|
||||
m_out->Print( aNestLevel+1,
|
||||
"(fill %s (mode %s) (arc_segments %d) (thermal_gap %s) (thermal_bridge_width %s)\n",
|
||||
(aZone->IsFilled()) ? "yes" : "no",
|
||||
(aZone->GetFillMode()) ? "segment" : "polygon",
|
||||
m_out->Print( aNestLevel+1, "(fill" );
|
||||
|
||||
// Default is not filled.
|
||||
if( aZone->IsFilled() )
|
||||
m_out->Print( 0, " yes" );
|
||||
|
||||
// Default is polygon filled.
|
||||
if( aZone->GetFillMode() )
|
||||
m_out->Print( 0, " (mode polygon)" );
|
||||
|
||||
m_out->Print( 0, " (arc_segments %d) (thermal_gap %s) (thermal_bridge_width %s)\n",
|
||||
aZone->GetArcSegCount(),
|
||||
FMT_IU( aZone->GetThermalReliefGap() ).c_str(),
|
||||
FMT_IU( aZone->GetThermalReliefCopperBridge() ).c_str() );
|
||||
|
||||
std::string smoothing;
|
||||
|
||||
switch( aZone->GetCornerSmoothingType() )
|
||||
if( aZone->GetCornerSmoothingType() != ZONE_SETTINGS::SMOOTHING_NONE )
|
||||
{
|
||||
case ZONE_SETTINGS::SMOOTHING_NONE: smoothing = "none"; break;
|
||||
case ZONE_SETTINGS::SMOOTHING_CHAMFER: smoothing = "chamfer"; break;
|
||||
case ZONE_SETTINGS::SMOOTHING_FILLET: smoothing = "fillet"; break;
|
||||
default:
|
||||
THROW_IO_ERROR( wxString::Format( _( "unknown zone corner smoothing type %d" ),
|
||||
aZone->GetCornerSmoothingType() ) );
|
||||
m_out->Print( aNestLevel+1, "(smoothing" );
|
||||
|
||||
switch( aZone->GetCornerSmoothingType() )
|
||||
{
|
||||
case ZONE_SETTINGS::SMOOTHING_CHAMFER:
|
||||
m_out->Print( 0, " chamfer" );
|
||||
break;
|
||||
|
||||
case ZONE_SETTINGS::SMOOTHING_FILLET:
|
||||
m_out->Print( 0, " fillet" );
|
||||
break;
|
||||
|
||||
default:
|
||||
THROW_IO_ERROR( wxString::Format( _( "unknown zone corner smoothing type %d" ),
|
||||
aZone->GetCornerSmoothingType() ) );
|
||||
}
|
||||
|
||||
if( aZone->GetCornerRadius() != 0 )
|
||||
m_out->Print( aNestLevel+1, " (radius %s))\n",
|
||||
FMT_IU( aZone->GetCornerRadius() ).c_str() );
|
||||
}
|
||||
|
||||
m_out->Print( aNestLevel+1, "(smoothing %s) (radius %s))\n",
|
||||
smoothing.c_str(), FMT_IU( aZone->GetCornerRadius() ).c_str() );
|
||||
m_out->Print( 0, ")\n" );
|
||||
|
||||
const std::vector< CPolyPt >& cv = aZone->m_Poly->corner;
|
||||
int newLine = 0;
|
||||
|
||||
if( cv.size() )
|
||||
{
|
||||
|
@ -1034,18 +1078,36 @@ void PCB_IO::format( ZONE_CONTAINER* aZone, int aNestLevel ) const
|
|||
|
||||
for( std::vector< CPolyPt >::const_iterator it = cv.begin(); it != cv.end(); ++it )
|
||||
{
|
||||
m_out->Print( aNestLevel+3, "(xy %s %s)\n",
|
||||
FMT_IU( it->x ).c_str(), FMT_IU( it->y ).c_str() );
|
||||
if( newLine == 0 )
|
||||
m_out->Print( aNestLevel+3, "(xy %s %s)",
|
||||
FMT_IU( it->x ).c_str(), FMT_IU( it->y ).c_str() );
|
||||
else
|
||||
m_out->Print( 0, " (xy %s %s)",
|
||||
FMT_IU( it->x ).c_str(), FMT_IU( it->y ).c_str() );
|
||||
|
||||
if( newLine < 4 )
|
||||
{
|
||||
newLine += 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
newLine = 0;
|
||||
m_out->Print( 0, "\n" );
|
||||
}
|
||||
|
||||
if( it->end_contour )
|
||||
{
|
||||
if( newLine != 0 )
|
||||
m_out->Print( 0, "\n" );
|
||||
|
||||
m_out->Print( aNestLevel+2, ")\n" );
|
||||
|
||||
if( it+1 != cv.end() )
|
||||
{
|
||||
newLine = 0;
|
||||
m_out->Print( aNestLevel+1, ")\n" );
|
||||
m_out->Print( aNestLevel+1, "(polygon\n" );
|
||||
m_out->Print( aNestLevel+2, "(pts\n" );
|
||||
m_out->Print( aNestLevel+2, "(pts" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1055,6 +1117,7 @@ void PCB_IO::format( ZONE_CONTAINER* aZone, int aNestLevel ) const
|
|||
|
||||
// Save the PolysList
|
||||
const std::vector< CPolyPt >& fv = aZone->GetFilledPolysList();
|
||||
newLine = 0;
|
||||
|
||||
if( fv.size() )
|
||||
{
|
||||
|
@ -1063,15 +1126,33 @@ void PCB_IO::format( ZONE_CONTAINER* aZone, int aNestLevel ) const
|
|||
|
||||
for( std::vector< CPolyPt >::const_iterator it = fv.begin(); it != fv.end(); ++it )
|
||||
{
|
||||
m_out->Print( aNestLevel+3, "(xy %s %s)\n",
|
||||
FMT_IU( it->x ).c_str(), FMT_IU( it->y ).c_str() );
|
||||
if( newLine == 0 )
|
||||
m_out->Print( aNestLevel+3, "(xy %s %s)",
|
||||
FMT_IU( it->x ).c_str(), FMT_IU( it->y ).c_str() );
|
||||
else
|
||||
m_out->Print( 0, " (xy %s %s)",
|
||||
FMT_IU( it->x ).c_str(), FMT_IU( it->y ).c_str() );
|
||||
|
||||
if( newLine < 4 )
|
||||
{
|
||||
newLine += 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
newLine = 0;
|
||||
m_out->Print( 0, "\n" );
|
||||
}
|
||||
|
||||
if( it->end_contour )
|
||||
{
|
||||
if( newLine != 0 )
|
||||
m_out->Print( 0, "\n" );
|
||||
|
||||
m_out->Print( aNestLevel+2, ")\n" );
|
||||
|
||||
if( it+1 != fv.end() )
|
||||
{
|
||||
newLine = 0;
|
||||
m_out->Print( aNestLevel+1, ")\n" );
|
||||
m_out->Print( aNestLevel+1, "(filled_polygon\n" );
|
||||
m_out->Print( aNestLevel+2, "(pts\n" );
|
||||
|
|
|
@ -301,6 +301,7 @@ BOARD_ITEM* PCB_PARSER::Parse() throw( IO_ERROR, PARSE_ERROR )
|
|||
{
|
||||
T token;
|
||||
BOARD_ITEM* item;
|
||||
LOCALE_IO toggle; // toggles on, then off, the C locale.
|
||||
|
||||
token = NextTok();
|
||||
|
||||
|
@ -617,19 +618,18 @@ void PCB_PARSER::parseLayers() throw( IO_ERROR, PARSE_ERROR )
|
|||
T token;
|
||||
wxString name;
|
||||
wxString type;
|
||||
int layerIndex;
|
||||
bool isVisible = true;
|
||||
int visibleLayers = 0;
|
||||
int enabledLayers = 0;
|
||||
std::vector< LAYER > layers;
|
||||
int copperLayerCount = 0;
|
||||
|
||||
for( token = NextTok(); token != T_RIGHT; token = NextTok() )
|
||||
{
|
||||
if( token != T_LEFT )
|
||||
Expecting( T_LEFT );
|
||||
|
||||
#if !USE_LAYER_NAMES
|
||||
NeedNUMBER( "layer index" );
|
||||
#endif
|
||||
layerIndex = parseInt( "layer index" );
|
||||
|
||||
NeedSYMBOL();
|
||||
name = FromUTF8();
|
||||
|
@ -652,14 +652,20 @@ void PCB_PARSER::parseLayers() throw( IO_ERROR, PARSE_ERROR )
|
|||
Expecting( "hide or )" );
|
||||
}
|
||||
|
||||
layers.push_back( LAYER( name, LAYER::ParseType( TO_UTF8( type ) ), isVisible ) );
|
||||
}
|
||||
enabledLayers |= 1 << layerIndex;
|
||||
|
||||
int copperLayerCount = 0;
|
||||
if( isVisible )
|
||||
visibleLayers |= 1 << layerIndex;
|
||||
|
||||
for( unsigned i = 0; i < layers.size(); i++ )
|
||||
{
|
||||
if( layers[i].m_Type != LT_UNDEFINED )
|
||||
enum LAYER_T layerType = LAYER::ParseType( TO_UTF8( type ) );
|
||||
LAYER layer( name, layerType, isVisible );
|
||||
layer.SetFixedListIndex( layerIndex );
|
||||
m_board->SetLayer( layerIndex, layer );
|
||||
m_layerMap[ name ] = layerIndex;
|
||||
wxLogDebug( wxT( "Mapping layer %s index index %d" ),
|
||||
GetChars( name ), layerIndex );
|
||||
|
||||
if( layerType != LT_UNDEFINED )
|
||||
copperLayerCount++;
|
||||
}
|
||||
|
||||
|
@ -667,54 +673,11 @@ void PCB_PARSER::parseLayers() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( (copperLayerCount < 2) || ((copperLayerCount % 2) != 0) )
|
||||
{
|
||||
wxString err;
|
||||
err.Printf( _( "%d is not a valid layer count" ), layers.size() );
|
||||
err.Printf( _( "%d is not a valid layer count" ), copperLayerCount );
|
||||
THROW_PARSE_ERROR( err, CurSource(), CurLine(), CurLineNumber(), CurOffset() );
|
||||
}
|
||||
|
||||
m_board->SetCopperLayerCount( copperLayerCount );
|
||||
|
||||
// Copper layers are sequential from front to back in the file but the current layer
|
||||
// design uses sequential layers from back to front except for the front layer which
|
||||
// is always vector index 15.
|
||||
for( unsigned i = 0; i < layers.size(); i++ )
|
||||
{
|
||||
int layerIndex = i;
|
||||
|
||||
// The copper layers can have different names but they always are at the beginning
|
||||
// and have a valid layer type. Non-copper layer name cannot be changed so the
|
||||
// list index can be looked up by name.
|
||||
if( layers[i].m_Type != LT_UNDEFINED )
|
||||
{
|
||||
if( i == 0 )
|
||||
layerIndex = LAYER_N_FRONT;
|
||||
else
|
||||
layerIndex = copperLayerCount - 1 - i;
|
||||
}
|
||||
else
|
||||
{
|
||||
layerIndex = LAYER::GetDefaultIndex( layers[i].m_Name );
|
||||
|
||||
if( layerIndex == UNDEFINED_LAYER )
|
||||
{
|
||||
wxString error;
|
||||
error.Printf( _( "Cannot determine fixed layer list index of layer name \"%s\"" ),
|
||||
GetChars( layers[i].m_Name ) );
|
||||
THROW_IO_ERROR( error );
|
||||
}
|
||||
}
|
||||
|
||||
enabledLayers |= 1 << layerIndex;
|
||||
|
||||
if( layers[i].IsVisible() )
|
||||
visibleLayers |= 1 << layerIndex;
|
||||
|
||||
layers[i].SetFixedListIndex( layerIndex );
|
||||
m_board->SetLayer( layerIndex, layers[i] );
|
||||
m_layerMap[ layers[i].m_Name ] = layerIndex;
|
||||
wxLogDebug( wxT( "Mapping layer %s index index %d" ),
|
||||
GetChars( layers[i].m_Name ), layerIndex );
|
||||
}
|
||||
|
||||
m_board->SetVisibleLayers( visibleLayers );
|
||||
m_board->SetEnabledLayers( enabledLayers );
|
||||
}
|
||||
|
@ -1119,7 +1082,7 @@ DRAWSEGMENT* PCB_PARSER::parseDRAWSEGMENT() throw( IO_ERROR, PARSE_ERROR )
|
|||
wxT( "Cannot parse " ) + GetTokenString( CurTok() ) + wxT( " as DRAWSEGMENT." ) );
|
||||
|
||||
T token;
|
||||
|
||||
wxPoint pt;
|
||||
auto_ptr< DRAWSEGMENT > segment( new DRAWSEGMENT( NULL ) );
|
||||
|
||||
switch( CurTok() )
|
||||
|
@ -1132,7 +1095,9 @@ DRAWSEGMENT* PCB_PARSER::parseDRAWSEGMENT() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( token != T_start )
|
||||
Expecting( T_start );
|
||||
|
||||
segment->SetStart( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetStart( pt );
|
||||
NeedRIGHT();
|
||||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
@ -1140,14 +1105,9 @@ DRAWSEGMENT* PCB_PARSER::parseDRAWSEGMENT() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( token != T_end )
|
||||
Expecting( T_end );
|
||||
|
||||
segment->SetEnd( parseXY() );
|
||||
NeedRIGHT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_angle )
|
||||
Expecting( T_angle );
|
||||
|
||||
segment->SetAngle( parseDouble( "segment angle" ) );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetEnd( pt );
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
|
@ -1159,15 +1119,20 @@ DRAWSEGMENT* PCB_PARSER::parseDRAWSEGMENT() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( token != T_center )
|
||||
Expecting( T_center );
|
||||
|
||||
segment->SetStart( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetStart( pt );
|
||||
NeedRIGHT();
|
||||
NeedLEFT();
|
||||
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_end )
|
||||
Expecting( T_end );
|
||||
|
||||
segment->SetEnd( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetEnd( pt );
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
|
@ -1191,19 +1156,22 @@ DRAWSEGMENT* PCB_PARSER::parseDRAWSEGMENT() throw( IO_ERROR, PARSE_ERROR )
|
|||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_pts )
|
||||
Expecting( T_pts );
|
||||
if( token != T_start )
|
||||
Expecting( T_start );
|
||||
|
||||
segment->SetStart( parseXY() );
|
||||
segment->SetEnd( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetStart( pt );
|
||||
NeedRIGHT();
|
||||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_angle )
|
||||
Expecting( T_angle );
|
||||
if( token != T_end )
|
||||
Expecting( T_end );
|
||||
|
||||
segment->SetAngle( parseDouble( "segment angle" ) * 10.0 );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetEnd( pt );
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
|
@ -1238,6 +1206,10 @@ DRAWSEGMENT* PCB_PARSER::parseDRAWSEGMENT() throw( IO_ERROR, PARSE_ERROR )
|
|||
|
||||
switch( token )
|
||||
{
|
||||
case T_angle:
|
||||
segment->SetAngle( parseDouble( "segment angle" ) * 10.0 );
|
||||
break;
|
||||
|
||||
case T_layer:
|
||||
segment->SetLayer( parseBoardItemLayer() );
|
||||
break;
|
||||
|
@ -1287,8 +1259,19 @@ TEXTE_PCB* PCB_PARSER::parseTEXTE_PCB() throw( IO_ERROR, PARSE_ERROR )
|
|||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
text->SetPosition( pt );
|
||||
text->SetOrientation( parseDouble( "angle" ) * 10.0 );
|
||||
NeedRIGHT();
|
||||
|
||||
// If there is no orientation defined, then it is the default value of 0 degrees.
|
||||
token = NextTok();
|
||||
|
||||
if( token == T_NUMBER )
|
||||
{
|
||||
text->SetOrientation( parseDouble() * 10.0 );
|
||||
NeedRIGHT();
|
||||
}
|
||||
else if( token != T_RIGHT )
|
||||
{
|
||||
Unexpected( CurText() );
|
||||
}
|
||||
|
||||
for( token = NextTok(); token != T_RIGHT; token = NextTok() )
|
||||
{
|
||||
|
@ -1725,8 +1708,18 @@ TEXTE_MODULE* PCB_PARSER::parseTEXTE_MODULE() throw( IO_ERROR, PARSE_ERROR )
|
|||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
text->SetPos0( pt );
|
||||
text->SetOrientation( parseDouble( "angle" ) * 10.0 );
|
||||
NeedRIGHT();
|
||||
token = NextTok();
|
||||
|
||||
// If there is no orientation defined, then it is the default value of 0 degrees.
|
||||
if( token == T_NUMBER )
|
||||
{
|
||||
text->SetOrientation( parseDouble() * 10.0 );
|
||||
NeedRIGHT();
|
||||
}
|
||||
else if( token != T_RIGHT )
|
||||
{
|
||||
Unexpected( CurText() );
|
||||
}
|
||||
|
||||
for( token = NextTok(); token != T_RIGHT; token = NextTok() )
|
||||
{
|
||||
|
@ -1763,6 +1756,7 @@ EDGE_MODULE* PCB_PARSER::parseEDGE_MODULE() throw( IO_ERROR, PARSE_ERROR )
|
|||
CurTok() == T_fp_line || CurTok() == T_fp_poly, NULL,
|
||||
wxT( "Cannot parse " ) + GetTokenString( CurTok() ) + wxT( " as EDGE_MODULE." ) );
|
||||
|
||||
wxPoint pt;
|
||||
T token;
|
||||
|
||||
auto_ptr< EDGE_MODULE > segment( new EDGE_MODULE( NULL ) );
|
||||
|
@ -1777,15 +1771,20 @@ EDGE_MODULE* PCB_PARSER::parseEDGE_MODULE() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( token != T_start )
|
||||
Expecting( T_start );
|
||||
|
||||
segment->SetStart0( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetStart0( pt );
|
||||
NeedRIGHT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_end )
|
||||
Expecting( T_end );
|
||||
|
||||
segment->SetEnd0( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetEnd0( pt );
|
||||
NeedRIGHT();
|
||||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_angle )
|
||||
|
@ -1803,7 +1802,9 @@ EDGE_MODULE* PCB_PARSER::parseEDGE_MODULE() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( token != T_center )
|
||||
Expecting( T_center );
|
||||
|
||||
segment->SetStart0( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetStart0( pt );
|
||||
NeedRIGHT();
|
||||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
@ -1811,7 +1812,9 @@ EDGE_MODULE* PCB_PARSER::parseEDGE_MODULE() throw( IO_ERROR, PARSE_ERROR )
|
|||
if( token != T_end )
|
||||
Expecting( T_end );
|
||||
|
||||
segment->SetEnd0( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetEnd0( pt );
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
|
@ -1835,11 +1838,23 @@ EDGE_MODULE* PCB_PARSER::parseEDGE_MODULE() throw( IO_ERROR, PARSE_ERROR )
|
|||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_pts )
|
||||
Expecting( T_pts );
|
||||
if( token != T_start )
|
||||
Expecting( T_start );
|
||||
|
||||
segment->SetStart0( parseXY() );
|
||||
segment->SetEnd0( parseXY() );
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetStart0( pt );
|
||||
|
||||
NeedRIGHT();
|
||||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_end )
|
||||
Expecting( T_end );
|
||||
|
||||
pt.x = parseBoardUnits( "X coordinate" );
|
||||
pt.y = parseBoardUnits( "Y coordinate" );
|
||||
segment->SetEnd0( pt );
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
|
@ -1945,7 +1960,7 @@ D_PAD* PCB_PARSER::parseD_PAD() throw( IO_ERROR, PARSE_ERROR )
|
|||
pad->SetShape( PAD_CIRCLE );
|
||||
break;
|
||||
|
||||
case T_rectangle:
|
||||
case T_rect:
|
||||
pad->SetShape( PAD_RECT );
|
||||
break;
|
||||
|
||||
|
@ -2203,10 +2218,6 @@ SEGVIA* PCB_PARSER::parseSEGVIA() throw( IO_ERROR, PARSE_ERROR )
|
|||
|
||||
switch( token )
|
||||
{
|
||||
case T_thru:
|
||||
via->SetShape( VIA_THROUGH );
|
||||
break;
|
||||
|
||||
case T_blind:
|
||||
via->SetShape( VIA_BLIND_BURIED );
|
||||
break;
|
||||
|
@ -2261,7 +2272,7 @@ SEGVIA* PCB_PARSER::parseSEGVIA() throw( IO_ERROR, PARSE_ERROR )
|
|||
break;
|
||||
|
||||
default:
|
||||
Expecting( "at, size, drill, layers, net, tstamp, or status" );
|
||||
Expecting( "blind, micro, at, size, drill, layers, net, tstamp, or status" );
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2339,25 +2350,31 @@ ZONE_CONTAINER* PCB_PARSER::parseZONE_CONTAINER() throw( IO_ERROR, PARSE_ERROR )
|
|||
break;
|
||||
|
||||
case T_connect_pads:
|
||||
token = NextTok();
|
||||
|
||||
switch( token )
|
||||
for( token = NextTok(); token != T_RIGHT; token = NextTok() )
|
||||
{
|
||||
case T_yes: zone->SetPadConnection( PAD_IN_ZONE ); break;
|
||||
case T_use_thermal: zone->SetPadConnection( THERMAL_PAD ); break;
|
||||
case T_no: zone->SetPadConnection( PAD_NOT_IN_ZONE ); break;
|
||||
default: Expecting( "yes, no, or use_thermal" );
|
||||
if( token == T_LEFT )
|
||||
token = NextTok();
|
||||
|
||||
switch( token )
|
||||
{
|
||||
case T_yes:
|
||||
zone->SetPadConnection( PAD_IN_ZONE );
|
||||
break;
|
||||
|
||||
case T_no:
|
||||
zone->SetPadConnection( PAD_NOT_IN_ZONE );
|
||||
break;
|
||||
|
||||
case T_clearance:
|
||||
zone->SetZoneClearance( parseBoardUnits( "zone clearance" ) );
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
default:
|
||||
Expecting( "yes, no, or clearance" );
|
||||
}
|
||||
}
|
||||
|
||||
NeedLEFT();
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_clearance )
|
||||
Expecting( T_clearance );
|
||||
|
||||
zone->SetZoneClearance( parseBoardUnits( "zone clearance" ) );
|
||||
NeedRIGHT();
|
||||
NeedRIGHT();
|
||||
break;
|
||||
|
||||
case T_min_thickness:
|
||||
|
@ -2366,22 +2383,17 @@ ZONE_CONTAINER* PCB_PARSER::parseZONE_CONTAINER() throw( IO_ERROR, PARSE_ERROR )
|
|||
break;
|
||||
|
||||
case T_fill:
|
||||
token = NextTok();
|
||||
|
||||
if( token != T_yes && token != T_no )
|
||||
Expecting( "yes or no" );
|
||||
|
||||
zone->SetIsFilled( token == T_yes );
|
||||
|
||||
for( token = NextTok(); token != T_RIGHT; token = NextTok() )
|
||||
{
|
||||
if( token != T_LEFT )
|
||||
Expecting( T_LEFT );
|
||||
|
||||
token = NextTok();
|
||||
if( token == T_LEFT )
|
||||
token = NextTok();
|
||||
|
||||
switch( token )
|
||||
{
|
||||
case T_yes:
|
||||
zone->SetIsFilled( true );
|
||||
break;
|
||||
|
||||
case T_mode:
|
||||
token = NextTok();
|
||||
|
||||
|
|
Loading…
Reference in New Issue