MemoBox: verschiedene charsets
-
Hallo,
ich benutze in einer Form eine MemoBox um mir dort die Ausgabe von einem Konsolenprogramm (z.B. ping) anzuzeigen, das ich mir CreateProcess starte.
Damit die Umlaute in der Memobox korrekt angezeigt werden, habe ich den Zeichensatz der MemoBox auf OEM_CHARSET umgestellt.
Nun ist es aber so, das wenn ich im Programm der MemoBox einen festen Text mit Lines->Add("äöü") hinzufügen will, diese Umlaute falsch dargestellt werden.Gibt es eine Möglichkeit beide Texte mit Umlauten korrekt darzustellen?
Danke und Gruß
Thomas
-
Das liegt einfach daran, daß die Umlaute in den verschiedenen Char-Sets sich an unterschiedlichen Position befinden, d.h. statt 'ä', 'ü', 'ö' etc. müßtest du halt den entsprechenden Char-Code verwenden: char(x) bzw. eine Konvertierungsfunktion schreiben.
(Am besten, du schaust dir mal die Zeichen im Windows Zubehör Programm "Zeichentabelle" für den verwendeten Zeichensatz an).
-
Danke, ich hab mir jetzt eine kleine Funktion geschrieben die dieses konvertiert:
void convertUmlToDosCharset(std::string &strRef) { // Zeichen DOS: Westeuropa Windows: Westlich // ä 0x84 0xE4 // Ä 0x8E 0xC4 // ö 0x94 0xF6 // Ö 0x99 0xD6 // ü 0x81 0xFC // Ü 0x9A 0xDC // ß 0xE1 0xDF unsigned int strLen; strLen = strRef.size(); for (unsigned int i = 0; i < strLen; i++) { if (strRef[i] == 0xFFFFFFE4) strRef[i] = 0x84; else if (strRef[i] == 0xFFFFFFC4) strRef[i] = 0x8E; else if (strRef[i] == 0xFFFFFFF6) strRef[i] = 0x94; else if (strRef[i] == 0xFFFFFFD6) strRef[i] = 0x99; else if (strRef[i] == 0xFFFFFFFC) strRef[i] = 0x81; else if (strRef[i] == 0xFFFFFFDC) strRef[i] = 0x9A; else if (strRef[i] == 0xFFFFFFDF) strRef[i] = 0xE1; } }In der Windows-Zeichentabelle findet man aber nicht die Info mit den führenden 0xFF, wo kommen die denn her?
-
Woher hast du denn die 8-stelligen Hexzahlen her? In einem std::string werden nur chars gespeichert (und diese sind auf den Windows-Systemen nur 8 Bit, dh. 1 Byte groß).
Also reicht:
if (strRef[i] == 0xE4) strRef[i] = 0x84;
-
Th schrieb:
Woher hast du denn die 8-stelligen Hexzahlen her? In einem std::string werden nur chars gespeichert (und diese sind auf den Windows-Systemen nur 8 Bit, dh. 1 Byte groß).
Also reicht:
if (strRef[i] == 0xE4) strRef[i] = 0x84;Ja, das hab ich mir eigentlich auch gedacht. Als das aber nicht funktionierte, habe ich mir das einzelne Zeichen mittels sprintf(ch, "%X", strRef[i]) in der Memobox ausgeben lassen, und dort erscheinen dann die 3 zusätzlichen Bytes. Die erscheinen jedoch nur bei den Umlauten, bzw. würden sonst führende Nullen nicht mit ausgegeben.
Ich hab mich auch über die 4 Byte gewundert (d.h. in C ist für char ja nur die Mindestgröße von 1 Byte festgelegt).
-
Also so ein Programm:
std::string strText; char chText[200]; strText = "Text mit ä, ö und ü"; for (int i = 0; i < strText.size(); i++) { sprintf(chText, "%d\t%c\t%x\t%d", i, strText[i], strText[i], sizeof(strText[i])); Memo1->Lines->Add(chText); }erzeugt folgende Ausgabe in der Memo:
0 T 54 1 1 e 65 1 2 x 78 1 3 t 74 1 4 20 1 5 m 6d 1 6 i 69 1 7 t 74 1 8 20 1 9 ä ffffffe4 1 10 , 2c 1 11 20 1 12 ö fffffff6 1 13 20 1 14 u 75 1 15 n 6e 1 16 d 64 1 17 20 1 18 ü fffffffc 1
-
Ach so, jetzt verstehe ich es.
Es liegt nur an der Ausgabe, da "%x" einen Integer erwartet. Und da ein String mit vorzeichenbehafteten Zeichen ([signed] char) arbeitet, werden negative Werte entsprechend des 2-Komplements so ausgegeben.
Aber für den Vergleich spielt das keine Rolle (und wie gesagt, du solltest es entfernen - für den Fall, daß du mit vorzeichenlosen Chars compilierst).
Alternativ könntest du bei der Ausgabe einfach die Parameter mittels static_cast<unsigned char>(...) angeben.