/// <summary>
    /// check if input body has collided with plane
    /// </summary>
    /// <param name="body"></param>
    /// <param name="plane"></param>
    /// <returns></returns>
    private MyCollision CollidedWithPlane(MyRigidBody body, MyPlaneCollider plane)
    {
        // default to no collision
        MyCollision collision = null;

        // get the mesh filter for the plane
        MeshFilter filter = plane.gameObject.GetComponent<MeshFilter>();

        // make sure it has a mesh filter
        if (filter && filter.mesh.normals.Length > 0)
        {
            // get one of the vertext normals --- first one should do as the are all the same
            var normal = filter.transform.TransformDirection(filter.mesh.normals[0]);

            // distance of sphere centre from plane
            float distanceFromSphereCentre = Mathf.Abs(Vector3.Dot(normal, transform.position)) + (plane as MyPlaneCollider).distance;

            // distance of sphere from plane
            float distanceFromSphere = distanceFromSphereCentre - distanceToSurface;

            // check for intersection
            if (distanceFromSphere < 0)
            {
                // create a new collision object, containing the vector of the normal and the distance from the plane
                collision = new MyCollision(this, plane, new Vector3(transform.position.x, transform.position.y - ((MySphereCollider)body).radius, transform.position.z), normal, distanceFromSphere);
            }
        }
        return collision;
    }
Exemple #2
0
        /// <summary>
        /// Check the Segment Collision and Remove colliding Cells with there later Generations
        /// </summary>
        /// <param name="_cellsToCheck">The List of Cells to Check the Collision with</param>
        /// <returns></returns>
        public HashSet <int> CheckCollision(List <Cell> _cellsToCheck)
        {
            List <Cell>   PolyPolyCheckList   = new List <Cell>();
            HashSet <int> StreetIDsToRecreate = new HashSet <int>();

            //Sphere Sphere Collsion | fast but not precies | Save the Cells that can possible collide for a more precies check
            for (int i = 0; i < _cellsToCheck.Count; i++)
            {
                if (!_cellsToCheck[i].IsBlocked &&
                    MyCollision.SphereSphere(m_Center, m_CollisionRadius, _cellsToCheck[i].m_PosCenter, _cellsToCheck[i].m_Radius))
                {
                    PolyPolyCheckList.Add(_cellsToCheck[i]);
                }
            }

            //Poly Poly Collision | slow but more precies
            for (int i = 0; i < PolyPolyCheckList.Count; i++)
            {
                if (!PolyPolyCheckList[i].IsBlocked && MyCollision.PolyPoly(PolyPolyCheckList[i].m_Corner, m_CornerPos))
                {
                    PolyPolyCheckList[i].Delete(); //Delete the Colliding Cell and the later Generations
                    int id = PolyPolyCheckList[i].m_Street.ID;
                    StreetIDsToRecreate.Add(id);   //Saves the Street ID to recreate the Grid Mesh
                }
            }

            return(StreetIDsToRecreate);
        }
    /// <summary>
    /// Check if the input body has corrected with a sphere
    /// </summary>
    /// <param name="body"></param>
    /// <param name="sphere"></param>
    /// <returns></returns>
    private MyCollision CollidedWithSphere(MyRigidBody body, MySphereCollider sphere)
    {
        // default to no collision
        MyCollision collision = null;

        // combined radius of both spheres
        float combinedRadius = this.distanceToSurface + ((MySphereCollider)sphere).radius;

        // the vector between the centres of the spheres
        Vector3 direction = sphere.transform.position - transform.position;

        // distance between centres
        float centreDistance = direction.magnitude;

        // normalise the direction
        direction /= centreDistance;

        // check interection
        if (centreDistance < combinedRadius)
        {
            // create a new collision object, containing the vector of the normal and the distance from the sphere
            collision = new MyCollision(this, sphere, new Vector3(transform.position.x, transform.position.y - ((MySphereCollider)body).radius, transform.position.z), direction, centreDistance);
        }

        return collision;
    }
Exemple #4
0
    private void ChooseNextDirection()
    {
        bool col = true;

        while (col == true)
        {
            _direction = GetRandomDirection(_direction);

            List <int> moveGroupIndicesAfterTurn = _direction.FrontMoveGroup();

            int collisionCount = 0;

            for (int i = 0; i < moveGroupIndicesAfterTurn.Count; i++)
            {
                CollisionType obstacle = MyCollision.Check(Cubes[moveGroupIndicesAfterTurn[i]], _direction, MyGameManager.MyGrid);
                if (obstacle == CollisionType.GridEdge || obstacle == CollisionType.Stone)
                {
                    Debug.Log("Collided with " + obstacle);
                    collisionCount++;
                }
            }

            if (collisionCount == 0)
            {
                col = false;
            }
        }
    }
