public override void Update(GameTime gameTime) { // If an item in a spatial partition changes (e.g. if it moves or if the AABB changes) you // have to call //_spatialPartition.Invalidate(changedGeometryobject); // If many or all items have changed you can call //_spatialPartition.Invalidate(); // After an item was invalidated, the spatial partition needs to be rebuilt. This happens // automatically when needed or when you call //_spatialPartition.Update(forceRebuild: false); // Get a ray which shoots forward. var cameraPose = GraphicsScreen.CameraNode.PoseWorld; var ray = new Ray { Origin = cameraPose.Position, Direction = cameraPose.ToWorldDirection(Vector3F.Forward), Length = 100, }; // Draw objects. var debugRenderer = GraphicsScreen.DebugRenderer; debugRenderer.Clear(); foreach (var geometricObject in _spatialPartition) debugRenderer.DrawObject(geometricObject, Color.LightGreen, false, false); GeometricObject closestHitGeometricObject = null; Triangle closestHitTriangle = new Triangle(); float closestHitDistance = float.PositiveInfinity; // Use the spatial partition to get all objects where the AABB overlaps the ray. foreach (var geometricObject in _spatialPartition.GetOverlaps(ray)) { var triangleMeshShape = (TriangleMeshShape)geometricObject.Shape; // Transform the ray into the local space of the triangle mesh. var localRay = new Ray { Origin = geometricObject.Pose.ToLocalPosition(ray.Origin), Direction = geometricObject.Pose.ToLocalDirection(ray.Direction), Length = ray.Length, }; // Use the spatial partition of the mesh shape to compute all triangles where the // AABB overlaps the ray. foreach (var triangleIndex in triangleMeshShape.Partition.GetOverlaps(localRay)) { var triangle = triangleMeshShape.Mesh.GetTriangle(triangleIndex); // Check if ray intersects the triangle and remember the closest hit. float hitDistance; if (GeometryHelper.GetContact(localRay, triangle, false, out hitDistance) && hitDistance < closestHitDistance) { closestHitGeometricObject = geometricObject; closestHitTriangle = triangle; closestHitDistance = hitDistance; } } } // Draw hit triangle. if (closestHitGeometricObject != null) debugRenderer.DrawTriangle(closestHitTriangle, closestHitGeometricObject.Pose, Vector3F.One, Color.Red, true, true); }
public override void Update(GameTime gameTime) { // If an item in a spatial partition changes (e.g. if it moves or if the AABB changes) you // have to call //_spatialPartition.Invalidate(changedGeometryobject); // If many or all items have changed you can call //_spatialPartition.Invalidate(); // After an item was invalidated, the spatial partition needs to be rebuilt. This happens // automatically when needed or when you call //_spatialPartition.Update(forceRebuild: false); // Get a ray which shoots forward. var cameraPose = GraphicsScreen.CameraNode.PoseWorld; var ray = new Ray { Origin = cameraPose.Position, Direction = cameraPose.ToWorldDirection(Vector3F.Forward), Length = 100, }; // Draw objects. var debugRenderer = GraphicsScreen.DebugRenderer; debugRenderer.Clear(); foreach (var geometricObject in _spatialPartition) { debugRenderer.DrawObject(geometricObject, Color.LightGreen, false, false); } GeometricObject closestHitGeometricObject = null; Triangle closestHitTriangle = new Triangle(); float closestHitDistance = float.PositiveInfinity; // Use the spatial partition to get all objects where the AABB overlaps the ray. foreach (var geometricObject in _spatialPartition.GetOverlaps(ray)) { var triangleMeshShape = (TriangleMeshShape)geometricObject.Shape; // Transform the ray into the local space of the triangle mesh. var localRay = new Ray { Origin = geometricObject.Pose.ToLocalPosition(ray.Origin), Direction = geometricObject.Pose.ToLocalDirection(ray.Direction), Length = ray.Length, }; // Use the spatial partition of the mesh shape to compute all triangles where the // AABB overlaps the ray. foreach (var triangleIndex in triangleMeshShape.Partition.GetOverlaps(localRay)) { var triangle = triangleMeshShape.Mesh.GetTriangle(triangleIndex); // Check if ray intersects the triangle and remember the closest hit. float hitDistance; if (GeometryHelper.GetContact(localRay, triangle, false, out hitDistance) && hitDistance < closestHitDistance) { closestHitGeometricObject = geometricObject; closestHitTriangle = triangle; closestHitDistance = hitDistance; } } } // Draw hit triangle. if (closestHitGeometricObject != null) { debugRenderer.DrawTriangle(closestHitTriangle, closestHitGeometricObject.Pose, Vector3F.One, Color.Red, true, true); } }