diff options
Diffstat (limited to 'app/bin/tcurve.c')
-rw-r--r-- | app/bin/tcurve.c | 312 |
1 files changed, 175 insertions, 137 deletions
diff --git a/app/bin/tcurve.c b/app/bin/tcurve.c index 00d1ef5..f133dc7 100644 --- a/app/bin/tcurve.c +++ b/app/bin/tcurve.c @@ -20,34 +20,26 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ -#include <assert.h> -#include <math.h> -#include <string.h> - #include "ccurve.h" #include "cjoin.h" #include "cstraigh.h" #include "cundo.h" #include "fileio.h" -#include "i18n.h" #include "layout.h" -#include "messages.h" #include "param.h" #include "track.h" -#include "utility.h" +#include "common-ui.h" static TRKTYP_T T_CURVE = -1; -struct extraData { +typedef struct extraDataCurve_t { + extraDataBase_t base; coOrd pos; DIST_T radius; BOOL_T circle; long helixTurns; coOrd descriptionOff; - }; -#define xpos extraData->pos -#define xradius extraData->radius -#define xcircle extraData->circle + } extraDataCurve_t; static int log_curve = 0; static int log_curveSegs = 0; @@ -62,8 +54,8 @@ static DIST_T GetLengthCurve( track_p ); static void GetCurveAngles( ANGLE_T *a0, ANGLE_T *a1, track_p trk ) { - struct extraData *xx = GetTrkExtraData(trk); assert( trk != NULL ); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); if (xx->circle != TRUE) { *a0 = NormalizeAngle( GetTrkEndAngle(trk,0) + 90 ); *a1 = NormalizeAngle( @@ -75,7 +67,7 @@ static void GetCurveAngles( ANGLE_T *a0, ANGLE_T *a1, track_p trk ) LOG( log_curve, 4, ( "getCurveAngles: = %0.3f %0.3f\n", *a0, *a1 ) ) } -static void SetCurveAngles( track_p p, ANGLE_T a0, ANGLE_T a1, struct extraData * xx ) +static void SetCurveAngles( track_p p, ANGLE_T a0, ANGLE_T a1, struct extraDataCurve_t * xx ) { coOrd pos0, pos1; xx->circle = (a0 == 0.0 && a1 == 0.0); @@ -85,7 +77,7 @@ static void SetCurveAngles( track_p p, ANGLE_T a0, ANGLE_T a1, struct extraData SetTrkEndPoint( p, 1, pos1, NormalizeAngle(a0+a1+90.0) ); } -static void ComputeCurveBoundingBox( track_p trk, struct extraData * xx ) +static void ComputeCurveBoundingBox( track_p trk, struct extraDataCurve_t * xx ) { coOrd p = xx->pos; DIST_T r = xx->radius; @@ -112,7 +104,6 @@ static void ComputeCurveBoundingBox( track_p trk, struct extraData * xx ) static void AdjustCurveEndPt( track_p t, EPINX_T inx, ANGLE_T a ) { - struct extraData *xx = GetTrkExtraData(t); coOrd pos; ANGLE_T aa; if (GetTrkType(t) != T_CURVE) { @@ -120,6 +111,7 @@ static void AdjustCurveEndPt( track_p t, EPINX_T inx, ANGLE_T a ) GetTrkIndex(t), inx, GetTrkType(t) ); return; } + struct extraDataCurve_t *xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); UndoModify( t ); LOG( log_curve, 1, ( "adjustCurveEndPt T%d[%d] a=%0.3f\n", GetTrkIndex(t), inx, a ) ) aa = a = NormalizeAngle(a); @@ -140,28 +132,28 @@ LOG( log_curve, 1, ( " E0:[%0.3f %0.3f] A%0.3f, E1:[%0.3f %0.3f] A%0.3f\n", static void GetTrkCurveCenter( track_p t, coOrd *p, DIST_T *r ) { - struct extraData *xx = GetTrkExtraData(t); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); *p = xx->pos; *r = xx->radius; } BOOL_T IsCurveCircle( track_p t ) { - struct extraData *xx; + struct extraDataCurve_t *xx; if ( GetTrkType(t) != T_CURVE ) return FALSE; - xx = GetTrkExtraData(t); + xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); return xx->circle || xx->helixTurns>0; } BOOL_T GetCurveMiddle( track_p trk, coOrd * pos ) { - struct extraData *xx; + struct extraDataCurve_t *xx; ANGLE_T a0, a1; if ( GetTrkType(trk) != T_CURVE ) return FALSE; - xx = GetTrkExtraData(trk); + xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); if (xx->circle || xx->helixTurns>0) { PointOnCircle( pos, xx->pos, xx->radius, 0 ); } else { @@ -171,6 +163,8 @@ BOOL_T GetCurveMiddle( track_p trk, coOrd * pos ) return TRUE; } +static DIST_T DistanceCurve( track_p t, coOrd * p ); + DIST_T CurveDescriptionDistance( coOrd pos, track_p trk, @@ -178,28 +172,41 @@ DIST_T CurveDescriptionDistance( BOOL_T show_hidden, BOOL_T * hidden) { - struct extraData *xx = GetTrkExtraData(trk); - coOrd p1; + coOrd p0,p1,pd; FLOAT_T ratio; ANGLE_T a, a0, a1; if (hidden) *hidden = FALSE; - if ( (GetTrkType( trk ) != T_CURVE )|| ((( GetTrkBits( trk ) & TB_HIDEDESC ) != 0) && !show_hidden)) - return 100000; + if ( (GetTrkType( trk ) != T_CURVE ) || ((( GetTrkBits( trk ) & TB_HIDEDESC ) != 0) && !show_hidden)) + return DIST_INF; + + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); coOrd offset = xx->descriptionOff; if (( GetTrkBits( trk ) & TB_HIDEDESC ) != 0) offset = zero; + if ( xx->helixTurns > 0 ) { - p1.x = xx->pos.x + offset.x; - p1.y = xx->pos.y + offset.y; + pd.x = xx->pos.x + offset.x; + pd.y = xx->pos.y + offset.y; + p0 = pd; + p1 = pd; } else { GetCurveAngles( &a0, &a1, trk ); - ratio = ( offset.x + 1.0 ) / 2.0; - a = a0 + ratio * a1; - ratio = ( offset.y + 1.0 ) / 2.0; - Translate( &p1, xx->pos, a, xx->radius * ratio ); + ratio = offset.x; + if (!IsCurveCircle( trk )) + a = NormalizeAngle(a0 + a1/2.0 + ratio * a1/ 2.0); + else + a = NormalizeAngle(360.0*ratio+a0); + ratio = offset.y+0.5; + if (ratio<0.0) ratio = 0.0; + if (ratio>1.0) ratio = 1.0; + Translate( &pd, xx->pos, a, xx->radius * ratio ); } if (hidden) *hidden = (GetTrkBits( trk ) & TB_HIDEDESC); - *dpos = p1; - return FindDistance( p1, pos ); + *dpos = pd; + + coOrd tpos = pos; + if (DistanceCurve(trk, &tpos)<FindDistance(pd, pos)) + return DistanceCurve(trk, &pos); + return FindDistance( pd, pos ); } @@ -208,7 +215,6 @@ static void DrawCurveDescription( drawCmd_p d, wDrawColor color ) { - struct extraData *xx = GetTrkExtraData(trk); wFont_p fp; coOrd pos, p0, p1; DIST_T elev0, elev1, dist, grade=0, sep=0; @@ -221,6 +227,7 @@ static void DrawCurveDescription( if ((labelEnable&LABELENABLE_TRKDESC)==0) return; + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); if ( xx->helixTurns > 0 ) { pos = xx->pos; pos.x += xx->descriptionOff.x; @@ -240,15 +247,17 @@ static void DrawCurveDescription( } fp = wStandardFont( F_TIMES, FALSE, FALSE ); if (elevValid) - sprintf( message, _("Helix: turns=%ld len=%0.2f grade=%0.1f%% sep=%0.2f"), + sprintf( message, _("Helix: Turns %ld L %0.2f Grade %0.1f%% Sep %0.2f"), xx->helixTurns, dist, grade*100.0, sep ); else - sprintf( message, _("Helix: turns=%ld len=%0.2f"), + sprintf( message, _("Helix: Turns %ld L %0.2f"), xx->helixTurns, dist ); + if (color == drawColorPreviewSelected) + DrawLine(d,xx->pos,pos,0,color); DrawBoxedString( BOX_BOX, d, pos, message, fp, (wFontSize_t)descriptionFontSize, color, 0.0 ); } else { dist = trackGauge/2.0; @@ -260,13 +269,36 @@ static void DrawCurveDescription( Translate( &p1, xx->pos, 180.0, dist ); DrawLine( d, p0, p1, 0, color ); GetCurveAngles( &a0, &a1, trk ); - ratio = ( xx->descriptionOff.x + 1.0 ) / 2.0; - a = a0 + ratio * a1; + ratio = xx->descriptionOff.x; // 1.0 to - 1.0 + if (! IsCurveCircle( trk )) + a = NormalizeAngle(ratio*a1/2.0 + a0 + a1/2.0); + else + a = NormalizeAngle(ratio*360.0+a0); PointOnCircle( &p0, xx->pos, xx->radius, a ); - sprintf( message, "R %s", FormatDistance( xx->radius ) ); - ratio = ( xx->descriptionOff.y + 1.0 ) / 2.0; - DrawDimLine( d, xx->pos, p0, message, (wFontSize_t)descriptionFontSize, ratio, 0, color, 0x11 ); + coOrd end0, end1; + DIST_T off; + Translate(&end0,xx->pos,a0,xx->radius); + Translate(&end1,xx->pos,a0+a1,xx->radius); + off = xx->radius-(cos(D2R(a1/2))*xx->radius); + ratio = xx->descriptionOff.y; + if (ratio < -0.5) ratio = -0.5; + if (ratio > 0.5) ratio = 0.5; + if (! IsCurveCircle(trk)) + sprintf( message, "R %s L %s A %0.3f O %s", FormatDistance( xx->radius ), + FormatDistance(FindDistance(end0,end1)),FindAngle(end1,end0), FormatDistance(off)); + else + sprintf( message, "R %s L %s A 360.0", FormatDistance( xx->radius ),FormatDistance(xx->radius*2*M_PI)); + DrawDimLine( d, xx->pos, p0, message, (wFontSize_t)descriptionFontSize, ratio+0.5, 0, color, 0x00 ); + + if (GetTrkBits( trk ) & TB_DETAILDESC) { + coOrd details_pos; + details_pos.x = (p0.x - xx->pos.x)*(ratio+0.5) + xx->pos.x; + details_pos.y = (p0.y - xx->pos.y)*(ratio+0.5) + xx->pos.y-(2*descriptionFontSize/mainD.dpi); + + AddTrkDetails(d, trk, details_pos, a1/180.0*M_PI*xx->radius, color); + } } + } @@ -275,66 +307,47 @@ STATUS_T CurveDescriptionMove( wAction_t action, coOrd pos ) { - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); static coOrd p0,p1; - static BOOL_T editMode; wDrawColor color; ANGLE_T a, a0, a1; DIST_T d; p0 = xx->pos; - switch (action) { - case C_DOWN: - DrawCurveDescription( trk, &mainD, wDrawColorWhite ); - case C_MOVE: - case C_UP: - editMode = TRUE; - color = GetTrkColor( trk, &mainD ); - if ( xx->helixTurns > 0 ) { - xx->descriptionOff.x = (pos.x-xx->pos.x); - xx->descriptionOff.y = (pos.y-xx->pos.y); - p1 = pos; - } else { - p1 = pos; - GetCurveAngles( &a0, &a1, trk ); - if ( a1 < 1 ) a1 = 1.0; - a = FindAngle( xx->pos, pos ); - if ( ! IsCurveCircle( trk ) ) { - a = NormalizeAngle( a - a0 ); - if ( a > a1 ) { - if ( a < a1 + ( 360.0 - a1 ) / 2 ) { - a = a1; - } else { - a = 0.0; - } + color = GetTrkColor( trk, &mainD ); + if ( xx->helixTurns > 0 ) { + xx->descriptionOff.x = (pos.x-xx->pos.x); + xx->descriptionOff.y = (pos.y-xx->pos.y); + p1 = pos; + } else { + p1 = pos; + GetCurveAngles( &a0, &a1, trk ); + if ( a1 < 1 ) a1 = 1.0; + a = FindAngle( xx->pos, pos ); + if ( ! IsCurveCircle( trk ) ) { + a = NormalizeAngle( a - a0 ); + if ( a > a1 ) { + if ( a < a1 + ( 360.0 - a1 ) / 2 ) { + a = a1; + } else { + a = 0.0; } } - xx->descriptionOff.x = ( a / a1 ) * 2.0 - 1.0; - d = FindDistance( xx->pos, pos ) / xx->radius; - if ( d > 0.9 ) - d = 0.9; - if ( d < 0.1 ) - d = 0.1; - xx->descriptionOff.y = d * 2.0 - 1.0; + xx->descriptionOff.x = ( a / a1 ) * 2.0 - 1.0; // -1 to 1, 0 in middle + } else { + a = FindAngle(xx->pos,pos); GetCurveAngles( &a0, &a1, trk ); - a = a0 + (0.5 * a1); - PointOnCircle( &p0, xx->pos, xx->radius/2, a ); - } - if (action == C_UP) { - editMode = FALSE; - DrawCurveDescription( trk, &mainD, wDrawColorBlack ); - } - return action==C_UP?C_TERMINATE:C_CONTINUE; - - case C_REDRAW: - if (editMode) { - DrawLine( &tempD, p0, p1, 0, wDrawColorBlue ); - DrawCurveDescription( trk, &tempD, wDrawColorBlue ); + xx->descriptionOff.x = NormalizeAngle((a - a0)/360.0); } - break; - + d = FindDistance( xx->pos, pos ) / xx->radius; + if ( d > 1.0 ) + d = 1.0; + if ( d < 0.0 ) + d = 0.0; + xx->descriptionOff.y = d-0.5; // -0.5 to 0.5, 0 in the middle } + return C_CONTINUE; } @@ -374,22 +387,21 @@ static descData_t crvDesc[] = { /*A1*/ { DESC_ANGLE, N_("CCW Angle"), &crvData.angle0 }, /*A2*/ { DESC_ANGLE, N_("CW Angle"), &crvData.angle1 }, /*GR*/ { DESC_FLOAT, N_("Grade"), &crvData.grade }, -/*PV*/ { DESC_PIVOT, N_("Pivot"), &crvData.pivot }, +/*PV*/ { DESC_PIVOT, N_("Lock"), &crvData.pivot }, /*LY*/ { DESC_LAYER, N_("Layer"), &crvData.layerNumber }, { DESC_NULL } }; static void UpdateCurve( track_p trk, int inx, descData_p descUpd, BOOL_T final ) { - struct extraData *xx = GetTrkExtraData(trk); BOOL_T updateEndPts; ANGLE_T a0, a1; EPINX_T ep; - struct extraData xx0; FLOAT_T turns; if ( inx == -1 ) return; - xx0 = *xx; + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); + struct extraDataCurve_t xx0 = *xx; updateEndPts = FALSE; GetCurveAngles( &a0, &a1, trk ); switch ( inx ) { @@ -540,11 +552,11 @@ static void UpdateCurve( track_p trk, int inx, descData_p descUpd, BOOL_T final static void DescribeCurve( track_p trk, char * str, CSIZE_T len ) { - struct extraData *xx = GetTrkExtraData(trk); ANGLE_T a0, a1; DIST_T d; int fix0, fix1; FLOAT_T turns; + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); GetCurveAngles( &a0, &a1, trk ); d = xx->radius * 2.0 * M_PI * a1 / 360.0; @@ -649,9 +661,9 @@ static void DescribeCurve( track_p trk, char * str, CSIZE_T len ) static DIST_T DistanceCurve( track_p t, coOrd * p ) { - struct extraData *xx = GetTrkExtraData(t); ANGLE_T a0, a1; DIST_T d; + struct extraDataCurve_t *xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); GetCurveAngles( &a0, &a1, t ); if ( xx->helixTurns > 0 ) { a0 = 0.0; @@ -663,10 +675,10 @@ static DIST_T DistanceCurve( track_p t, coOrd * p ) static void DrawCurve( track_p t, drawCmd_p d, wDrawColor color ) { - struct extraData *xx = GetTrkExtraData(t); ANGLE_T a0, a1; track_p tt = t; long widthOptions = DTS_LEFT|DTS_RIGHT; + struct extraDataCurve_t *xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); GetCurveAngles( &a0, &a1, t ); if (xx->circle) { @@ -684,7 +696,6 @@ static void DrawCurve( track_p t, drawCmd_p d, wDrawColor color ) } DrawCurvedTrack( d, xx->pos, xx->radius, a0, a1, - GetTrkEndPos(t,0), GetTrkEndPos(t,1), t, color, widthOptions ); DrawEndPt( d, t, 0, color ); DrawEndPt( d, t, 1, color ); @@ -696,12 +707,13 @@ static void DeleteCurve( track_p t ) static BOOL_T WriteCurve( track_p t, FILE * f ) { - struct extraData *xx = GetTrkExtraData(t); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); long options; BOOL_T rc = TRUE; options = GetTrkWidth(t) & 0x0F; - if ( ( ( GetTrkBits(t) & TB_HIDEDESC ) != 0 ) == ( xx->helixTurns > 0 ) ) - options |= 0x80; + if ( ( GetTrkBits(t) & TB_HIDEDESC ) == 0 ) + // 0x80 means Show Description + options |= 0x80; rc &= fprintf(f, "CURVE %d %d %ld 0 0 %s %d %0.6f %0.6f 0 %0.6f %ld %0.6f %0.6f\n", GetTrkIndex(t), GetTrkLayer(t), (long)options, GetTrkScaleName(t), GetTrkVisible(t)|(GetTrkNoTies(t)?1<<2:0)|(GetTrkBridge(t)?1<<3:0), xx->pos.x, xx->pos.y, xx->radius, @@ -714,7 +726,7 @@ static BOOL_T WriteCurve( track_p t, FILE * f ) static BOOL_T ReadCurve( char * line ) { - struct extraData *xx; + struct extraDataCurve_t *xx; track_p t; wIndex_t index; BOOL_T visible; @@ -739,7 +751,7 @@ static BOOL_T ReadCurve( char * line ) if ( !ReadSegs() ) return FALSE; t = NewTrack( index, T_CURVE, 0, sizeof *xx ); - xx = GetTrkExtraData(t); + xx = GET_EXTRA_DATA(t, T_CURVE, extraDataCurve_t); xx->helixTurns = helixTurns; xx->descriptionOff = descriptionOff; if ( paramVersion < 3 ) { @@ -756,8 +768,15 @@ static BOOL_T ReadCurve( char * line ) SetTrkWidth(t, (int)(options&3)); xx->pos = p; xx->radius = r; - if ( ( ( options & 0x80 ) != 0 ) == ( xx->helixTurns > 0 ) ) - SetTrkBits(t,TB_HIDEDESC); + if ( paramVersion < VERSION_DESCRIPTION2 ) { + if ( xx->helixTurns <= 0 ) { + // Descriptions on by default for helix, off for curves + SetTrkBits(t,TB_HIDEDESC); + } + } else { + if ( paramVersion < VERSION_DESCRIPTION2 || ( ( options & 0x80 ) == 0 ) ) + SetTrkBits(t,TB_HIDEDESC); + } SetEndPts(t,2); if (GetTrkEndAngle( t, 0 ) == 270.0 && GetTrkEndAngle( t, 1 ) == 90.0 ) @@ -768,7 +787,7 @@ static BOOL_T ReadCurve( char * line ) static void MoveCurve( track_p trk, coOrd orig ) { - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); xx->pos.x += orig.x; xx->pos.y += orig.y; ComputeCurveBoundingBox( trk, xx ); @@ -776,14 +795,14 @@ static void MoveCurve( track_p trk, coOrd orig ) static void RotateCurve( track_p trk, coOrd orig, ANGLE_T angle ) { - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); Rotate( &xx->pos, orig, angle ); ComputeCurveBoundingBox( trk, xx ); } static void RescaleCurve( track_p trk, FLOAT_T ratio ) { - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); xx->pos.x *= ratio; xx->pos.y *= ratio; xx->radius *= ratio; @@ -801,7 +820,7 @@ static ANGLE_T GetAngleCurve( track_p trk, coOrd pos, EPINX_T *ep0, EPINX_T *ep1 static BOOL_T SplitCurve( track_p trk, coOrd pos, EPINX_T ep, track_p *leftover, EPINX_T * ep0, EPINX_T * ep1 ) { - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); ANGLE_T a, a0, a1; track_p trk1; @@ -841,7 +860,7 @@ static BOOL_T SplitCurve( track_p trk, coOrd pos, EPINX_T ep, track_p *leftover, static BOOL_T TraverseCurve( traverseTrack_p trvTrk, DIST_T * distR ) { track_p trk = trvTrk->trk; - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); ANGLE_T a, a0, a1, a2, a3; DIST_T arcDist; DIST_T circum; @@ -936,18 +955,19 @@ static BOOL_T TraverseCurve( traverseTrack_p trvTrk, DIST_T * distR ) static BOOL_T EnumerateCurve( track_p trk ) { - struct extraData *xx; + struct extraDataCurve_t *xx; ANGLE_T a0, a1; DIST_T d; if (trk != NULL) { - xx = GetTrkExtraData(trk); + xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); GetCurveAngles( &a0, &a1, trk ); d = (xx->radius + (GetTrkGauge(trk)/2.0))* 2.0 * M_PI * a1 / 360.0; if (xx->helixTurns > 0) d += (xx->helixTurns-(xx->circle?1:0)) * (xx->radius+(GetTrkGauge(trk)/2.0)) * 2.0 * M_PI; ScaleLengthIncrement( GetTrkScale(trk), d ); + return TRUE; } - return TRUE; + return FALSE; } static BOOL_T TrimCurve( track_p trk, EPINX_T ep, DIST_T dist, coOrd endpos, ANGLE_T angle, DIST_T endradius, coOrd endcenter ) @@ -957,7 +977,7 @@ static BOOL_T TrimCurve( track_p trk, EPINX_T ep, DIST_T dist, coOrd endpos, ANG ANGLE_T a, aa; ANGLE_T a0, a1; coOrd pos, center; - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); if (xx->helixTurns>0) { ErrorMessage( MSG_CANT_TRIM_HELIX ); return FALSE; @@ -984,8 +1004,6 @@ static BOOL_T MergeCurve( track_p trk1, EPINX_T ep1 ) { - struct extraData *xx0 = GetTrkExtraData(trk0); - struct extraData *xx1 = GetTrkExtraData(trk1); ANGLE_T a00, a01, a10, a11; DIST_T d; track_p trk2; @@ -997,6 +1015,8 @@ static BOOL_T MergeCurve( if ( IsCurveCircle(trk0) || IsCurveCircle(trk1) ) return FALSE; + struct extraDataCurve_t *xx0 = GET_EXTRA_DATA(trk0, T_CURVE, extraDataCurve_t); + struct extraDataCurve_t *xx1 = GET_EXTRA_DATA(trk1, T_CURVE, extraDataCurve_t); if ( xx0->helixTurns > 0 || xx1->helixTurns > 0 ) return FALSE; @@ -1034,7 +1054,7 @@ static BOOL_T MergeCurve( ConnectTracks( trk0, ep0, trk2, ep2 ); } DrawNewTrack( trk0 ); - ComputeCurveBoundingBox( trk0, GetTrkExtraData(trk0) ); + ComputeCurveBoundingBox( trk0, GET_EXTRA_DATA(trk0, T_CURVE, extraDataCurve_t) ); return TRUE; } @@ -1055,7 +1075,7 @@ static STATUS_T ModifyCurve( track_p trk, wAction_t action, coOrd pos ) ANGLE_T a, aa1, aa2; DIST_T r, d; track_p trk1; - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); switch ( action ) { @@ -1185,7 +1205,7 @@ static DIST_T GetLengthCurve( track_p trk ) DIST_T dist, rad; ANGLE_T a0, a1; coOrd cen; - struct extraData *xx = GetTrkExtraData(trk); + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); GetTrkCurveCenter( trk, &cen, &rad ); if (xx->circle) @@ -1201,7 +1221,6 @@ static DIST_T GetLengthCurve( track_p trk ) static BOOL_T GetParamsCurve( int inx, track_p trk, coOrd pos, trackParams_t * params ) { - struct extraData *xx = GetTrkExtraData(trk); params->type = curveTypeCurve; GetTrkCurveCenter( trk, ¶ms->arcP, ¶ms->arcR); GetCurveAngles( ¶ms->arcA0, ¶ms->arcA1, trk ); @@ -1214,6 +1233,7 @@ static BOOL_T GetParamsCurve( int inx, track_p trk, coOrd pos, trackParams_t * p FormatDistance( params->arcR ), FormatDistance( easeR ) ); return FALSE; } + struct extraDataCurve_t *xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); if ( inx == PARAMS_EXTEND && ( IsCurveCircle(trk) || xx->helixTurns > 0 ) ) { ErrorMessage( MSG_CANT_EXTEND_HELIX ); return FALSE; @@ -1262,7 +1282,7 @@ static BOOL_T MoveEndPtCurve( track_p *trk, EPINX_T *ep, coOrd pos, DIST_T d0 ) static BOOL_T QueryCurve( track_p trk, int query ) { - struct extraData * xx = GetTrkExtraData(trk); + struct extraDataCurve_t * xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); switch ( query ) { case Q_CAN_PARALLEL: case Q_CAN_MODIFYRADIUS: @@ -1305,7 +1325,7 @@ static void FlipCurve( coOrd orig, ANGLE_T angle ) { - struct extraData * xx = GetTrkExtraData(trk); + struct extraDataCurve_t * xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); FlipPoint( &xx->pos, orig, angle ); ComputeCurveBoundingBox( trk, xx ); } @@ -1321,8 +1341,8 @@ static BOOL_T MakeParallelCurve( coOrd * p1R, BOOL_T track) { - struct extraData * xx = GetTrkExtraData(trk); - struct extraData * xx1; + struct extraDataCurve_t * xx = GET_EXTRA_DATA(trk, T_CURVE, extraDataCurve_t); + struct extraDataCurve_t * xx1; DIST_T rad; ANGLE_T a0, a1; @@ -1336,7 +1356,7 @@ static BOOL_T MakeParallelCurve( if ( newTrkR ) { if (track) { *newTrkR = NewCurvedTrack( xx->pos, rad, a0, a1, 0 ); - xx1 = GetTrkExtraData(*newTrkR); + xx1 = GET_EXTRA_DATA(*newTrkR, T_CURVE, extraDataCurve_t); xx1->helixTurns = xx->helixTurns; xx1->circle = xx->circle; } @@ -1376,8 +1396,8 @@ static BOOL_T MakeParallelCurve( static wBool_t CompareCurve( track_cp trk1, track_cp trk2 ) { - struct extraData * ed1 = GetTrkExtraData( trk1 ); - struct extraData * ed2 = GetTrkExtraData( trk2 ); + struct extraDataCurve_t * ed1 = GET_EXTRA_DATA( trk1, T_CURVE, extraDataCurve_t ); + struct extraDataCurve_t * ed2 = GET_EXTRA_DATA( trk2, T_CURVE, extraDataCurve_t ); char * cp = message+strlen(message); REGRESS_CHECK_POS( "POS", ed1, ed2, pos ) REGRESS_CHECK_DIST( "RADIUS", ed1, ed2, radius ) @@ -1581,7 +1601,8 @@ EXPORT void PlotCurve( coOrd pos1, coOrd pos2, curveData_t * curveData, - BOOL_T constrain ) //Make the Radius be in steps of radiusGranularity (1/8) + BOOL_T constrain, //Make the Radius be in steps of radiusGranularity (1/8) + DIST_T desired_r) //Target one radius if close { DIST_T d0, d2, r; ANGLE_T angle, a0, a1, a2; @@ -1604,19 +1625,36 @@ LOG( log_curve, 3, ( "Straight: %0.3f < %0.3f\n", d0*sin(D2R(a1)), (4.0/75.0)*ma } else if (a1 >= 179.0 && a1 <= 181.0) { curveData->type = curveTypeNone; } else { + BOOL_T found = FALSE; if (a1<180.0) { a2 = NormalizeAngle( angle + 90.0 ); - if (constrain) - curveData->curveRadius = ConstrainR( d0/sin(D2R(a1)) ); - else - curveData->curveRadius = d0/sin(D2R(a1)); + if (desired_r > 0.0) { + if (IsClose(fabs(d0/sin(D2R(a1))-desired_r))) { + curveData->curveRadius = desired_r; + found = TRUE; + } + } + if (!found) { + if (constrain) + curveData->curveRadius = ConstrainR( d0/sin(D2R(a1)) ); + else + curveData->curveRadius = d0/sin(D2R(a1)); + } } else { a1 -= 360.0; a2 = NormalizeAngle( angle - 90.0 ); - if (constrain) - curveData->curveRadius = ConstrainR( d0/sin(D2R(-a1)) ); - else - curveData->curveRadius = d0/sin(D2R(-a1)); + if (desired_r > 0.0) { + if (IsClose(fabs(d0/sin(D2R(-a1))-desired_r))) { + curveData->curveRadius = desired_r; + found = TRUE; + } + } + if (!found){ + if (constrain) + curveData->curveRadius = ConstrainR( d0/sin(D2R(-a1)) ); + else + curveData->curveRadius = d0/sin(D2R(-a1)); + } } if (curveData->curveRadius > 1000) { LOG( log_curve, 3, ( "Straight %0.3f > 1000\n", curveData->curveRadius ) ) @@ -1702,10 +1740,10 @@ LOG( log_curve, 3, ( "Straight: %0.3f < %0.3f\n", d0*sin(D2R(a1)), (4.0/75.0)*ma EXPORT track_p NewCurvedTrack( coOrd pos, DIST_T r, ANGLE_T a0, ANGLE_T a1, long helixTurns ) { - struct extraData *xx; + struct extraDataCurve_t *xx; track_p p; p = NewTrack( 0, T_CURVE, 2, sizeof *xx ); - xx = GetTrkExtraData(p); + xx = GET_EXTRA_DATA(p, T_CURVE, extraDataCurve_t); xx->pos = pos; xx->radius = r; xx->helixTurns = helixTurns; |