Example #1
0
 /// <summary>
 /// Exact compare, no epsilon.
 /// </summary>
 /// <param name="sphere"></param>
 /// <returns></returns>
 public bool Equals(idSphere sphere)
 {
     return((_origin == sphere.Origin) && (_radius == sphere.Radius));
 }
Example #2
0
 /// <summary>
 /// Compare with epsilon.
 /// </summary>
 /// <param name="sphere"></param>
 /// <param name="epsilon"></param>
 /// <returns></returns>
 public bool Equals(idSphere sphere, float epsilon)
 {
     return((_origin.Compare(sphere.Origin, epsilon) == true) && (idMath.Abs(_radius - sphere.Radius) <= epsilon));
 }
Example #3
0
		/// <summary>
		/// Exact compare, no epsilon.
		/// </summary>
		/// <param name="sphere"></param>
		/// <returns></returns>
		public bool Equals(idSphere sphere)
		{
			return ((_origin == sphere.Origin) && (_radius == sphere.Radius));
		}
Example #4
0
		/// <summary>
		/// Compare with epsilon.
		/// </summary>
		/// <param name="sphere"></param>
		/// <param name="epsilon"></param>
		/// <returns></returns>
		public bool Equals(idSphere sphere, float epsilon)
		{
			return ((_origin.Compare(sphere.Origin, epsilon) == true) && (idMath.Abs(_radius - sphere.Radius) <= epsilon));
		}
Example #5
0
		/// <remarks>
		/// Used for both light volumes and model volumes.
		/// <para/>
		/// This does not clip the points by the planes, so some slop occurs.
		/// <para/>
		/// tr.viewCount should be bumped before calling, allowing it
		/// to prevent double checking areas.
		/// <para/>
		/// We might alternatively choose to do this with an area flow.
		/// </remarks>
		/// <param name="def"></param>
		/// <param name="?"></param>
		/// <param name="sphere"></param>
		/// <param name="pointCount"></param>
		/// <param name="points"></param>
		private void PushVolumeIntoTree_r(idRenderEntity def, /* idRenderLight */ object light, idSphere sphere, int pointCount, Vector3[] points, int nodeNumber)
		{
			if(nodeNumber < 0)
			{
				int areaNumber = -1 - nodeNumber;
				PortalArea area = _portalAreas[areaNumber];

				if(area.ViewCount == idE.RenderSystem.ViewCount)
				{
					return;	// already added a reference here
				}

				area.ViewCount = idE.RenderSystem.ViewCount;

				if(def != null)
				{
					AddEntityRefToArea(def, area);
				}

				if(light != null)
				{
					idConsole.Warning("TODO: AddLightRefToArea( light, area );");
				}

				return;
			}

			AreaNode node = _areaNodes[nodeNumber];

			// if we know that all possible children nodes only touch an area
			// we have already marked, we can early out
			if((idE.CvarSystem.GetBool("r_useNodeCommonChildren") == true) && (node.CommonChildrenArea != idRenderWorld.ChildrenHaveMultipleAreas))
			{
				// note that we do NOT try to set a reference in this area
				// yet, because the test volume may yet wind up being in the
				// solid part, which would cause bounds slightly poked into
				// a wall to show up in the next room
				if(_portalAreas[node.CommonChildrenArea].ViewCount == idE.RenderSystem.ViewCount)
				{
					return;
				}
			}

			// if the bounding sphere is completely on one side, don't
			// bother checking the individual points
			float distance = node.Plane.Distance(sphere.Origin);

			if(distance >= sphere.Radius)
			{
				nodeNumber = node.Children[0];

				if(nodeNumber != 0) // 0 = solid
				{
					PushVolumeIntoTree_r(def, light, sphere, pointCount, points, nodeNumber);
				}

				return;
			}

			if(distance <= -sphere.Radius)
			{
				nodeNumber = node.Children[1];

				if(nodeNumber != 0) // 0 = solid
				{
					PushVolumeIntoTree_r(def, light, sphere, pointCount, points, nodeNumber);
				}

				return;
			}

			// exact check all the points against the node plane
			bool front = false;
			bool back = false;

			for(int i = 0; i < pointCount; i++)
			{
				float d = ((points[i] * node.Plane.Normal) + new Vector3(node.Plane.Normal.Z, node.Plane.Normal.Z, node.Plane.Normal.Z)).Length();

				if(d >= 0.0f)
				{
					front = true;
				}
				else if(d <= 0.0f)
				{
					back = true;
				}

				if((back == true) && (front == true))
				{
					break;
				}
			}

			if(front == true)
			{
				nodeNumber = node.Children[0];

				if(nodeNumber != 0) // 0 = solid
				{
					PushVolumeIntoTree_r(def, light, sphere, pointCount, points, nodeNumber);
				}
			}

			if(back == true)
			{
				nodeNumber = node.Children[1];

				if(nodeNumber != 0) // 0 = solid
				{
					PushVolumeIntoTree_r(def, light, sphere, pointCount, points, nodeNumber);
				}
			}
		}
Example #6
0
		private void PushVolumeIntoTree(idRenderEntity def, /* idRenderLight */ object light, int pointCount, Vector3[] points)
		{
			if(_areaNodes == null)
			{
				return;
			}

			// calculate a bounding sphere for the points
			Vector3 mid = Vector3.Zero;
			Vector3 dir;
			float radSquared = 0;
			float lr = 0;

			for(int i = 0; i < pointCount; i++)
			{
				mid += points[i];
			}

			mid *= (1.0f / pointCount);

			for(int i = 0; i < pointCount; i++)
			{
				dir = points[i] - mid;
				lr = (dir * dir).Length();

				if(lr > radSquared)
				{
					radSquared = lr;
				}
			}

			idSphere sphere = new idSphere(mid, idMath.Sqrt(radSquared));

			PushVolumeIntoTree_r(def, light, sphere, pointCount, points, 0);
		}