Exemple #5
0
        /// <summary>
        /// Check if the HitPos is over an Building/Area
        /// </summary>
        /// <param name="b"></param>
        /// <returns></returns>
        protected bool CheckAreaCollision(out ABuilding b)
        {
            List <Area> SphereSphere = new List <Area>();

            b = null;

            foreach (Area area in BuildingManager.m_AllAreas)
            {
                if (MyCollision.SphereSphere(new Vector2(m_hitPos.x, m_hitPos.z), 0.8f, new Vector2(area.m_OP.Position.x, area.m_OP.Position.z), area.m_Radius))
                {
                    SphereSphere.Add(area);
                }
            }
            if (SphereSphere.Count == 0)
            {
                return(false);
            }
            else
            {
                int   index           = -1;
                float closestDistance = float.MaxValue;
                for (int i = 0; i < SphereSphere.Count; i++)
                {
                    float distance = Vector3.SqrMagnitude(SphereSphere[i].m_OP.Position - m_hitPos);
                    if (distance < closestDistance)
                    {
                        closestDistance = distance;
                        index           = i;
                    }
                }
                b = SphereSphere[index].m_Building;
                return(true);
            }
        }
    /// <summary>
    /// Check to see if a collision has occured with any other rigid bodies
    /// </summary>
    /// <param name="body"></param>
    /// <returns></returns>
    public override MyCollision CheckCollision(MyRigidBody other)
    {
        // declare null MyCollision for return
        MyCollision collision = null;

        // check for collision with other spheres
        if(other is MySphereRigidBody && other.name != name)
        {
            // combined radius of both spheres
            float combinedRadius = this.radius + ((MySphereRigidBody)other).radius;

            // the vector between the centres of the spheres
            Vector3 direction = other.transform.position - transform.position;

            // distance between centres
            float centreDistance = direction.magnitude;

            // normalise the direction
            direction /= centreDistance;

            // check interection
            if(centreDistance < combinedRadius)
            {
                // create a new collision object, containing the vector of the normal and the distance from the sphere
                collision = new MyCollision(this, other, direction, centreDistance);
            }
        }
        else if(other is MyPlaneRigidBody) //check for collision with a plane
        {
            // get the mesh filter for the plane
            MeshFilter filter = other.gameObject.GetComponent<MeshFilter>();

            // make sure it has a mesh filter
            if (filter && filter.mesh.normals.Length > 0)
            {
                // get one of the vertext normals --- first one should do as the are all the same
                var normal = filter.transform.TransformDirection(filter.mesh.normals[0]);

                // distance of sphere centre from plane
                float distanceFromSphereCentre = Mathf.Abs(Vector3.Dot(normal, transform.position)) + (other as MyPlaneRigidBody).distance;

                // distance of sphere from plane
                float distanceFromSphere = distanceFromSphereCentre - radius;

                // check for intersection
                if (distanceFromSphere < 0)
                {
                    // create a new collision object, containing the vector of the normal and the distance from the plane
                    collision = new MyCollision(this, other, normal, distanceFromSphere);
                }
            }
        }

        // return the collision
        return collision;
    }
