Fix rendering/plotting of arcs with tiny angle and huge radius.
Fixes https://gitlab.com/kicad/code/kicad/-/issues/17343
(cherry picked from commit 4d66a8ebdb
)
This commit is contained in:
parent
ed89827908
commit
6df17bba99
|
@ -879,19 +879,19 @@ void GERBER_PLOTTER::plotArc( const SHAPE_ARC& aArc, bool aPlotInRegion )
|
|||
|
||||
|
||||
void GERBER_PLOTTER::plotArc( const VECTOR2I& aCenter, const EDA_ANGLE& aStartAngle,
|
||||
const EDA_ANGLE& aEndAngle, int aRadius, bool aPlotInRegion )
|
||||
const EDA_ANGLE& aEndAngle, double aRadius, bool aPlotInRegion )
|
||||
{
|
||||
VECTOR2I start, end;
|
||||
start.x = aCenter.x + KiROUND( aRadius * aStartAngle.Cos() );
|
||||
start.y = aCenter.y + KiROUND( aRadius * aStartAngle.Sin() );
|
||||
start.x = KiROUND( aCenter.x + aRadius * aStartAngle.Cos() );
|
||||
start.y = KiROUND( aCenter.y + aRadius * aStartAngle.Sin() );
|
||||
|
||||
if( !aPlotInRegion )
|
||||
MoveTo( start );
|
||||
else
|
||||
LineTo( start );
|
||||
|
||||
end.x = aCenter.x + KiROUND( aRadius * aEndAngle.Cos() );
|
||||
end.y = aCenter.y + KiROUND( aRadius * aEndAngle.Sin() );
|
||||
end.x = KiROUND( aCenter.x + aRadius * aEndAngle.Cos() );
|
||||
end.y = KiROUND( aCenter.y + aRadius * aEndAngle.Sin() );
|
||||
VECTOR2D devEnd = userToDeviceCoordinates( end );
|
||||
// devRelCenter is the position on arc center relative to the arc start, in Gerber coord.
|
||||
VECTOR2D devRelCenter = userToDeviceCoordinates( aCenter ) - userToDeviceCoordinates( start );
|
||||
|
|
|
@ -581,11 +581,11 @@ void HPGL_PLOTTER::Arc( const VECTOR2D& aCenter, const EDA_ANGLE& aStartAngle,
|
|||
EDA_ANGLE startAngle = -aStartAngle;
|
||||
|
||||
// Calculate arc start point:
|
||||
VECTOR2I cmap( aCenter.x + KiROUND( aRadius * startAngle.Cos() ),
|
||||
aCenter.y - KiROUND( aRadius * startAngle.Sin() ) );
|
||||
VECTOR2I cmap( KiROUND( aCenter.x + aRadius * startAngle.Cos() ),
|
||||
KiROUND( aCenter.y - aRadius * startAngle.Sin() ) );
|
||||
VECTOR2D cmap_dev = userToDeviceCoordinates( cmap );
|
||||
|
||||
startOrAppendItem( cmap_dev, wxString::Format( "AA %.0f,%.0f,%.0f,%g",
|
||||
startOrAppendItem( cmap_dev, wxString::Format( "AA %.0f,%.0f,%g,%g",
|
||||
centre_device.x,
|
||||
centre_device.y,
|
||||
angle.AsDegrees(),
|
||||
|
|
|
@ -354,21 +354,21 @@ void PDF_PLOTTER::Arc( const VECTOR2D& aCenter, const EDA_ANGLE& aStartAngle,
|
|||
SetCurrentLineWidth( aWidth );
|
||||
|
||||
// Usual trig arc plotting routine...
|
||||
start.x = aCenter.x + KiROUND( aRadius * (-startAngle).Cos() );
|
||||
start.y = aCenter.y + KiROUND( aRadius * (-startAngle).Sin() );
|
||||
start.x = KiROUND( aCenter.x + aRadius * ( -startAngle ).Cos() );
|
||||
start.y = KiROUND( aCenter.y + aRadius * ( -startAngle ).Sin() );
|
||||
VECTOR2D pos_dev = userToDeviceCoordinates( start );
|
||||
fprintf( m_workFile, "%g %g m ", pos_dev.x, pos_dev.y );
|
||||
|
||||
for( EDA_ANGLE ii = startAngle + delta; ii < endAngle; ii += delta )
|
||||
{
|
||||
end.x = aCenter.x + KiROUND( aRadius * (-ii).Cos() );
|
||||
end.y = aCenter.y + KiROUND( aRadius * (-ii).Sin() );
|
||||
end.x = KiROUND( aCenter.x + aRadius * ( -ii ).Cos() );
|
||||
end.y = KiROUND( aCenter.y + aRadius * ( -ii ).Sin() );
|
||||
pos_dev = userToDeviceCoordinates( end );
|
||||
fprintf( m_workFile, "%g %g l ", pos_dev.x, pos_dev.y );
|
||||
}
|
||||
|
||||
end.x = aCenter.x + KiROUND( aRadius * (-endAngle).Cos() );
|
||||
end.y = aCenter.y + KiROUND( aRadius * (-endAngle).Sin() );
|
||||
end.x = KiROUND( aCenter.x + aRadius * ( -endAngle ).Cos() );
|
||||
end.y = KiROUND( aCenter.y + aRadius * ( -endAngle ).Sin() );
|
||||
pos_dev = userToDeviceCoordinates( end );
|
||||
fprintf( m_workFile, "%g %g l ", pos_dev.x, pos_dev.y );
|
||||
|
||||
|
|
|
@ -292,7 +292,7 @@ protected:
|
|||
* be initialized before calling it if needed.
|
||||
*/
|
||||
void plotArc( const VECTOR2I& aCenter, const EDA_ANGLE& aStartAngle, const EDA_ANGLE& aEndAngle,
|
||||
int aRadius, bool aPlotInRegion );
|
||||
double aRadius, bool aPlotInRegion );
|
||||
void plotArc( const SHAPE_ARC& aArc, bool aPlotInRegion );
|
||||
|
||||
/**
|
||||
|
|
|
@ -193,8 +193,7 @@ bool TestSegmentHit( const VECTOR2I& aRefPoint, const VECTOR2I& aStart, const VE
|
|||
*/
|
||||
inline double GetLineLength( const VECTOR2I& aPointA, const VECTOR2I& aPointB )
|
||||
{
|
||||
// Implicitly casted to double
|
||||
return hypot( aPointA.x - aPointB.x, aPointA.y - aPointB.y );
|
||||
return hypot( (double) aPointA.x - aPointB.x, (double) aPointA.y - aPointB.y );
|
||||
}
|
||||
|
||||
// These are the usual degrees <-> radians conversion routines
|
||||
|
|
|
@ -1355,7 +1355,10 @@ EDA_ANGLE PCB_ARC::GetAngle() const
|
|||
|
||||
EDA_ANGLE PCB_ARC::GetArcAngleStart() const
|
||||
{
|
||||
EDA_ANGLE angleStart( m_Start - GetPosition() );
|
||||
VECTOR2I pos( GetPosition() );
|
||||
VECTOR2D dir( (double) m_Start.x - pos.x, (double) m_Start.y - pos.y );
|
||||
|
||||
EDA_ANGLE angleStart( dir );
|
||||
return angleStart.Normalize();
|
||||
}
|
||||
|
||||
|
@ -1363,7 +1366,10 @@ EDA_ANGLE PCB_ARC::GetArcAngleStart() const
|
|||
// Note: used in python tests. Ignore CLion's claim that it's unused....
|
||||
EDA_ANGLE PCB_ARC::GetArcAngleEnd() const
|
||||
{
|
||||
EDA_ANGLE angleEnd( m_End - GetPosition() );
|
||||
VECTOR2I pos( GetPosition() );
|
||||
VECTOR2D dir( (double) m_End.x - pos.x, (double) m_End.y - pos.y );
|
||||
|
||||
EDA_ANGLE angleEnd( dir );
|
||||
return angleEnd.Normalize();
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue