Implement visual zone dumping and fix the default fill algo setting.

This commit is contained in:
Jeff Young 2020-09-22 22:05:24 +01:00
parent 7e5a6371c1
commit fb7f98b51d
5 changed files with 54 additions and 32 deletions

View File

@ -36,7 +36,7 @@
#include <math_for_graphics.h>
#include <settings/color_settings.h>
#include <settings/settings_manager.h>
#include "zone_filler.h"
ZONE_CONTAINER::ZONE_CONTAINER( BOARD_ITEM_CONTAINER* aParent, bool aInModule )
: BOARD_CONNECTED_ITEM( aParent, aInModule ? PCB_MODULE_ZONE_AREA_T : PCB_ZONE_AREA_T ),
@ -67,7 +67,7 @@ ZONE_CONTAINER::ZONE_CONTAINER( BOARD_ITEM_CONTAINER* aParent, bool aInModule )
m_cornerRadius = 0;
SetLocalFlags( 0 ); // flags tempoarry used in zone calculations
m_Poly = new SHAPE_POLY_SET(); // Outlines
m_fillVersion = 6; // set the "old" way to build filled polygon areas (before 6.0.x)
m_fillVersion = 5; // set the "old" way to build filled polygon areas (before 6.0.x)
m_islandRemovalMode = ISLAND_REMOVAL_MODE::ALWAYS;
aParent->GetZoneSettings().ExportSetting( *this );
@ -363,6 +363,15 @@ void ZONE_CONTAINER::SetCornerRadius( unsigned int aRadius )
}
bool ZONE_CONTAINER::GetFilledPolysUseThickness( PCB_LAYER_ID aLayer ) const
{
if( ZONE_FILLER::s_DumpZonesWhenFilling && LSET::InternalCuMask().Contains( aLayer ) )
return false;
return GetFilledPolysUseThickness();
}
bool ZONE_CONTAINER::HitTest( const wxPoint& aPosition, int aAccuracy ) const
{
// Normally accuracy is zoom-relative, but for the generic HitTest we just use

View File

@ -680,6 +680,7 @@ public:
unsigned int GetCornerRadius() const { return m_cornerRadius; }
bool GetFilledPolysUseThickness() const { return m_fillVersion == 5; }
bool GetFilledPolysUseThickness( PCB_LAYER_ID aLayer ) const;
int GetFillVersion() const { return m_fillVersion; }
void SetFillVersion( int aVersion ) { m_fillVersion = aVersion; }

View File

@ -1260,7 +1260,11 @@ void PCB_PAINTER::draw( const ZONE_CONTAINER* aZone, int aLayer )
return;
// Set up drawing options
int outline_thickness = aZone->GetFilledPolysUseThickness() ? aZone->GetMinThickness() : 0;
int outline_thickness = 0;
if( aZone->GetFilledPolysUseThickness( layer ) )
outline_thickness = aZone->GetMinThickness();
m_gal->SetStrokeColor( color );
m_gal->SetFillColor( color );
m_gal->SetLineWidth( outline_thickness );

View File

@ -41,7 +41,6 @@
#include <board_commit.h>
#include <widgets/progress_reporter.h>
#include <geometry/shape_poly_set.h>
#include <geometry/shape_file_io.h>
#include <geometry/convex_hull.h>
#include <geometry/geometry_utils.h>
#include <confirm.h>
@ -50,7 +49,6 @@
#include "zone_filler.h"
static const double s_RoundPadThermalSpokeAngle = 450; // in deci-degrees
static const bool s_DumpZonesWhenFilling = false;
ZONE_FILLER::ZONE_FILLER( BOARD* aBoard, COMMIT* aCommit ) :
@ -324,6 +322,9 @@ bool ZONE_FILLER::Fill( std::vector<ZONE_CONTAINER*>& aZones, bool aCheck, wxWin
{
for( PCB_LAYER_ID layer : zone.m_zone->GetLayerSet().Seq() )
{
if( s_DumpZonesWhenFilling && LSET::InternalCuMask().Contains( layer ) )
continue;
if( !zone.m_islands.count( layer ) )
continue;
@ -362,6 +363,9 @@ bool ZONE_FILLER::Fill( std::vector<ZONE_CONTAINER*>& aZones, bool aCheck, wxWin
{
for( PCB_LAYER_ID layer : zone->GetLayerSet().Seq() )
{
if( s_DumpZonesWhenFilling && LSET::InternalCuMask().Contains( layer ) )
continue;
SHAPE_POLY_SET poly = zone->GetFilledPolysList( layer );
for( int ii = 0; ii < poly.OutlineCount(); ii++ )
@ -893,6 +897,18 @@ void ZONE_FILLER::buildCopperItemClearances( const ZONE_CONTAINER* aZone, PCB_LA
}
#define DUMP_POLYS_TO_COPPER_LAYER( a, b, c ) \
{ if( s_DumpZonesWhenFilling && dumpLayer == b ) \
{ \
m_board->SetLayerName( b, c ); \
a.Simplify( SHAPE_POLY_SET::PM_STRICTLY_SIMPLE ); \
a.Fracture( SHAPE_POLY_SET::PM_STRICTLY_SIMPLE ); \
aRawPolys = a; \
aFinalPolys = a; \
return; \
} \
}
/**
* 1 - Creates the main zone outline using a correction to shrink the resulting area by
* m_ZoneMinThickness / 2. The result is areas with a margin of m_ZoneMinThickness / 2
@ -909,6 +925,11 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
SHAPE_POLY_SET& aRawPolys,
SHAPE_POLY_SET& aFinalPolys )
{
PCB_LAYER_ID dumpLayer = aLayer;
if( s_DumpZonesWhenFilling && LSET::InternalCuMask().Contains( aLayer ) )
aLayer = F_Cu;
m_maxError = m_board->GetDesignSettings().m_MaxError;
// Features which are min_width should survive pruning; features that are *less* than
@ -928,30 +949,20 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
std::deque<SHAPE_LINE_CHAIN> thermalSpokes;
SHAPE_POLY_SET clearanceHoles;
std::unique_ptr<SHAPE_FILE_IO> dumper( new SHAPE_FILE_IO(
s_DumpZonesWhenFilling ? "zones_dump.txt" : "", SHAPE_FILE_IO::IOM_APPEND ) );
aRawPolys = aSmoothedOutline;
if( s_DumpZonesWhenFilling )
dumper->BeginGroup( "clipper-zone" );
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In1_Cu, "smoothed-outline" );
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
knockoutThermalReliefs( aZone, aLayer, aRawPolys );
if( s_DumpZonesWhenFilling )
dumper->Write( &aRawPolys, "solid-areas-minus-thermal-reliefs" );
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In2_Cu, "minus-thermal-reliefs" );
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
buildCopperItemClearances( aZone, aLayer, clearanceHoles );
if( s_DumpZonesWhenFilling )
dumper->Write( &aRawPolys, "clearance holes" );
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
@ -965,12 +976,16 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
static const bool USE_BBOX_CACHES = true;
SHAPE_POLY_SET testAreas = aRawPolys;
testAreas.BooleanSubtract( clearanceHoles, SHAPE_POLY_SET::PM_FAST );
DUMP_POLYS_TO_COPPER_LAYER( testAreas, In3_Cu, "minus-clearance-holes" );
// Prune features that don't meet minimum-width criteria
if( half_min_width - epsilon > epsilon )
{
testAreas.Deflate( half_min_width - epsilon, numSegs, cornerStrategy );
DUMP_POLYS_TO_COPPER_LAYER( testAreas, In4_Cu, "spoke-test-deflated" );
testAreas.Inflate( half_min_width - epsilon, numSegs, cornerStrategy );
DUMP_POLYS_TO_COPPER_LAYER( testAreas, In5_Cu, "spoke-test-reinflated" );
}
if( m_progressReporter && m_progressReporter->IsCancelled() )
@ -1011,23 +1026,19 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
}
}
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
if( s_DumpZonesWhenFilling )
dumper->Write( &aRawPolys, "solid-areas-with-thermal-spokes" );
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In6_Cu, "plus-spokes" );
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
aRawPolys.BooleanSubtract( clearanceHoles, SHAPE_POLY_SET::PM_FAST );
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In7_Cu, "trimmed-spokes" );
// Prune features that don't meet minimum-width criteria
if( half_min_width - epsilon > epsilon )
aRawPolys.Deflate( half_min_width - epsilon, numSegs, cornerStrategy );
if( s_DumpZonesWhenFilling )
dumper->Write( &aRawPolys, "solid-areas-before-hatching" );
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In8_Cu, "deflated" );
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
@ -1036,8 +1047,7 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
if( aZone->GetFillMode() == ZONE_FILL_MODE::HATCH_PATTERN )
addHatchFillTypeOnZone( aZone, aLayer, aRawPolys );
if( s_DumpZonesWhenFilling )
dumper->Write( &aRawPolys, "solid-areas-after-hatching" );
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In9_Cu, "after-hatching" );
if( m_progressReporter && m_progressReporter->IsCancelled() )
return;
@ -1053,6 +1063,8 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
aRawPolys.Inflate( half_min_width - epsilon, numSegs, cornerStrategy );
}
DUMP_POLYS_TO_COPPER_LAYER( aRawPolys, In10_Cu, "after-reinflating" );
// Ensure additive changes (thermal stubs and particularly inflating acute corners) do not
// add copper outside the zone boundary or inside the clearance holes
aRawPolys.BooleanIntersection( aSmoothedOutline, SHAPE_POLY_SET::PM_FAST );
@ -1060,13 +1072,7 @@ void ZONE_FILLER::computeRawFilledArea( const ZONE_CONTAINER* aZone, PCB_LAYER_I
aRawPolys.Fracture( SHAPE_POLY_SET::PM_FAST );
if( s_DumpZonesWhenFilling )
dumper->Write( &aRawPolys, "areas_fractured" );
aFinalPolys = aRawPolys;
if( s_DumpZonesWhenFilling )
dumper->EndGroup();
}

View File

@ -47,6 +47,8 @@ public:
bool Fill( std::vector<ZONE_CONTAINER*>& aZones, bool aCheck = false,
wxWindow* aParent = nullptr );
static const bool s_DumpZonesWhenFilling = true;
private:
void addKnockout( D_PAD* aPad, PCB_LAYER_ID aLayer, int aGap, SHAPE_POLY_SET& aHoles );