Don't depend on a pad being connected to a non-zone when filling zones.
If the pad hasn't already been owned by another zone, and the zone we're currently filling can connect to it, then we want to try to flash it even if it's not connected to anything else. Fixes https://gitlab.com/kicad/code/kicad/issues/13415
This commit is contained in:
parent
53dedb2c99
commit
e509fa0fc9
|
@ -247,7 +247,7 @@ bool PAD::FlashLayer( LSET aLayers ) const
|
|||
}
|
||||
|
||||
|
||||
bool PAD::FlashLayer( int aLayer ) const
|
||||
bool PAD::FlashLayer( int aLayer, bool aOnlyCheckIfPermitted ) const
|
||||
{
|
||||
if( aLayer == UNDEFINED_LAYER )
|
||||
return true;
|
||||
|
@ -304,9 +304,20 @@ bool PAD::FlashLayer( int aLayer ) const
|
|||
// clearance.
|
||||
// See https://gitlab.com/kicad/code/kicad/-/issues/11299.
|
||||
if( m_zoneLayerConnections[ aLayer ] == ZLC_CONNECTED )
|
||||
{
|
||||
return true;
|
||||
|
||||
return board->GetConnectivity()->IsConnectedOnLayer( this, aLayer, types );
|
||||
}
|
||||
else if( m_zoneLayerConnections[ aLayer ] == ZLC_UNCONNECTED )
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else /* ZLC_UNRESOLVED */
|
||||
{
|
||||
if( aOnlyCheckIfPermitted )
|
||||
return true;
|
||||
else
|
||||
return board->GetConnectivity()->IsConnectedOnLayer( this, aLayer, types );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -631,9 +631,16 @@ public:
|
|||
* Check to see whether the pad should be flashed on the specific layer.
|
||||
*
|
||||
* @param aLayer Layer to check for connectivity
|
||||
* @param aOnlyCheckIfPermitted indicates that the routine should just return whether or not
|
||||
* a flashed connection is permitted on this layer (without checking for a connection)
|
||||
* @return true if connected by pad or track (or optionally zone)
|
||||
*/
|
||||
bool FlashLayer( int aLayer ) const;
|
||||
bool FlashLayer( int aLayer, bool aOnlyCheckIfPermitted = false ) const;
|
||||
|
||||
bool CanFlashLayer( int aLayer )
|
||||
{
|
||||
return FlashLayer( aLayer, true );
|
||||
}
|
||||
|
||||
PCB_LAYER_ID GetLayer() const override;
|
||||
|
||||
|
|
|
@ -305,6 +305,7 @@ COLOR4D PCB_RENDER_SETTINGS::GetColor( const VIEW_ITEM* aItem, int aLayer ) cons
|
|||
{
|
||||
PCB_LAYER_ID primary = GetPrimaryHighContrastLayer();
|
||||
bool isActive = m_highContrastLayers.count( aLayer );
|
||||
bool hide = false;
|
||||
|
||||
switch( originalLayer )
|
||||
{
|
||||
|
@ -313,7 +314,10 @@ COLOR4D PCB_RENDER_SETTINGS::GetColor( const VIEW_ITEM* aItem, int aLayer ) cons
|
|||
const PAD* pad = static_cast<const PAD*>( item );
|
||||
|
||||
if( !pad->FlashLayer( primary ) )
|
||||
{
|
||||
isActive = false;
|
||||
hide = true;
|
||||
}
|
||||
|
||||
if( m_PadEditModePad && pad != m_PadEditModePad )
|
||||
isActive = false;
|
||||
|
@ -328,7 +332,10 @@ COLOR4D PCB_RENDER_SETTINGS::GetColor( const VIEW_ITEM* aItem, int aLayer ) cons
|
|||
|
||||
// Target graphic is active if the via crosses the primary layer
|
||||
if( via->GetLayerSet().test( primary ) == 0 )
|
||||
{
|
||||
isActive = false;
|
||||
hide = true;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
@ -338,7 +345,10 @@ COLOR4D PCB_RENDER_SETTINGS::GetColor( const VIEW_ITEM* aItem, int aLayer ) cons
|
|||
const PCB_VIA* via = static_cast<const PCB_VIA*>( item );
|
||||
|
||||
if( !via->FlashLayer( primary ) )
|
||||
{
|
||||
isActive = false;
|
||||
hide = true;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
@ -380,8 +390,12 @@ COLOR4D PCB_RENDER_SETTINGS::GetColor( const VIEW_ITEM* aItem, int aLayer ) cons
|
|||
|
||||
if( !isActive )
|
||||
{
|
||||
if( m_ContrastModeDisplay == HIGH_CONTRAST_MODE::HIDDEN || IsNetnameLayer( aLayer ) )
|
||||
if( m_ContrastModeDisplay == HIGH_CONTRAST_MODE::HIDDEN
|
||||
|| IsNetnameLayer( aLayer )
|
||||
|| hide )
|
||||
{
|
||||
color = COLOR4D::CLEAR;
|
||||
}
|
||||
else
|
||||
{
|
||||
color = color.Mix( m_layerColors[LAYER_PCB_BACKGROUND], m_hiContrastFactor );
|
||||
|
|
|
@ -734,10 +734,16 @@ void ZONE_FILLER::knockoutThermalReliefs( const ZONE* aZone, PCB_LAYER_ID aLayer
|
|||
constraint = bds.m_DRCEngine->EvalRules( THERMAL_RELIEF_GAP_CONSTRAINT, pad, aZone,
|
||||
aLayer );
|
||||
padClearance = constraint.GetValue().Min();
|
||||
holeClearance = padClearance;
|
||||
|
||||
if( pad->FlashLayer( aLayer ) )
|
||||
if( pad->CanFlashLayer( aLayer ) )
|
||||
{
|
||||
aThermalConnectionPads.push_back( pad );
|
||||
addKnockout( pad, aLayer, padClearance, holes );
|
||||
}
|
||||
else if( pad->GetDrillSize().x > 0 )
|
||||
{
|
||||
pad->TransformHoleToPolygon( holes, padClearance, m_maxError, ERROR_OUTSIDE );
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
|
@ -750,13 +756,22 @@ void ZONE_FILLER::knockoutThermalReliefs( const ZONE* aZone, PCB_LAYER_ID aLayer
|
|||
else
|
||||
padClearance = aZone->GetLocalClearance();
|
||||
|
||||
constraint = bds.m_DRCEngine->EvalRules( PHYSICAL_HOLE_CLEARANCE_CONSTRAINT, pad,
|
||||
aZone, aLayer );
|
||||
if( pad->FlashLayer( aLayer ) )
|
||||
{
|
||||
addKnockout( pad, aLayer, padClearance, holes );
|
||||
}
|
||||
else if( pad->GetDrillSize().x > 0 )
|
||||
{
|
||||
constraint = bds.m_DRCEngine->EvalRules( PHYSICAL_HOLE_CLEARANCE_CONSTRAINT,
|
||||
pad, aZone, aLayer );
|
||||
|
||||
if( constraint.GetValue().Min() > padClearance )
|
||||
holeClearance = constraint.GetValue().Min();
|
||||
else
|
||||
holeClearance = padClearance;
|
||||
if( constraint.GetValue().Min() > padClearance )
|
||||
holeClearance = constraint.GetValue().Min();
|
||||
else
|
||||
holeClearance = padClearance;
|
||||
|
||||
pad->TransformHoleToPolygon( holes, holeClearance, m_maxError, ERROR_OUTSIDE );
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
|
@ -764,11 +779,6 @@ void ZONE_FILLER::knockoutThermalReliefs( const ZONE* aZone, PCB_LAYER_ID aLayer
|
|||
// No knockout
|
||||
continue;
|
||||
}
|
||||
|
||||
if( pad->FlashLayer( aLayer ) )
|
||||
addKnockout( pad, aLayer, padClearance, holes );
|
||||
else if( pad->GetDrillSize().x > 0 )
|
||||
pad->TransformHoleToPolygon( holes, holeClearance, m_maxError, ERROR_OUTSIDE );
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue