コード例 #1
0
        public static void DrawDebugHull(NativeHull hull, RigidTransform t, DebugHullFlags options = DebugHullFlags.All, Color BaseColor = default)
        {
            if (!hull.IsValid)
            {
                throw new ArgumentException("Hull is not valid", nameof(hull));
            }

            if (options == DebugHullFlags.None)
            {
                return;
            }

            if (BaseColor == default)
            {
                BaseColor = Color.yellow;
            }

            float faceExplosionDistance = (options & DebugHullFlags.ExplodeFaces) != 0 ? 0.3f : 0;

            // Iterate each twin pair at the same time.
            for (int j = 0; j < hull.EdgeCount; j = j + 2)
            {
                var edge = hull.GetEdge(j);
                var twin = hull.GetEdge(j + 1);

                var edgePlane = edge.Face != -1 ? hull.GetPlane(edge.Face) : new NativePlane();
                var twinPlane = twin.Face != -1 ? hull.GetPlane(twin.Face) : new NativePlane();

                var rotatedEdgeNormal = math.rotate(t, edgePlane.Normal);
                var rotatedTwinNormal = math.rotate(t, twinPlane.Normal);

                var edgeVertex1 = math.transform(t, hull.GetVertex(edge.Origin));
                var twinVertex1 = math.transform(t, hull.GetVertex(twin.Origin));
                var edgeVertex2 = math.transform(t, hull.GetVertex(edge.Origin));
                var twinVertex2 = math.transform(t, hull.GetVertex(twin.Origin));

                if ((options & DebugHullFlags.Outline) != 0)
                {
                    Debug.DrawLine(edgeVertex1 + rotatedEdgeNormal * faceExplosionDistance, twinVertex1 + rotatedEdgeNormal * faceExplosionDistance, BaseColor);
                    Debug.DrawLine(edgeVertex2 + rotatedTwinNormal * faceExplosionDistance, twinVertex2 + rotatedTwinNormal * faceExplosionDistance, BaseColor);
                }

                if ((options & DebugHullFlags.EdgeLinks) != 0)
                {
                    Debug.DrawLine((edgeVertex1 + twinVertex1) / 2 + rotatedEdgeNormal * faceExplosionDistance, (edgeVertex2 + twinVertex2) / 2 + rotatedTwinNormal * faceExplosionDistance, Color.gray);
                }
            }

            if ((options & DebugHullFlags.PlaneNormals) != 0)
            {
                for (int i = 0; i < hull.FaceCount; i++)
                {
                    var centroid = math.transform(t, hull.CalculateFaceCentroid(hull.GetFace(i)));
                    var normal   = math.rotate(t, hull.GetPlane(i).Normal);
                    DebugDrawer.DrawArrow(centroid, normal * 0.2f, BaseColor);
                }
            }

            if ((options & DebugHullFlags.Indices) != 0)
            {
                var dupeCheck = new HashSet <Vector3>();
                for (int i = 0; i < hull.VertexCount; i++)
                {
                    // Offset the label if multiple verts are on the same position.
                    var v      = math.transform(t, hull.GetVertex(i));
                    var offset = dupeCheck.Contains(v) ? (float3)Vector3.forward * 0.05f : 0;

                    DebugDrawer.DrawLabel(v + offset, i.ToString());
                    dupeCheck.Add(v);
                }
            }

            if ((options & DebugHullFlags.FaceWinding) != 0)
            {
                for (int i = 0; i < hull.FaceCount; i++)
                {
                    var face        = hull.GetFace(i);
                    var plane       = hull.GetPlane(i);
                    var tPlane      = t * plane;
                    var edge        = hull.GetEdge(face.Edge);
                    var startOrigin = edge.Origin;

                    do
                    {
                        var nextEdge  = hull.GetEdge(edge.Next);
                        var startVert = math.transform(t, hull.GetVertex(edge.Origin));
                        var endVert   = math.transform(t, hull.GetVertex(nextEdge.Origin));

                        var center = (endVert + startVert) / 2;
                        var dir    = math.normalize(endVert - startVert);

                        var insetDir = math.normalize(math.cross(tPlane.Normal, dir));

                        if ((options & DebugHullFlags.ExplodeFaces) != 0)
                        {
                            DebugDrawer.DrawArrow(center + tPlane.Normal * faceExplosionDistance, dir * 0.2f, Color.black);
                        }
                        else
                        {
                            DebugDrawer.DrawArrow(center + tPlane.Normal * faceExplosionDistance + insetDir * 0.1f, dir * 0.2f, Color.black);
                        }

                        edge = nextEdge;
                    } while (edge.Origin != startOrigin);
                }
            }
        }
