Moved utilities for angles in trigo.h

New conversion routines and sin/cos implementation for angles in decidegrees
This commit is contained in:
Lorenzo Marcantonio 2013-05-02 20:06:58 +02:00
parent 226b3d64be
commit 78e41187b3
47 changed files with 187 additions and 155 deletions

View File

@ -387,7 +387,7 @@ void PLOTTER::segmentAsOval( const wxPoint& start, const wxPoint& end, int width
else if( size.x == 0 ) else if( size.x == 0 )
orient = 900; orient = 900;
else else
orient = -(int) ( RAD2DEG( atan2( (double)size.y, (double)size.x ) ) * 10.0 ); orient = -ArcTangente( size.y, size.x );
size.x = KiROUND( hypot( size.x, size.y ) ) + width; size.x = KiROUND( hypot( size.x, size.y ) ) + width;
size.y = width; size.y = width;
@ -407,9 +407,7 @@ void PLOTTER::sketchOval( const wxPoint& pos, const wxSize& aSize, int orient,
if( size.x > size.y ) if( size.x > size.y )
{ {
EXCHG( size.x, size.y ); EXCHG( size.x, size.y );
orient += 900; orient = AddAngles( orient, 900 );
if( orient >= 3600 )
orient -= 3600;
} }
deltaxy = size.y - size.x; /* distance between centers of the oval */ deltaxy = size.y - size.x; /* distance between centers of the oval */

View File

@ -423,9 +423,7 @@ void DXF_PLOTTER::FlashPadOval( const wxPoint& pos, const wxSize& aSize, int ori
if( size.x > size.y ) if( size.x > size.y )
{ {
EXCHG( size.x, size.y ); EXCHG( size.x, size.y );
orient += 900; orient = AddAngles( orient, 900 );
if( orient >= 3600 )
orient -= 3600;
} }
sketchOval( pos, size, orient, -1 ); sketchOval( pos, size, orient, -1 );
} }

View File

@ -287,12 +287,12 @@ void GERBER_PLOTTER::Arc( const wxPoint& aCenter, int aStAngle, int aEndAngle,
{ {
wxASSERT( outputFile ); wxASSERT( outputFile );
wxPoint start, end; wxPoint start, end;
start.x = aCenter.x + KiROUND( aRadius*cos( DEG2RAD( aStAngle/10.0 ) ) ); start.x = aCenter.x + KiROUND( cosdecideg( aRadius, aStAngle ) );
start.y = aCenter.y - KiROUND( aRadius*sin( DEG2RAD( aStAngle/10.0 ) ) ); start.y = aCenter.y - KiROUND( sindecideg( aRadius, aStAngle ) );
SetCurrentLineWidth( aWidth ); SetCurrentLineWidth( aWidth );
MoveTo( start ); MoveTo( start );
end.x = aCenter.x + KiROUND( aRadius*cos( DEG2RAD( aEndAngle/10.0 ) ) ); end.x = aCenter.x + KiROUND( cosdecideg( aRadius, aEndAngle ) );
end.y = aCenter.y - KiROUND( aRadius*sin( DEG2RAD( aEndAngle/10.0 ) ) ); end.y = aCenter.y - KiROUND( sindecideg( aRadius, aEndAngle ) );
DPOINT devEnd = userToDeviceCoordinates( end ); DPOINT devEnd = userToDeviceCoordinates( end );
DPOINT devCenter = userToDeviceCoordinates( aCenter ) DPOINT devCenter = userToDeviceCoordinates( aCenter )
- userToDeviceCoordinates( start ); - userToDeviceCoordinates( start );

View File

@ -401,8 +401,8 @@ void HPGL_PLOTTER::Arc( const wxPoint& centre, int StAngle, int EndAngle, int ra
// Calculate start point, // Calculate start point,
wxPoint cmap; wxPoint cmap;
cmap.x = int( centre.x + ( radius * cos( DEG2RAD( StAngle / 10.0 ) ) ) ); cmap.x = centre.x + KiROUND( cosdecideg( radius, StAngle ) );
cmap.y = int( centre.y - ( radius * sin( DEG2RAD( StAngle / 10.0 ) ) ) ); cmap.y = centre.y - KiROUND( sindecideg( radius, StAngle ) );
DPOINT cmap_dev = userToDeviceCoordinates( cmap ); DPOINT cmap_dev = userToDeviceCoordinates( cmap );
fprintf( outputFile, fprintf( outputFile,
@ -431,10 +431,8 @@ void HPGL_PLOTTER::FlashPadOval( const wxPoint& pos, const wxSize& aSize, int or
*/ */
if( size.x > size.y ) if( size.x > size.y )
{ {
EXCHG( size.x, size.y ); orient += 900; EXCHG( size.x, size.y );
orient = AddAngles( orient, 900 );
if( orient >= 3600 )
orient -= 3600;
} }
deltaxy = size.y - size.x; // distance between centers of the oval deltaxy = size.y - size.x; // distance between centers of the oval

View File

@ -219,23 +219,20 @@ void PDF_PLOTTER::Arc( const wxPoint& centre, int StAngle, int EndAngle, int rad
SetCurrentLineWidth( width ); SetCurrentLineWidth( width );
// Usual trig arc plotting routine... // Usual trig arc plotting routine...
double alpha = DEG2RAD( StAngle / 10.0 ); start.x = centre.x + KiROUND( cosdecideg( radius, -StAngle ) );
start.x = centre.x + (int) ( radius * cos( -alpha ) ); start.y = centre.y + KiROUND( sindecideg( radius, -StAngle ) );
start.y = centre.y + (int) ( radius * sin( -alpha ) );
DPOINT pos_dev = userToDeviceCoordinates( start ); DPOINT pos_dev = userToDeviceCoordinates( start );
fprintf( workFile, "%g %g m ", pos_dev.x, pos_dev.y ); fprintf( workFile, "%g %g m ", pos_dev.x, pos_dev.y );
for( int ii = StAngle + delta; ii < EndAngle; ii += delta ) for( int ii = StAngle + delta; ii < EndAngle; ii += delta )
{ {
alpha = DEG2RAD( ii / 10.0 ); end.x = centre.x + KiROUND( cosdecideg( radius, -ii ) );
end.x = centre.x + (int) ( radius * cos( -alpha ) ); end.y = centre.y + KiROUND( sindecideg( radius, -ii ) );
end.y = centre.y + (int) ( radius * sin( -alpha ) );
pos_dev = userToDeviceCoordinates( end ); pos_dev = userToDeviceCoordinates( end );
fprintf( workFile, "%g %g l ", pos_dev.x, pos_dev.y ); fprintf( workFile, "%g %g l ", pos_dev.x, pos_dev.y );
} }
alpha = DEG2RAD( EndAngle / 10.0 ); end.x = centre.x + KiROUND( cosdecideg( radius, -EndAngle ) );
end.x = centre.x + (int) ( radius * cos( -alpha ) ); end.y = centre.y + KiROUND( sindecideg( radius, -EndAngle ) );
end.y = centre.y + (int) ( radius * sin( -alpha ) );
pos_dev = userToDeviceCoordinates( end ); pos_dev = userToDeviceCoordinates( end );
fprintf( workFile, "%g %g l ", pos_dev.x, pos_dev.y ); fprintf( workFile, "%g %g l ", pos_dev.x, pos_dev.y );

View File

@ -75,9 +75,7 @@ void PSLIKE_PLOTTER::FlashPadOval( const wxPoint& pos, const wxSize& aSize, int
if( size.x > size.y ) if( size.x > size.y )
{ {
EXCHG( size.x, size.y ); EXCHG( size.x, size.y );
orient += 900; orient = AddAngles( orient, 900 );
if( orient >= 3600 )
orient -= 3600;
} }
delta = size.y - size.x; delta = size.y - size.x;
@ -345,11 +343,6 @@ void PSLIKE_PLOTTER::computeTextParameters( const wxPoint& aPos,
double *ctm_f, double *ctm_f,
double *heightFactor ) double *heightFactor )
{ {
// These are for the rotation matrix
double alpha = DEG2RAD( aOrient / 10.0 );
double sinalpha = sin( alpha );
double cosalpha = cos( alpha );
// Compute the starting position (compensated for alignment) // Compute the starting position (compensated for alignment)
wxPoint start_pos = aPos; wxPoint start_pos = aPos;
@ -399,6 +392,10 @@ void PSLIKE_PLOTTER::computeTextParameters( const wxPoint& aPos,
*wideningFactor = sz_dev.y / sz_dev.x; *wideningFactor = sz_dev.y / sz_dev.x;
// The CTM transformation matrix // The CTM transformation matrix
double alpha = DECIDEG2RAD( aOrient );
double sinalpha = sin( alpha );
double cosalpha = cos( alpha );
*ctm_a = cosalpha; *ctm_a = cosalpha;
*ctm_b = sinalpha; *ctm_b = sinalpha;
*ctm_c = -sinalpha; *ctm_c = -sinalpha;

View File

@ -361,12 +361,12 @@ void SVG_PLOTTER::Arc( const wxPoint& centre, int StAngle, int EndAngle, int rad
start += centre_dev; start += centre_dev;
end += centre_dev; end += centre_dev;
double theta1 = StAngle * M_PI / 1800.0; double theta1 = DECIDEG2RAD( StAngle );
if( theta1 < 0 ) if( theta1 < 0 )
theta1 = theta1 + M_PI * 2; theta1 = theta1 + M_PI * 2;
double theta2 = EndAngle * M_PI / 1800.0; double theta2 = DECIDEG2RAD( EndAngle );
if( theta2 < 0 ) if( theta2 < 0 )
theta2 = theta2 + M_PI * 2; theta2 = theta2 + M_PI * 2;

View File

@ -199,7 +199,8 @@ double ArcTangente( int dy, int dx )
return 1800 - 450; return 1800 - 450;
} }
return atan2( dy, dx ) / M_PI * 1800; // Of course dy and dx are treated as double
return RAD2DECIDEG( atan2( dy, dx ) );
} }
@ -232,7 +233,7 @@ void RotatePoint( int* pX, int* pY, double angle )
} }
else else
{ {
double fangle = DEG2RAD( angle / 10.0 ); double fangle = DECIDEG2RAD( angle );
double sinus = sin( fangle ); double sinus = sin( fangle );
double cosinus = cos( fangle ); double cosinus = cos( fangle );
double fpx = (*pY * sinus ) + (*pX * cosinus ); double fpx = (*pY * sinus ) + (*pX * cosinus );
@ -313,7 +314,7 @@ void RotatePoint( double* pX, double* pY, double angle )
} }
else else
{ {
double fangle = DEG2RAD( angle / 10.0 ); double fangle = DECIDEG2RAD( angle );
double sinus = sin( fangle ); double sinus = sin( fangle );
double cosinus = cos( fangle ); double cosinus = cos( fangle );

View File

@ -7,7 +7,7 @@
#include "eda_doc.h" #include "eda_doc.h"
#include "kicad_string.h" #include "kicad_string.h"
#include "wxstruct.h" #include "wxstruct.h"
#include <macros.h>
#include "protos.h" #include "protos.h"
#include "class_library.h" #include "class_library.h"
#include "dialog_helpers.h" #include "dialog_helpers.h"

View File

@ -74,15 +74,15 @@ bool TRANSFORM::MapAngles( int* aAngle1, int* aAngle2 ) const
*aAngle2 += 1; *aAngle2 += 1;
} }
x = cos( *aAngle1 * M_PI / 1800.0 ); x = cos( DECIDEG2RAD( *aAngle1 ) );
y = sin( *aAngle1 * M_PI / 1800.0 ); y = sin( DECIDEG2RAD( *aAngle1 ) );
t = x * x1 + y * y1; t = x * x1 + y * y1;
y = x * x2 + y * y2; y = x * x2 + y * y2;
x = t; x = t;
*aAngle1 = KiROUND( ArcTangente( y, x ) ); *aAngle1 = KiROUND( ArcTangente( y, x ) );
x = cos( *aAngle2 * M_PI / 1800.0 ); x = cos( DECIDEG2RAD( *aAngle2 ) );
y = sin( *aAngle2 * M_PI / 1800.0 ); y = sin( DECIDEG2RAD( *aAngle2 ) );
t = x * x1 + y * y1; t = x * x1 + y * y1;
y = x * x2 + y * y2; y = x * x2 + y * y2;
x = t; x = t;

View File

@ -176,8 +176,8 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
ConvertShapeToPolygon( aParent, polybuffer ); ConvertShapeToPolygon( aParent, polybuffer );
// shape rotation: // shape rotation:
rotation = KiROUND( params[6].GetValue( tool ) * 10.0 ); rotation = params[6].GetValue( tool ) * 10.0;
if( rotation ) if( rotation != 0)
{ {
for( unsigned ii = 0; ii < polybuffer.size(); ii++ ) for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
RotatePoint( &polybuffer[ii], -rotation ); RotatePoint( &polybuffer[ii], -rotation );
@ -205,8 +205,8 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
ConvertShapeToPolygon( aParent, polybuffer ); ConvertShapeToPolygon( aParent, polybuffer );
// shape rotation: // shape rotation:
rotation = KiROUND( params[5].GetValue( tool ) * 10.0 ); rotation = params[5].GetValue( tool ) * 10.0;
if( rotation ) if( rotation != 0 )
{ {
for( unsigned ii = 0; ii < polybuffer.size(); ii++ ) for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
RotatePoint( &polybuffer[ii], -rotation ); RotatePoint( &polybuffer[ii], -rotation );
@ -234,8 +234,8 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
ConvertShapeToPolygon( aParent, polybuffer ); ConvertShapeToPolygon( aParent, polybuffer );
// shape rotation: // shape rotation:
rotation = KiROUND( params[5].GetValue( tool ) * 10.0 ); rotation = params[5].GetValue( tool ) * 10.0;
if( rotation ) if( rotation != 0)
{ {
for( unsigned ii = 0; ii < polybuffer.size(); ii++ ) for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
RotatePoint( &polybuffer[ii], -rotation ); RotatePoint( &polybuffer[ii], -rotation );
@ -264,7 +264,7 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
ConvertShapeToPolygon( aParent, polybuffer ); ConvertShapeToPolygon( aParent, polybuffer );
// shape rotation: // shape rotation:
rotation = KiROUND( params[5].GetValue( tool ) * 10.0 ); rotation = params[5].GetValue( tool ) * 10.0;
// Because a thermal shape has 4 identical sub-shapes, only one is created in polybuffer. // Because a thermal shape has 4 identical sub-shapes, only one is created in polybuffer.
// We must draw 4 sub-shapes rotated by 90 deg // We must draw 4 sub-shapes rotated by 90 deg
@ -329,7 +329,7 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
// Draw the cross: // Draw the cross:
ConvertShapeToPolygon( aParent, polybuffer ); ConvertShapeToPolygon( aParent, polybuffer );
rotation = KiROUND( params[8].GetValue( tool ) * 10.0 ); rotation = params[8].GetValue( tool ) * 10.0;
for( unsigned ii = 0; ii < polybuffer.size(); ii++ ) for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
{ {
// shape rotation: // shape rotation:
@ -352,7 +352,7 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
* type is not stored in parameters list, so the first parameter is exposure * type is not stored in parameters list, so the first parameter is exposure
*/ */
int numPoints = (int) params[1].GetValue( tool ); int numPoints = (int) params[1].GetValue( tool );
rotation = KiROUND( params[numPoints * 2 + 4].GetValue( tool ) * 10.0 ); rotation = params[numPoints * 2 + 4].GetValue( tool ) * 10.0;
wxPoint pos; wxPoint pos;
// Read points. numPoints does not include the starting point, so add 1. // Read points. numPoints does not include the starting point, so add 1.
for( int i = 0; i<numPoints + 1; ++i ) for( int i = 0; i<numPoints + 1; ++i )
@ -392,7 +392,7 @@ void AM_PRIMITIVE::DrawBasicShape( GERBER_DRAW_ITEM* aParent,
ConvertShapeToPolygon( aParent, polybuffer ); ConvertShapeToPolygon( aParent, polybuffer );
// rotate polygon and move it to the actual position // rotate polygon and move it to the actual position
rotation = KiROUND( params[5].GetValue( tool ) * 10.0 ); rotation = params[5].GetValue( tool ) * 10.0;
for( unsigned ii = 0; ii < polybuffer.size(); ii++ ) for( unsigned ii = 0; ii < polybuffer.size(); ii++ )
{ {
RotatePoint( &polybuffer[ii], -rotation ); RotatePoint( &polybuffer[ii], -rotation );
@ -512,8 +512,7 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( GERBER_DRAW_ITEM* aParent,
int outerRadius = scaletoIU( params[2].GetValue( tool ), m_GerbMetric ) / 2; int outerRadius = scaletoIU( params[2].GetValue( tool ), m_GerbMetric ) / 2;
int innerRadius = scaletoIU( params[3].GetValue( tool ), m_GerbMetric ) / 2; int innerRadius = scaletoIU( params[3].GetValue( tool ), m_GerbMetric ) / 2;
int halfthickness = scaletoIU( params[4].GetValue( tool ), m_GerbMetric ) / 2; int halfthickness = scaletoIU( params[4].GetValue( tool ), m_GerbMetric ) / 2;
int angle_start = KiROUND( asin( int angle_start = RAD2DECIDEG( asin( (double) halfthickness / innerRadius ) );
(double) halfthickness / innerRadius ) * 1800 / M_PI );
// Draw shape in the first cadrant (X and Y > 0) // Draw shape in the first cadrant (X and Y > 0)
wxPoint pos, startpos; wxPoint pos, startpos;
@ -537,7 +536,7 @@ void AM_PRIMITIVE::ConvertShapeToPolygon( GERBER_DRAW_ITEM* aParent,
// outer arc // outer arc
startpos.x = outerRadius; startpos.x = outerRadius;
startpos.y = 0; startpos.y = 0;
angle_start = KiROUND( asin( (double) halfthickness / outerRadius ) * 1800 / M_PI ); angle_start = RAD2DECIDEG( asin( (double) halfthickness / outerRadius ) );
angle_end = 900 - angle_start; angle_end = 900 - angle_start;
// First point, near Y axis, outer arc // First point, near Y axis, outer arc

View File

@ -115,7 +115,7 @@ wxPoint GERBER_DRAW_ITEM::GetABPosition( const wxPoint& aXYPosition ) const
abPos += m_layerOffset + m_imageParams->m_ImageOffset; abPos += m_layerOffset + m_imageParams->m_ImageOffset;
abPos.x = KiROUND( abPos.x * m_drawScale.x ); abPos.x = KiROUND( abPos.x * m_drawScale.x );
abPos.y = KiROUND( abPos.y * m_drawScale.y ); abPos.y = KiROUND( abPos.y * m_drawScale.y );
int rotation = KiROUND(m_lyrRotation*10) + (m_imageParams->m_ImageRotation*10); int rotation = m_lyrRotation * 10 + m_imageParams->m_ImageRotation * 10;
if( rotation ) if( rotation )
RotatePoint( &abPos, -rotation ); RotatePoint( &abPos, -rotation );
@ -142,7 +142,7 @@ wxPoint GERBER_DRAW_ITEM::GetXYPosition( const wxPoint& aABPosition )
if( !m_mirrorB ) if( !m_mirrorB )
NEGATE( xyPos.y ); NEGATE( xyPos.y );
int rotation = KiROUND(m_lyrRotation*10) + (m_imageParams->m_ImageRotation*10); int rotation = m_lyrRotation * 10 + m_imageParams->m_ImageRotation * 10;
if( rotation ) if( rotation )
RotatePoint( &xyPos, rotation ); RotatePoint( &xyPos, rotation );

View File

@ -247,7 +247,7 @@ void GBR_TO_PCB_EXPORTER::export_non_copper_item( GERBER_DRAW_ITEM* aGbrItem, LA
(double) ( aGbrItem->m_End.x - aGbrItem->m_ArcCentre.x ) ); (double) ( aGbrItem->m_End.x - aGbrItem->m_ArcCentre.x ) );
shape = ARC_SHAPE; shape = ARC_SHAPE;
angle = KiROUND( (a - b) / M_PI * 1800.0 ); angle = KiROUND( RAD2DECIDEG(a - b) );
seg_start = aGbrItem->m_ArcCentre; seg_start = aGbrItem->m_ArcCentre;
if( angle < 0 ) if( angle < 0 )
@ -333,7 +333,7 @@ void GBR_TO_PCB_EXPORTER::export_segarc_copper_item( GERBER_DRAW_ITEM* aGbrItem,
seg_start = curr_start; seg_start = curr_start;
wxPoint curr_end = start; wxPoint curr_end = start;
RotatePoint( &curr_end, aGbrItem->m_ArcCentre, RotatePoint( &curr_end, aGbrItem->m_ArcCentre,
-(int) (DELTA_ANGLE * ii * 1800 / M_PI) ); -RAD2DECIDEG( DELTA_ANGLE * ii ) );
seg_end = curr_end; seg_end = curr_end;
// Reverse Y axis: // Reverse Y axis:
NEGATE( seg_start.y ); NEGATE( seg_start.y );

View File

@ -32,6 +32,7 @@
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <build_version.h> #include <build_version.h>
#include <macros.h> #include <macros.h>
#include <trigo.h>
#include <base_units.h> #include <base_units.h>
#include <colors_selection.h> #include <colors_selection.h>
#include <class_gbr_layer_box_selector.h> #include <class_gbr_layer_box_selector.h>

View File

@ -30,7 +30,7 @@
#ifndef EDA_TEXT_H_ #ifndef EDA_TEXT_H_
#define EDA_TEXT_H_ #define EDA_TEXT_H_
#include <macros.h> // NORMALIZE_ANGLE_POS( angle ); #include <trigo.h> // NORMALIZE_ANGLE_POS( angle );
#include <common.h> // wxStringSplit #include <common.h> // wxStringSplit
#include <gr_basic.h> // EDA_DRAW_MODE_T #include <gr_basic.h> // EDA_DRAW_MODE_T
#include <base_struct.h> // EDA_RECT #include <base_struct.h> // EDA_RECT

View File

@ -63,56 +63,10 @@ template<class T> inline void NEGATE( T &x ) { x = -x; }
/// # of elements in an array /// # of elements in an array
#define DIM( x ) unsigned( sizeof(x) / sizeof( (x)[0] ) ) // not size_t #define DIM( x ) unsigned( sizeof(x) / sizeof( (x)[0] ) ) // not size_t
inline double DEG2RAD( double deg ) { return deg * M_PI / 180.0; } /// Exchange two values
inline double RAD2DEG( double rad ) { return rad * 180.0 / M_PI; } // std::swap works only with arguments of the same type (which is saner);
// here the compiler will figure out what to do (I hope to get rid of
/// Normalize angle to be in the -360.0 .. 360.0: // this soon or late)
template<class T> inline void NORMALIZE_ANGLE_360( T& Angle )
{
while( Angle < -3600 )
Angle += 3600;
while( Angle > 3600 )
Angle -= 3600;
}
/// Normalize angle to be in the 0.0 .. 360.0 range:
template<class T> inline void NORMALIZE_ANGLE_POS( T& Angle )
{
while( Angle < 0 )
Angle += 3600;
while( Angle >= 3600 )
Angle -= 3600;
}
template<class T> inline void NEGATE_AND_NORMALIZE_ANGLE_POS( T& Angle )
{
Angle = -Angle;
while( Angle < 0 )
Angle += 3600;
while( Angle >= 3600 )
Angle -= 3600;
}
/// Normalize angle to be in the -90.0 .. 90.0 range
template<class T> inline void NORMALIZE_ANGLE_90( T& Angle )
{
while( Angle < -900 )
Angle += 1800;
while( Angle > 900 )
Angle -= 1800;
}
/// Normalize angle to be in the -180.0 .. 180.0 range
template<class T> inline void NORMALIZE_ANGLE_180( T& Angle )
{
while( Angle <= -1800 )
Angle += 3600;
while( Angle > 1800 )
Angle -= 3600;
}
/// Exchange two values; std::swap works only with arguments of the
// same type; here the compiler will figure out what to do (I hope)
template<class T, class T2> inline void EXCHG( T& a, T2& b ) template<class T, class T2> inline void EXCHG( T& a, T2& b )
{ {
T temp = a; T temp = a;

View File

@ -155,4 +155,88 @@ inline double GetLineLength( const wxPoint& aPointA, const wxPoint& aPointB )
aPointA.y - aPointB.y ); aPointA.y - aPointB.y );
} }
// These are the usual degrees <-> radians conversion routines
inline double DEG2RAD( double deg ) { return deg * M_PI / 180.0; }
inline double RAD2DEG( double rad ) { return rad * 180.0 / M_PI; }
// These are the same *but* work with the internal 'decidegrees' unit
inline double DECIDEG2RAD( double deg ) { return deg * M_PI / 1800.0; }
inline double RAD2DECIDEG( double rad ) { return rad * 1800.0 / M_PI; }
/* These are templated over T (and not simply double) because eeschema
is still using int for angles in some place */
/// Normalize angle to be in the -360.0 .. 360.0:
template <class T> inline void NORMALIZE_ANGLE_360( T &Angle )
{
while( Angle < -3600 )
Angle += 3600;
while( Angle > 3600 )
Angle -= 3600;
}
/// Normalize angle to be in the 0.0 .. 360.0 range:
template <class T> inline void NORMALIZE_ANGLE_POS( T &Angle )
{
while( Angle < 0 )
Angle += 3600;
while( Angle >= 3600 )
Angle -= 3600;
}
/// Add two angles (keeping the result normalized). T2 is here
// because most of the time it's an int (and templates don't promote in
// that way)
template <class T, class T2> inline T AddAngles( T a1, T2 a2 )
{
a1 += a2;
NORMALIZE_ANGLE_POS( a1 );
return a1;
}
template <class T> inline void NEGATE_AND_NORMALIZE_ANGLE_POS( T &Angle )
{
Angle = -Angle;
while( Angle < 0 )
Angle += 3600;
while( Angle >= 3600 )
Angle -= 3600;
}
/// Normalize angle to be in the -90.0 .. 90.0 range
template <class T> inline void NORMALIZE_ANGLE_90( T &Angle )
{
while( Angle < -900 )
Angle += 1800;
while( Angle > 900 )
Angle -= 1800;
}
/// Normalize angle to be in the -180.0 .. 180.0 range
template <class T> inline void NORMALIZE_ANGLE_180( T &Angle )
{
while( Angle <= -1800 )
Angle += 3600;
while( Angle > 1800 )
Angle -= 3600;
}
/**
* Circle generation utility: computes r * sin(a)
* Where a is in decidegrees, not in radians.
*/
inline double sindecideg( double r, double a )
{
return r * sin( DECIDEG2RAD( a ) );
}
/**
* Circle generation utility: computes r * cos(a)
* Where a is in decidegrees, not in radians.
*/
inline double cosdecideg( double r, double a )
{
return r * cos( DECIDEG2RAD( a ) );
}
#endif #endif

View File

@ -209,7 +209,8 @@ void TraceFilledRectangle( int ux0, int uy0, int ux1, int uy1,
/* Same as above, but the rectangle is inclined angle angle. */ /* Same as above, but the rectangle is inclined angle angle. */
void TraceFilledRectangle( int ux0, int uy0, int ux1, int uy1, void TraceFilledRectangle( int ux0, int uy0, int ux1, int uy1,
int angle, LAYER_MSK masque_layer, int color, int op_logic ); int angle, LAYER_MSK masque_layer,
int color, int op_logic );
/* QUEUE.CPP */ /* QUEUE.CPP */
void FreeQueue(); void FreeQueue();

View File

@ -776,8 +776,8 @@ void TraceCircle( int ux0, int uy0, int ux1, int uy1, int lg, LAYER_NUM layer,
for( ii = 1; ii < nb_segm; ii++ ) for( ii = 1; ii < nb_segm; ii++ )
{ {
angle = (3600 * ii) / nb_segm; angle = (3600 * ii) / nb_segm;
x1 = (int) ( radius * cos( DEG2RAD( (double)angle / 10.0 ) ) ); x1 = KiROUND( cosdecideg( radius, angle ) );
y1 = (int) ( radius * sin( DEG2RAD( (double)angle / 10.0 ) ) ); y1 = KiROUND( sindecideg( radius, angle ) );
DrawSegmentQcq( x0 + ux0, y0 + uy0, x1 + ux0, y1 + uy0, lg, layer, color, op_logic ); DrawSegmentQcq( x0 + ux0, y0 + uy0, x1 + ux0, y1 + uy0, lg, layer, color, op_logic );
x0 = x1; x0 = x1;
y0 = y1; y0 = y1;
@ -827,8 +827,8 @@ void TraceArc( int ux0, int uy0, int ux1, int uy1, int ArcAngle, int lg,
NORMALIZE_ANGLE_POS( angle ); NORMALIZE_ANGLE_POS( angle );
x1 = (int) ( radius * cos( DEG2RAD( (double)angle / 10.0 ) ) ); x1 = KiROUND( cosdecideg( radius, angle ) );
y1 = (int) ( radius * sin( DEG2RAD( (double)angle / 10.0 ) ) ); y1 = KiROUND( cosdecideg( radius, angle ) );
DrawSegmentQcq( x0 + ux0, y0 + uy0, x1 + ux0, y1 + uy0, lg, layer, color, op_logic ); DrawSegmentQcq( x0 + ux0, y0 + uy0, x1 + ux0, y1 + uy0, lg, layer, color, op_logic );
x0 = x1; x0 = x1;
y0 = y1; y0 = y1;

View File

@ -144,7 +144,7 @@ void MODULE::TransformGraphicShapesWithClearanceToPolygonSet(
default: default:
D( printf( "Error: Shape %d not implemented!\n", D( printf( "Error: Shape %d not implemented!\n",
((EDGE_MODULE*) item)->m_Shape ); ) ((EDGE_MODULE*) item)->GetShape() ); )
break; break;
} }
break; break;
@ -828,7 +828,7 @@ void CreateThermalReliefPadPolygon( std::vector<CPolyPt>& aCornerBuffer,
wxPoint intpoint = corner; wxPoint intpoint = corner;
intpoint.y -= aThermalGap / 4; intpoint.y -= aThermalGap / 4;
corners_buffer.push_back( intpoint + shape_offset ); corners_buffer.push_back( intpoint + shape_offset );
RotatePoint( &corner, 90 ); RotatePoint( &corner, 90 ); // 9 degrees of thermal fillet
} }
else else
{ {
@ -850,7 +850,7 @@ void CreateThermalReliefPadPolygon( std::vector<CPolyPt>& aCornerBuffer,
corner_end.x = corner_end.x =
(int) sqrt( ( (double) outer_radius * (int) sqrt( ( (double) outer_radius *
outer_radius ) - ( (double) corner_end.y * corner_end.y ) ); outer_radius ) - ( (double) corner_end.y * corner_end.y ) );
RotatePoint( &corner_end, -90 ); RotatePoint( &corner_end, -90 ); // 9 degrees of thermal fillet
// calculate intermediate arc points till limit is reached // calculate intermediate arc points till limit is reached
while( (corner.y > corner_end.y) && (corner.x < corner_end.x) ) while( (corner.y > corner_end.y) && (corner.x < corner_end.x) )
@ -878,10 +878,7 @@ void CreateThermalReliefPadPolygon( std::vector<CPolyPt>& aCornerBuffer,
} }
aCornerBuffer.back().end_contour = true; aCornerBuffer.back().end_contour = true;
angle += 1800; // this is calculate hole 3 angle = AddAngles( angle, 1800 ); // this is calculate hole 3
if( angle >= 3600 )
angle -= 3600;
} }
// Create holes, that are the mirrored from the previous holes // Create holes, that are the mirrored from the previous holes
@ -906,10 +903,7 @@ void CreateThermalReliefPadPolygon( std::vector<CPolyPt>& aCornerBuffer,
} }
aCornerBuffer.back().end_contour = true; aCornerBuffer.back().end_contour = true;
angle += 1800; angle = AddAngles( angle, 1800 );
if( angle >= 3600 )
angle -= 3600;
} }
} }
break; break;
@ -982,10 +976,7 @@ void CreateThermalReliefPadPolygon( std::vector<CPolyPt>& aCornerBuffer,
} }
aCornerBuffer.back().end_contour = true; aCornerBuffer.back().end_contour = true;
angle += 1800; // this is calculate hole 3 angle = AddAngles( angle, 1800 ); // this is calculate hole 3
if( angle >= 3600 )
angle -= 3600;
} }
// Create holes, that are the mirrored from the previous holes // Create holes, that are the mirrored from the previous holes
@ -1008,10 +999,7 @@ void CreateThermalReliefPadPolygon( std::vector<CPolyPt>& aCornerBuffer,
} }
aCornerBuffer.back().end_contour = true; aCornerBuffer.back().end_contour = true;
angle += 1800; angle = AddAngles( angle, 1800 );
if( angle >= 3600 )
angle -= 3600;
} }
} }

View File

@ -307,7 +307,7 @@ void DIMENSION::AdjustDimensionDetails( bool aDoNotChangeText )
textPos.y = (m_crossBarF.y + m_featureLineGF.y) / 2; textPos.y = (m_crossBarF.y + m_featureLineGF.y) / 2;
m_Text.SetTextPosition( textPos ); m_Text.SetTextPosition( textPos );
double newAngle = -(angle * 1800 / M_PI); double newAngle = -RAD2DECIDEG( angle );
NORMALIZE_ANGLE_POS( newAngle ); NORMALIZE_ANGLE_POS( newAngle );

View File

@ -45,6 +45,7 @@
#include <pcbnew.h> #include <pcbnew.h>
#include <protos.h> #include <protos.h>
#include <math_for_graphics.h>
#include <class_board.h> #include <class_board.h>
#include <class_module.h> #include <class_module.h>

View File

@ -6,7 +6,7 @@
#include <gr_basic.h> #include <gr_basic.h>
#include <common.h> #include <common.h>
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <macros.h>
#include <pcbnew.h> #include <pcbnew.h>
#include <class_board.h> #include <class_board.h>

View File

@ -716,7 +716,7 @@ void D_PAD::BuildPadPolygon( wxPoint aCoord[4], wxSize aInflateValue,
else if( delta.x ) // left and right segment is vertical else if( delta.x ) // left and right segment is vertical
{ {
// Calculate angle of lower (or upper) segment with horizontal axis // Calculate angle of lower (or upper) segment with horizontal axis
angle = atan2( double( m_DeltaSize.x ), double( m_Size.x ) ); angle = atan2( m_DeltaSize.x, m_Size.x );
// lower and upper sides are moved by aInflateValue.x in their perpendicular direction // lower and upper sides are moved by aInflateValue.x in their perpendicular direction
// We must calculate the corresponding displacement on the vertical axis // We must calculate the corresponding displacement on the vertical axis

View File

@ -736,9 +736,9 @@ void TRACK::Draw( EDA_DRAW_PANEL* panel, wxDC* aDC, GR_DRAWMODE aDrawMode,
} }
else else
{ {
/* atan2 is *not* the solution here, since can give upside /* atan2 is *not* the solution here, since it can give upside
down text. We want to work only in the first and fourth quadrant */ down text. We want to work only in the first and fourth quadrant */
angle = 10 * RAD2DEG( -atan( double( dy )/ double( dx ) ) ); angle = RAD2DECIDEG( -atan( double( dy ) / double( dx ) ) );
} }
} }
@ -921,8 +921,8 @@ void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* aDC, GR_DRAWMODE aDrawMode,
( (SEGVIA*) this )->ReturnLayerPair( &layer_top, &layer_bottom ); ( (SEGVIA*) this )->ReturnLayerPair( &layer_top, &layer_bottom );
// lines for the top layer // lines for the top layer
RotatePoint( &ax, &ay, layer_top * 3600 / brd->GetCopperLayerCount( ) ); RotatePoint( &ax, &ay, layer_top * 3600.0 / brd->GetCopperLayerCount( ) );
RotatePoint( &bx, &by, layer_top * 3600 / brd->GetCopperLayerCount( ) ); RotatePoint( &bx, &by, layer_top * 3600.0 / brd->GetCopperLayerCount( ) );
GRLine( panel->GetClipBox(), aDC, m_Start.x + aOffset.x - ax, GRLine( panel->GetClipBox(), aDC, m_Start.x + aOffset.x - ax,
m_Start.y + aOffset.y - ay, m_Start.y + aOffset.y - ay,
m_Start.x + aOffset.x - bx, m_Start.x + aOffset.x - bx,
@ -930,8 +930,8 @@ void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* aDC, GR_DRAWMODE aDrawMode,
// lines for the bottom layer // lines for the bottom layer
ax = 0; ay = radius; bx = 0; by = drill_radius; ax = 0; ay = radius; bx = 0; by = drill_radius;
RotatePoint( &ax, &ay, layer_bottom * 3600 / brd->GetCopperLayerCount( ) ); RotatePoint( &ax, &ay, layer_bottom * 3600.0 / brd->GetCopperLayerCount( ) );
RotatePoint( &bx, &by, layer_bottom * 3600 / brd->GetCopperLayerCount( ) ); RotatePoint( &bx, &by, layer_bottom * 3600.0 / brd->GetCopperLayerCount( ) );
GRLine( panel->GetClipBox(), aDC, m_Start.x + aOffset.x - ax, GRLine( panel->GetClipBox(), aDC, m_Start.x + aOffset.x - ax,
m_Start.y + aOffset.y - ay, m_Start.y + aOffset.y - ay,
m_Start.x + aOffset.x - bx, m_Start.x + aOffset.x - bx,

View File

@ -36,6 +36,7 @@
#include <base_units.h> #include <base_units.h>
#include <convert_from_iu.h> #include <convert_from_iu.h>
#include <wildcards_and_files_ext.h> #include <wildcards_and_files_ext.h>
#include <macros.h>
#include <pcbnew.h> #include <pcbnew.h>
#include <pcbplot.h> #include <pcbplot.h>

View File

@ -40,6 +40,7 @@
#include <pcbnew_id.h> #include <pcbnew_id.h>
#include <class_track.h> #include <class_track.h>
#include <macros.h>
#include <dialog_design_rules.h> #include <dialog_design_rules.h>
#include <wx/generic/gridctrl.h> #include <wx/generic/gridctrl.h>

View File

@ -41,6 +41,7 @@
#include <3d_viewer.h> #include <3d_viewer.h>
#include <wxPcbStruct.h> #include <wxPcbStruct.h>
#include <base_units.h> #include <base_units.h>
#include <macros.h>
#include <class_module.h> #include <class_module.h>
#include <class_text_mod.h> #include <class_text_mod.h>

View File

@ -32,6 +32,7 @@
#include <wxPcbStruct.h> #include <wxPcbStruct.h>
#include <pcbplot.h> #include <pcbplot.h>
#include <gendrill_Excellon_writer.h> #include <gendrill_Excellon_writer.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_track.h> #include <class_track.h>

View File

@ -34,6 +34,7 @@
#include <gr_basic.h> #include <gr_basic.h>
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <wxBasePcbFrame.h> #include <wxBasePcbFrame.h>
#include <macros.h>
#include <drag.h> #include <drag.h>
#include <pcbnew.h> #include <pcbnew.h>

View File

@ -868,10 +868,7 @@ bool DRC::checkClearanceSegmToPad( const D_PAD* aPad, int aSegmentWidth, int aMi
if( padHalfsize.x > padHalfsize.y ) if( padHalfsize.x > padHalfsize.y )
{ {
EXCHG( padHalfsize.x, padHalfsize.y ); EXCHG( padHalfsize.x, padHalfsize.y );
orient += 900; orient = AddAngles( orient, 900 );
if( orient >= 3600 )
orient -= 3600;
} }
deltay = padHalfsize.y - padHalfsize.x; deltay = padHalfsize.y - padHalfsize.x;

View File

@ -37,6 +37,7 @@
#include <pcbnew.h> #include <pcbnew.h>
#include <protos.h> #include <protos.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_drawsegment.h> #include <class_drawsegment.h>

View File

@ -487,7 +487,7 @@ static void export_vrml_oval_pad( LAYER_NUM layer, double xc, double yc,
fan.c.x = xc; fan.c.x = xc;
fan.c.y = yc; fan.c.y = yc;
double angle = orient / 1800.0 * M_PI; double angle = DECIDEG2RAD( orient );
int divisions = SEGM_COUNT_PER_360 / 2; int divisions = SEGM_COUNT_PER_360 / 2;
if( dy > dx ) if( dy > dx )
@ -1118,8 +1118,8 @@ static void export_vrml_module( BOARD* aPcb, MODULE* aModule,
compose_quat( q1, q2, q1 ); compose_quat( q1, q2, q1 );
// Note here aModule->GetOrientation() is in 0.1 degrees, // Note here aModule->GetOrientation() is in 0.1 degrees,
// so module rotation is aModule->GetOrientation() / 1800.0 // so module rotation has to be converted to radians
build_quat( 0, 0, 1, aModule->GetOrientation() / 1800.0 * M_PI, q2 ); build_quat( 0, 0, 1, DECIDEG2RAD( aModule->GetOrientation() ), q2 );
compose_quat( q1, q2, q1 ); compose_quat( q1, q2, q1 );
from_quat( q1, rot ); from_quat( q1, rot );

View File

@ -35,6 +35,7 @@
#include <3d_viewer.h> #include <3d_viewer.h>
#include <pcbcommon.h> #include <pcbcommon.h>
#include <msgpanel.h> #include <msgpanel.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_module.h> #include <class_module.h>

View File

@ -34,6 +34,7 @@
#include <drawtxt.h> #include <drawtxt.h>
#include <confirm.h> #include <confirm.h>
#include <kicad_string.h> #include <kicad_string.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>

View File

@ -39,6 +39,7 @@
#include <plot_common.h> #include <plot_common.h>
#include <trigo.h> #include <trigo.h>
#include <macros.h>
#include <kicad_string.h> #include <kicad_string.h>
#include <wxPcbStruct.h> #include <wxPcbStruct.h>
#include <appl_wxstruct.h> #include <appl_wxstruct.h>

View File

@ -559,7 +559,7 @@ MODULE* GPCB_FPL_CACHE::parseMODULE( LINE_READER* aLineReader ) throw( IO_ERROR,
} }
// Negate angle (due to Y reversed axis) and convert it to internal units // Negate angle (due to Y reversed axis) and convert it to internal units
angle = - angle * 1800.0 / M_PI; angle = - RAD2DECIDEG( angle );
pad->SetOrientation( KiROUND( angle ) ); pad->SetOrientation( KiROUND( angle ) );
wxPoint padPos( (x1 + x2) / 2, (y1 + y2) / 2 ); wxPoint padPos( (x1 + x2) / 2, (y1 + y2) / 2 );

View File

@ -34,6 +34,7 @@
#include <3d_viewer.h> #include <3d_viewer.h>
#include <pcbcommon.h> #include <pcbcommon.h>
#include <msgpanel.h> #include <msgpanel.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_module.h> #include <class_module.h>

View File

@ -32,6 +32,7 @@
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <confirm.h> #include <confirm.h>
#include <trigo.h> #include <trigo.h>
#include <macros.h>
#include <wxBasePcbFrame.h> #include <wxBasePcbFrame.h>
#include <pcbnew.h> #include <pcbnew.h>

View File

@ -121,8 +121,8 @@ void PCB_ARC::Parse( XNODE* aNode,
if( lNode ) if( lNode )
m_angle = StrToInt1Units( lNode->GetNodeContent() ); m_angle = StrToInt1Units( lNode->GetNodeContent() );
m_startX = KiROUND( m_positionX + (double)r * cos( a * M_PI / 1800.0 ) ); m_startX = m_positionX + KiROUND( cosdecideg( r, a ) );
m_startY = KiROUND( m_positionY - (double)r * sin( a * M_PI / 1800.0 ) ); m_startY = m_positionY - KiROUND( sindecideg( r, a ) );
} }
} }

View File

@ -40,6 +40,7 @@
#include <pcb_plot_params.h> #include <pcb_plot_params.h>
#include <wx/ffile.h> #include <wx/ffile.h>
#include <dialog_plot.h> #include <dialog_plot.h>
#include <macros.h>
/** Get the 'traditional' gerber extension depending on the layer /** Get the 'traditional' gerber extension depending on the layer

View File

@ -37,6 +37,7 @@
#include <trigo.h> #include <trigo.h>
#include <wxBasePcbFrame.h> #include <wxBasePcbFrame.h>
#include <pcbcommon.h> #include <pcbcommon.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_module.h> #include <class_module.h>

View File

@ -33,6 +33,7 @@
#include <base_struct.h> #include <base_struct.h>
#include <drawtxt.h> #include <drawtxt.h>
#include <trigo.h> #include <trigo.h>
#include <macros.h>
#include <wxBasePcbFrame.h> #include <wxBasePcbFrame.h>
#include <pcbcommon.h> #include <pcbcommon.h>

View File

@ -9,6 +9,7 @@
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <colors_selection.h> #include <colors_selection.h>
#include <wxBasePcbFrame.h> #include <wxBasePcbFrame.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_module.h> #include <class_module.h>

View File

@ -56,6 +56,7 @@
#include <class_track.h> #include <class_track.h>
#include <specctra.h> #include <specctra.h>
#include <macros.h>
namespace DSN { namespace DSN {

View File

@ -36,6 +36,7 @@
#include <confirm.h> // DisplayError() #include <confirm.h> // DisplayError()
#include <gestfich.h> // EDA_FileSelector() #include <gestfich.h> // EDA_FileSelector()
#include <trigo.h> // RotatePoint() #include <trigo.h> // RotatePoint()
#include <macros.h>
#include <set> // std::set #include <set> // std::set
#include <map> // std::map #include <map> // std::map

View File

@ -36,6 +36,7 @@
#include <confirm.h> // DisplayError() #include <confirm.h> // DisplayError()
#include <gestfich.h> // EDA_FileSelector() #include <gestfich.h> // EDA_FileSelector()
#include <wxPcbStruct.h> #include <wxPcbStruct.h>
#include <macros.h>
#include <class_board.h> #include <class_board.h>
#include <class_module.h> #include <class_module.h>