Gerbview: Aperture Macro: handle overwriting of variables
Gerbview did not handle redefinition of variable like $3 = $3 / 2 This redefinition is sometimes found in Gerber files. This is a long standing issue now fixed. Fixes #7222 https://gitlab.com/kicad/code/kicad/issues/7222
This commit is contained in:
parent
eb240fda9a
commit
54b4f0e673
|
@ -69,7 +69,8 @@ bool AM_PARAM::IsImmediate() const
|
||||||
return is_immediate;
|
return is_immediate;
|
||||||
}
|
}
|
||||||
|
|
||||||
double AM_PARAM::GetValue( const D_CODE* aDcode ) const
|
|
||||||
|
double AM_PARAM::GetValueFromMacro( APERTURE_MACRO* aApertureMacro ) const
|
||||||
{
|
{
|
||||||
// In macros, actual values are sometimes given by an expression like:
|
// In macros, actual values are sometimes given by an expression like:
|
||||||
// 0-$2/2-$4
|
// 0-$2/2-$4
|
||||||
|
@ -102,22 +103,15 @@ double AM_PARAM::GetValue( const D_CODE* aDcode ) const
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PUSHPARM:
|
case PUSHPARM:
|
||||||
// a defered value: get the actual parameter from the aDcode
|
// a defered value: get the actual parameter from the aperture macro
|
||||||
if( aDcode ) // should be always true here
|
if( aApertureMacro ) // should be always true here
|
||||||
{
|
{
|
||||||
if( item.GetIndex() <= aDcode->GetParamCount() )
|
// Get the actual value
|
||||||
{
|
curr_value = aApertureMacro->GetLocalParamValue( item.GetIndex() );
|
||||||
curr_value = aDcode->GetParam( item.GetIndex() );
|
|
||||||
}
|
|
||||||
else // Get parameter from local param definition
|
|
||||||
{
|
|
||||||
const APERTURE_MACRO * am_parent = aDcode->GetMacro();
|
|
||||||
curr_value = am_parent->GetLocalParam( aDcode, item.GetIndex() );
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
wxFAIL_MSG( wxT( "AM_PARAM::GetValue(): NULL param aDcode" ) );
|
wxFAIL_MSG( wxT( "AM_PARAM::GetValue(): NULL param aApertureMacro" ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
ops.emplace_back( curr_value );
|
ops.emplace_back( curr_value );
|
||||||
|
@ -129,10 +123,8 @@ double AM_PARAM::GetValue( const D_CODE* aDcode ) const
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
wxFAIL_MSG( wxString::Format( wxT( "AM_PARAM::GetValue(): dcode %d prm %d/%d: "
|
wxFAIL_MSG( wxString::Format( wxT( "AM_PARAM::GetValue(): unexpected prm type %d" ),
|
||||||
"unexpected type %d" ),
|
item.GetType() ) );
|
||||||
aDcode ? aDcode->m_Num_Dcode : -1, ii,
|
|
||||||
m_paramStack.size(), item.GetType() ) );
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -142,6 +134,7 @@ double AM_PARAM::GetValue( const D_CODE* aDcode ) const
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* add an operator/operand to the current stack
|
* add an operator/operand to the current stack
|
||||||
* aType = NOP, PUSHVALUE, PUSHPARM, ADD, SUB, MUL, DIV, EQUATE
|
* aType = NOP, PUSHVALUE, PUSHPARM, ADD, SUB, MUL, DIV, EQUATE
|
||||||
|
|
|
@ -295,7 +295,7 @@ public:
|
||||||
void PushOperator( parm_item_type aType, double aValue );
|
void PushOperator( parm_item_type aType, double aValue );
|
||||||
void PushOperator( parm_item_type aType, int aValue = 0);
|
void PushOperator( parm_item_type aType, int aValue = 0);
|
||||||
|
|
||||||
double GetValue( const D_CODE* aDcode ) const;
|
double GetValueFromMacro( APERTURE_MACRO* aApertureMacro ) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test if this AM_PARAM holds an immediate parameter or is a pointer into a parameter held
|
* Test if this AM_PARAM holds an immediate parameter or is a pointer into a parameter held
|
||||||
|
|
|
@ -55,7 +55,7 @@ static VECTOR2I mapPt( double x, double y, bool isMetric )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool AM_PRIMITIVE::IsAMPrimitiveExposureOn( const D_CODE* aDcode ) const
|
bool AM_PRIMITIVE::IsAMPrimitiveExposureOn( APERTURE_MACRO* aApertMacro ) const
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
* Some but not all primitives use the first parameter as an exposure control.
|
* Some but not all primitives use the first parameter as an exposure control.
|
||||||
|
@ -75,7 +75,7 @@ bool AM_PRIMITIVE::IsAMPrimitiveExposureOn( const D_CODE* aDcode ) const
|
||||||
case AMP_OUTLINE:
|
case AMP_OUTLINE:
|
||||||
case AMP_POLYGON:
|
case AMP_POLYGON:
|
||||||
// All have an exposure parameter and can return a value (0 or 1)
|
// All have an exposure parameter and can return a value (0 or 1)
|
||||||
return m_Params[0].GetValue( aDcode ) != 0;
|
return m_Params[0].GetValueFromMacro( aApertMacro ) != 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case AMP_THERMAL: // Exposure is always on
|
case AMP_THERMAL: // Exposure is always on
|
||||||
|
@ -88,11 +88,7 @@ bool AM_PRIMITIVE::IsAMPrimitiveExposureOn( const D_CODE* aDcode ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO(snh): Remove hard coded count
|
void AM_PRIMITIVE::ConvertBasicShapeToPolygon( APERTURE_MACRO* aApertMacro,
|
||||||
const int seg_per_circle = 64; // Number of segments to approximate a circle
|
|
||||||
|
|
||||||
|
|
||||||
void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
|
||||||
SHAPE_POLY_SET& aShapeBuffer )
|
SHAPE_POLY_SET& aShapeBuffer )
|
||||||
{
|
{
|
||||||
// Draw the primitive shape for flashed items.
|
// Draw the primitive shape for flashed items.
|
||||||
|
@ -100,7 +96,7 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
static std::vector<VECTOR2I> polybuffer;
|
static std::vector<VECTOR2I> polybuffer;
|
||||||
polybuffer.clear();
|
polybuffer.clear();
|
||||||
|
|
||||||
const D_CODE* tool = aDcode;
|
aApertMacro->EvalLocalParams( *this );
|
||||||
|
|
||||||
switch( m_Primitive_id )
|
switch( m_Primitive_id )
|
||||||
{
|
{
|
||||||
|
@ -112,12 +108,12 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* <rotation> is a optional parameter: rotation from origin.
|
* <rotation> is a optional parameter: rotation from origin.
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
ConvertShapeToPolygon( tool, polybuffer );
|
ConvertShapeToPolygon( aApertMacro, polybuffer );
|
||||||
|
|
||||||
// shape rotation (if any):
|
// shape rotation (if any):
|
||||||
if( m_Params.size() >= 5 )
|
if( m_Params.size() >= 5 )
|
||||||
{
|
{
|
||||||
EDA_ANGLE rotation( m_Params[4].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[4].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
if( !rotation.IsZero() )
|
if( !rotation.IsZero() )
|
||||||
{
|
{
|
||||||
|
@ -141,10 +137,10 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* type (2), exposure, width, start.x, start.y, end.x, end.y, rotation
|
* type (2), exposure, width, start.x, start.y, end.x, end.y, rotation
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
ConvertShapeToPolygon( tool, polybuffer );
|
ConvertShapeToPolygon( aApertMacro, polybuffer );
|
||||||
|
|
||||||
// shape rotation:
|
// shape rotation:
|
||||||
EDA_ANGLE rotation( m_Params[6].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[6].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
if( !rotation.IsZero() )
|
if( !rotation.IsZero() )
|
||||||
{
|
{
|
||||||
|
@ -165,10 +161,10 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* type (21), exposure, ,width, height, center pos.x, center pos.y, rotation
|
* type (21), exposure, ,width, height, center pos.x, center pos.y, rotation
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
ConvertShapeToPolygon( tool, polybuffer );
|
ConvertShapeToPolygon( aApertMacro, polybuffer );
|
||||||
|
|
||||||
// shape rotation:
|
// shape rotation:
|
||||||
EDA_ANGLE rotation( m_Params[5].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[5].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
if( !rotation.IsZero() )
|
if( !rotation.IsZero() )
|
||||||
{
|
{
|
||||||
|
@ -186,10 +182,10 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* type (22), exposure, ,width, height, corner pos.x, corner pos.y, rotation
|
* type (22), exposure, ,width, height, corner pos.x, corner pos.y, rotation
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
ConvertShapeToPolygon( tool, polybuffer );
|
ConvertShapeToPolygon( aApertMacro, polybuffer );
|
||||||
|
|
||||||
// shape rotation:
|
// shape rotation:
|
||||||
EDA_ANGLE rotation( m_Params[5].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[5].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
if( !rotation.IsZero() )
|
if( !rotation.IsZero() )
|
||||||
{
|
{
|
||||||
|
@ -210,12 +206,12 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* on.
|
* on.
|
||||||
*/
|
*/
|
||||||
std::vector<VECTOR2I> subshape_poly;
|
std::vector<VECTOR2I> subshape_poly;
|
||||||
VECTOR2I center( mapPt( m_Params[0].GetValue( tool ),
|
VECTOR2I center( mapPt( m_Params[0].GetValueFromMacro( aApertMacro ),
|
||||||
m_Params[1].GetValue( tool ), m_GerbMetric ) );
|
m_Params[1].GetValueFromMacro( aApertMacro ), m_GerbMetric ) );
|
||||||
ConvertShapeToPolygon( tool, subshape_poly );
|
ConvertShapeToPolygon( aApertMacro, subshape_poly );
|
||||||
|
|
||||||
// shape rotation:
|
// shape rotation:
|
||||||
EDA_ANGLE rotation( m_Params[5].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[5].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
// Because a thermal shape has 4 identical sub-shapes, only one is created in subshape_poly.
|
// Because a thermal shape has 4 identical sub-shapes, only one is created in subshape_poly.
|
||||||
// We must draw 4 sub-shapes rotated by 90 deg
|
// We must draw 4 sub-shapes rotated by 90 deg
|
||||||
|
@ -256,17 +252,17 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* crosshair len, rotation. The type is not stored in parameters list, so the first
|
* crosshair len, rotation. The type is not stored in parameters list, so the first
|
||||||
* parameter is pos.x.
|
* parameter is pos.x.
|
||||||
*/
|
*/
|
||||||
int outerDiam = scaletoIU( m_Params[2].GetValue( tool ), m_GerbMetric );
|
int outerDiam = scaletoIU( m_Params[2].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
int penThickness = scaletoIU( m_Params[3].GetValue( tool ), m_GerbMetric );
|
int penThickness = scaletoIU( m_Params[3].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
int gap = scaletoIU( m_Params[4].GetValue( tool ), m_GerbMetric );
|
int gap = scaletoIU( m_Params[4].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
int numCircles = KiROUND( m_Params[5].GetValue( tool ) );
|
int numCircles = KiROUND( m_Params[5].GetValueFromMacro( aApertMacro ) );
|
||||||
|
|
||||||
// Adjust the allowed approx error to convert arcs to segments:
|
// Adjust the allowed approx error to convert arcs to segments:
|
||||||
int arc_to_seg_error = gerbIUScale.mmToIU( 0.005 ); // Allow 5 microns
|
int arc_to_seg_error = gerbIUScale.mmToIU( 0.005 ); // Allow 5 microns
|
||||||
|
|
||||||
// Draw circles @ position pos.x, pos.y given by the tool:
|
// Draw circles @ position pos.x, pos.y given by the tool:
|
||||||
VECTOR2I center( mapPt( m_Params[0].GetValue( tool ), m_Params[1].GetValue( tool ),
|
VECTOR2I center( mapPt( m_Params[0].GetValueFromMacro( aApertMacro ),
|
||||||
m_GerbMetric ) );
|
m_Params[1].GetValueFromMacro( aApertMacro ), m_GerbMetric ) );
|
||||||
|
|
||||||
// adjust outerDiam by this on each nested circle
|
// adjust outerDiam by this on each nested circle
|
||||||
int diamAdjust = ( gap + penThickness ) * 2;
|
int diamAdjust = ( gap + penThickness ) * 2;
|
||||||
|
@ -292,9 +288,9 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
}
|
}
|
||||||
|
|
||||||
// Draw the cross:
|
// Draw the cross:
|
||||||
ConvertShapeToPolygon( tool, polybuffer );
|
ConvertShapeToPolygon( aApertMacro, polybuffer );
|
||||||
|
|
||||||
EDA_ANGLE rotation( m_Params[8].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[8].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
|
for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
|
||||||
{
|
{
|
||||||
|
@ -325,11 +321,11 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
// m_Params[0] is the exposure and m_Params[1] is the corners count after the first corner
|
// m_Params[0] is the exposure and m_Params[1] is the corners count after the first corner
|
||||||
int numCorners = (int) m_Params[1].GetValue( tool );
|
int numCorners = (int) m_Params[1].GetValueFromMacro( aApertMacro );
|
||||||
|
|
||||||
// the shape rotation is the last param of list, after corners
|
// the shape rotation is the last param of list, after corners
|
||||||
int last_prm = m_Params.size() - 1;
|
int last_prm = m_Params.size() - 1;
|
||||||
EDA_ANGLE rotation( m_Params[last_prm].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[last_prm].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
VECTOR2I pos;
|
VECTOR2I pos;
|
||||||
|
|
||||||
// Read points.
|
// Read points.
|
||||||
|
@ -340,9 +336,9 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
|
|
||||||
for( int i = 0; i <= numCorners; ++i )
|
for( int i = 0; i <= numCorners; ++i )
|
||||||
{
|
{
|
||||||
pos.x = scaletoIU( m_Params[prm_idx].GetValue( tool ), m_GerbMetric );
|
pos.x = scaletoIU( m_Params[prm_idx].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
prm_idx++;
|
prm_idx++;
|
||||||
pos.y = scaletoIU( m_Params[prm_idx].GetValue( tool ), m_GerbMetric );
|
pos.y = scaletoIU( m_Params[prm_idx].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
prm_idx++;
|
prm_idx++;
|
||||||
polybuffer.push_back(pos);
|
polybuffer.push_back(pos);
|
||||||
|
|
||||||
|
@ -373,13 +369,14 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
* type(5), exposure, vertices count, pox.x, pos.y, diameter, rotation
|
* type(5), exposure, vertices count, pox.x, pos.y, diameter, rotation
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
VECTOR2I curPos( mapPt( m_Params[2].GetValue( tool ), m_Params[3].GetValue( tool ), m_GerbMetric ) );
|
VECTOR2I curPos( mapPt( m_Params[2].GetValueFromMacro( aApertMacro ),
|
||||||
|
m_Params[3].GetValueFromMacro( aApertMacro ), m_GerbMetric ) );
|
||||||
|
|
||||||
// Creates the shape:
|
// Creates the shape:
|
||||||
ConvertShapeToPolygon( tool, polybuffer );
|
ConvertShapeToPolygon( aApertMacro, polybuffer );
|
||||||
|
|
||||||
// rotate polygon
|
// rotate polygon
|
||||||
EDA_ANGLE rotation( m_Params[5].GetValue( tool ), DEGREES_T );
|
EDA_ANGLE rotation( m_Params[5].GetValueFromMacro( aApertMacro ), DEGREES_T );
|
||||||
|
|
||||||
for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
|
for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
|
||||||
{
|
{
|
||||||
|
@ -408,11 +405,9 @@ void AM_PRIMITIVE::ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
void AM_PRIMITIVE::ConvertShapeToPolygon( APERTURE_MACRO* aApertMacro,
|
||||||
std::vector<VECTOR2I>& aBuffer )
|
std::vector<VECTOR2I>& aBuffer )
|
||||||
{
|
{
|
||||||
const D_CODE* tool = aDcode;
|
|
||||||
|
|
||||||
switch( m_Primitive_id )
|
switch( m_Primitive_id )
|
||||||
{
|
{
|
||||||
case AMP_CIRCLE:
|
case AMP_CIRCLE:
|
||||||
|
@ -423,17 +418,19 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
* <rotation> is a optional parameter: rotation from origin.
|
* <rotation> is a optional parameter: rotation from origin.
|
||||||
* type is not stored in parameters list, so the first parameter is exposure
|
* type is not stored in parameters list, so the first parameter is exposure
|
||||||
*/
|
*/
|
||||||
int radius = scaletoIU( m_Params[1].GetValue( tool ), m_GerbMetric ) / 2;
|
int radius = scaletoIU( m_Params[1].GetValueFromMacro( aApertMacro ), m_GerbMetric ) / 2;
|
||||||
|
|
||||||
// A circle primitive can have a 0 size (for instance when used in roundrect macro),
|
// A circle primitive can have a 0 size (for instance when used in roundrect macro),
|
||||||
// so skip it
|
// so skip it
|
||||||
if( radius <= 0 )
|
if( radius <= 0 )
|
||||||
break;
|
break;
|
||||||
|
|
||||||
VECTOR2I center = mapPt( m_Params[2].GetValue( tool ), m_Params[3].GetValue( tool ),
|
VECTOR2I center = mapPt( m_Params[2].GetValueFromMacro( aApertMacro ), m_Params[3].GetValueFromMacro( aApertMacro ),
|
||||||
m_GerbMetric );
|
m_GerbMetric );
|
||||||
VECTOR2I corner;
|
VECTOR2I corner;
|
||||||
EDA_ANGLE delta = ANGLE_360 / seg_per_circle; // rot angle in 0.1 degree
|
|
||||||
|
const int seg_per_circle = 64; // Number of segments to approximate a circle
|
||||||
|
EDA_ANGLE delta = ANGLE_360 / seg_per_circle;
|
||||||
|
|
||||||
for( EDA_ANGLE angle = ANGLE_0; angle < ANGLE_360; angle += delta )
|
for( EDA_ANGLE angle = ANGLE_0; angle < ANGLE_360; angle += delta )
|
||||||
{
|
{
|
||||||
|
@ -450,11 +447,11 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
case AMP_LINE2:
|
case AMP_LINE2:
|
||||||
case AMP_LINE20: // Line with rectangle ends. (Width, start and end pos + rotation)
|
case AMP_LINE20: // Line with rectangle ends. (Width, start and end pos + rotation)
|
||||||
{
|
{
|
||||||
int width = scaletoIU( m_Params[1].GetValue( tool ), m_GerbMetric );
|
int width = scaletoIU( m_Params[1].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
VECTOR2I start =
|
VECTOR2I start =
|
||||||
mapPt( m_Params[2].GetValue( tool ), m_Params[3].GetValue( tool ), m_GerbMetric );
|
mapPt( m_Params[2].GetValueFromMacro( aApertMacro ), m_Params[3].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
VECTOR2I end =
|
VECTOR2I end =
|
||||||
mapPt( m_Params[4].GetValue( tool ), m_Params[5].GetValue( tool ), m_GerbMetric );
|
mapPt( m_Params[4].GetValueFromMacro( aApertMacro ), m_Params[5].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
VECTOR2I delta = end - start;
|
VECTOR2I delta = end - start;
|
||||||
int len = KiROUND( EuclideanNorm( delta ) );
|
int len = KiROUND( EuclideanNorm( delta ) );
|
||||||
|
|
||||||
|
@ -485,9 +482,9 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
case AMP_LINE_CENTER:
|
case AMP_LINE_CENTER:
|
||||||
{
|
{
|
||||||
VECTOR2I size =
|
VECTOR2I size =
|
||||||
mapPt( m_Params[1].GetValue( tool ), m_Params[2].GetValue( tool ), m_GerbMetric );
|
mapPt( m_Params[1].GetValueFromMacro( aApertMacro ), m_Params[2].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
VECTOR2I pos =
|
VECTOR2I pos =
|
||||||
mapPt( m_Params[3].GetValue( tool ), m_Params[4].GetValue( tool ), m_GerbMetric );
|
mapPt( m_Params[3].GetValueFromMacro( aApertMacro ), m_Params[4].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
|
|
||||||
// Build poly:
|
// Build poly:
|
||||||
pos.x -= size.x / 2;
|
pos.x -= size.x / 2;
|
||||||
|
@ -505,9 +502,9 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
case AMP_LINE_LOWER_LEFT:
|
case AMP_LINE_LOWER_LEFT:
|
||||||
{
|
{
|
||||||
VECTOR2I size =
|
VECTOR2I size =
|
||||||
mapPt( m_Params[1].GetValue( tool ), m_Params[2].GetValue( tool ), m_GerbMetric );
|
mapPt( m_Params[1].GetValueFromMacro( aApertMacro ), m_Params[2].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
VECTOR2I lowerLeft =
|
VECTOR2I lowerLeft =
|
||||||
mapPt( m_Params[3].GetValue( tool ), m_Params[4].GetValue( tool ), m_GerbMetric );
|
mapPt( m_Params[3].GetValueFromMacro( aApertMacro ), m_Params[4].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
|
|
||||||
// Build poly:
|
// Build poly:
|
||||||
aBuffer.push_back( lowerLeft );
|
aBuffer.push_back( lowerLeft );
|
||||||
|
@ -526,14 +523,14 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
// this first rotated by 90, 180 and 270 deg.
|
// this first rotated by 90, 180 and 270 deg.
|
||||||
// m_Params = center.x (unused here), center.y (unused here), outside diam, inside diam,
|
// m_Params = center.x (unused here), center.y (unused here), outside diam, inside diam,
|
||||||
// crosshair thickness.
|
// crosshair thickness.
|
||||||
int outerRadius = scaletoIU( m_Params[2].GetValue( tool ), m_GerbMetric ) / 2;
|
int outerRadius = scaletoIU( m_Params[2].GetValueFromMacro( aApertMacro ), m_GerbMetric ) / 2;
|
||||||
int innerRadius = scaletoIU( m_Params[3].GetValue( tool ), m_GerbMetric ) / 2;
|
int innerRadius = scaletoIU( m_Params[3].GetValueFromMacro( aApertMacro ), m_GerbMetric ) / 2;
|
||||||
|
|
||||||
// Safety checks to guarantee no divide-by-zero
|
// Safety checks to guarantee no divide-by-zero
|
||||||
outerRadius = std::max( 1, outerRadius );
|
outerRadius = std::max( 1, outerRadius );
|
||||||
innerRadius = std::max( 1, innerRadius );
|
innerRadius = std::max( 1, innerRadius );
|
||||||
|
|
||||||
int halfthickness = scaletoIU( m_Params[4].GetValue( tool ), m_GerbMetric ) / 2;
|
int halfthickness = scaletoIU( m_Params[4].GetValueFromMacro( aApertMacro ), m_GerbMetric ) / 2;
|
||||||
EDA_ANGLE angle_start( asin( (double) halfthickness / innerRadius ), RADIANS_T );
|
EDA_ANGLE angle_start( asin( (double) halfthickness / innerRadius ), RADIANS_T );
|
||||||
|
|
||||||
// Draw shape in the first quadrant (X and Y > 0)
|
// Draw shape in the first quadrant (X and Y > 0)
|
||||||
|
@ -582,8 +579,8 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
{
|
{
|
||||||
// A cross hair with n concentric circles. Only the cross is built as
|
// A cross hair with n concentric circles. Only the cross is built as
|
||||||
// polygon because circles can be drawn easily
|
// polygon because circles can be drawn easily
|
||||||
int crossHairThickness = scaletoIU( m_Params[6].GetValue( tool ), m_GerbMetric );
|
int crossHairThickness = scaletoIU( m_Params[6].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
int crossHairLength = scaletoIU( m_Params[7].GetValue( tool ), m_GerbMetric );
|
int crossHairLength = scaletoIU( m_Params[7].GetValueFromMacro( aApertMacro ), m_GerbMetric );
|
||||||
|
|
||||||
// Create cross. First create 1/4 of the shape.
|
// Create cross. First create 1/4 of the shape.
|
||||||
// Others point are the same, rotated by 90, 180 and 270 deg
|
// Others point are the same, rotated by 90, 180 and 270 deg
|
||||||
|
@ -616,8 +613,8 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( const D_CODE* aDcode,
|
||||||
|
|
||||||
case AMP_POLYGON: // Creates a regular polygon
|
case AMP_POLYGON: // Creates a regular polygon
|
||||||
{
|
{
|
||||||
int vertexcount = KiROUND( m_Params[1].GetValue( tool ) );
|
int vertexcount = KiROUND( m_Params[1].GetValueFromMacro( aApertMacro ) );
|
||||||
int radius = scaletoIU( m_Params[4].GetValue( tool ), m_GerbMetric ) / 2;
|
int radius = scaletoIU( m_Params[4].GetValueFromMacro( aApertMacro ), m_GerbMetric ) / 2;
|
||||||
|
|
||||||
// rs274x said: vertex count = 3 ... 10, and the first corner is on the X axis
|
// rs274x said: vertex count = 3 ... 10, and the first corner is on the X axis
|
||||||
if( vertexcount < 3 )
|
if( vertexcount < 3 )
|
||||||
|
|
|
@ -117,18 +117,21 @@ public:
|
||||||
* In a aperture macro shape, a basic primitive with exposure off is a hole in the shape
|
* In a aperture macro shape, a basic primitive with exposure off is a hole in the shape
|
||||||
* it is NOT a negative shape
|
* it is NOT a negative shape
|
||||||
*/
|
*/
|
||||||
bool IsAMPrimitiveExposureOn( const D_CODE* aDcode ) const;
|
bool IsAMPrimitiveExposureOn( APERTURE_MACRO* aApertMacro ) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generate the polygonal shape of the primitive shape of an aperture
|
* Generate the polygonal shape of the primitive shape of an aperture
|
||||||
* macro instance.
|
* macro instance.
|
||||||
*
|
*
|
||||||
* @param aParent is the parent GERBER_DRAW_ITEM which is actually drawn.
|
* @param aApertMacro is the aperture macro using this primitive.
|
||||||
* @param aShapeBuffer is a SHAPE_POLY_SET to put the shape converted to a polygon.
|
* @param aShapeBuffer is a SHAPE_POLY_SET to put the shape converted to a polygon.
|
||||||
* @param aShapePos is the actual shape position.
|
|
||||||
*/
|
*/
|
||||||
|
#if 0
|
||||||
void ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
void ConvertBasicShapeToPolygon( const D_CODE* aDcode,
|
||||||
SHAPE_POLY_SET& aShapeBuffer );
|
SHAPE_POLY_SET& aShapeBuffer );
|
||||||
|
#endif
|
||||||
|
void ConvertBasicShapeToPolygon( APERTURE_MACRO* aApertMacro,
|
||||||
|
SHAPE_POLY_SET& aShapeBuffer );
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/**
|
/**
|
||||||
|
@ -141,7 +144,8 @@ private:
|
||||||
* converted because circles are very easy to draw (no rotation problem) so convert
|
* converted because circles are very easy to draw (no rotation problem) so convert
|
||||||
* them in polygons and draw them as polygons is not a good idea.
|
* them in polygons and draw them as polygons is not a good idea.
|
||||||
*/
|
*/
|
||||||
void ConvertShapeToPolygon( const D_CODE* aDcode, std::vector<VECTOR2I>& aBuffer );
|
//void ConvertShapeToPolygon( const D_CODE* aDcode, std::vector<VECTOR2I>& aBuffer );
|
||||||
|
void ConvertShapeToPolygon( APERTURE_MACRO* aApertMacroe, std::vector<VECTOR2I>& aBuffer );
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -32,6 +32,55 @@
|
||||||
#include <aperture_macro.h>
|
#include <aperture_macro.h>
|
||||||
#include <gerber_draw_item.h>
|
#include <gerber_draw_item.h>
|
||||||
|
|
||||||
|
void APERTURE_MACRO::InitLocalParams( const D_CODE* aDcode )
|
||||||
|
{
|
||||||
|
// store the initial values coming from aDcode into m_localParamValues
|
||||||
|
// for n parameters, they are local params $1 to $n
|
||||||
|
m_localParamValues.clear();
|
||||||
|
|
||||||
|
// Note: id_param = 1... n, not 0
|
||||||
|
for( unsigned id_param = 1; id_param <= aDcode->GetParamCount(); id_param++ )
|
||||||
|
m_localParamValues[id_param] = aDcode->GetParam( id_param );
|
||||||
|
|
||||||
|
m_paramLevelEval = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void APERTURE_MACRO::EvalLocalParams( const AM_PRIMITIVE& aPrimitive )
|
||||||
|
{
|
||||||
|
// Evaluate m_localParamValues from current m_paramLevelEval to
|
||||||
|
// aPrimitive.m_LocalParamLevel
|
||||||
|
// if m_paramLevelEval >= m_LocalParamLevel, do nothing: the
|
||||||
|
// m_localParamValues are already up to date
|
||||||
|
|
||||||
|
if( m_paramLevelEval >= aPrimitive.m_LocalParamLevel )
|
||||||
|
return;
|
||||||
|
|
||||||
|
for( ; m_paramLevelEval < aPrimitive.m_LocalParamLevel; m_paramLevelEval++ )
|
||||||
|
{
|
||||||
|
AM_PARAM& am_param = m_localParamStack.at( m_paramLevelEval );
|
||||||
|
int prm_index = am_param.GetIndex();
|
||||||
|
|
||||||
|
double value = am_param.GetValueFromMacro( this );
|
||||||
|
|
||||||
|
// if am_param value is not yet stored in m_localParamValues, add it.
|
||||||
|
// if it is already in m_localParamValues, update its value;
|
||||||
|
m_localParamValues[ prm_index ] = value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
double APERTURE_MACRO::GetLocalParamValue( int aIndex )
|
||||||
|
{
|
||||||
|
// return the local param value stored in m_localParamValues
|
||||||
|
// if not existing, returns 0
|
||||||
|
|
||||||
|
if( m_localParamValues.find( aIndex ) != m_localParamValues.end() )
|
||||||
|
return m_localParamValues[ aIndex ];
|
||||||
|
|
||||||
|
return 0.0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void APERTURE_MACRO::AddPrimitiveToList( AM_PRIMITIVE& aPrimitive )
|
void APERTURE_MACRO::AddPrimitiveToList( AM_PRIMITIVE& aPrimitive )
|
||||||
{
|
{
|
||||||
|
@ -57,20 +106,21 @@ SHAPE_POLY_SET* APERTURE_MACRO::GetApertureMacroShape( const GERBER_DRAW_ITEM* a
|
||||||
SHAPE_POLY_SET holeBuffer;
|
SHAPE_POLY_SET holeBuffer;
|
||||||
|
|
||||||
m_shape.RemoveAllContours();
|
m_shape.RemoveAllContours();
|
||||||
D_CODE * dcode = aParent->GetDcodeDescr();
|
D_CODE* dcode = aParent->GetDcodeDescr();
|
||||||
|
InitLocalParams( dcode );
|
||||||
|
|
||||||
for( AM_PRIMITIVE& prim_macro : m_primitivesList )
|
for( AM_PRIMITIVE& prim_macro : m_primitivesList )
|
||||||
{
|
{
|
||||||
if( prim_macro.m_Primitive_id == AMP_COMMENT )
|
if( prim_macro.m_Primitive_id == AMP_COMMENT )
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if( prim_macro.IsAMPrimitiveExposureOn( dcode ) )
|
if( prim_macro.IsAMPrimitiveExposureOn( this ) )
|
||||||
{
|
{
|
||||||
prim_macro.ConvertBasicShapeToPolygon( dcode, m_shape );
|
prim_macro.ConvertBasicShapeToPolygon( this, m_shape );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
prim_macro.ConvertBasicShapeToPolygon( dcode, holeBuffer );
|
prim_macro.ConvertBasicShapeToPolygon( this, holeBuffer );
|
||||||
|
|
||||||
if( holeBuffer.OutlineCount() ) // we have a new hole in shape: remove the hole
|
if( holeBuffer.OutlineCount() ) // we have a new hole in shape: remove the hole
|
||||||
{
|
{
|
||||||
|
@ -105,27 +155,3 @@ SHAPE_POLY_SET* APERTURE_MACRO::GetApertureMacroShape( const GERBER_DRAW_ITEM* a
|
||||||
|
|
||||||
return &m_shape;
|
return &m_shape;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
double APERTURE_MACRO::GetLocalParam( const D_CODE* aDcode, unsigned aParamId ) const
|
|
||||||
{
|
|
||||||
// find parameter descr.
|
|
||||||
const AM_PARAM * param = nullptr;
|
|
||||||
|
|
||||||
for( unsigned ii = 0; ii < m_localParamStack.size(); ii ++ )
|
|
||||||
{
|
|
||||||
if( m_localParamStack[ii].GetIndex() == aParamId )
|
|
||||||
{
|
|
||||||
param = &m_localParamStack[ii];
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( param == nullptr ) // not found
|
|
||||||
return 0.0;
|
|
||||||
|
|
||||||
// Evaluate parameter
|
|
||||||
double value = param->GetValue( aDcode );
|
|
||||||
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
|
@ -68,6 +68,9 @@ class SHAPE_POLY_SET;
|
||||||
class APERTURE_MACRO
|
class APERTURE_MACRO
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
APERTURE_MACRO() :
|
||||||
|
m_paramLevelEval( 0 )
|
||||||
|
{}
|
||||||
/**
|
/**
|
||||||
* Usually, parameters are defined inside the aperture primitive using immediate mode or
|
* Usually, parameters are defined inside the aperture primitive using immediate mode or
|
||||||
* deferred mode.
|
* deferred mode.
|
||||||
|
@ -82,14 +85,37 @@ public:
|
||||||
*/
|
*/
|
||||||
double GetLocalParam( const D_CODE* aDcode, unsigned aParamId ) const;
|
double GetLocalParam( const D_CODE* aDcode, unsigned aParamId ) const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Init m_localParamValues to a initial values coming from aDcode and
|
||||||
|
* clear m_paramLevelEval
|
||||||
|
* must be called once before trying to build the aperture macro shape
|
||||||
|
* corresponding to aDcode
|
||||||
|
*/
|
||||||
|
void InitLocalParams( const D_CODE* aDcode );
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Evaluate m_localParamValues from current m_paramLevelEval to
|
||||||
|
* aPrimitive m_LocalParamLevel
|
||||||
|
* if m_paramLevelEval >= m_LocalParamLevel, do nothing
|
||||||
|
* after call, m_paramLevelEval = m_LocalParamLevel
|
||||||
|
*/
|
||||||
|
void EvalLocalParams( const AM_PRIMITIVE& aPrimitive );
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return the local param value stored in m_localParamValues
|
||||||
|
* @param aIndex is the param Id (from $n)
|
||||||
|
* if not found, returns 0
|
||||||
|
*/
|
||||||
|
double GetLocalParamValue( int aIndex );
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Calculate the primitive shape for flashed items.
|
* Calculate the primitive shape for flashed items.
|
||||||
*
|
*
|
||||||
* When an item is flashed, this is the shape of the item.
|
* When an item is flashed, this is the shape of the item.
|
||||||
*
|
*
|
||||||
* @param aParent is the parent #GERBER_DRAW_ITEM which is actually drawn.
|
|
||||||
* @return the shape of the item.
|
* @return the shape of the item.
|
||||||
|
* @param aParent is the parent #GERBER_DRAW_ITEM which is actually drawn.
|
||||||
|
* @param aShapePos is the position of the shape to build.
|
||||||
*/
|
*/
|
||||||
SHAPE_POLY_SET* GetApertureMacroShape( const GERBER_DRAW_ITEM* aParent,
|
SHAPE_POLY_SET* GetApertureMacroShape( const GERBER_DRAW_ITEM* aParent,
|
||||||
const VECTOR2I& aShapePos );
|
const VECTOR2I& aShapePos );
|
||||||
|
@ -125,6 +151,20 @@ private:
|
||||||
*/
|
*/
|
||||||
AM_PARAMS m_localParamStack;
|
AM_PARAMS m_localParamStack;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* m_localParamValues is the current value of local parameters after evaluation
|
||||||
|
* the key is the local param id (from $n) and the value is double
|
||||||
|
*/
|
||||||
|
std::map<int, double> m_localParamValues;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* the current level of local param values evaluation
|
||||||
|
* when a primitive is evaluated, if its m_LocalParamLevel is smaller than
|
||||||
|
* m_paramLevelEval, all local params must be evaluated from current m_paramLevelEval
|
||||||
|
* upto m_LocalParamLevel before use in this primitive
|
||||||
|
*/
|
||||||
|
int m_paramLevelEval;
|
||||||
|
|
||||||
SHAPE_POLY_SET m_shape; ///< The shape of the item, calculated by GetApertureMacroShape
|
SHAPE_POLY_SET m_shape; ///< The shape of the item, calculated by GetApertureMacroShape
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -105,6 +105,7 @@ public:
|
||||||
* Return a parameter stored in parameter list.
|
* Return a parameter stored in parameter list.
|
||||||
*
|
*
|
||||||
* @param aIdx is the index of parameter.
|
* @param aIdx is the index of parameter.
|
||||||
|
* for n parameters from the Dcode definition, aIdx = 1 .. n, not 0
|
||||||
*/
|
*/
|
||||||
double GetParam( unsigned aIdx ) const
|
double GetParam( unsigned aIdx ) const
|
||||||
{
|
{
|
||||||
|
|
|
@ -320,7 +320,6 @@ const BOX2I GERBER_DRAW_ITEM::GetBoundingBox() const
|
||||||
|
|
||||||
case GBR_SPOT_MACRO:
|
case GBR_SPOT_MACRO:
|
||||||
case GBR_SPOT_POLY:
|
case GBR_SPOT_POLY:
|
||||||
{
|
|
||||||
if( code )
|
if( code )
|
||||||
{
|
{
|
||||||
if( code->m_Polygon.OutlineCount() == 0 )
|
if( code->m_Polygon.OutlineCount() == 0 )
|
||||||
|
@ -331,7 +330,6 @@ const BOX2I GERBER_DRAW_ITEM::GetBoundingBox() const
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
|
|
||||||
case GBR_SEGMENT:
|
case GBR_SEGMENT:
|
||||||
{
|
{
|
||||||
|
@ -861,12 +859,7 @@ bool GERBER_DRAW_ITEM::HitTest( const VECTOR2I& aRefPos, int aAccuracy ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
case GBR_SPOT_MACRO:
|
case GBR_SPOT_MACRO:
|
||||||
{
|
return m_AbsolutePolygon.Contains( VECTOR2I( aRefPos ), -1, aAccuracy );
|
||||||
// Aperture macro polygons are already in absolute coordinates
|
|
||||||
SHAPE_POLY_SET* p =
|
|
||||||
GetDcodeDescr()->GetMacro()->GetApertureMacroShape( this, m_Start );
|
|
||||||
return p->Contains( VECTOR2I( aRefPos ), -1, aAccuracy );
|
|
||||||
}
|
|
||||||
|
|
||||||
case GBR_SEGMENT:
|
case GBR_SEGMENT:
|
||||||
case GBR_CIRCLE:
|
case GBR_CIRCLE:
|
||||||
|
|
|
@ -566,21 +566,26 @@ void GERBVIEW_PAINTER::drawFlashedShape( GERBER_DRAW_ITEM* aItem, bool aFilled )
|
||||||
|
|
||||||
void GERBVIEW_PAINTER::drawApertureMacro( GERBER_DRAW_ITEM* aParent, bool aFilled )
|
void GERBVIEW_PAINTER::drawApertureMacro( GERBER_DRAW_ITEM* aParent, bool aFilled )
|
||||||
{
|
{
|
||||||
|
if( aParent->m_AbsolutePolygon.OutlineCount() == 0 )
|
||||||
|
{
|
||||||
D_CODE* code = aParent->GetDcodeDescr();
|
D_CODE* code = aParent->GetDcodeDescr();
|
||||||
APERTURE_MACRO* macro = code->GetMacro();
|
APERTURE_MACRO* macro = code->GetMacro();
|
||||||
SHAPE_POLY_SET* macroShape = macro->GetApertureMacroShape( aParent, aParent->m_Start );
|
aParent->m_AbsolutePolygon = *macro->GetApertureMacroShape( aParent, aParent->m_Start );
|
||||||
|
}
|
||||||
|
|
||||||
|
SHAPE_POLY_SET& polyset = aParent->m_AbsolutePolygon;
|
||||||
|
|
||||||
if( !gvconfig()->m_Display.m_DisplayPolygonsFill )
|
if( !gvconfig()->m_Display.m_DisplayPolygonsFill )
|
||||||
m_gal->SetLineWidth( m_gerbviewSettings.m_outlineWidth );
|
m_gal->SetLineWidth( m_gerbviewSettings.m_outlineWidth );
|
||||||
|
|
||||||
if( !aFilled )
|
if( !aFilled )
|
||||||
{
|
{
|
||||||
for( int i = 0; i < macroShape->OutlineCount(); i++ )
|
for( int i = 0; i < polyset.OutlineCount(); i++ )
|
||||||
m_gal->DrawPolyline( macroShape->COutline( i ) );
|
m_gal->DrawPolyline( polyset.COutline( i ) );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
m_gal->DrawPolygon( *macroShape );
|
m_gal->DrawPolygon( polyset );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1132,7 +1132,7 @@ bool GERBER_FILE_IMAGE::ReadApertureMacro( char *aBuff, unsigned int aBuffSize,
|
||||||
// in advance, i.e. be immediate.
|
// in advance, i.e. be immediate.
|
||||||
wxASSERT( prim.m_Params[1].IsImmediate() );
|
wxASSERT( prim.m_Params[1].IsImmediate() );
|
||||||
|
|
||||||
paramCount = (int) prim.m_Params[1].GetValue( nullptr ) * 2 + 1;
|
paramCount = (int) prim.m_Params[1].GetValueFromMacro( nullptr ) * 2 + 1;
|
||||||
|
|
||||||
for( int jj = 0; jj < paramCount && *aText != '*'; ++jj )
|
for( int jj = 0; jj < paramCount && *aText != '*'; ++jj )
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in New Issue