Exemple #7
0
    private IEnumerator MineStone()
    {
        List <int> moveGroupIndices = _direction.FrontMoveGroup();



        List <Direction> minePatternDirection;


        for (int i = 0; i < moveGroupIndices.Count; i++)
        {
            CollisionType obstacle = MyCollision.Check(Cubes[moveGroupIndices[i]], _direction, MyGameManager.MyGrid);
            if (obstacle == CollisionType.Stone)
            {
                int nextX = (int)_direction.DirectionToVector().x + (int)GridTools.GridPosition(Cubes[moveGroupIndices[i]].transform.position).x;
                int nextY = (int)_direction.DirectionToVector().y + (int)GridTools.GridPosition(Cubes[moveGroupIndices[i]].transform.position).y;

                if (i == 0)
                {
                    minePatternDirection = new List <Direction> {
                        _direction.TurnLeft(), _direction.TurnLeft().TurnRight(), _direction.TurnLeft().TurnRight().TurnLeft()
                    };
                }
                else
                {
                    minePatternDirection = new List <Direction> {
                        _direction.TurnRight(), _direction.TurnRight().TurnLeft(), _direction.TurnRight().TurnLeft().TurnRight()
                    };
                }

                _direction = minePatternDirection[0];
                yield return(StartCoroutine(MoveParts(_direction.FrontMoveGroup(), timeToMove)));

                _direction = minePatternDirection[1];
                yield return(StartCoroutine(MoveParts(_direction.FrontMoveGroup(), timeToMove)));

                yield return(StartCoroutine(MoveParts(_direction.Opposite().FrontMoveGroup(), timeToMove)));

                yield return(StartCoroutine(MoveParts(_direction.FrontMoveGroup(), timeToMove)));

                yield return(new WaitForSeconds(2f));


                Destroy(MyGameManager.StoneInstances[new Vector2(nextX, nextY)]);
                MyGameManager.MyGrid.Cells[nextX, nextY] = 0;

                yield return(StartCoroutine(MoveParts(_direction.Opposite().FrontMoveGroup(), timeToMove)));

                _direction = minePatternDirection[2];
                yield return(StartCoroutine(MoveParts(_direction.Opposite().FrontMoveGroup(), timeToMove)));
            }
        }

        yield return(null);
    }
    /// <summary>
    /// Deal with floating point errors in the positional calculations
    /// </summary>
    /// <param name="collision"></param>
    public void PositionalCorrection(MyCollision collision)
    {
        float percent = 0.2f; // usually 20% to 80%
        float slop = 0.01f; // usually 0.01 to 0.1

        if (collision.bodyA is MyBoxRigidBody || collision.bodyB is MyBoxRigidBody)
            percent = 0.01f;
        Vector3 correction = (Mathf.Max(Mathf.Abs(collision.penetration - slop), 0.0f) / (collision.bodyA.inverseMass + collision.bodyB.inverseMass)) * percent * collision.collisionNormal;
        collision.bodyA.transform.position += collision.bodyA.inverseMass * correction;
        collision.bodyB.transform.position -= collision.bodyB.inverseMass * correction;
    }
Exemple #9
0
    private static void ResolveInelastic(MyCollision collision)
    {
        var A = collision.colliderA;
        var B = collision.colliderB;

        var velocity = A.mass / (A.mass + B.mass) * A.velocity
                       + B.mass / (A.mass + B.mass) * B.velocity;

        A.velocity = velocity;
        B.velocity = velocity;
    }
        /// <summary>
        /// Checks whether the current BoundingFrustum intersects the specified Ray.
        /// </summary>
        /// <param name="ray">The Ray to check for intersection with.</param>
        /// <param name="inDistance">The distance at which the ray enters the frustum if there is an intersection and the ray starts outside the frustum.</param>
        /// <param name="outDistance">The distance at which the ray exits the frustum if there is an intersection.</param>
        /// <returns><c>true</c> if the current BoundingFrustum intersects the specified Ray.</returns>
        public bool Intersects(ref MyRay ray, out float?inDistance, out float?outDistance)
        {
            if (Contains(ray.Position) != MyContainmentType.Disjoint)
            {
                float nearstPlaneDistance = float.MaxValue;
                for (int i = 0; i < 6; i++)
                {
                    var   plane = GetPlane(i);
                    float distance;
                    if (MyCollision.RayIntersectsPlane(ref ray, ref plane, out distance) && distance < nearstPlaneDistance)
                    {
                        nearstPlaneDistance = distance;
                    }
                }

                inDistance  = nearstPlaneDistance;
                outDistance = null;
                return(true);
            }
            else
            {
                //We will find the two points at which the ray enters and exists the frustum
                //These two points make a line which center inside the frustum if the ray intersects it
                //Or outside the frustum if the ray intersects frustum planes outside it.
                float minDist = float.MaxValue;
                float maxDist = float.MinValue;
                for (int i = 0; i < 6; i++)
                {
                    var   plane = GetPlane(i);
                    float distance;
                    if (MyCollision.RayIntersectsPlane(ref ray, ref plane, out distance))
                    {
                        minDist = Math.Min(minDist, distance);
                        maxDist = Math.Max(maxDist, distance);
                    }
                }

                MyVector3 minPoint = ray.Position + ray.Direction * minDist;
                MyVector3 maxPoint = ray.Position + ray.Direction * maxDist;
                MyVector3 center   = (minPoint + maxPoint) / 2f;
                if (Contains(ref center) != MyContainmentType.Disjoint)
                {
                    inDistance  = minDist;
                    outDistance = maxDist;
                    return(true);
                }
                else
                {
                    inDistance  = null;
                    outDistance = null;
                    return(false);
                }
            }
        }
    /// <summary>
    /// deal with floating point errors in the positional calculations
    /// </summary>
    /// <param name="collision"></param>
    public void PositionalCorrection(MyCollision collision)
    {
        float percent = 0.2f; // usually 20% to 80%
        float slop = 0.01f; // usually 0.01 to 0.1

        if (collision.bodyA is MyBoxCollider || collision.bodyB is MyBoxCollider)
            percent = 0.01f;
        Vector3 correction = (Mathf.Max(Mathf.Abs(collision.penetration - slop), 0.0f) / (collision.bodyA.inverseMass + collision.bodyB.inverseMass)) * percent * collision.collisionNormal;
        collision.bodyA.transform.position += collision.bodyA.inverseMass * correction;
        //collision.bodyB.transform.position -= collision.bodyB.inverseMass * correction;
    }
