Entwickler-Ecke
Basistechnologien - CharSet mit allen in der Konsole darstellbaren Zeichen
Palladin007 - Mo 09.09.13 12:39
Titel: CharSet mit allen in der Konsole darstellbaren Zeichen
Moin,
Kennt jemand eine Möglichkeit, wie ich aus der Kodierung der Konsole heraus finden kann, ob die Konsole ein Zeichen darstellen kann, oder nicht?
Ich möchte einen Adapter schreiben, der Zeichen für Zeichen prüft, ob die Eingabe akzeptiert wird und andernfalls einfach nichts tut.
Wenn aber kein Zeichensatz angegeben wurde, dann soll der Satz genommen werden, der alle Zeichen enthält, die dargestellt werden können.
Kennt da wer eine Möglichkeit, bei allen 65535 möglichen Zeichen?
Gruß
PS:
Da ich darauf leider ziemlich schnell eine Antwort benötige, habe ich die gleiche Frage auf einem anderen Forum gestellt. Hier der [url=http://www.mycsharp.de/wbb2/thread.php?threadid=109327]Link[/URL].
Wurde geschlossen -.-
Palladin007 - Mo 09.09.13 13:41
Da ich WPF gerne außen vor lassen möchte, habe ich mir gleich die zweite Möglichkeit angeschaut und das scheint bisher genau das zu sein, was ich suche. :D
Aber eine Frage hab ich noch: Der Font, kann ich davon aus gehen, dass "Courier New" der Font der Konsole ist, oder gibt es da Andere?
Gruß
Palladin007 - Mo 09.09.13 13:52
Leider hat sich damit jetzt ein weiteres Problem ergeben :(
Scheinbar ist es nicht ohne Weiteres möglich, den aktuellen Font der Konsole heraus zu finden, da es auf der einen Seite einen Font gibt, der von der Konsole selber gerendert wird (Rasterschrift, hab ich irgendwo gelesen) und eine Reihe anderer Fonts, die der Nutzer aber selber fest legen und ich von der Konsole nicht abfragen kann.
Gibt es in C# und .NET eine Möglichkeit, das irgendwie heraus zu finden?
Palladin007 - Mo 09.09.13 14:44
Ich hab es jetzt so versucht:
C#-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42:
| [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] public class CONSOLE_FONT_INFOEX { private int cbSize; public CONSOLE_FONT_INFOEX() { cbSize = Marshal.SizeOf(typeof(CONSOLE_FONT_INFOEX)); } public int FontIndex; public short FontWidth; public short FontHeight; public int FontFamily; public int FontWeight; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 32)] public string FaceName; }
class ConsoleHelper { [DllImport("kernel32.dll", CharSet = CharSet.Unicode, SetLastError = true)] extern static bool GetCurrentConsoleFontEx(IntPtr hConsoleOutput, bool bMaximumWindow, [In, Out] CONSOLE_FONT_INFOEX lpConsoleCurrentFont);
public static void GetConsoleFont() { Type consoleType = typeof(Console);
IntPtr _consoleOutputHandle = (IntPtr)consoleType.InvokeMember( "_consoleOutputHandle", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.GetField, null, null, null);
CONSOLE_FONT_INFOEX currentFont = new CONSOLE_FONT_INFOEX(); bool success = GetCurrentConsoleFontEx( _consoleOutputHandle, false, currentFont);
} } |
Ich verstehe nur wenig, daher fällt es mir ziemlich schwer, den Fehler zu finden, aber der Inhalt von currentFont ist leer. :/
Ich habe testweise auch mal den Font der Konsole immer geändert und dann geschaut, was drin steht, aber es bleibt leer.
Edit:
Ich habe gerade gesehen, dass ich diese Methode aus deinem dritten Link nutzen kann:
C#-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40:
| public static IntPtr getConsoleOutputHandle() { Type consoleType = typeof(System.Console);
FieldInfo _consoleOutputHandle_fieldinfo = consoleType.GetField("_consoleOutputHandle", BindingFlags.NonPublic | BindingFlags.Static);
IntPtr RetVal;
System.Console.BackgroundColor = System.Console.BackgroundColor;
try { RetVal = (IntPtr)_consoleOutputHandle_fieldinfo.GetValue(null); }
catch (Exception) { RetVal = IntPtr.Zero; }
return RetVal; } |
Und damit funktioniert es jetzt :D
Ich schreibe das ganze noch ordentlich zusammen und poste dann die ganze Klasse, wenn jemand Anderes das gleiche Problem haben sollte ^^
Ralf Jansen - Mo 09.09.13 14:55
Schreib mal vor den currentFont Parameter ref beim GetCurrentConsoleFontEx Aufruf. hat sich erledigt.
Palladin007 - Mo 09.09.13 15:13
Ein Problem hab ich noch:
C#-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18:
| [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] private class CONSOLE_FONT_INFOEX { private int cbSize;
public int FontIndex; public short FontWidth; public short FontHeight; public int FontFamily; public int FontWeight; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 32)] public string FaceName;
public CONSOLE_FONT_INFOEX() { cbSize = Marshal.SizeOf(typeof(CONSOLE_FONT_INFOEX)); } } |
Das Objeckt davon enthält ja die ausgelesenen Daten.
Aber wie bekomme ich aus Diesen jetzt den passenden Font raus?
Der Name ist ja der Anzeigename des Fonts, nicht der Familien-Namen. Außerdem - wie bekomme ich emSize raus?
Oder die FontFamilie aus dieser Zahl?
Der Style sollte ja unwichtig sein, für das, was ich brauche.
Edit:
Ich hab es jetzt erst einmal so gelöst:
C#-Quelltext
1:
| new Font(fontInfo.FaceName, fontInfo.FontHeight) |
Es funktioniert, wenn aber da ein Fehler drin sein sollte, oder das nicht ganz genau ist, würde ich mich über Korrekturen freuen.
Für die Neugierigen, hier die ganze Klasse (neben der Klasse CONSOLE_FONT_INFOEX):
C#-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58: 59: 60: 61: 62: 63: 64: 65: 66: 67: 68: 69: 70: 71: 72: 73: 74: 75: 76: 77: 78:
| public class ConsoleHelper { [DllImport("kernel32.dll", CharSet = CharSet.Unicode, SetLastError = true)] private extern static bool GetCurrentConsoleFontEx(IntPtr hConsoleOutput, bool bMaximumWindow, [In, Out] CONSOLE_FONT_INFOEX lpConsoleCurrentFont);
[DllImport("gdi32.dll", EntryPoint = "GetGlyphIndicesW")] private static extern uint GetGlyphIndices([In] IntPtr hdc, [In] [MarshalAs(UnmanagedType.LPTStr)] string lpsz, int c, [Out] ushort[] pgi, uint fl);
[DllImport("gdi32.dll")] private static extern IntPtr SelectObject(IntPtr hdc, IntPtr hgdiobj);
private const uint GGI_MARK_NONEXISTING_GLYPHS = 0x01; private static Graphics _graphics = Graphics.FromImage(new Bitmap(1, 1));
public static bool DoesGlyphExist(char c) { var fontInfo = GetCurrentConsoleFontEx(); return DoesGlyphExist(c, new Font(fontInfo.FaceName, fontInfo.FontHeight)); }
public static bool DoesGlyphExist(char c, Font font) { IntPtr hdc = _graphics.GetHdc(); ushort[] glyphIndices;
try { IntPtr hfont = font.ToHfont();
SelectObject(hdc, hfont);
string testString = new string(c, 1); glyphIndices = new ushort[testString.Length];
GetGlyphIndices(hdc, testString, testString.Length, glyphIndices, GGI_MARK_NONEXISTING_GLYPHS);
} finally { _graphics.ReleaseHdc(hdc); }
return (glyphIndices[0] != 0xffff); }
public static CONSOLE_FONT_INFOEX GetCurrentConsoleFontEx() { Type consoleType = typeof(Console); IntPtr _consoleOutputHandle = getConsoleOutputHandle();
CONSOLE_FONT_INFOEX currentFont = new CONSOLE_FONT_INFOEX(); bool success = GetCurrentConsoleFontEx( _consoleOutputHandle, false, currentFont);
return currentFont; }
private static IntPtr getConsoleOutputHandle() { Type consoleType = typeof(System.Console); FieldInfo _consoleOutputHandle_fieldinfo = consoleType.GetField("_consoleOutputHandle", BindingFlags.NonPublic | BindingFlags.Static); Console.BackgroundColor = System.Console.BackgroundColor;
IntPtr RetVal;
try { RetVal = (IntPtr)_consoleOutputHandle_fieldinfo.GetValue(null); } catch (Exception) { RetVal = IntPtr.Zero; }
return RetVal; } } |
Entwickler-Ecke.de based on phpBB
Copyright 2002 - 2011 by Tino Teuber, Copyright 2011 - 2025 by Christian Stelzmann Alle Rechte vorbehalten.
Alle Beiträge stammen von dritten Personen und dürfen geltendes Recht nicht verletzen.
Entwickler-Ecke und die zugehörigen Webseiten distanzieren sich ausdrücklich von Fremdinhalten jeglicher Art!