计算快速终点

时间:2014-04-19 18:30:37

标签: c++ c optimization line

我想要的是,我有2点的信息,起点x,y和中点x,y和我需要找到终点线,直到某种边界,如窗口

这就是我的所作所为:

//function for calculating the end point from one location, to specific end location
//like a bullet moving forward in a line
//x,y start location(mouse), x2,y2(rect point location one of the 4) mid point, qx,qy end point(shadow or triangle draw location)
void screenEnd(int x, int y, int x2, int y2, int*qx,int*qy)
{
x = x2-x;
y = y2-y;

float tx = x2,ty = y2;

float result = atan2((float)y,(float)x) * 180 / PI;

float tempx = cos ( result * PI / 180.0 );
float tempy = sin ( result * PI / 180.0 );

bool check = true;
//this part needs optimization
while(check)
{
    if(tx < 0|| ty < 0|| tx > 1280 || ty > 720)
    {
        check = false;
    }           
    else
    {
        tx += tempx;
        ty += tempy;
    }
}

*qx = tx;
*qy = ty;
}

我所做的只是增加点直到它结束。 有没有更快的方法?

1 个答案:

答案 0 :(得分:0)

经典的窗口剪辑任务。

考虑一个参数方程,其中p是点(x,y)

p(0)   = x, y
p(0.5) = x2, y2
p(1)   = x+2*(x2-x), y + 2*(y2-y)
p(t)   = p(0) + t*(p(1) - p(0))
clip window = 0,0 to 720, 1280  (suspect you really want 719,1279)

最初绘制的细分受众群的范围从t=0.0t=1.0。针对边界框的4个边中的每个边测试该段,可能会减小t范围。甚至可能一起消除所有。

以下是一些旧代码,足以让你前进。

#include <math.h>

int cliptest(int dz, int z, double *t0, double *t1) {
  if (dz < 0) {
    double t = ((double) z) / dz;
    if (t > *t1)
      return 0;
    if (t > *t0)
      *t0 = t;
  } else if (dz > 0) {
    double t = ((double) z) / dz;
    if (t < *t0)
      return 0;
    if (t < *t1)
      *t1 = t;
  } else {
    if (z < 0)
      return 0;
  }
  return 1;
}

int clipper(int *px0, int *py0, int *px1, int *py1, int minx, int miny,
        int maxx, int maxy) {
  double t0, t1;
  int dx, dy;

  t0 = 0.0;
  t1 = 1.0;
  dy = *py1 - *py0;
  dx = *px1 - *px0;
  if (cliptest(-dx, *px0 - minx, &t0, &t1)
          && cliptest(dx, maxx - *px0, &t0, &t1)
          && cliptest(-dy, *py0 - miny, &t0, &t1)
          && cliptest(dy, maxy - *py0, &t0, &t1)) {
    if (t1 < 1.0) {
      *px1 = round(*px0 + t1*dx);
      *py1 = round(*py0 + t1*dy);
    }
    if (t0 > 0.0) {
      *px0 = round(*px0 + t0*dx);
      *py0 = round(*py0 + t0*dy);
    }
    return 1;
  }
  return 0;
}

int x0 = x;
int y0 = y;
int x1 = x + 2*(x2-x); // Form end point
int y1 = x + 2*(y2-y);
if (clipper(&x0, &y0, &x1, &y1, 0, 0, 720, 1280)) 
  Draw(x0, y0, x1, y2);
else 
  Handle_LineTotallyClippedOut();