Exemple #12
0
        /// <summary>
        /// Check für Collider with a OverlapSphere
        /// </summary>
        /// <returns>return true if another Cell from a diffrent Street ID collid</returns>
        public bool CheckForCollision()
        {
            List<Cell> cellToCheck = new List<Cell>();
            List<StreetSegment> segToCheck = new List<StreetSegment>();
            List<Cross> crossToCheck = new List<Cross>();

            //Sphere Sphere
            //Cell Cell
            foreach (Cell c in GridManager.m_AllCells)
                if (c.ID != this.ID && MyCollision.SphereSphere(this.m_PosCenter, this.m_Radius, c.m_PosCenter, c.m_Radius))
                    cellToCheck.Add(c);

            List<StreetComponent> allComponetns = StreetComponentManager.GetAllStreetComponents();
            //Cell Segment
            for (int i = 0; i < allComponetns.Count; i++)
            {
                StreetComponent comp = allComponetns[i];

                if (comp.ID == this.ID) continue;
                if (comp is Street)
                {
                    Street s = (Street)comp;
                    foreach (StreetSegment seg in s.m_Segments)
                        if (MyCollision.SphereSphere(this.m_PosCenter, this.m_Radius, seg.m_Center, seg.m_CollisionRadius))
                            segToCheck.Add(seg);
                }
                else if (comp is Cross)
                {
                    Cross c = (Cross)comp;
                    if (MyCollision.SphereSphere(this.m_PosCenter, this.m_Radius, c.m_center, 1.7f))
                        crossToCheck.Add(c);
                }
            }

            //Poly Poly
            //Cell Cross
            foreach (Cross c in crossToCheck)
                if (MyCollision.PolyPoly(this.m_Corner, c.m_corners))
                    return true;

            //Cell Segment
            foreach (StreetSegment seg in segToCheck)
                if (MyCollision.PolyPoly(this.m_Corner, seg.m_CornerPos))
                    return true;

            //Cell Cell
            foreach (Cell c in cellToCheck)
                if (MyCollision.PolyPoly(this.m_Corner, c.m_Corner))
                    return true;

            return false;
        }
        private MyPlaneIntersectionType PlaneIntersectsPoints(ref MyPlane plane, MyVector3[] points)
        {
            var result = MyCollision.PlaneIntersectsPoint(ref plane, ref points[0]);

            for (int i = 1; i < points.Length; i++)
            {
                if (MyCollision.PlaneIntersectsPoint(ref plane, ref points[i]) != result)
                {
                    return(MyPlaneIntersectionType.Intersecting);
                }
            }
            return(result);
        }
Exemple #14
0
    private void ResolveElastic(MyCollision collision)
    {
        var A = collision.colliderA;
        var B = collision.colliderB;

        var av = A.velocity - (2 * B.mass) / (A.mass + B.mass)
                 * Vector3.Project(A.velocity - B.velocity, A.transform.position - B.transform.position);

        var bv = B.velocity - (2 * A.mass) / (A.mass + B.mass)
                 * Vector3.Project(B.velocity - A.velocity, B.transform.position - A.transform.position);

        A.velocity = av;
        B.velocity = bv;
    }
Exemple #15
0
 public override void MyOnCollisionEnter(MyCollision c)
 {
     // Adjust the velocity of the cannon ball
     if (c.gameObject.GetComponent <CannonBall>())
     {
         if (gameObject.GetComponent <Renderer>().material.color.a > 0)
         {
             CannonBall cb = c.gameObject.GetComponent <CannonBall>();
             cb.vx -= vx * 30;
             cb.vy += vy * 30;
             cb.GhostDestroy();
         }
     }
 }
    /// <summary>
    /// Checks for collisions with other bodies
    /// </summary>
    /// <param name="other"></param>
    /// <returns></returns>
    public MyCollision CheckCollision(MyRigidBody other)
    {
        // no collision by default
        MyCollision collision = null;

        // only check for collisions on bodies that we are interested in
        switch (this.RigidBodyType)
        {
            case global::RigidBodyType.SOLID_SPHERE:
            case global::RigidBodyType.HOLLOW_SPHERE:
            case global::RigidBodyType.SOLID_BOX:
                collision = Collided(this, other);
                break;
            default:
                break;
        }
        return collision;
    }
Exemple #17
0
        /// <summary>
        /// Determines whether there is an intersection between a <see cref="MyRay"/> and a <see cref="MyOrientedBoundingBox"/>.
        /// </summary>
        /// <param name="ray">The ray to test.</param>
        /// <param name="point">When the method completes, contains the point of intersection,
        /// or <see cref="MyVector3.Zero"/> if there was no intersection.</param>
        /// <returns>Whether the two objects intersected.</returns>
        public bool Intersects(ref MyRay ray, out MyVector3 point)
        {
            // Put ray in box space
            MyMatrix invTrans;
            MyMatrix.Invert(ref Transformation, out invTrans);

            MyRay bRay;
            MyVector3.TransformNormal(ref ray.Direction, ref invTrans, out bRay.Direction);
            MyVector3.TransformCoordinate(ref ray.Position, ref invTrans, out bRay.Position);

            //Perform a regular ray to BoundingBox check
            var bb = new MyBoundingBox(-Extents, Extents);
            var intersects = MyCollision.RayIntersectsBox(ref bRay, ref bb, out point);

            //Put the result intersection back to world
            if (intersects)
                MyVector3.TransformCoordinate(ref point, ref Transformation, out point);

            return intersects;
        }
    private MyCollision Collided(MyRigidBody object1, MyRigidBody object2)
    {
        MyCollision collision = null;
        switch(object2.RigidBodyType)
        {
            case global::RigidBodyType.PLANE:
                collision =  CollidedWithPlane(object1, object2 as MyPlaneCollider);
                break;
            case global::RigidBodyType.SOLID_SPHERE:
            case global::RigidBodyType.HOLLOW_SPHERE:
                collision = CollidedWithSphere(object1, object2 as MySphereCollider);
                break;
            case global::RigidBodyType.SOLID_BOX:
                collision = CollidedWithBox(object1, object2 as MyBoxCollider);
                break;
            default:
                break;

        }
        return collision;
    }
Exemple #19
0
        public void CheckGridCollision()
        {
            m_center     = new Vector2(transform.position.x, transform.position.z);
            m_corners[0] = m_center + new Vector2(1.2f, 1.2f);
            m_corners[1] = m_center + new Vector2(-1.2f, 1.2f);
            m_corners[2] = m_center + new Vector2(-1.2f, -1.2f);
            m_corners[3] = m_center + new Vector2(1.2f, -1.2f);

            HashSet <int> StreetsToRecreate = new HashSet <int>();
            List <Cell>   PolyPolyCheckList = new List <Cell>();
            List <Cell>   CellsToCheck      = GridManager.m_AllCells;

            //Sphere Sphere Coll
            for (int i = 0; i < CellsToCheck.Count; i++)
            {
                if (MyCollision.SphereSphere(m_center, 1.7f, CellsToCheck[i].m_PosCenter, CellsToCheck[i].m_Radius))
                {
                    PolyPolyCheckList.Add(CellsToCheck[i]);
                }
            }

            //Poly Poly Coll
            for (int i = 0; i < PolyPolyCheckList.Count; i++)
            {
                if (MyCollision.PolyPoly(PolyPolyCheckList[i].m_Corner, m_corners))
                {
                    PolyPolyCheckList[i].Delete();
                    int id = PolyPolyCheckList[i].m_Street.ID;
                    StreetsToRecreate.Add(id);
                }
            }

            //Recreate Grid
            foreach (int i in StreetsToRecreate)
            {
                Street s = StreetComponentManager.GetStreetByID(i);
                GridManager.RemoveGridMesh(s);
                MeshGenerator.CreateGridMesh(s, s.m_GridObj.GetComponent <MeshFilter>(), s.m_GridRenderer);
            }
        }
        /// <summary>
        /// Determines the intersection relationship between the frustum and a bounding box.
        /// </summary>
        /// <param name="box">The box.</param>
        /// <returns>Type of the containment</returns>
        public MyContainmentType Contains(ref MyBoundingBox box)
        {
            MyVector3 p, n;
            MyPlane   plane;
            var       result = MyContainmentType.Contains;

            for (int i = 0; i < 6; i++)
            {
                plane = GetPlane(i);
                GetBoxToPlanePVertexNVertex(ref box, ref plane.Normal, out p, out n);
                if (MyCollision.PlaneIntersectsPoint(ref plane, ref p) == MyPlaneIntersectionType.Back)
                {
                    return(MyContainmentType.Disjoint);
                }

                if (MyCollision.PlaneIntersectsPoint(ref plane, ref n) == MyPlaneIntersectionType.Back)
                {
                    result = MyContainmentType.Intersects;
                }
            }
            return(result);
        }
Exemple #21
0
    public override void MyOnCollisionEnter(MyCollision c)
    {
        if (c.gameObject.GetComponent <Ground>())
        {
            Debug.Log("I hit the ground");
            DestroySelf();
        }

        if (c.gameObject.GetComponent <Stonehenge>())
        {
            Stonehenge stonehenge = c.gameObject.GetComponent <Stonehenge>();
            if (transform.position.y > c.gameObject.transform.position.y + 0.2f)           // Top collision
            {
                Debug.Log("Top collision");
                vy          = Mathf.Abs(vy - (gravity * elapsedTime)) * restitution;
                elapsedTime = 0;
            }
            else             // Side collision
            {
                vx = -vx * restitution;
            }
        }
    }
        /// <summary>
        /// Get the distance which when added to camera position along the lookat direction will do the effect of zoom to extents (zoom to fit) operation,
        /// so all the passed points will fit in the current view.
        /// if the returned value is positive, the camera will move toward the lookat direction (ZoomIn).
        /// if the returned value is negative, the camera will move in the reverse direction of the lookat direction (ZoomOut).
        /// </summary>
        /// <param name="points">The points.</param>
        /// <returns>The zoom to fit distance</returns>
        public float GetZoomToExtentsShiftDistance(MyVector3[] points)
        {
            float vAngle = (float)((Math.PI / 2.0 - Math.Acos(MyVector3.Dot(pNear.Normal, pTop.Normal))));
            float vSin   = (float)Math.Sin(vAngle);
            float hAngle = (float)((Math.PI / 2.0 - Math.Acos(MyVector3.Dot(pNear.Normal, pLeft.Normal))));
            float hSin   = (float)Math.Sin(hAngle);
            float horizontalToVerticalMapping = vSin / hSin;

            var ioFrustrum = GetInsideOutClone();

            float maxPointDist = float.MinValue;

            for (int i = 0; i < points.Length; i++)
            {
                float pointDist = MyCollision.DistancePlanePoint(ref ioFrustrum.pTop, ref points[i]);
                pointDist = Math.Max(pointDist, MyCollision.DistancePlanePoint(ref ioFrustrum.pBottom, ref points[i]));
                pointDist = Math.Max(pointDist, MyCollision.DistancePlanePoint(ref ioFrustrum.pLeft, ref points[i]) * horizontalToVerticalMapping);
                pointDist = Math.Max(pointDist, MyCollision.DistancePlanePoint(ref ioFrustrum.pRight, ref points[i]) * horizontalToVerticalMapping);

                maxPointDist = Math.Max(maxPointDist, pointDist);
            }
            return(-maxPointDist / vSin);
        }
Exemple #23
0
 /// <summary>
 /// Determines if there is an intersection between the current object and a triangle.
 /// </summary>
 /// <param name="vertex1">The first vertex of the triangle to test.</param>
 /// <param name="vertex2">The second vertex of the triangle to test.</param>
 /// <param name="vertex3">The third vertex of the triangle to test.</param>
 /// <returns>Whether the two objects intersected.</returns>
 public bool Intersects(ref MyVector3 vertex1, ref MyVector3 vertex2, ref MyVector3 vertex3)
 {
     return(MyCollision.SphereIntersectsTriangle(ref this, ref vertex1, ref vertex2, ref vertex3));
 }
