让我们举例说,我有以下2个向量:
*B
*A
我想要的矢量是C
*C *B
*A
我要做的是生成方形轮廓。我使用2d slurp:其中v0将是A而v2将是B.现在我使用sslerp2D来制作圆边但我也想要常规方形边缘因此我想要修改它。
POINTFLOAT slerp2d( const POINTFLOAT &v0,
const POINTFLOAT &v1, float t )
{
float dot = (v0.x * v1.x + v0.y * v1.y);
if( dot < -1.0f ) dot = -1.0f;
if( dot > 1.0f ) dot = 1.0f;
float theta_0 = acos( dot );
float theta = theta_0 * t;
POINTFLOAT v2;
v2.x = -v0.y;
v2.y = v0.x;
POINTFLOAT result;
result.x = v0.x * cos(theta) + v2.x * sin(theta);
result.y = v0.y * cos(theta) + v2.y * sin(theta);
return result;
}
由于
编辑:
我生成这样的轮廓:
void OGLSHAPE::GenerateLinePoly(std::vector<DOUBLEPOINT> &input, int width)
{
OutlineVec.clear();
if(input.size() < 2)
{
return;
}
if(connected)
{
input.push_back(input[0]);
input.push_back(input[1]);
}
float w = width / 2.0f;
//glBegin(GL_TRIANGLES);
for( size_t i = 0; i < input.size()-1; ++i )
{
POINTFLOAT cur;
cur.x = input[i].point[0];
cur.y = input[i].point[1];
POINTFLOAT nxt;
nxt.x = input[i+1].point[0];
nxt.y = input[i+1].point[1];
POINTFLOAT b;
b.x = nxt.x - cur.x;
b.y = nxt.y - cur.y;
b = normalize(b);
POINTFLOAT b_perp;
b_perp.x = -b.y;
b_perp.y = b.x;
POINTFLOAT p0;
POINTFLOAT p1;
POINTFLOAT p2;
POINTFLOAT p3;
p0.x = cur.x + b_perp.x * w;
p0.y = cur.y + b_perp.y * w;
p1.x = cur.x - b_perp.x * w;
p1.y = cur.y - b_perp.y * w;
p2.x = nxt.x + b_perp.x * w;
p2.y = nxt.y + b_perp.y * w;
p3.x = nxt.x - b_perp.x * w;
p3.y = nxt.y - b_perp.y * w;
OutlineVec.push_back(p0.x);
OutlineVec.push_back(p0.y);
OutlineVec.push_back(p1.x);
OutlineVec.push_back(p1.y);
OutlineVec.push_back(p2.x);
OutlineVec.push_back(p2.y);
OutlineVec.push_back(p2.x);
OutlineVec.push_back(p2.y);
OutlineVec.push_back(p1.x);
OutlineVec.push_back(p1.y);
OutlineVec.push_back(p3.x);
OutlineVec.push_back(p3.y);
// only do joins when we have a prv
if( i == 0 ) continue;
POINTFLOAT prv;
prv.x = input[i-1].point[0];
prv.y = input[i-1].point[1];
POINTFLOAT a;
a.x = prv.x - cur.x;
a.y = prv.y - cur.y;
a = normalize(a);
POINTFLOAT a_perp;
a_perp.x = a.y;
a_perp.y = -a.x;
float det = a.x * b.y - b.x * a.y;
if( det > 0 )
{
a_perp.x = -a_perp.x;
a_perp.y = -a_perp.y;
b_perp.x = -b_perp.x;
b_perp.y = -b_perp.y;
}
// TODO: do inner miter calculation
// flip around normals and calculate round join points
a_perp.x = -a_perp.x;
a_perp.y = -a_perp.y;
b_perp.x = -b_perp.x;
b_perp.y = -b_perp.y;
size_t num_pts = 4;
std::vector< POINTFLOAT> round( 1 + num_pts + 1 );
POINTFLOAT nc;
nc.x = cur.x + (a_perp.x * w);
nc.y = cur.y + (a_perp.y * w);
round.front() = nc;
nc.x = cur.x + (b_perp.x * w);
nc.y = cur.y + (b_perp.y * w);
round.back() = nc;
for( size_t j = 1; j < num_pts+1; ++j )
{
float t = (float)j/(float)(num_pts+1);
if( det > 0 )
{
POINTFLOAT nin;
nin = slerp2d( b_perp, a_perp, 1.0f-t );
nin.x *= w;
nin.y *= w;
nin.x += cur.x;
nin.y += cur.y;
round[j] = nin;
}
else
{
POINTFLOAT nin;
nin = slerp2d( a_perp, b_perp, t );
nin.x *= w;
nin.y *= w;
nin.x += cur.x;
nin.y += cur.y;
round[j] = nin;
}
}
for( size_t j = 0; j < round.size()-1; ++j )
{
OutlineVec.push_back(cur.x);
OutlineVec.push_back(cur.y);
if( det > 0 )
{
OutlineVec.push_back(round[j + 1].x);
OutlineVec.push_back(round[j + 1].y);
OutlineVec.push_back(round[j].x);
OutlineVec.push_back(round[j].y);
}
else
{
OutlineVec.push_back(round[j].x);
OutlineVec.push_back(round[j].y);
OutlineVec.push_back(round[j + 1].x);
OutlineVec.push_back(round[j + 1].y);
}
}
}
}
答案 0 :(得分:3)
你似乎在使用积分,而不是矢量。如果你有两个点(X 1 ,Y 1 ),(X 2 ,Y 2 ),那么(X 1 ,Y 2 )和(X 2 ,Y 1 )都应该形成直角三角形前两点[编辑:提供,当然,前两个点不形成垂直或水平线]。对于您提供的输入,一个是您标记为C
的点,另一个将在右下角给出镜像三角形。
进一步编辑:我不太清楚你对一个不完全是90度的角度的意思。对于原始线是垂直或水平的上述情况,从这些中的一个形成无限多种直角三角形是微不足道的:为第二侧选择任意长度并从两点之一以90度延伸。你的第三面(斜边)将从新点延伸到两个原点的其他。如果你愿意的话,你也可以构造一个无限多种其他直角三角形,原始对形成斜边(尽管它涉及更加困难的数学 - A 2 = C 2 -B 2 ,其中C是原始线的长度,B是您在0..C范围内选择的任意长度。