using Azimuth; using Blacklight.Core; using Blacklight.Core.Cameras; using Clave; namespace Konis.Testbed { /// /// Spawns the demo's effect where the left button goes down, on the ground under the pointer. /// public class ClickSpawner : IInputConsumer { private readonly ParticleDemo demo; private readonly WindowHandle window; private readonly Camera camera; public ClickSpawner(ParticleDemo demo, WindowHandle window, Camera camera) { this.demo = demo; this.window = window; this.camera = camera; } /// /// Gets or sets how many seconds ahead of the click a spawned effect starts. /// public float PreWarmSeconds { get; set; } /// /// Returns where on the ground a pixel of the window shows, or false when the view can't tell. /// public bool TryGroundAt(Vector pixel, out Vector3 position) { // Pixels put the origin top left with y down. Projection space is centered with y up. var centered = new Vector(pixel.X - window.Width / 2.0, -(pixel.Y - window.Height / 2.0)); Vector scene = camera.ProjectionToWorld.TransformPoint(centered); return demo.Projection.TryUnproject(scene, 0, out position); } public bool PointerDown(PointerInput input) { if (input.Buttons != PointerButtons.Left || !TryGroundAt(input.PixelPos, out Vector3 position)) { return false; } demo.Spawn(position, PreWarmSeconds); return true; } public bool PointerMove(PointerInput input) { return false; } public bool PointerUp(PointerInput input) { return false; } public bool Wheel(Scalar ticks, Vector pixelPos) { return false; } public bool KeyDown(KeyboardSnapshot keyboard) { return false; } public bool KeyUp(KeyboardSnapshot keyboard) { return false; } public void SyncKeys(KeyboardSnapshot keyboard) { } public void CancelKeys() { } } }