Performance: remove associated triangle sets when removing outline.

This saves us having to re-triangulate at the end of zone filling.
This commit is contained in:
Jeff Young 2022-02-16 17:00:54 +00:00
parent 327ddad79f
commit b1bd8421e0
6 changed files with 55 additions and 24 deletions

View File

@ -155,6 +155,7 @@ public:
size_t GetTriangleCount() const { return m_triangles.size(); }
int GetSourceOutlineIndex() const { return m_sourceOutline; }
void SetSourceOutlineIndex( int aIndex ) { m_sourceOutline = aIndex; }
std::deque<TRI>& Triangles() { return m_triangles; }
const std::deque<TRI>& Triangles() const { return m_triangles; }
@ -1251,6 +1252,12 @@ public:
///< Delete \a aIdx-th polygon from the set.
void DeletePolygon( int aIdx );
///< Delete \a aIdx-th polygon and its triangulation data from the set.
///< If called with \a aUpdateHash false, caller must call UpdateTriangulationDataHash().
void DeletePolygonAndTriangulationData( int aIdx, bool aUpdateHash = true );
void UpdateTriangulationDataHash();
/**
* Return a chamfered version of the \a aIndex-th polygon.
*

View File

@ -1639,6 +1639,34 @@ void SHAPE_POLY_SET::DeletePolygon( int aIdx )
}
void SHAPE_POLY_SET::DeletePolygonAndTriangulationData( int aIdx, bool aUpdateHash )
{
m_polys.erase( m_polys.begin() + aIdx );
if( m_triangulationValid )
{
for( int ii = m_triangulatedPolys.size() - 1; ii >= 0; --ii )
{
std::unique_ptr<TRIANGULATED_POLYGON>& triangleSet = m_triangulatedPolys[ii];
if( triangleSet->GetSourceOutlineIndex() == aIdx )
m_triangulatedPolys.erase( m_triangulatedPolys.begin() + ii );
else if( triangleSet->GetSourceOutlineIndex() > aIdx )
triangleSet->SetSourceOutlineIndex( triangleSet->GetSourceOutlineIndex() - 1 );
}
if( aUpdateHash )
m_hash = checksum();
}
}
void SHAPE_POLY_SET::UpdateTriangulationDataHash()
{
m_hash = checksum();
}
void SHAPE_POLY_SET::Append( const SHAPE_POLY_SET& aSet )
{
m_polys.insert( m_polys.end(), aSet.m_polys.begin(), aSet.m_polys.end() );

View File

@ -139,17 +139,12 @@ void PCB_EDIT_FRAME::Edit_Zone_Params( ZONE* aZone )
reporter = std::make_unique<WX_PROGRESS_REPORTER>( this, title, 4 );
filler.SetProgressReporter( reporter.get() );
if( !filler.Fill( zones_to_refill ) )
{
GetBoard()->GetConnectivity()->Build( GetBoard() );
// User has already OK'ed dialog so we're going to go ahead and commit even if the
// fill was cancelled.
}
(void) filler.Fill( zones_to_refill );
}
}
commit.Push( _( "Modify zone properties" ) );
GetBoard()->GetConnectivity()->RecalculateRatsnest();
commit.Push( _( "Modify zone properties" ), true, true, false );
GetBoard()->GetConnectivity()->Build( GetBoard() );
pickedList.ClearItemsList(); // s_ItemsListPicker is no longer owner of picked items
}

View File

@ -967,10 +967,9 @@ bool PCB_EDIT_FRAME::OpenProjectFiles( const std::vector<wxString>& aFileSet, in
filler.SetProgressReporter( &progressReporter );
if( filler.Fill( toFill ) )
{
commit.Push( _( "Convert Zone(s)" ) );
GetBoard()->BuildConnectivity( &progressReporter );
}
commit.Push( _( "Convert Zone(s)" ), true, true, false );
GetBoard()->BuildConnectivity( &progressReporter );
}
// from EDA_APPL which was first loaded BOARD only:

View File

@ -84,8 +84,7 @@ void ZONE_FILLER_TOOL::CheckAllZones( wxWindow* aCaller, PROGRESS_REPORTER* aRep
if( filler.Fill( toFill, true, aCaller ) )
{
board()->GetConnectivity()->Build( board() );
commit.Push( _( "Fill Zone(s)" ) );
commit.Push( _( "Fill Zone(s)" ), true, true, false );
getEditFrame<PCB_EDIT_FRAME>()->m_ZoneFillsDirty = false;
}
else
@ -93,6 +92,8 @@ void ZONE_FILLER_TOOL::CheckAllZones( wxWindow* aCaller, PROGRESS_REPORTER* aRep
commit.Revert();
}
board()->GetConnectivity()->Build( board() );
canvas()->Refresh();
m_fillInProgress = false;
}
@ -157,8 +158,6 @@ void ZONE_FILLER_TOOL::FillAllZones( wxWindow* aCaller, PROGRESS_REPORTER* aRepo
if( filler.Fill( toFill ) )
{
reporter->AdvancePhase();
board()->GetConnectivity()->Build( board(), reporter.get() );
commit.Push( _( "Fill Zone(s)" ), true, true, false );
frame->m_ZoneFillsDirty = false;
}
@ -167,6 +166,8 @@ void ZONE_FILLER_TOOL::FillAllZones( wxWindow* aCaller, PROGRESS_REPORTER* aRepo
commit.Revert();
}
board()->GetConnectivity()->Build( board(), reporter.get() );
if( filler.IsDebug() )
frame->UpdateUserInterface();
@ -214,12 +215,14 @@ int ZONE_FILLER_TOOL::ZoneFill( const TOOL_EVENT& aEvent )
if( filler.Fill( toFill ) )
{
reporter->AdvancePhase();
board()->GetConnectivity()->Build( board(), reporter.get() );
commit.Push( _( "Fill Zone(s)" ), true, true, false );
}
else
{
commit.Revert();
}
board()->GetConnectivity()->Build( board(), reporter.get() );
canvas()->Refresh();
m_fillInProgress = false;

View File

@ -347,13 +347,14 @@ bool ZONE_FILLER::Fill( std::vector<ZONE*>& aZones, bool aCheck, wxWindow* aPare
SHAPE_LINE_CHAIN& outline = poly->Outline( idx );
if( mode == ISLAND_REMOVAL_MODE::ALWAYS )
poly->DeletePolygon( idx );
poly->DeletePolygonAndTriangulationData( idx, false );
else if ( mode == ISLAND_REMOVAL_MODE::AREA && outline.Area() < minArea )
poly->DeletePolygon( idx );
poly->DeletePolygonAndTriangulationData( idx, false );
else
zone.m_zone->SetIsIsland( layer, idx );
}
poly->UpdateTriangulationDataHash();
zone.m_zone->CalculateFilledArea();
if( m_progressReporter && m_progressReporter->IsCancelled() )
@ -378,9 +379,10 @@ bool ZONE_FILLER::Fill( std::vector<ZONE*>& aZones, bool aCheck, wxWindow* aPare
std::vector<SHAPE_LINE_CHAIN>& island = poly->Polygon( ii );
if( island.empty() || !m_boardOutline.Contains( island.front().CPoint( 0 ) ) )
poly->DeletePolygon( ii );
poly->DeletePolygonAndTriangulationData( ii, false );
}
poly->UpdateTriangulationDataHash();
zone->CalculateFilledArea();
if( m_progressReporter && m_progressReporter->IsCancelled() )
@ -388,9 +390,6 @@ bool ZONE_FILLER::Fill( std::vector<ZONE*>& aZones, bool aCheck, wxWindow* aPare
}
}
// Re-cache triangulation after removing islands
m_board->CacheTriangulation( m_progressReporter, aZones );
if( aCheck )
{
bool outOfDate = false;