Cursorposition auslesen bzw. aktuell halten...

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
mutetella
User
Beiträge: 1695
Registriert: Donnerstag 5. März 2009, 17:10
Kontaktdaten:

Um ein erweitertes Eingabefeld, quasi ein 'ext_input()', zu realisieren, gehe ich wie folgt vor:

Code: Alles auswählen

  ___
| stdin: '' -> warte
|    Tastatureingabe: 'a'
| ___
  ___
|stdin: 'a' -> übersetze Zeichen
|    lese 'a', übersetze als 'a', zeige 'a' an
|    sende '\033[?6n'
| __
  ___
|stdin: '\x1b[?20;1R' -> übersetze Zeichen
|    lese '\x1b' bis 'R', übersetze als (20, 1)
| __
  ___
|stdin: '' -> warte
|    Eingabe aus Zwischenspeicher: 'wort'
| __
  ___
|stdin: 'wort\x1b[?20;2R' -> übersetze Zeichen
|    lese 'w', übersetze als 'w', zeige 'w' an
|    sende '\033[?6n'
| __
  ___
|stdin: 'ort\x1b[?20;2R\x1b[?20;3R' -> übersetze Zeichen
|    lese 'o', übersetze als 'o', zeige 'o' an
|    sende '\033[?6n'
| __
  ___
|stdin: 'rt\x1b[?20;2R\x1b[?20;3R\x1b[?20;4R' -> übersetze Zeichen
|    lese 'r', übersetze als 'r', zeige 'r' an
|    sende '\033[?6n'
| __
...
Nachdem also etwas aus dem Zwischenspeicher eingefügt wird (oder auch dann, wenn Tasten sehr, sehr schnell hintereinander eingetippt(-trommelt) werden) erhält man erst wieder einen xterm-Report, wenn die Zeichen zuvor abgearbeitet sind.
Mein Ansatz:
  • Alle Zeichen bis zum xterm-Report auslesen, den Report auswerten und die zwischengespeicherten Zeichen dann wie 'stdin' behandeln und danach wieder auf 'stdin' wechseln.
    Mit anderen Worten: Zwischen jedes anzeigbare Zeichen einen xterm-Report einfügen.
  • Auf die ständige (teure) xterm-Abfrage verzichten, die Koordinaten einmal abfragen und intern aktuell halten.
Ich denke mal, die Cursorposition einmalig abzufragen und intern aktuell zu halten ist am sinnvollsten.

Was meint ihr?

mutetella
Entspanne dich und wisse, dass es Zeit für alles gibt. (YogiTea Teebeutel Weisheit ;-) )
jerch
User
Beiträge: 1669
Registriert: Mittwoch 4. März 2009, 14:19

Darf man fragen, wofür Du das brauchst? Normalerweise kümmert sich der Terminalemulator um die Cursorbelange. Für den Fall , dass Dein Programm sich selbst drum kümmern soll, gibts curses. Mir scheint, Du möchtest ein Pferd von hinten aufzäumen, aber vllt. versteh' ich Dich auch falsch.
mutetella
User
Beiträge: 1695
Registriert: Donnerstag 5. März 2009, 17:10
Kontaktdaten:

@jerch:
Für Eingaben in meinem Kalender bietet mir 'raw_input()' bzw. 'input()' etwas zu wenig (z. B. Eingabe auf bestimmte Länge oder type beschränken, newline verhindern etc.).
'curses' oder 'urwid' sind dazu allerdings wieder zu viel des Guten. Zudem kann ich Methoden wie curses' 'getch()' erst dann verwenden, wenn ich das aktuelle Terminalfenster vorübergehend aufgebe.
Und: Es macht Spaß und ist sehr lehrreich (auch dank Deiner Hilfe bisher), dem Terminal mal unter die Decke zu schauen...

mutetella
Entspanne dich und wisse, dass es Zeit für alles gibt. (YogiTea Teebeutel Weisheit ;-) )
jerch
User
Beiträge: 1669
Registriert: Mittwoch 4. März 2009, 14:19

Um zeichenweise an den Input zu kommen, musst Du ja den kanonischen Modus abstellen. Ansonsten wirst Du auch das NL nicht los. Bei der Gelegenheit würde ich den Echomodus auch abstellen und die Repräsentation des Terminals komplett ins Programm verlegen, also auch das Wissen um die Cursorposition. Den Cursor selbst kannst Du mit Escape-Sequenzen bewegen, leider sind die nicht terminalübergreifend gleich. Die Emulatoren unter X benutzen quasi alle die xterm-Syntax, so dass Du diese mit einheitlichen Sequenzen steuern kannst. Für andere Tasten (Pfeil- und Funktionstasten etc.) ist es dann nicht mehr so. Genau aus diesem Grund gibt es curses. Es hat eine DB der verschiedenen Terminals mit deren Funktionalität und mappt die Eigenheiten auf ein standardisiertes API und macht so dem Programmierer das Leben leichter.
Wenn Du dann die Zeichen von STDIN gelesen und geparst hast, kannst Du sie aufs Terminal rausschreiben. Die neue Cursorposition kennst Du implizit vom zu schreibenden String. ABER: Die Stringlänge ist nicht gleich Offset der Cursorposition, da es Steuerzeichen ohne Ausgaberepräsentation (z.B Escape-Sequenzen) und nicht zu letzt Multibytezeichen (Utf8 lässt grüßen) gibt. Die Bestimmung der korrekten Länge ist also ziemlich aufwändig.

Ich hatte mal ein kleines Snippet für die Benutzung der Pfeil- und Funktionstasten geschrieben, vllt. findest Du da die ein oder andere Anregung --> http://www.python-forum.de/viewtopic.ph ... 52#p179152
Antworten