using Azimuth; using Blacklight.Core.Cameras; using UnitTestSharp; namespace Blacklight.WebGL2.UnitTests { public class WebGL2InputTests : TestFixture { public class RecordingConsumer : IInputConsumer { public PointerInput? LastPointerDown; public PointerInput? LastPointerMove; public PointerInput? LastPointerUp; public int? LastWheelTicks; public Vector? LastWheelPixelPos; public Key? LastKeyDown; public Key? LastKeyUp; public void PointerDown(PointerInput input) { LastPointerDown = input; } public void PointerMove(PointerInput input) { LastPointerMove = input; } public void PointerUp(PointerInput input) { LastPointerUp = input; } public void Wheel(int ticks, Vector pixelPos) { LastWheelTicks = ticks; LastWheelPixelPos = pixelPos; } public void KeyDown(Key key) { LastKeyDown = key; } public void KeyUp(Key key) { LastKeyUp = key; } } public class ButtonCodeToPointerButtonsTests : TestFixture { public void ZeroMapsToLeft() { CheckEqual(PointerButtons.Left, WebGL2Input.ButtonCodeToPointerButtons(0)); } public void OneMapsToMiddle() { CheckEqual(PointerButtons.Middle, WebGL2Input.ButtonCodeToPointerButtons(1)); } public void TwoMapsToRight() { CheckEqual(PointerButtons.Right, WebGL2Input.ButtonCodeToPointerButtons(2)); } public void UnknownCodeMapsToNone() { CheckEqual(PointerButtons.None, WebGL2Input.ButtonCodeToPointerButtons(3)); } } public class ButtonsBitmaskToPointerButtonsTests : TestFixture { public void ZeroMapsToNone() { CheckEqual(PointerButtons.None, WebGL2Input.ButtonsBitmaskToPointerButtons(0)); } public void OneMapsToLeft() { CheckEqual(PointerButtons.Left, WebGL2Input.ButtonsBitmaskToPointerButtons(1)); } public void TwoMapsToRight() { CheckEqual(PointerButtons.Right, WebGL2Input.ButtonsBitmaskToPointerButtons(2)); } public void FourMapsToMiddle() { CheckEqual(PointerButtons.Middle, WebGL2Input.ButtonsBitmaskToPointerButtons(4)); } public void CombinedBitsMapToCombinedFlags() { CheckEqual(PointerButtons.Left | PointerButtons.Right | PointerButtons.Middle, WebGL2Input.ButtonsBitmaskToPointerButtons(7)); } // Bit 8 is the browser's "back" button (W3C buttons=8); not one of PointerButtons' cases. public void UnmodeledBitIsIgnored() { CheckEqual(PointerButtons.Left, WebGL2Input.ButtonsBitmaskToPointerButtons(9)); } } public class OnPointerDownTests : TestFixture { public void TranslatesPositionAndButtonCodeToPointerDown() { var consumer = new RecordingConsumer(); WebGL2Input.OnPointerDown(consumer, 12, 34, 2); CheckEqual(new Vector(12, 34), consumer.LastPointerDown.Value.PixelPos); CheckEqual(PointerButtons.Right, consumer.LastPointerDown.Value.Buttons); } } public class OnPointerMoveTests : TestFixture { public void TranslatesPositionAndBitmaskToPointerMove() { var consumer = new RecordingConsumer(); WebGL2Input.OnPointerMove(consumer, 1, 2, 3); CheckEqual(new Vector(1, 2), consumer.LastPointerMove.Value.PixelPos); CheckEqual(PointerButtons.Left | PointerButtons.Right, consumer.LastPointerMove.Value.Buttons); } } public class OnPointerUpTests : TestFixture { public void TranslatesPositionAndButtonCodeToPointerUp() { var consumer = new RecordingConsumer(); WebGL2Input.OnPointerUp(consumer, 5, 6, 0); CheckEqual(new Vector(5, 6), consumer.LastPointerUp.Value.PixelPos); CheckEqual(PointerButtons.Left, consumer.LastPointerUp.Value.Buttons); } } public class OnWheelTests : TestFixture { public void FlipsDeltaYSign() { var consumer = new RecordingConsumer(); WebGL2Input.OnWheel(consumer, 7, 8, 120); CheckEqual(-120, consumer.LastWheelTicks.Value); CheckEqual(new Vector(7, 8), consumer.LastWheelPixelPos.Value); } } public class OnKeyDownTests : TestFixture { public static readonly (string, Key)[] MappedCodes = { ("KeyA", Key.A), ("KeyB", Key.B), ("KeyC", Key.C), ("KeyD", Key.D), ("KeyE", Key.E), ("KeyF", Key.F), ("KeyG", Key.G), ("KeyH", Key.H), ("KeyI", Key.I), ("KeyJ", Key.J), ("KeyK", Key.K), ("KeyL", Key.L), ("KeyM", Key.M), ("KeyN", Key.N), ("KeyO", Key.O), ("KeyP", Key.P), ("KeyQ", Key.Q), ("KeyR", Key.R), ("KeyS", Key.S), ("KeyT", Key.T), ("KeyU", Key.U), ("KeyV", Key.V), ("KeyW", Key.W), ("KeyX", Key.X), ("KeyY", Key.Y), ("KeyZ", Key.Z), ("Digit0", Key.Digit0), ("Digit1", Key.Digit1), ("Digit2", Key.Digit2), ("Digit3", Key.Digit3), ("Digit4", Key.Digit4), ("Digit5", Key.Digit5), ("Digit6", Key.Digit6), ("Digit7", Key.Digit7), ("Digit8", Key.Digit8), ("Digit9", Key.Digit9), ("F1", Key.F1), ("F2", Key.F2), ("F3", Key.F3), ("F4", Key.F4), ("F5", Key.F5), ("F6", Key.F6), ("F7", Key.F7), ("F8", Key.F8), ("F9", Key.F9), ("F10", Key.F10), ("F11", Key.F11), ("F12", Key.F12), ("ArrowUp", Key.ArrowUp), ("ArrowDown", Key.ArrowDown), ("ArrowLeft", Key.ArrowLeft), ("ArrowRight", Key.ArrowRight), ("Home", Key.Home), ("End", Key.End), ("PageUp", Key.PageUp), ("PageDown", Key.PageDown), ("Insert", Key.Insert), ("Delete", Key.Delete), ("Space", Key.Space), ("Enter", Key.Enter), ("Escape", Key.Escape), ("Tab", Key.Tab), ("Backspace", Key.Backspace), ("CapsLock", Key.CapsLock), ("ShiftLeft", Key.ShiftLeft), ("ShiftRight", Key.ShiftRight), ("ControlLeft", Key.ControlLeft), ("ControlRight", Key.ControlRight), ("AltLeft", Key.AltLeft), ("AltRight", Key.AltRight), ("Minus", Key.Minus), ("Equal", Key.Equal), ("BracketLeft", Key.BracketLeft), ("BracketRight", Key.BracketRight), ("Backslash", Key.Backslash), ("Semicolon", Key.Semicolon), ("Quote", Key.Quote), ("Comma", Key.Comma), ("Period", Key.Period), ("Slash", Key.Slash), ("Backquote", Key.Backquote), }; public void TranslatesEveryMappedCodeToItsPortableEquivalent() { foreach (var (code, expected) in MappedCodes) { var consumer = new RecordingConsumer(); WebGL2Input.OnKeyDown(consumer, code); CheckEqual(expected, consumer.LastKeyDown.Value); } } public void UnmappedKeyDoesNotReachConsumer() { var consumer = new RecordingConsumer(); WebGL2Input.OnKeyDown(consumer, "NumLock"); CheckNull(consumer.LastKeyDown); } } public class OnKeyUpTests : TestFixture { public void MappedCodeTranslatesToItsPortableEquivalent() { var consumer = new RecordingConsumer(); WebGL2Input.OnKeyUp(consumer, "KeyW"); CheckEqual(Key.W, consumer.LastKeyUp.Value); } public void UnmappedKeyDoesNotReachConsumer() { var consumer = new RecordingConsumer(); WebGL2Input.OnKeyUp(consumer, "NumLock"); CheckNull(consumer.LastKeyUp); } } } }