Use SCOPED_FLAGS_CLEANER more carefully.

Other methods used ConvertOutlineToPolygon's SKIP_STRUCT state.

Fixes https://gitlab.com/kicad/code/kicad/-/issues/16321
This commit is contained in:
Alex Shvartzkop 2023-12-09 19:24:47 +03:00
parent d8bb9b1e66
commit a161829f86
1 changed files with 36 additions and 21 deletions

View File

@ -180,9 +180,10 @@ static bool isCopperOutside( const FOOTPRINT* aFootprint, SHAPE_POLY_SET& aShape
}
bool ConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SET& aPolygons,
int aErrorMax, int aChainingEpsilon, bool aAllowDisjoint,
OUTLINE_ERROR_HANDLER* aErrorHandler, bool aAllowUseArcsInPolygons )
bool doConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SET& aPolygons,
int aErrorMax, int aChainingEpsilon, bool aAllowDisjoint,
OUTLINE_ERROR_HANDLER* aErrorHandler, bool aAllowUseArcsInPolygons,
SCOPED_FLAGS_CLEANER& aCleaner )
{
if( aShapeList.size() == 0 )
return true;
@ -209,7 +210,6 @@ bool ConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SE
VECTOR2I prevPt;
std::vector<SHAPE_LINE_CHAIN> contours;
SCOPED_FLAGS_CLEANER cleaner( SKIP_STRUCT );
for( PCB_SHAPE* shape : startCandidates )
shape->ClearFlags( SKIP_STRUCT );
@ -218,7 +218,7 @@ bool ConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SE
{
graphic = (PCB_SHAPE*) *startCandidates.begin();
graphic->SetFlags( SKIP_STRUCT );
cleaner.insert( graphic );
aCleaner.insert( graphic );
startCandidates.erase( startCandidates.begin() );
contours.emplace_back();
@ -438,7 +438,7 @@ bool ConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SE
prevGraphic = graphic;
graphic = nextGraphic;
graphic->SetFlags( SKIP_STRUCT );
cleaner.insert( graphic );
aCleaner.insert( graphic );
startCandidates.erase( graphic );
continue;
}
@ -587,6 +587,18 @@ bool ConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SE
}
bool ConvertOutlineToPolygon( std::vector<PCB_SHAPE*>& aShapeList, SHAPE_POLY_SET& aPolygons,
int aErrorMax, int aChainingEpsilon, bool aAllowDisjoint,
OUTLINE_ERROR_HANDLER* aErrorHandler, bool aAllowUseArcsInPolygons )
{
SCOPED_FLAGS_CLEANER cleaner( SKIP_STRUCT );
return doConvertOutlineToPolygon( aShapeList, aPolygons, aErrorMax, aChainingEpsilon,
aAllowDisjoint, aErrorHandler, aAllowUseArcsInPolygons,
cleaner );
}
bool TestBoardOutlinesGraphicItems( BOARD* aBoard, int aMinDist,
OUTLINE_ERROR_HANDLER* aErrorHandler )
{
@ -724,10 +736,11 @@ bool BuildBoardPolygonOutlines( BOARD* aBoard, SHAPE_POLY_SET& aOutlines, int aE
int aChainingEpsilon, OUTLINE_ERROR_HANDLER* aErrorHandler,
bool aAllowUseArcsInPolygons )
{
PCB_TYPE_COLLECTOR items;
bool success = false;
PCB_TYPE_COLLECTOR items;
SHAPE_POLY_SET fpHoles;
bool success = false;
SHAPE_POLY_SET fpHoles;
SCOPED_FLAGS_CLEANER cleaner( SKIP_STRUCT );
// Get all the shapes into 'items', then keep only those on layer == Edge_Cuts.
items.Collect( aBoard, { PCB_SHAPE_T } );
@ -753,11 +766,11 @@ bool BuildBoardPolygonOutlines( BOARD* aBoard, SHAPE_POLY_SET& aOutlines, int aE
if( !fpSegList.empty() )
{
SHAPE_POLY_SET fpOutlines;
success = ConvertOutlineToPolygon( fpSegList, fpOutlines, aErrorMax, aChainingEpsilon,
false,
// don't report errors here; the second pass also
// gets an opportunity to use these segments
nullptr, aAllowUseArcsInPolygons );
success = doConvertOutlineToPolygon( fpSegList, fpOutlines, aErrorMax, aChainingEpsilon,
false,
// don't report errors here; the second pass also
// gets an opportunity to use these segments
nullptr, aAllowUseArcsInPolygons, cleaner );
// Test to see if we should make holes or outlines. Holes are made if the footprint
// has copper outside of a single, closed outline. If there are multiple outlines,
@ -795,8 +808,8 @@ bool BuildBoardPolygonOutlines( BOARD* aBoard, SHAPE_POLY_SET& aOutlines, int aE
if( segList.size() )
{
success = ConvertOutlineToPolygon( segList, aOutlines, aErrorMax, aChainingEpsilon,
true, aErrorHandler, aAllowUseArcsInPolygons );
success = doConvertOutlineToPolygon( segList, aOutlines, aErrorMax, aChainingEpsilon, true,
aErrorHandler, aAllowUseArcsInPolygons, cleaner );
}
if( !success || !aOutlines.OutlineCount() )
@ -976,9 +989,11 @@ bool BuildFootprintPolygonOutlines( BOARD* aBoard, SHAPE_POLY_SET& aOutlines, in
return false;
}
PCB_TYPE_COLLECTOR items;
SHAPE_POLY_SET outlines;
bool success = false;
PCB_TYPE_COLLECTOR items;
SHAPE_POLY_SET outlines;
bool success = false;
SCOPED_FLAGS_CLEANER cleaner( SKIP_STRUCT );
// Get all the SHAPEs into 'items', then keep only those on layer == Edge_Cuts.
items.Collect( aBoard, { PCB_SHAPE_T } );
@ -994,8 +1009,8 @@ bool BuildFootprintPolygonOutlines( BOARD* aBoard, SHAPE_POLY_SET& aOutlines, in
if( !segList.empty() )
{
success = ConvertOutlineToPolygon( segList, outlines, aErrorMax, aChainingEpsilon,
true, aErrorHandler );
success = doConvertOutlineToPolygon( segList, outlines, aErrorMax, aChainingEpsilon, true,
aErrorHandler, false, cleaner );
}
// A closed outline was found on Edge_Cuts