public override void CalculateLocalMouse(Microsoft.Xna.Framework.Ray MouseRay, Action<Gem.Render.SceneNode, float> HoverCallback) { MouseHover = false; var localMouse = GetLocalMouseRay(MouseRay); GridTraversal.Raycast(localMouse.Position, localMouse.Direction, PickRadius, (x, y, z, normal) => { if (!World.check(x, y, z)) return false; if (World.CellAt(x, y, z).Block == null) return false; if (World.CellAt(x, y, z).Block.Solid == false) return false; HiliteQuad = Gem.Geo.Gen.CreateQuad(); // Align quad with correct face. if (normal.Z < 0) // normal points down. Gem.Geo.Gen.Transform(HiliteQuad, Matrix.CreateFromAxisAngle(Vector3.UnitX, Gem.Math.Angle.PI)); else if (normal.Z == 0) Gem.Geo.Gen.Transform(HiliteQuad, Matrix.CreateFromAxisAngle( Vector3.Cross(-Vector3.UnitZ, normal), -Gem.Math.Angle.PI / 2)); // Move quad to center of block. Gem.Geo.Gen.Transform(HiliteQuad, Matrix.CreateTranslation(x + 0.5f, y + 0.5f, z + 0.5f)); // Move quad out to correct surface. Gem.Geo.Gen.Transform(HiliteQuad, Matrix.CreateTranslation(normal * 0.52f)); var faceIntersection = HiliteQuad.RayIntersection(localMouse); //if (faceIntersection.Intersects == false) throw new InvalidProgramException(); HoverCallback(this, faceIntersection.Distance); HoverBlock = new Coordinate(x, y, z); AdjacentHoverBlock = new Coordinate((int)(x + normal.X), (int)(y + normal.Y), (int)(z + normal.Z)); HoverNormal = normal; return true; }); }