Skip to content

Instantly share code, notes, and snippets.

@agatemosu
Created May 1, 2024 18:34
Show Gist options
  • Save agatemosu/f69c435a4221f57c31a32e447cce0bd5 to your computer and use it in GitHub Desktop.
Save agatemosu/f69c435a4221f57c31a32e447cce0bd5 to your computer and use it in GitHub Desktop.
Easy-peasy options selector for the terminal.
using System;
using System.Collections.Generic;
public static class Program
{
public static void Main()
{
string[] options = [
"option 0",
"option 1",
"option 2",
"option 3",
"option 4",
"option 5",
"option 6",
"option 7",
"option 8",
"option 10",
"option 11",
"option 12"
];
int optionIndex = Selector.Select(options);
Console.WriteLine();
Console.WriteLine($"Option selected: {options[optionIndex]}");
}
}
public static class Selector
{
public static int Select(string[] options)
{
int maxOptions = Math.Min(options.Length, 6);
int startIndex = 0;
int index = 0;
printOptions(options, index, startIndex, maxOptions);
while (true)
{
if (!Console.KeyAvailable)
continue;
ConsoleKeyInfo keyInfo = Console.ReadKey(true);
// ReSharper disable once SwitchStatementHandlesSomeKnownEnumValuesWithDefault
switch (keyInfo.Key)
{
case ConsoleKey.UpArrow:
index--;
// Ensure index doesn't go below 0
if (index < 0)
index = 0;
// Move startIndex up if possible
if (startIndex > index)
startIndex--;
break;
case ConsoleKey.DownArrow:
index++;
// Ensure index doesn't exceed the length of options
if (index >= options.Length)
index = options.Length - 1;
// Move startIndex down if necessary
if (index >= startIndex + maxOptions)
startIndex++;
break;
case ConsoleKey.Enter:
return index;
default:
continue;
}
Console.SetCursorPosition(0, Console.CursorTop - maxOptions);
printOptions(options, index, startIndex, maxOptions);
}
}
private static void printOptions(
IReadOnlyList<string> options,
int index,
int startIndex,
int maxOptions
)
{
for (int i = startIndex; i < startIndex + maxOptions; i++)
{
// Clear the current line
Console.Write(new string(' ', Console.WindowWidth));
// Set the cursor position to the beginning of the line
Console.SetCursorPosition(0, Console.CursorTop);
if (index == i)
{
Console.ForegroundColor = ConsoleColor.White;
Console.Write(" => ");
}
else
{
Console.ForegroundColor = ConsoleColor.DarkGray;
Console.Write(" - ");
}
Console.Write(options[i]);
Console.WriteLine();
}
Console.ResetColor();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment