mikrocontroller.net

Forum: PC-Programmierung C++ cout umleiten


Autor: Bernd (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi,

folgendes Problem: Ich habe eine Klasse von streambuf abgeleitet, um 
cout (umzubiegen). Sehe nachfolgenden Code.
class NRedirectStream : public streambuf {
  HWND  control;
public:
  //typedef std::char_traits<char> traits_type; 
  //typedef traits_type::int_type  int_type; 

  NRedirectStream(HWND hwnd) {
    control = hwnd;
  };
  virtual streamsize xsputn(const char_type *_Ptr,  streamsize _Count) {
    unsigned long length = GetWindowTextLength(control);
    wchar_t *text = new wchar_t[length+_Count*2+1];
    GetWindowText(control, text, length+1);
    wchar_t* target = text+length;
    const char* source = _Ptr;
    for (int i = 0; i<_Count; i++) {
      char c = *source++;
      if (c == '\n') *target++ = '\r';
      *target++ = (wchar_t)c;
    }
    *target = 0;
    SetWindowText(control, text);
    delete [] text;
    return _Count;
    return __super::xsputn(_Ptr, _Count);
  };

    virtual int_type overflow(int_type c) { 
      return traits_type::not_eof(c);
    };
};

Das ganze funktionniert auch teilweise.
Beispiel:

cout << "Der Name ist " << name << ".\n";

Von dieser Zeile wird für "Der Name ist " und ".\n" jeweils xsputn 
aufgerufen. Nur für die Variable name (vom Type string in C++) nicht.
Weiß jemand, woran es liegen kann, dass Literale richtig verarbeitet 
werden und Strings (c++ Klasse string) als Variable keinen Aufruf von 
xsputn erzeugen? Auch wenn ich int, long, float übergebe, streikt meine 
Klasse.

Autor: Jorge (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
name ist nicht const

Autor: Hermann-Josef (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo Bernd,

hier könnte sich ggf. ein Hinweis dazu finden:
  http://www.inf.uni-konstanz.de/~kuehl/c++/iostream/
siehe das Beispiel wstream.cc.

Leider funktionieren die Beispiele dort evtl. nicht mehr mit einem 
neueren Kompiler (gcc 3.3.x oder 4.x). Eines (prfxstream.cc) habe ich 
mal umgestrickt.

Die Idee ist eigentlich, dass die neue Stream-Klasse von std::ostream 
ableitet, damit hat die neue Klasse automatisch alle <<-Operatoren 
mitgeerbt.

Dann implementiert man eine streambuf-Klasse, die mit dem eigentlichen 
Problem zu tun hat, und die man im Konstruktor der neuen Klasse dem 
Konstruktor von std::ostream als Argument übergibt.

Was sich in der C++-Implementierung gegenüber (vermutlich) gcc 2.95 
geändert hat, sind die Namen der Methoden zum Synchronisieren der 
streambufs, falls man die benötigt.

Etwas komplexerer Code findet sich meines Wissens auch bei Boost, hier 
in einer beim letzten Besuch der Web-Site nicht akzeptierten 
Implementierung einer Logging-Klasse.

Viel Erfolg
Hermann-Josef

Autor: Hermann-Josef (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
... hmmh, das löst das Problem wohl nicht wirklich, es sei man ersetzt 
im gesamten Code cout durch den eigenen ostream.

Wie wäre es den streambuf in cout durch einen eigenen zu ersetzen?

http://bytes.com/forum/thread133345.html

Hermann-Josef

Autor: Arc Net (arc)
Datum:

Bewertung
0 lesenswert
nicht lesenswert

Autor: Bernd (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich habe es jetzt geschaft das Beispiel hier 
(http://www.codeproject.com/KB/edit/editlog.aspx) erfolgreich zu 
übertragen.

Aber eigentlich ist es immer noch nicht das Gelbe vom Ei.

Um in die Standardausgabe zu schreiben gibt es unter C++/CLI folgende 
Möglichkeiten:

1. printf(...)               // C Variante
2. cout << ...               // C++ Variante
3. Console::WriteLine(...)   // C++/CLI Variante

Bisher funktioniert keine der Varianten für alle drei Formen.

Eigenlich wird immer nur auf Klassenebene (Beispiel 2 und 3) gearbeitet.
Wie aber bekomme ich den WAHREN Datenstrom, den Windows tatsächlich an 
ein Konsolenfenster schickt? Denn die Varianten 1-3 senden ja alle auch 
gemischt in einer Anwendung Text an das gleiche Konsolenfenster. 
Irgendwo müssen die Datenströme ja zusammenlaufen.

Autor: Jorge (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Unter Unix heissen die 1 2 und 3 "stdin" "stdout" "stderr" ich glaub bei 
Windoof ist es das gleiche

Autor: Jorge (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert

Autor: I_ H. (i_h)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Mal eine Frage: Wieso willst du cout eigentlich umleiten? Die Shell kann 
das in den meisten Fällen viel besser.

Autor: Bernd (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Mal eine Frage: Wieso willst du cout eigentlich umleiten? Die Shell kann
> das in den meisten Fällen viel besser.

Weil ich ein paar C++ Klassen habe, die z.B. cout verwenden. C++/CLI 
Klassen verwenden Console::Write und alte C funktionen printf. Und ich 
möchte diese Ausgaben in ein .NET TextBox beziehungsweise in ein Windows 
Edit Control umleiten.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.