Fix a crash bug in DRC, and equate Margin to Edge.Cuts.
This commit is contained in:
parent
b123318cf6
commit
ff3bd7e72a
|
@ -63,7 +63,7 @@ bool DRC_RULE_CONDITION::EvaluateFor( const BOARD_ITEM* aItemA, const BOARD_ITEM
|
||||||
} );
|
} );
|
||||||
|
|
||||||
BOARD_ITEM* a = const_cast<BOARD_ITEM*>( aItemA );
|
BOARD_ITEM* a = const_cast<BOARD_ITEM*>( aItemA );
|
||||||
BOARD_ITEM* b = aItemB ? const_cast<BOARD_ITEM*>( aItemB ) : DELETED_BOARD_ITEM::GetInstance();
|
BOARD_ITEM* b = const_cast<BOARD_ITEM*>( aItemB );
|
||||||
|
|
||||||
ctx.SetItems( a, b );
|
ctx.SetItems( a, b );
|
||||||
|
|
||||||
|
|
|
@ -188,7 +188,7 @@ bool DRC_TEST_PROVIDER_EDGE_CLEARANCE::Run()
|
||||||
return true;
|
return true;
|
||||||
};
|
};
|
||||||
|
|
||||||
forEachGeometryItem( { PCB_SHAPE_T }, LSET( Edge_Cuts ), queryBoardOutlineItems );
|
forEachGeometryItem( { PCB_SHAPE_T }, LSET( 2, Edge_Cuts, Margin ), queryBoardOutlineItems );
|
||||||
forEachGeometryItem( s_allBasicItemsButZones, LSET::AllCuMask(), queryBoardGeometryItems );
|
forEachGeometryItem( s_allBasicItemsButZones, LSET::AllCuMask(), queryBoardGeometryItems );
|
||||||
|
|
||||||
for( const std::unique_ptr<PCB_SHAPE>& edge : edges )
|
for( const std::unique_ptr<PCB_SHAPE>& edge : edges )
|
||||||
|
|
|
@ -199,11 +199,15 @@ bool DRC_TEST_PROVIDER_SILK_CLEARANCE::Run()
|
||||||
};
|
};
|
||||||
|
|
||||||
forEachGeometryItem( s_allBasicItems, LSET( 2, F_SilkS, B_SilkS ), addToSilkTree );
|
forEachGeometryItem( s_allBasicItems, LSET( 2, F_SilkS, B_SilkS ), addToSilkTree );
|
||||||
forEachGeometryItem( s_allBasicItems, LSET::FrontMask() | LSET::BackMask(), countTargets );
|
forEachGeometryItem( s_allBasicItems,
|
||||||
|
LSET::FrontMask() | LSET::BackMask() | LSET( 2, Edge_Cuts, Margin ),
|
||||||
|
countTargets );
|
||||||
|
|
||||||
targets *= 2; // One for adding to RTree; one for testing
|
targets *= 2; // One for adding to RTree; one for testing
|
||||||
|
|
||||||
forEachGeometryItem( s_allBasicItems, LSET::FrontMask() | LSET::BackMask(), addToTargetTree );
|
forEachGeometryItem( s_allBasicItems,
|
||||||
|
LSET::FrontMask() | LSET::BackMask() | LSET( 2, Edge_Cuts, Margin ),
|
||||||
|
addToTargetTree );
|
||||||
|
|
||||||
reportAux( _("Testing %d silkscreen features against %d board items."),
|
reportAux( _("Testing %d silkscreen features against %d board items."),
|
||||||
silkTree.size(),
|
silkTree.size(),
|
||||||
|
@ -219,6 +223,7 @@ bool DRC_TEST_PROVIDER_SILK_CLEARANCE::Run()
|
||||||
DRC_RTREE::LAYER_PAIR( F_SilkS, F_Fab ),
|
DRC_RTREE::LAYER_PAIR( F_SilkS, F_Fab ),
|
||||||
DRC_RTREE::LAYER_PAIR( F_SilkS, F_Cu ),
|
DRC_RTREE::LAYER_PAIR( F_SilkS, F_Cu ),
|
||||||
DRC_RTREE::LAYER_PAIR( F_SilkS, Edge_Cuts ),
|
DRC_RTREE::LAYER_PAIR( F_SilkS, Edge_Cuts ),
|
||||||
|
DRC_RTREE::LAYER_PAIR( F_SilkS, Margin ),
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, B_SilkS ),
|
DRC_RTREE::LAYER_PAIR( B_SilkS, B_SilkS ),
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Mask ),
|
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Mask ),
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Adhes ),
|
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Adhes ),
|
||||||
|
@ -226,7 +231,8 @@ bool DRC_TEST_PROVIDER_SILK_CLEARANCE::Run()
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, B_CrtYd ),
|
DRC_RTREE::LAYER_PAIR( B_SilkS, B_CrtYd ),
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Fab ),
|
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Fab ),
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Cu ),
|
DRC_RTREE::LAYER_PAIR( B_SilkS, B_Cu ),
|
||||||
DRC_RTREE::LAYER_PAIR( B_SilkS, Edge_Cuts )
|
DRC_RTREE::LAYER_PAIR( B_SilkS, Edge_Cuts ),
|
||||||
|
DRC_RTREE::LAYER_PAIR( B_SilkS, Margin )
|
||||||
};
|
};
|
||||||
|
|
||||||
targetTree.QueryCollidingPairs( &silkTree, layerPairs, checkClearance, m_largestClearance,
|
targetTree.QueryCollidingPairs( &silkTree, layerPairs, checkClearance, m_largestClearance,
|
||||||
|
|
|
@ -1039,31 +1039,35 @@ bool PNS_KICAD_IFACE_BASE::syncTextItem( PNS::NODE* aWorld, EDA_TEXT* aText, PCB
|
||||||
|
|
||||||
bool PNS_KICAD_IFACE_BASE::syncGraphicalItem( PNS::NODE* aWorld, PCB_SHAPE* aItem )
|
bool PNS_KICAD_IFACE_BASE::syncGraphicalItem( PNS::NODE* aWorld, PCB_SHAPE* aItem )
|
||||||
{
|
{
|
||||||
if( aItem->GetLayer() != Edge_Cuts && !IsCopperLayer( aItem->GetLayer() ) )
|
if( aItem->GetLayer() == Edge_Cuts
|
||||||
return false;
|
|| aItem->GetLayer() == Margin
|
||||||
|
|| IsCopperLayer( aItem->GetLayer() ) )
|
||||||
// TODO: where do we handle filled polygons on copper layers?
|
|
||||||
if( aItem->GetShape() == S_POLYGON && aItem->IsFilled() )
|
|
||||||
return false;
|
|
||||||
|
|
||||||
for( SHAPE* shape : aItem->MakeEffectiveShapes() )
|
|
||||||
{
|
{
|
||||||
std::unique_ptr<PNS::SOLID> solid = std::make_unique<PNS::SOLID>();
|
// TODO: where do we handle filled polygons on copper layers?
|
||||||
|
if( aItem->GetShape() == S_POLYGON && aItem->IsFilled() )
|
||||||
|
return false;
|
||||||
|
|
||||||
if( aItem->GetLayer() == Edge_Cuts )
|
for( SHAPE* shape : aItem->MakeEffectiveShapes() )
|
||||||
solid->SetLayers( LAYER_RANGE( F_Cu, B_Cu ) );
|
{
|
||||||
else
|
std::unique_ptr<PNS::SOLID> solid = std::make_unique<PNS::SOLID>();
|
||||||
solid->SetLayer( aItem->GetLayer() );
|
|
||||||
|
|
||||||
solid->SetNet( -1 );
|
if( aItem->GetLayer() == Edge_Cuts || aItem->GetLayer() == Margin )
|
||||||
solid->SetParent( aItem );
|
solid->SetLayers( LAYER_RANGE( F_Cu, B_Cu ) );
|
||||||
solid->SetShape( shape );
|
else
|
||||||
solid->SetRoutable( false );
|
solid->SetLayer( aItem->GetLayer() );
|
||||||
|
|
||||||
aWorld->Add( std::move( solid ) );
|
solid->SetNet( -1 );
|
||||||
|
solid->SetParent( aItem );
|
||||||
|
solid->SetShape( shape );
|
||||||
|
solid->SetRoutable( false );
|
||||||
|
|
||||||
|
aWorld->Add( std::move( solid ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -216,7 +216,8 @@ void PCB_INSPECTION_TOOL::reportClearance( DRC_CONSTRAINT_TYPE_T aClearanceType,
|
||||||
|
|
||||||
if( aClearanceType == CLEARANCE_CONSTRAINT )
|
if( aClearanceType == CLEARANCE_CONSTRAINT )
|
||||||
{
|
{
|
||||||
if( ( aA && aA->GetLayer() == Edge_Cuts ) || ( aB && aB->GetLayer() == Edge_Cuts ) )
|
if( ( aA && ( aA->GetLayerSet() & LSET( 2, Edge_Cuts, Margin ) ).any() )
|
||||||
|
|| ( aB && ( aB->GetLayerSet() & LSET( 2, Edge_Cuts, Margin ) ).any() ) )
|
||||||
{
|
{
|
||||||
auto edgeConstraint = drcEngine.EvalRulesForItems( EDGE_CLEARANCE_CONSTRAINT, aA, aB,
|
auto edgeConstraint = drcEngine.EvalRulesForItems( EDGE_CLEARANCE_CONSTRAINT, aA, aB,
|
||||||
aLayer, r );
|
aLayer, r );
|
||||||
|
@ -321,13 +322,13 @@ int PCB_INSPECTION_TOOL::InspectClearance( const TOOL_EVENT& aEvent )
|
||||||
|
|
||||||
reportClearance( SILK_CLEARANCE_CONSTRAINT, layer, a, b, r );
|
reportClearance( SILK_CLEARANCE_CONSTRAINT, layer, a, b, r );
|
||||||
}
|
}
|
||||||
else if( !( a->GetLayerSet() & LSET( 2, layer, Edge_Cuts ) ).any() )
|
else if( !( a->GetLayerSet() & LSET( 3, layer, Edge_Cuts, Margin ) ).any() )
|
||||||
{
|
{
|
||||||
r->Report( wxString::Format( _( "%s not present on layer %s. No clearance defined." ),
|
r->Report( wxString::Format( _( "%s not present on layer %s. No clearance defined." ),
|
||||||
a->GetSelectMenuText( r->GetUnits() ),
|
a->GetSelectMenuText( r->GetUnits() ),
|
||||||
m_frame->GetBoard()->GetLayerName( layer ) ) );
|
m_frame->GetBoard()->GetLayerName( layer ) ) );
|
||||||
}
|
}
|
||||||
else if( !( b->GetLayerSet() & LSET( 2, layer, Edge_Cuts ) ).any() )
|
else if( !( b->GetLayerSet() & LSET( 3, layer, Edge_Cuts, Margin ) ).any() )
|
||||||
{
|
{
|
||||||
r->Report( wxString::Format( _( "%s not present on layer %s. No clearance defined." ),
|
r->Report( wxString::Format( _( "%s not present on layer %s. No clearance defined." ),
|
||||||
b->GetSelectMenuText( r->GetUnits() ),
|
b->GetSelectMenuText( r->GetUnits() ),
|
||||||
|
|
|
@ -796,21 +796,29 @@ void ZONE_FILLER::buildCopperItemClearances( const ZONE* aZone, PCB_LAYER_ID aLa
|
||||||
auto knockoutGraphicClearance =
|
auto knockoutGraphicClearance =
|
||||||
[&]( BOARD_ITEM* aItem )
|
[&]( BOARD_ITEM* aItem )
|
||||||
{
|
{
|
||||||
// A item on the Edge_Cuts is always seen as on any layer:
|
// A item on the Edge_Cuts or Margin is always seen as on any layer:
|
||||||
if( !aItem->IsOnLayer( aLayer ) && !aItem->IsOnLayer( Edge_Cuts ) )
|
if( aItem->IsOnLayer( aLayer )
|
||||||
return;
|
|| aItem->IsOnLayer( Edge_Cuts )
|
||||||
|
|| aItem->IsOnLayer( Margin ) )
|
||||||
if( aItem->GetBoundingBox().Intersects( zone_boundingbox ) )
|
|
||||||
{
|
{
|
||||||
int gap = evalRulesForItems( CLEARANCE_CONSTRAINT, aZone, aItem, aLayer );
|
if( aItem->GetBoundingBox().Intersects( zone_boundingbox ) )
|
||||||
|
|
||||||
if( aItem->IsOnLayer( Edge_Cuts ) )
|
|
||||||
{
|
{
|
||||||
gap = std::max( gap, evalRulesForItems( EDGE_CLEARANCE_CONSTRAINT, aZone,
|
int gap = evalRulesForItems( CLEARANCE_CONSTRAINT, aZone, aItem, aLayer );
|
||||||
aItem, Edge_Cuts ) );
|
|
||||||
}
|
|
||||||
|
|
||||||
addKnockout( aItem, aLayer, gap, aItem->IsOnLayer( Edge_Cuts ), aHoles );
|
if( aItem->IsOnLayer( Edge_Cuts ) )
|
||||||
|
{
|
||||||
|
gap = std::max( gap, evalRulesForItems( EDGE_CLEARANCE_CONSTRAINT,
|
||||||
|
aZone, aItem, Edge_Cuts ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
if( aItem->IsOnLayer( Margin ) )
|
||||||
|
{
|
||||||
|
gap = std::max( gap, evalRulesForItems( EDGE_CLEARANCE_CONSTRAINT,
|
||||||
|
aZone, aItem, Margin ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
addKnockout( aItem, aLayer, gap, aItem->IsOnLayer( Edge_Cuts ), aHoles );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue