private void btnReset_Click(object sender, EventArgs e)
 {
     _sphere = new Sphere(GetMiddlePoint(), new DoubleVector(0, 1, 0, -1, 0, 0), 200);
     _prevRadians = 0;
     _currentRadians = 0;
     trackBar1.Value = 0;
 }
Example #2
0
        /// <summary>
        /// This will return a transform for a model or camera so that the model/camera will be placed and oriented just like
        /// the physical sphere.  Just set my return to model.Transform
        /// </summary>
        /// <param name="modelSphere">The tranform will be applied to the model that is described by this modelSphere</param>
        /// <param name="physicalSphere">This is where the model should be transformed to (the physical location)</param>
        public static Transform3D GetTransfromForSlaving(Sphere modelSphere, Sphere physicalSphere)
        {
            Transform3DGroup retVal = new Transform3DGroup();

            // Rotate
            MyQuaternion rotation = modelSphere.DirectionFacing.GetAngleAroundAxis(physicalSphere.DirectionFacing);
            retVal.Children.Add(new RotateTransform3D(new QuaternionRotation3D(new Quaternion(rotation.X, rotation.Y, rotation.Z, rotation.W))));

            //// Translate
            //MyVector offset = physicalSphere.Position - modelSphere.Position;
            //retVal.Children.Add(new TranslateTransform3D(offset.X, offset.Y, offset.Z));

            // Exit Function
            return retVal;
        }
Example #3
0
        /// <summary>
        /// The only reason you would pass in your own guid is when loading a previously saved scene (the token
        /// works good for processing in ram, but when stuff needs to go to file, use the guid)
        /// </summary>
        public RadarBlip(Sphere sphere, CollisionStyle collisionStyle, RadarBlipQual blipQual, long token, Guid objectID)
        {
            _sphere = sphere;

            _collisionStyle = collisionStyle;

            _token = token;

            _qual = blipQual;
            _qualInt = _qual.GetHashCode();

            _objectID = objectID;
        }