Exemple #24
0
        /// <summary>
        /// Determines if there is an intersection between the current object and a <see cref="MyRay"/>.
        /// </summary>
        /// <param name="ray">The ray to test.</param>
        /// <returns>Whether the two objects intersected.</returns>
        public bool Intersects(ref MyRay ray)
        {
            float distance;

            return(MyCollision.RayIntersectsSphere(ref ray, ref this, out distance));
        }
Exemple #25
0
 /// <summary>
 /// Determines whether the current objects contains a <see cref="MyBoundingSphere"/>.
 /// </summary>
 /// <param name="sphere">The sphere to test.</param>
 /// <returns>The type of containment the two objects have.</returns>
 public MyContainmentType Contains(ref MyBoundingSphere sphere)
 {
     return(MyCollision.SphereContainsSphere(ref this, ref sphere));
 }
Exemple #26
0
 /// <summary>
 /// Determines whether the current objects contains a <see cref="MyBoundingBox"/>.
 /// </summary>
 /// <param name="box">The box to test.</param>
 /// <returns>The type of containment the two objects have.</returns>
 public MyContainmentType Contains(ref MyBoundingBox box)
 {
     return(MyCollision.SphereContainsBox(ref this, ref box));
 }
Exemple #27
0
 /// <summary>
 /// Determines whether the current objects contains a triangle.
 /// </summary>
 /// <param name="vertex1">The first vertex of the triangle to test.</param>
 /// <param name="vertex2">The second vertex of the triangle to test.</param>
 /// <param name="vertex3">The third vertex of the triangle to test.</param>
 /// <returns>The type of containment the two objects have.</returns>
 public MyContainmentType Contains(ref MyVector3 vertex1, ref MyVector3 vertex2, ref MyVector3 vertex3)
 {
     return(MyCollision.SphereContainsTriangle(ref this, ref vertex1, ref vertex2, ref vertex3));
 }
Exemple #28
0
 /// <summary>
 /// Determines whether the current objects contains a point.
 /// </summary>
 /// <param name="point">The point to test.</param>
 /// <returns>The type of containment the two objects have.</returns>
 public MyContainmentType Contains(ref MyVector3 point)
 {
     return(MyCollision.SphereContainsPoint(ref this, ref point));
 }
Exemple #29
0
 /// <summary>
 /// Determines if there is an intersection between the current object and a <see cref="MyBoundingSphere"/>.
 /// </summary>
 /// <param name="sphere">The sphere to test.</param>
 /// <returns>Whether the two objects intersected.</returns>
 public bool Intersects(ref MyBoundingSphere sphere)
 {
     return(MyCollision.SphereIntersectsSphere(ref this, ref sphere));
 }
