mirror of
https://github.com/nsnail/spectre.console.git
synced 2025-04-16 08:52:50 +08:00
93 lines
2.8 KiB
C#
93 lines
2.8 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
using Spectre.Console;
|
|
|
|
namespace Generator.Commands
|
|
{
|
|
public sealed class AsciiCastInput : IAnsiConsoleInput
|
|
{
|
|
private readonly Queue<(ConsoleKeyInfo?, int)> _input;
|
|
private readonly Random _random = new Random();
|
|
|
|
public AsciiCastInput()
|
|
{
|
|
_input = new Queue<(ConsoleKeyInfo?, int)>();
|
|
}
|
|
|
|
public void PushText(string input, int keypressDelayMs)
|
|
{
|
|
if (input is null)
|
|
{
|
|
throw new ArgumentNullException(nameof(input));
|
|
}
|
|
|
|
foreach (var character in input)
|
|
{
|
|
PushCharacter(character, keypressDelayMs);
|
|
}
|
|
}
|
|
|
|
public void PushTextWithEnter(string input, int keypressDelayMs)
|
|
{
|
|
PushText(input, keypressDelayMs);
|
|
PushKey(ConsoleKey.Enter, keypressDelayMs);
|
|
}
|
|
|
|
public void PushCharacter(char input, int keypressDelayMs)
|
|
{
|
|
var delay = keypressDelayMs + _random.Next((int)(keypressDelayMs * -.2), (int)(keypressDelayMs * .2));
|
|
|
|
switch (input)
|
|
{
|
|
case '↑':
|
|
PushKey(ConsoleKey.UpArrow, keypressDelayMs);
|
|
break;
|
|
case '↓':
|
|
PushKey(ConsoleKey.DownArrow, keypressDelayMs);
|
|
break;
|
|
case '↲':
|
|
PushKey(ConsoleKey.Enter, keypressDelayMs);
|
|
break;
|
|
case '¦':
|
|
_input.Enqueue((null, delay));
|
|
break;
|
|
default:
|
|
var control = char.IsUpper(input);
|
|
_input.Enqueue((new ConsoleKeyInfo(input, (ConsoleKey)input, false, false, control), delay));
|
|
break;
|
|
}
|
|
}
|
|
|
|
public void PushKey(ConsoleKey input, int keypressDelayMs)
|
|
{
|
|
var delay = keypressDelayMs + _random.Next((int)(keypressDelayMs * -.2), (int)(keypressDelayMs * .2));
|
|
_input.Enqueue((new ConsoleKeyInfo((char)input, input, false, false, false), delay));
|
|
}
|
|
|
|
public bool IsKeyAvailable()
|
|
{
|
|
return _input.Count > 0;
|
|
}
|
|
|
|
public ConsoleKeyInfo? ReadKey(bool intercept)
|
|
{
|
|
if (_input.Count == 0)
|
|
{
|
|
throw new InvalidOperationException("No input available.");
|
|
}
|
|
|
|
var result = _input.Dequeue();
|
|
|
|
Thread.Sleep(result.Item2);
|
|
return result.Item1;
|
|
}
|
|
|
|
public Task<ConsoleKeyInfo?> ReadKeyAsync(bool intercept, CancellationToken cancellationToken)
|
|
{
|
|
return Task.FromResult(ReadKey(intercept));
|
|
}
|
|
}
|
|
}
|