mirror of
https://git.do.srb2.org/STJr/ZoneBuilder.git
synced 2024-11-10 06:41:49 +00:00
Updated: sector triangulation logic now works ~50% faster than DB2 implementation.
This commit is contained in:
parent
41ae6b3c55
commit
62835e28fb
1 changed files with 57 additions and 56 deletions
|
@ -783,6 +783,8 @@ namespace CodeImp.DoomBuilder.Geometry
|
|||
Vector2D pos0 = t[0].Position;
|
||||
Vector2D pos1 = t[1].Position;
|
||||
Vector2D pos2 = t[2].Position;
|
||||
Vector2D vpos;
|
||||
LinkedListNode<EarClipVertex> p;
|
||||
|
||||
// Go for all reflex vertices
|
||||
foreach(EarClipVertex rv in reflexes)
|
||||
|
@ -791,7 +793,61 @@ namespace CodeImp.DoomBuilder.Geometry
|
|||
if((rv.Position != pos0) && (rv.Position != pos1) && (rv.Position != pos2))
|
||||
{
|
||||
// Return false on intersection
|
||||
if(PointInsideTriangle(t, rv.MainListNode)) return false;
|
||||
|
||||
// This checks if a point is inside a triangle
|
||||
// When the point is on an edge of the triangle, it depends on the lines
|
||||
// adjacent to the point if it is considered inside or not
|
||||
// NOTE: vertices in t must be in clockwise order!
|
||||
|
||||
// If the triangle has no area, there can never be a point inside
|
||||
if(TriangleHasArea(t))
|
||||
{
|
||||
//mxd
|
||||
pos0 = t[0].Position;
|
||||
pos1 = t[1].Position;
|
||||
pos2 = t[2].Position;
|
||||
p = rv.MainListNode;
|
||||
vpos = p.Value.Position;
|
||||
|
||||
//mxd. Check bounds first...
|
||||
if( vpos.x < Math.Min(pos0.x, Math.Min(pos1.x, pos2.x)) ||
|
||||
vpos.x > Math.Max(pos0.x, Math.Max(pos1.x, pos2.x)) ||
|
||||
vpos.y < Math.Min(pos0.y, Math.Min(pos1.y, pos2.y)) ||
|
||||
vpos.y > Math.Max(pos0.y, Math.Max(pos1.y, pos2.y))) continue;
|
||||
|
||||
float lineside01 = Line2D.GetSideOfLine(pos0, pos1, vpos);
|
||||
float lineside12 = Line2D.GetSideOfLine(pos1, pos2, vpos);
|
||||
float lineside20 = Line2D.GetSideOfLine(pos2, pos0, vpos);
|
||||
float u_on_line = 0.5f;
|
||||
|
||||
// If point p is on the line of an edge, find out where on the edge segment p is.
|
||||
if(lineside01 == 0.0f)
|
||||
u_on_line = Line2D.GetNearestOnLine(pos0, pos1, vpos);
|
||||
else if(lineside12 == 0.0f)
|
||||
u_on_line = Line2D.GetNearestOnLine(pos1, pos2, vpos);
|
||||
else if(lineside20 == 0.0f)
|
||||
u_on_line = Line2D.GetNearestOnLine(pos2, pos0, vpos);
|
||||
|
||||
// If any of the lineside results are 0 then that means the point p lies on that edge and we
|
||||
// need to test if the lines adjacent to the point p are in the triangle or not.
|
||||
// If the lines are intersecting the triangle, we also consider the point inside.
|
||||
if(lineside01 == 0.0f || lineside12 == 0.0f || lineside20 == 0.0f)
|
||||
{
|
||||
// When the point p is outside the edge segment, then it is not inside the triangle
|
||||
if(u_on_line < 0.0f || u_on_line > 1.0f) continue;
|
||||
|
||||
// Point p is on an edge segment. We'll have to decide by it's lines if we call it inside or outside the triangle.
|
||||
LinkedListNode<EarClipVertex> p1 = p.Previous ?? p.List.Last;
|
||||
if(LineInsideTriangle(t, vpos, p1.Value.Position)) return false;
|
||||
|
||||
LinkedListNode<EarClipVertex> p2 = p.Next ?? p.List.First;
|
||||
if(LineInsideTriangle(t, vpos, p2.Value.Position)) return false;
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
if(lineside01 < 0.0f && lineside12 < 0.0f && lineside20 < 0.0f) return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -817,61 +873,6 @@ namespace CodeImp.DoomBuilder.Geometry
|
|||
return (Line2D.GetSideOfLine(t[0].Position, t[2].Position, t[1].Position) < 0.0f);
|
||||
}
|
||||
|
||||
// This checks if a point is inside a triangle
|
||||
// When the point is on an edge of the triangle, it depends on the lines
|
||||
// adjacent to the point if it is considered inside or not
|
||||
// NOTE: vertices in t must be in clockwise order!
|
||||
private static bool PointInsideTriangle(EarClipVertex[] t, LinkedListNode<EarClipVertex> p)
|
||||
{
|
||||
// If the triangle has no area, there can never be a point inside
|
||||
if(TriangleHasArea(t))
|
||||
{
|
||||
//mxd
|
||||
Vector2D pos0 = t[0].Position;
|
||||
Vector2D pos1 = t[1].Position;
|
||||
Vector2D pos2 = t[2].Position;
|
||||
|
||||
float lineside01 = Line2D.GetSideOfLine(pos0, pos1, p.Value.Position);
|
||||
float lineside12 = Line2D.GetSideOfLine(pos1, pos2, p.Value.Position);
|
||||
float lineside20 = Line2D.GetSideOfLine(pos2, pos0, p.Value.Position);
|
||||
float u_on_line = 0.5f;
|
||||
|
||||
// If point p is on the line of an edge, find out where on the edge segment p is.
|
||||
if(lineside01 == 0.0f)
|
||||
u_on_line = Line2D.GetNearestOnLine(pos0, pos1, p.Value.Position);
|
||||
else if(lineside12 == 0.0f)
|
||||
u_on_line = Line2D.GetNearestOnLine(pos1, pos2, p.Value.Position);
|
||||
else if(lineside20 == 0.0f)
|
||||
u_on_line = Line2D.GetNearestOnLine(pos2, pos0, p.Value.Position);
|
||||
|
||||
// If any of the lineside results are 0 then that means the point p lies on that edge and we
|
||||
// need to test if the lines adjacent to the point p are in the triangle or not.
|
||||
// If the lines are intersecting the triangle, we also consider the point inside.
|
||||
if((lineside01 == 0.0f) || (lineside12 == 0.0f) || (lineside20 == 0.0f))
|
||||
{
|
||||
// When the point p is outside the edge segment, then it is not inside the triangle
|
||||
if((u_on_line < 0.0f) || (u_on_line > 1.0f))
|
||||
return false;
|
||||
|
||||
// Point p is on an edge segment. We'll have to decide by it's lines if we call it inside or outside the triangle.
|
||||
LinkedListNode<EarClipVertex> p1 = p.Previous ?? p.List.Last;
|
||||
LinkedListNode<EarClipVertex> p2 = p.Next ?? p.List.First;
|
||||
if(LineInsideTriangle(t, p.Value.Position, p1.Value.Position)) return true;
|
||||
if(LineInsideTriangle(t, p.Value.Position, p2.Value.Position)) return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
return (lineside01 < 0.0f) && (lineside12 < 0.0f) && (lineside20 < 0.0f);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// This checks if a line is inside a triangle (touching the triangle is allowed)
|
||||
// NOTE: We already know p1 is on an edge segment of the triangle
|
||||
private static bool LineInsideTriangle(EarClipVertex[] t, Vector2D p1, Vector2D p2)
|
||||
|
|
Loading…
Reference in a new issue