using Amphora; using System; using System.Collections.Generic; using UnitTestSharp; namespace Glass.UnitTests { public class EntryTypeAheadTests : TestFixture { private static readonly Duration OneSecond = Duration.FromSeconds(1); private static FileEntry[] Files(params string[] names) { var returnMe = new FileEntry[names.Length]; for (int i = 0; i < names.Length; ++i) { returnMe[i] = new FileEntry(names[i], IsDirectory: false); } return returnMe; } public class FindTests : TestFixture { public void AName_IsFoundByTheCharactersItStartsWith() { var typeAhead = new EntryTypeAhead(); CheckEqual(2, typeAhead.Find(Files("alpha", "apple", "banana"), null, "b")); } public void TheMatch_IgnoresCase() { var typeAhead = new EntryTypeAhead(); CheckEqual(1, typeAhead.Find(Files("Alpha", "BANANA"), null, "bAn")); } public void NothingSelected_StartsAtTheTop() { var typeAhead = new EntryTypeAhead(); CheckEqual(0, typeAhead.Find(Files("alpha", "apple"), null, "a")); } public void ASelection_IsWhereTheSearchStarts() { var typeAhead = new EntryTypeAhead(); CheckEqual(2, typeAhead.Find(Files("apple", "banana", "avocado"), 1, "a")); } public void TheSearch_WrapsPastTheEnd() { var typeAhead = new EntryTypeAhead(); CheckEqual(0, typeAhead.Find(Files("alpha", "banana", "cherry"), 2, "a")); } public void TheSelection_WinsWhileItStillFits() { var typeAhead = new EntryTypeAhead(); CheckEqual(1, typeAhead.Find(Files("apple", "apricot"), 1, "a")); } public void AnotherCharacter_MovesOnOnceTheSelectionStopsFitting() { var typeAhead = new EntryTypeAhead(); FileEntry[] entries = Files("apple", "apricot", "banana"); CheckEqual(0, typeAhead.Find(entries, null, "a")); CheckEqual(0, typeAhead.Find(entries, 0, "p")); CheckEqual(1, typeAhead.Find(entries, 0, "r")); } public void SeveralCharactersAtOnce_AreAddedWhole() { var typeAhead = new EntryTypeAhead(); CheckEqual(1, typeAhead.Find(Files("banana", "apple"), null, "ap")); CheckEqual("ap", typeAhead.Typed); } public void NothingFitting_ReturnsNullAndKeepsTheCharacters() { var typeAhead = new EntryTypeAhead(); CheckNull(typeAhead.Find(Files("alpha", "banana"), 1, "x")); CheckEqual("x", typeAhead.Typed); } public void AnEmptyList_ReturnsNull() { var typeAhead = new EntryTypeAhead(); CheckNull(typeAhead.Find(Files(), null, "a")); } public void NoCharacters_ReturnsNullAndChangesNothing() { var typeAhead = new EntryTypeAhead(); typeAhead.Find(Files("alpha"), null, "a"); CheckNull(typeAhead.Find(Files("alpha"), 0, "")); CheckEqual("a", typeAhead.Typed); } public void ASelectionSomethingElseMoved_StartsANewSearch() { var typeAhead = new EntryTypeAhead(); FileEntry[] entries = Files("apple", "banana", "cherry"); typeAhead.Find(entries, null, "b"); CheckEqual(0, typeAhead.Find(entries, 2, "a")); CheckEqual("a", typeAhead.Typed); } public void ARepeatedCharacter_CyclesThroughTheNamesItStarts() { var typeAhead = new EntryTypeAhead(); FileEntry[] entries = Files("apple", "avocado", "banana", "apricot"); CheckEqual(0, typeAhead.Find(entries, null, "a")); CheckEqual(1, typeAhead.Find(entries, 0, "a")); CheckEqual(3, typeAhead.Find(entries, 1, "a")); CheckEqual(0, typeAhead.Find(entries, 3, "a")); } public void ARepeatedCharacter_TypesARealNameThatStartsWithTheRepeats() { var typeAhead = new EntryTypeAhead(); FileEntry[] entries = Files("alpha", "aardvark", "apple"); CheckEqual(0, typeAhead.Find(entries, null, "a")); CheckEqual(1, typeAhead.Find(entries, 0, "a")); } public void DifferentCharacters_DoNotCycle() { var typeAhead = new EntryTypeAhead(); FileEntry[] entries = Files("apple", "avocado"); typeAhead.Find(entries, null, "a"); CheckNull(typeAhead.Find(entries, 0, "z")); } public void NullEntries_Throws() { CheckThrow(typeof(ArgumentNullException)); new EntryTypeAhead().Find(null, null, "a"); } public void NullText_Throws() { CheckThrow(typeof(ArgumentNullException)); new EntryTypeAhead().Find(Files("a"), null, null); } public void ASelectionPastTheEnd_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new EntryTypeAhead().Find(Files("a"), 1, "a"); } public void ANegativeSelection_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new EntryTypeAhead().Find(Files("a"), -1, "a"); } } public class ResetTests : TestFixture { public void Always_ForgetsTheCharacters() { var typeAhead = new EntryTypeAhead(); typeAhead.Find(Files("alpha"), null, "a"); typeAhead.Reset(); CheckEqual("", typeAhead.Typed); } } public class WaitTests : TestFixture { public void ALongEnoughQuiet_ForgetsTheCharacters() { var typeAhead = new EntryTypeAhead(); typeAhead.Find(Files("alpha"), null, "a"); typeAhead.Wait(Duration.FromMilliseconds(600), OneSecond); CheckEqual("a", typeAhead.Typed); typeAhead.Wait(Duration.FromMilliseconds(400), OneSecond); CheckEqual("", typeAhead.Typed); } public void TypingAnotherCharacter_RestartsTheQuiet() { var typeAhead = new EntryTypeAhead(); FileEntry[] entries = Files("apple"); typeAhead.Find(entries, null, "a"); typeAhead.Wait(Duration.FromMilliseconds(900), OneSecond); typeAhead.Find(entries, 0, "p"); typeAhead.Wait(Duration.FromMilliseconds(900), OneSecond); CheckEqual("ap", typeAhead.Typed); } public void WaitingWithNothingTyped_CountsNothingTowardTheNextSearch() { var typeAhead = new EntryTypeAhead(); typeAhead.Wait(Duration.FromSeconds(10), OneSecond); typeAhead.Find(Files("alpha"), null, "a"); typeAhead.Wait(Duration.FromMilliseconds(500), OneSecond); CheckEqual("a", typeAhead.Typed); } } } }