Example #4
0
 /// <summary>
 /// This is the basic constructor.  These are the only things that need to be passed in.
 /// </summary>
 public RadarBlip(Sphere sphere, CollisionStyle collisionStyle, RadarBlipQual blipQual, long token)
     : this(sphere, collisionStyle, blipQual, token, Guid.NewGuid())
 {
 }
        public static MyVector IsIntersecting_SphereTriangle(Sphere sphere, Triangle triangle)
        {
            // Find the point on the triangle closest to the sphere's center
            MyVector retVal = triangle.GetClosestPointOnTriangle(sphere.Position);

            // Sphere and triangle intersect if the (squared) distance from sphere
            // center to point is less than the (squared) sphere radius
            MyVector v = retVal - sphere.Position;
            if (MyVector.Dot(v, v) <= sphere.Radius * sphere.Radius)
            {
                return retVal;
            }
            else
            {
                return null;
            }
        }
        /// <summary>
        /// This static method just returns the point of intersection (or null).
        /// </summary>
        public static MyVector IsIntersecting_SphereSphere(Sphere sphere1, Sphere sphere2)
        {
            MyVector lineBetween = sphere2.Position - sphere1.Position;

            double distanceSquared = lineBetween.GetMagnitudeSquared();
            double sumRadii = sphere1.Radius + sphere2.Radius;

            // See if they missed each other
            if (distanceSquared > sumRadii * sumRadii)
            {
                return null;
            }

            // Figure out the percent of penetration
            double distance = Math.Sqrt(distanceSquared);
            double percentPenetrating = (sumRadii - distance) / sumRadii;

            // Turn lineBetween into a vector the length of ball1's radius
            lineBetween.BecomeUnitVector();
            lineBetween.Multiply(sphere1.Radius);
            lineBetween.Multiply(1 - percentPenetrating);		// shorten the line by the amount penetrating

            // Exit Function
            return sphere1.Position + lineBetween;
        }
        /// <summary>
        /// This overload simply returns a boolean (less expensive)
        /// </summary>
        public static bool IsIntersecting_SphereSphere_Bool(Sphere sphere1, Sphere sphere2)
        {
            MyVector lineBetween = sphere2.Position - sphere1.Position;

            double sumRadii = sphere1.Radius + sphere2.Radius;

            return lineBetween.GetMagnitudeSquared() <= sumRadii * sumRadii;
        }
            /// <summary>
            /// This overload compares the sphere and polygon (no up front sphere/sphere check)
            /// </summary>
            public static MyVector[] IsIntersecting_SpherePolygon(Sphere sphere, MyVector polygonCenterPoint, IMyPolygon polygon)
            {
                List<MyVector> retVal = new List<MyVector>();

                // See if I need to recurse on the polygon's children
                if (polygon.HasChildren)
                {
                    #region Test Child Polys

                    MyVector[] curCollisions;

                    // Call myself for each of the child polys
                    foreach (IMyPolygon childPoly in polygon.ChildPolygons)
                    {
                        curCollisions = IsIntersecting_SpherePolygon(sphere, polygonCenterPoint, childPoly);

                        if (curCollisions != null)
                        {
                            retVal.AddRange(curCollisions);
                        }
                    }

                    if (retVal.Count > 0)
                    {
                        return retVal.ToArray();
                    }
                    else
                    {
                        return null;
                    }

                    #endregion
                }

                #region Test Edges

                // Compare the sphere with the edges
                MyVector curCollision;
                foreach (Triangle triangle in polygon.Triangles)
                {
                    curCollision = CollisionHandler.IsIntersecting_SphereTriangle(sphere, polygonCenterPoint + triangle);

                    if (curCollision != null)
                    {
                        retVal.Add(curCollision);
                    }
                }

                if (retVal.Count > 0)
                {
                    return retVal.ToArray();
                }

                #endregion



                //TODO:  collide the sphere with the interior of the poly



                // Exit Function
                return null;
            }
            /// <summary>
            /// This overload will do a sphere/sphere check first, and if those intersect, then it will do the more
            /// expensive sphere/poly check
            /// </summary>
            /// <param name="polygonSphere">A sphere that totally surrounds the polygon</param>
            public static MyVector[] IsIntersecting_SpherePolygon(Sphere sphere, MyVector polygonCenterPoint, IMyPolygon polygon, Sphere polygonSphere)
            {
                // Do a sphere/sphere check first
                if (!CollisionHandler.IsIntersecting_SphereSphere_Bool(sphere, polygonSphere))
                {
                    return null;
                }

                // The spheres intersect.  Now do the sphere/poly check
                return IsIntersecting_SpherePolygon(sphere, polygonCenterPoint, polygon);
            }
            /*


			// It looks like his definition of a polygon is simply a list of vectors.  It doesn't appear to be made of triangles,
			// but arbitrary sided faces.
			//
			// Actually, the more I think about it, I think is definition of a poly is strictly 2D.  This should be replaced with
			// triangle
			//typedef std::vector<Vector3> poly_t;



			// This function should probably be moved to triangle (assuming it's not the same as GetClosestPointOnTriangle())
			private bool PointInPoly(MyVector p, poly_t v, Vector n)
			{
				for (int i = 0; i < v.size(); i++)
				{
					if (Vector.Dot(p - v[i], Vector.Cross(n, v[(i + 1) % v.size()] - v[i]), false) < 0d)
					{
						return false;
					}
				}

				return true;
			}

			private Vector ClosestPointOnPlane(Vector p, Vector n, float d)
			{
				return p - (n * (Vector.Dot(p, n, false) - d));
			}

			private Vector ClosestPointOnSegment(Vector p, Vector p1, Vector p2)
			{
				Vector dir = p2 - p1;
				Vector diff = p - p1;

				double t = Vector.Dot(diff, dir, false) / Vector.Dot(dir, dir, false);
				if (t <= 0.0f)
				{
					return p1;
				}
				else if (t >= 1.0f)
				{
					return p2;
				}

				return p1 + t * dir;
			}

Vector3 ClosestPointOnPoly(const Vector3& p, const poly_t& v)
{
    // Poly plane
    Vector3 n = Vector3::Normalize(Vector3::Cross(v[1] - v[0], v[2] - v[0]));
    float d = v[0].Dot(n);
	
    // Closest point on plane to p
    Vector3 closest = ClosestPointOnPlane(p, n, d);
	
    // If p is in the poly, we've found our closest point
    if (PointInPoly(closest, v, n))
        return closest;
		
    // Else find the closest point to a poly edge
    bool found = false;
    float minDist;
    for (int i = 0; i < v.size(); ++i)
    {
        Vector3 temp = ClosestPointOnSegment(p, v[i], v[(i + 1) % v.size()]);
        float dist = Vector3::LengthSquared(p - temp);
        if (!found || dist < minDist)
        {
            found = true;
            minDist = dist;
            closest = temp;
        }
    }
    return closest;
}

bool IntersectSpherePoly(const Vector3& c, float r, const poly_t& poly, Vector3& n, float& d)
{
    Vector3 p = ClosestPointOnPoly(c, poly);
    n = c - p;
    float dist = n.LengthSquared();
    if (dist > r * r)
        return false;
		
    dist = Math::Sqrt(dist);
    n /= dist;
    d = r - dist;
    return true;
}







*/

            #endregion


            public static MyVector[] TestCollision(out MyVector trueCollision, Sphere sphere, MyVector polygonCenterPoint, IMyPolygon polygon, Sphere polygonSphere)
            {
                MyVector[] retVal = IsIntersecting_SpherePolygon(sphere, polygonCenterPoint, polygon, polygonSphere);

                if (retVal == null)
                {
                    trueCollision = null;
                    return null;
                }

                // Find the closest point
                double minDist = double.MaxValue;
                int minDistIndex = -1;

                for (int returnCntr = 0; returnCntr < retVal.Length; returnCntr++)
                {
                    double curDist = Utility3D.GetDistance3D(sphere.Position, retVal[returnCntr]);
                    if (curDist < minDist)
                    {
                        minDist = curDist;
                        minDistIndex = returnCntr;
                    }
                }

                trueCollision = retVal[minDistIndex];
                return retVal;
            }