Exemple #30
0
 /// <summary>
 /// Determines if there is an intersection between the current object and a <see cref="MyBoundingBox"/>.
 /// </summary>
 /// <param name="box">The box to test.</param>
 /// <returns>Whether the two objects intersected.</returns>
 public bool Intersects(ref MyBoundingBox box)
 {
     return(MyCollision.BoxIntersectsSphere(ref box, ref this));
 }
    /// <summary>
    /// Resolves a collision between this and another rigid body
    /// </summary>
    /// <param name="body"></param>
    public void ResolveCollision(MyCollision collision)
    {
        if ((collision.bodyA is MyPlaneRigidBody && (collision.bodyB is MySphereRigidBody || collision.bodyB is MyBoxRigidBody)) || ((collision.bodyA is MySphereRigidBody || collision.bodyA is MyBoxRigidBody) && collision.bodyB is MyPlaneRigidBody))
        {
            // Calculate relative velocity
            Vector3 relativeVelocity = collision.bodyA.velocity - collision.bodyB.velocity;

            // Calculate relative velocity in terms of the normal direction
            float velocityAlongNormal = Vector3.Dot(relativeVelocity, collision.collisionNormal);

            // Do not resolve if velocities are separating
            if (velocityAlongNormal > 0)
                return;

            // Calculate restitution
            float e = Mathf.Min(collision.bodyA.restitution, collision.bodyB.restitution);

            // Calculate impulse scalar
            float j = -(1 + e) * velocityAlongNormal;
            j /= collision.bodyA.inverseMass + collision.bodyB.inverseMass;

            // Apply impulse
            Vector3 impulse = j * collision.collisionNormal;
            collision.bodyA.velocity += collision.bodyA.inverseMass * impulse;
            collision.bodyB.velocity -= collision.bodyB.inverseMass * impulse;

            // recalcuate the relative velocity
            relativeVelocity = collision.bodyA.velocity - collision.bodyB.velocity;

            // get the tangent vector
            Vector3 tangent = Vector3.Dot(relativeVelocity, collision.collisionNormal) * collision.collisionNormal;
            tangent.Normalize();

            // get the magnitude of the force along the friction vactor
            float jt = -Vector3.Dot(relativeVelocity, tangent);
            jt /= collision.bodyA.inverseMass + collision.bodyB.inverseMass;

            // get average coefficioent of friciotn in collision
            float mu = (collision.bodyA.staticFriction + collision.bodyB.staticFriction) / 2;

            // Clamp magnitude of friction and create impulse vector
            Vector3 frictionImpulse;
            if(Mathf.Abs( jt ) < j * mu)
                frictionImpulse = jt * tangent;
            else
            {
                dynamicFriction = (collision.bodyA.dynamicFriction + collision.bodyB.dynamicFriction) / 2;
                frictionImpulse = -j * tangent * dynamicFriction;;
            }

            // Apply
            collision.bodyA.velocity += collision.bodyA.inverseMass * frictionImpulse;
            collision.bodyB.velocity -= collision.bodyB.inverseMass * frictionImpulse;

            // correct the position
            PositionalCorrection(collision);
        }

        if (collision.bodyA is MySphereRigidBody && collision.bodyB is MySphereRigidBody)
        {
            // Calculate relative velocity
            Vector3 relativeVelocity = collision.bodyB.velocity - collision.bodyA.velocity;

            // Calculate relative velocity in terms of the normal direction
            float velocityAlongNormal = Vector3.Dot(relativeVelocity, collision.collisionNormal);

            // Do not resolve if velocities are separating
            if (velocityAlongNormal > 0)
                return;

            // Calculate restitution
            float e = Mathf.Min(collision.bodyA.restitution, collision.bodyB.restitution);

            // Calculate impulse scalar
            float j = -(1 + e) * velocityAlongNormal;
            j /= collision.bodyA.inverseMass + collision.bodyB.inverseMass;

            // Apply impulse
            Vector3 impulse = j * collision.collisionNormal;
            collision.bodyA.velocity -= collision.bodyA.inverseMass * impulse;
            collision.bodyB.velocity += collision.bodyB.inverseMass * impulse;

            // recalcuate the relative velocity
            relativeVelocity = collision.bodyA.velocity - collision.bodyB.velocity;

            // get the tangent vector
            Vector3 tangent = Vector3.Dot(relativeVelocity, collision.collisionNormal) * collision.collisionNormal;
            tangent.Normalize();

            // get the magnitude of the force along the friction vactor
            float jt = -Vector3.Dot(relativeVelocity, tangent);
            jt /= collision.bodyA.inverseMass + collision.bodyB.inverseMass;

            // get average coefficioent of friciotn in collision
            float mu = (collision.bodyA.staticFriction + collision.bodyB.staticFriction) / 2;

            // Clamp magnitude of friction and create impulse vector
            Vector3 frictionImpulse;
            if (Mathf.Abs(jt) < j * mu)
                frictionImpulse = jt * tangent;
            else
            {
                dynamicFriction = (collision.bodyA.dynamicFriction + collision.bodyB.dynamicFriction) / 2;
                frictionImpulse = -j * tangent * dynamicFriction; ;
            }

            // Apply
            collision.bodyA.velocity -= collision.bodyA.inverseMass * frictionImpulse;
            collision.bodyB.velocity += collision.bodyB.inverseMass * frictionImpulse;
        }
    }
Exemple #32
0
 /// <summary>
 /// Determines if there is an intersection between the current object and a <see cref="MyPlane"/>.
 /// </summary>
 /// <param name="plane">The plane to test.</param>
 /// <returns>Whether the two objects intersected.</returns>
 public MyPlaneIntersectionType Intersects(ref MyPlane plane)
 {
     return(MyCollision.PlaneIntersectsSphere(ref plane, ref this));
 }
Exemple #33
0
 /// <summary>
 /// Determines if there is an intersection between the current object and a <see cref="MyRay"/>.
 /// </summary>
 /// <param name="ray">The ray to test.</param>
 /// <param name="point">When the method completes, contains the point of intersection,
 /// or <see cref="MyVector3.Zero"/> if there was no intersection.</param>
 /// <returns>Whether the two objects intersected.</returns>
 public bool Intersects(ref MyRay ray, out MyVector3 point)
 {
     return(MyCollision.RayIntersectsSphere(ref ray, ref this, out point));
 }