Tweaked the line clamping algorithm (Issue 186): Multiples of 45° use orthogonal projection (again), ISO lines are now constrained to exact 2:1 lines and their length is projected on most significant axis, horizontal or vertical

git-svn-id: svn://pulkomandy.tk/GrafX2/trunk@922 416bcca6-2ee7-4201-b75f-2eb2f807beb1
This commit is contained in:
Yves Rizoud 2009-07-15 20:11:07 +00:00
parent 7fc318a856
commit 9d0c73b5be
2 changed files with 116 additions and 49 deletions

BIN
gfx2.cfg

Binary file not shown.

149
graph.c
View File

@ -1362,7 +1362,6 @@ void Clamp_coordinates_regular_angle(short ax, short ay, short* bx, short* by)
{ {
int dx, dy; int dx, dy;
float angle; float angle;
float length;
dx = *bx-ax; dx = *bx-ax;
dy = *by-ay; dy = *by-ay;
@ -1370,49 +1369,117 @@ void Clamp_coordinates_regular_angle(short ax, short ay, short* bx, short* by)
// No mouse move: no need to clamp anything // No mouse move: no need to clamp anything
if (dx==0 || dy == 0) return; if (dx==0 || dy == 0) return;
// Determine angle (heading)
angle = atan2(dx, dy); angle = atan2(dx, dy);
// Horizontal < 15/16 // Get absolute values, useful from now on:
if (angle < M_PI*(-15.0/16.0) || angle > M_PI*(15.0/16.0)) //dx=abs(dx);
angle = M_PI*(16.0/16.0); //dy=abs(dy);
// 15/16 < Iso < 13/16
else if (angle < M_PI*(-13.0/16.0))
angle = -2.677945045;
// 13/16 < 45deg (3pi/4) < 11/16
else if (angle < M_PI*(-11.0/16.0))
angle = M_PI*(-12.0/16.0);
// 11/16 < "vertical iso" < 9/19
else if (angle < M_PI*(-9.0/16.0))
angle = -2.034443936;
// 9/16 < vertical < 7/16
else if (angle < M_PI*(-7.0/16.0))
angle = M_PI*(-8.0/16.0);
else if (angle < M_PI*(-5.0/16.0))
angle = -1.107148718;
else if (angle < M_PI*(-3.0/16.0))
angle = M_PI*(-4.0/16.0);
else if (angle < M_PI*(-1.0/16.0))
angle = -0.463647609;
else if (angle < M_PI*(1.0/16.0))
angle = M_PI*(0.0/16.0);
else if (angle < M_PI*(3.0/16.0))
angle = 0.463647609;
else if (angle < M_PI*(5.0/16.0))
angle = M_PI*(4.0/16.0);
else if (angle < M_PI*(7.0/16.0))
angle = 1.107148718;
else if (angle < M_PI*(9.0/16.0))
angle = M_PI*(8.0/16.0);
else if (angle < M_PI*(11.0/16.0))
angle = 2.034443936;
else if (angle < M_PI*(13.0/16.0))
angle = M_PI*(12.0/16.0);
else //if (angle < M_PI*(15.0/16.0))
angle = 2.677945045;
length = sqrt((float)(dx)*(float)(dx)+(float)(dy)*(float)(dy)); // Negative Y
*bx=ax + lrintf(sin(angle)*length); if (angle < M_PI*(-15.0/16.0) || angle > M_PI*(15.0/16.0))
*by=ay + lrintf(cos(angle)*length); {
*bx=ax;
*by=ay + dy;
}
// Iso close to negative Y
else if (angle < M_PI*(-13.0/16.0))
{
dy=dy | 1; // Round up to next odd number
*bx=ax + dy/2;
*by=ay + dy;
}
// 45deg
else if (angle < M_PI*(-11.0/16.0))
{
*by = (*by + ay + dx)/2;
*bx = ax - ay + *by;
}
// Iso close to negative X
else if (angle < M_PI*(-9.0/16.0))
{
dx=dx | 1; // Round up to next odd number
*bx=ax + dx;
*by=ay + dx/2;
}
// Negative X
else if (angle < M_PI*(-7.0/16.0))
{
*bx=ax + dx;
*by=ay;
}
// Iso close to negative X
else if (angle < M_PI*(-5.0/16.0))
{
dx=dx | 1; // Round up to next odd number
*bx=ax + dx;
*by=ay - dx/2;
}
// 45 degrees
else if (angle < M_PI*(-3.0/16.0))
{
*by = (*by + ay - dx)/2;
*bx = ax + ay - *by;
}
// Iso close to positive Y
else if (angle < M_PI*(-1.0/16.0))
{
dy=dy | 1; // Round up to next odd number
*bx=ax - dy/2;
*by=ay + dy;
}
// Positive Y
else if (angle < M_PI*(1.0/16.0))
{
*bx=ax;
*by=ay + dy;
}
// Iso close to positive Y
else if (angle < M_PI*(3.0/16.0))
{
dy=dy | 1; // Round up to next odd number
*bx=ax + dy/2;
*by=ay + dy;
}
// 45 degrees
else if (angle < M_PI*(5.0/16.0))
{
*by = (*by + ay + dx)/2;
*bx = ax - ay + *by;
}
// Iso close to positive X
else if (angle < M_PI*(7.0/16.0))
{
dx=dx | 1; // Round up to next odd number
*bx=ax + dx;
*by=ay + dx/2;
}
// Positive X
else if (angle < M_PI*(9.0/16.0))
{
*bx=ax + dx;
*by=ay;
}
// Iso close to positive X
else if (angle < M_PI*(11.0/16.0))
{
dx=dx | 1; // Round up to next odd number
*bx=ax + dx;
*by=ay - dx/2;
}
// 45 degrees
else if (angle < M_PI*(13.0/16.0))
{
*by = (*by + ay - dx)/2;
*bx = ax + ay - *by;
}
// Iso close to negative Y
else //if (angle < M_PI*(15.0/16.0))
{
dy=dy | 1; // Round up to next odd number
*bx=ax - dy/2;
*by=ay + dy;
}
return; return;
} }