Convert extended ASCII characters to it's right presentation using Console.ReadKey() method and ConsoleKeyInfo variable

Posted by mishamosher on Stack Overflow See other posts from Stack Overflow or by mishamosher
Published on 2012-03-31T07:26:09Z Indexed on 2012/03/31 11:29 UTC
Read the original article Hit count: 397

Filed under:
|

Readed about 30 minutes, and didn't found some specific for this in this site.

Suppose the following, in C#, console application:

ConsoleKeyInfo cki;
cki = Console.ReadKey(true);
Console.WriteLine(cki.KeyChar.ToString()); //Or Console.WriteLine(cki.KeyChar) as well
Console.ReadKey(true);

Now, let's put ¿ in the console entry, and asign it to cki via a Console.ReadKey(true). What will be shown isn't the ¿ symbol, the ¨ symbol is the one that's shown instead. And the same happens with many other characters. Examples: ñ shows ¤, ¡ shows -, ´ shows ï.

Now, let's take the same code snipplet and add some things for a more Console.ReadLine() like behavior:

string data = string.Empty;
ConsoleKeyInfo cki;
for (int i = 0; i < 10; i++)
{
    cki = Console.ReadKey(true);
    data += cki.KeyChar;
}
Console.WriteLine(data);
Console.ReadKey(true);

The question, how to handle this by the right way, end printing the right characters that should be stored on data, not things like ¨, ¤, -, ï, etc?

Please note that I want a solution that works with ConsoleKeyInfo and Console.ReadKey(), not use other variable types, or read methods.

EDIT:

Because ReadKey() method, that comes from Console namespace, depends on Kernel32.dll and it definetively bad handles the extended ASCII and unicode, it's not an option anymore to just find a valid conversion for what it returns.

The only valid way to handle the bad behavior of ReadKey() is to use the cki.Key property that's written in cki = Console.ReadKey(true) execution and apply a switch to it, then, return the right values on dependence of what key was pressed.

For example, to handle the Ñ key pressing:

string data = string.Empty;
ConsoleKeyInfo cki;
cki = Console.ReadKey(true);
switch (cki.Key)
{
    case ConsoleKey.Oem3:
        if (cki.Modifiers.ToString().Contains("Shift")) //Could added handlers for Alt and Control, but not putted in here to keep the code small and simple
            data += "Ñ";
        else
            data += "ñ";
        break;
}
Console.WriteLine(data);
Console.ReadKey(true);

So, now the question has a wider focus... Which others functions completes it's execution with only one key pressed, and returns what's pressed (a substitute of ReadKey())? I think that there's not such substitutes, but a confirmed answer would be usefull.

EDIT2:

HA! Found the way, for something I used for so many times Windows 98 SE. There are the codepages, the ones responsibles for how's presented the info in the console.

ReadLine() reconfigures the codepage to use properly the extended ASCII and Unicode characters. ReadKey() leaves it in EN-US default (codepage 850).

Just use a codepage that prints the characters you want, and that's all. Refer to http://en.wikipedia.org/wiki/Code_page for some of them :)

So, for the Ñ key press, the solution is this:

Console.OutputEncoding = Encoding.GetEncoding(1252); //Also 28591 is valid for `Ñ` key, and others too
string data = string.Empty;
ConsoleKeyInfo cki;
cki = Console.ReadKey(true);
data += cki.KeyChar;
Console.WriteLine(data);
Console.ReadKey(true);

Simple :)

Now I'm wrrr with myself... how could I forget those codepages!?

Question answered, so, no more about this!

© Stack Overflow or respective owner

Related posts about encoding

Related posts about console