Files
spectre.console/src/Spectre.Console.Cli/Internal/TextBuffer.cs
2022-05-15 00:09:52 +02:00

89 lines
1.8 KiB
C#

namespace Spectre.Console.Cli;
internal sealed class TextBuffer : IDisposable
{
// There is some kind of bug
private readonly StringReader _reader;
public bool ReachedEnd => _reader.Peek() == -1;
public string Original { get; }
public int Position { get; private set; }
public TextBuffer(string text)
{
_reader = new StringReader(text);
Original = text;
Position = 0;
}
public TextBuffer(TextBuffer? buffer, string text)
{
_reader = new StringReader(text);
Original = buffer != null ? buffer.Original + " " + text : text;
Position = buffer?.Position + 1 ?? 0;
}
public void Dispose()
{
_reader.Dispose();
}
public char Peek()
{
return (char)_reader.Peek();
}
public bool TryPeek(out char character)
{
var value = _reader.Peek();
if (value == -1)
{
character = '\0';
return false;
}
character = (char)value;
return true;
}
public void Consume()
{
EnsureNotAtEnd();
Read();
}
public void Consume(char character)
{
EnsureNotAtEnd();
if (Read() != character)
{
throw new InvalidOperationException($"Expected '{character}' token.");
}
}
public bool IsNext(char character)
{
if (TryPeek(out var result))
{
return result == character;
}
return false;
}
public char Read()
{
EnsureNotAtEnd();
var result = (char)_reader.Read();
Position++;
return result;
}
private void EnsureNotAtEnd()
{
if (ReachedEnd)
{
throw new InvalidOperationException("Can't read past the end of the buffer.");
}
}
}