Reputation: 182
I have to press a button twice in order for this code to display the pressed button on the console. Any idea what is wrong with this code?
I tried to trace and debug the code, but the break points at the read and write don't always fire in the while loop when I press a key.
using System;
using System.IO;
namespace ConsoleApplication3
{
public class Program
{
private interface IReader
{
ReadResult Read();
}
private interface IWriter
{
void Write(char character);
}
public class ConsoleWriter : IWriter
{
public void Write(char character)
{
Console.Write(character);
}
}
public class FileWriter : IWriter, IDispose
{
private readonly StreamWriter _streamWriter;
public FileWriter(StreamWriter streamWriter)
{
_streamWriter = streamWriter;
}
public void Write(char character)
{
_streamWriter.Write(character);
}
public void Dispose()
{
_streamWriter.Dispose();
}
}
public class ConsoleRead : IReader
{
public ReadResult Read()
{
return new ReadResult(Console.ReadKey(true).KeyChar, Console.ReadKey(true).Key == ConsoleKey.Escape);
}
}
private static void Main(string[] args)
{
IReader reader = new ConsoleRead();
IWriter writer = new ConsoleWriter();
Copy(reader, writer);
}
private static void Copy(IReader MyReader, IWriter MyWriter)
{
while (true)
{
var readResult = MyReader.Read();
if (readResult._shouldQuit)
break;
MyWriter.Write(readResult._readCharacter);
}
}
public interface IDispose
{
void Dispose();
}
public class ReadResult
{
public readonly char _readCharacter;
public readonly bool _shouldQuit;
public ReadResult(char ReadCharacter, bool ShouldQuit)
{
_readCharacter = ReadCharacter;
_shouldQuit = ShouldQuit;
}
}
}
}
Upvotes: 0
Views: 778
Reputation: 1808
You're calling ReadKey
twice in this function:
public ReadResult Read()
{
return new ReadResult(Console.ReadKey(true).KeyChar, Console.ReadKey(true).Key == ConsoleKey.Escape);
}
Call it once and store in a variable:
public ReadResult Read()
{
var temp = Console.ReadKey(true);
return new ReadResult(temp.KeyChar, temp.Key == ConsoleKey.Escape);
}
Upvotes: 1
Reputation: 82934
You are calling Console.ReadKey()
twice, once to get the character and once to determine if escape was pressed.
To have it read only once, change your ConsoleRead
class to be:
public class ConsoleRead : IReader
{
public ReadResult Read()
{
var key = Console.ReadKey(true);
return new ReadResult(key.KeyChar, key.Key == ConsoleKey.Escape);
}
}
This captures the key pressed, then uses it to create the ReadResult
.
Upvotes: 1