コード例 #2
0
    public void DrawHullCollision(GameObject a, GameObject b, RigidTransform t1, NativeHull hull1, RigidTransform t2, NativeHull hull2)
    {
        var collision = HullCollision.GetDebugCollisionInfo(t1, hull1, t2, hull2);

        if (collision.IsColliding)
        {
            if (DrawIntersection) // Visualize all faces of the intersection
            {
                HullIntersection.DrawNativeHullHullIntersection(t1, hull1, t2, hull2);
            }

            if (DrawContact || LogContact)  // Visualize the minimal contact calcluation for physics
            {
                //var manifold = HullOperations.GetContact.Invoke(t1, hull1, t2, hull2);

                var sw1          = System.Diagnostics.Stopwatch.StartNew();
                var tmp          = new NativeManifold(Allocator.Persistent);
                var normalResult = HullIntersection.NativeHullHullContact(ref tmp, t1, hull1, t2, hull2);
                sw1.Stop();
                tmp.Dispose();

                var sw2         = System.Diagnostics.Stopwatch.StartNew();
                var burstResult = HullOperations.TryGetContact.Invoke(out NativeManifold manifold, t1, hull1, t2, hull2);
                sw2.Stop();

                if (LogContact)
                {
                    Debug.Log($"GetContact between '{a.name}'/'{b.name}' took: {sw1.Elapsed.TotalMilliseconds:N4}ms (Normal), {sw2.Elapsed.TotalMilliseconds:N4}ms (Burst)");
                }

                if (DrawContact && burstResult)
                {
                    // Do something with manifold

                    HullDrawingUtility.DebugDrawManifold(manifold);

                    //var points = manifold.Points;

                    for (int i = 0; i < manifold.Length; i++)
                    {
                        var point = manifold[i];
                        DebugDrawer.DrawSphere(point.Position, 0.02f);
                        DebugDrawer.DrawArrow(point.Position, manifold.Normal * 0.2f);

                        var penentrationPoint = point.Position + manifold.Normal * point.Distance;
                        DebugDrawer.DrawLabel(penentrationPoint, $"{point.Distance:N2}");

                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.InEdge1, t1, hull1);
                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.OutEdge1, t1, hull1);
                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.InEdge2, t1, hull1);
                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.OutEdge2, t1, hull1);

                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.InEdge1, t2, hull2);
                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.OutEdge1, t2, hull2);
                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.InEdge2, t2, hull2);
                        HullDrawingUtility.DrawEdge(point.Id.FeaturePair.OutEdge2, t2, hull2);

                        DebugDrawer.DrawDottedLine(point.Position, penentrationPoint);
                    }

                    manifold.Dispose();
                }
            }

            if (DrawIsCollided)
            {
                DebugDrawer.DrawSphere(t1.pos, 0.1f, UnityColors.GhostDodgerBlue);
                DebugDrawer.DrawSphere(t2.pos, 0.1f, UnityColors.GhostDodgerBlue);
            }
        }

        if (DrawClosestFace)
        {
            var color1 = collision.Face1.Distance > 0 ? UnityColors.Red.ToOpacity(0.3f) : UnityColors.Yellow.ToOpacity(0.3f);
            HullDrawingUtility.DrawFaceWithOutline(collision.Face1.Index, t1, hull1, color1, UnityColors.Black);

            var color2 = collision.Face2.Distance > 0 ? UnityColors.Red.ToOpacity(0.3f) : UnityColors.Yellow.ToOpacity(0.3f);
            HullDrawingUtility.DrawFaceWithOutline(collision.Face2.Index, t2, hull2, color2, UnityColors.Black);
        }
    }
コード例 #3
0
    private static unsafe void DrawTests(int threadIndex, float3 start, float3 end, NativeString512 text, DrawingMethods methods, NativeArray <float3> polygon)
    {
        float3 offset = Vector3.up * 0.05f + Vector3.left * 0.05f;
        float3 center = (start + (end - start) / 2);

        if (methods.Sphere)
        {
            DebugDrawer.DrawSphere(start, 0.75f, UnityColors.GhostDodgerBlue);
        }

        if (methods.RectangleWithOutline)
        {
            var size   = 0.25f;
            var points = stackalloc[]
            {
                center + offset + new float3(0, 0, 0),
                center + offset + new float3(0, size, 0),
                center + offset + new float3(0, size, size),
                center + offset + new float3(0, 0, size)
            };

            DebugDrawer.DrawSolidRectangleWithOutline(points, UnityColors.LightYellow, UnityColors.Yellow);
        }

        if (methods.Polygon)
        {
            DebugDrawer.DrawAAConvexPolygon(polygon, center + (float3)Vector3.down * 0.25f, UnityColors.GhostDodgerBlue);
        }

        if (methods.Line)
        {
            DebugDrawer.DrawLine(start + offset, end + offset);
        }

        if (methods.Ray)
        {
            DebugDrawer.DrawRay(center, Vector3.up, UnityColors.MediumBlue);
        }

        if (methods.Cone)
        {
            DebugDrawer.DrawCone(center + (float3)Vector3.up * 0.5f, Vector3.up, UnityColors.DarkKhaki, 22.5f);
        }

        if (methods.Circle)
        {
            DebugDrawer.DrawCircle(center, Vector3.up, 0.25f, UnityColors.AliceBlue);
        }

        if (methods.DottedLine)
        {
            DebugDrawer.DrawDottedLine(start, end, Color.yellow);
        }

        if (methods.WireCube)
        {
            DebugDrawer.DrawWireCube(end, Vector3.one / 2, Color.yellow);
        }

        if (methods.DottedWireCube)
        {
            DebugDrawer.DrawDottedWireCube(end, Vector3.one, Color.black);
        }

        if (methods.Label)
        {
            DebugDrawer.DrawLabel(center + (float3)Vector3.down * 0.25f, text);
        }

        if (methods.Arrow)
        {
            DebugDrawer.DrawArrow(start + (float3)Vector3.up * 0.5f, Vector3.up, Color.blue);
        }

        if (methods.Log)
        {
            DebugDrawer.Log(threadIndex, text);
        }

        if (methods.LogWarning)
        {
            DebugDrawer.LogWarning(text);
        }

        if (methods.LogError)
        {
            DebugDrawer.LogError(text);
        }

        if (methods.Point)
        {
            DebugDrawer.DrawPoint(center + (float3)Vector3.forward, UnityColors.Lavender, 0.25f);
        }
    }
}