Wer das Tk-Textwidget in eigenen Programmen nur zum Anzeigen von Ascii-Text nutzt, ahnt vielleicht nicht, was in diesem unscheinbaren Multitalent alles steckt. Es fungiert als Editor inklusive Undo-Funktion, beherrscht viele Formatierungen und Schriften, bettet weitere Widgets ein und Interaktionen lassen sich für jeden einzelnen Buchstaben programmieren. Das Widget unterstützt jede wichtige Aktion zur Textdarstellung und -Bearbeitung, daher dient es seit Jahren als Basis für ausgewachsene Editoren wie den Source-Navigator[1].
Einfacher Editor
Listing 1 enthält einen einfachen Editor, wie er in Abbildung 1 zu sehen ist. Mit ihm öffnet und speichert der Benutzer normale Textdateien. Der Aufruf in Zeile 5 erzeugt das Textwidget und verbindet es mit den beiden Scrollbars, die in Zeile 8 und 9 angelegt werden. Darauf folgt ein Label, das den Namen der geöffneten Datei zeigt. Die Zeilen 12 bis 20 kümmern sich um das Layout-Management, also um das automatische Anordnen der Widgets im Fenster.
01 #!/usr/bin/wish
02 package require Tk
03
04 # GUI erzeugen
05 text .text -bg white -undo yes -wrap word
06 -yscrollcommand ".vscroll set"
07 -xscrollcommand ".hscroll set"
08 scrollbar .hscroll -orient horizontal -command ".text xview"
09 scrollbar .vscroll -orient vertical -command ".text yview"
10 label .status -font 8 -textvariable ::currentFile
11
12 grid .text .vscroll -sticky nesw
13 grid .hscroll -sticky ew
14 grid .status -sticky ew
15
16 grid rowconfigure . 0 -weight 1
17 grid rowconfigure . 1 -weight 0
18 grid rowconfigure . 2 -weight 0
19 grid columnconfigure . 0 -weight 1
20 grid columnconfigure . 1 -weight 0
21
22 # Menü erzeugen
23 menu .menu
24 . configure -menu .menu
25
26 menu .menu.file -tearoff 0
27 .menu add cascade -menu .menu.file -label "Datei"
28 .menu.file add command -label "Öffnen" -command openFile
29 .menu.file add command -label "Speichern unter..." -command saveFileAs
30 .menu.file add separator
31 .menu.file add command -label "Beenden" -command {exit 0}
32
33 menu .menu.edit -tearoff 0
34 .menu add cascade -menu .menu.edit -label "Edit "
35 .menu.edit add command -label "Rückgängig machen "
36 -command {.text edit undo}
37 .menu.edit add command -label "Wiederherstellen "
38 -command {.text edit redo}
39 .menu.file add separator
40 .menu.edit add command -label "Euro-Symbol einfügen"
41 -command {.text insert "insert" u20ac}
42 .menu.edit add command -label "Zeile löschen"
43 -command {.text delete "insert linestart" "insert lineend"}
44 .menu.edit add command -label "Zum Zeilenanfang"
45 -command {.text mark set insert "insert linestart"}
46
47 set dateitypen {
48 {"Textdateien" {.txt} }
49 {"Tcl-Skripte" {.tcl} }
50 {"C-Dateien" {.c .h} }
51 {"Alle Dateien" *}
52 }
53
54 proc openFile {} {
55 while {true} {
56 set fileName [tk_getOpenFile -filetypes $::dateitypen]
57 if {[string length $fileName] == 0} {
58 break
59 } elseif {[file exists $fileName] && [file readable $fileName]} {
60 set fd [open $fileName r]
61 .text delete 1.0 end
62 .text insert 1.0 [read $fd]
63 close $fd
64 set ::currentFile $fileName
65 break
66 } else {
67 tk_messageBox -icon error -title "Lesefehler"
68 -message "Datei «$fileName» kann nicht gelesen werden"
69 }
70 }
71 }
72
73 proc saveFileAs {} {
74 while {true} {
75 set fileName [tk_getSaveFile -filetypes $::dateitypen
76 -initialfile [file tail $::currentFile]]
77 if {[string length $fileName] == 0} {
78 break
79 } elseif {[catch {
80 set fd [open $fileName w]
81 puts -nonewline $fd [.text get 1.0 "end -1c"]
82 close $fd
83 } err]} {
84 set antwort [tk_messageBox -type retrycancel
85 -icon error -title "Fehler"
86 -message "Beim Abspeichern trat ein Fehler auf:n$err"]
87 if {[string match "cancel" $antwort]} {
88 break
89 }
90 set $fileName ""
91 } else {
92 set ::currentFile $fileName
93 break
94 }
95 }
96 }
|
Abbildung 1: Der Editor aus Listing 1 zeigt wichtige Funktionen des Textwidgets. Er öffnet und schreibt Dateien und beherrscht unbegrenztes Undo und Redo.
Undo inklusive
Neben den üblichen Optionen wie Farben und Darstellung der Ränder kennt das Textwidget ein Reihe eigener Optionen. Mit »-undo yes« ist der eingebaute Undo-Mechanismus aktivierbar, »-wrap Variante« gibt an, wie Textzeilen darzustellen sind, die nicht in die Breite des Widgets passen. Zur Auswahl stehen dafür der Umbruch nach ganzen Wörtern »word«, buchstabenweise »char« oder kein Umbruch »none«.
Das Textwidget bietet per Default die plattformüblichen Tastenkombinationen zum Bewegen des Cursors, Ausschneiden, Kopieren oder Rückgängigmachen. Der Benutzer greift also in die gewohnten Tasten oder zur Maus, um Texte zu schreiben und zu bearbeiten.
Dem Tcl-Skript bietet das Textwidget einige Kommandos, um Text auszulesen, einzufügen oder zu löschen. Diese Befehle benötigen ein oder zwei Positionsangaben, um die gewünschte Stelle zu benennen. Am einfachsten ist die absolute Angabe von Zeile und Buchstabe, durch einen Punkt getrennt. Die Zeilennummern beginnen bei 1, die Spalten bei 0, die linke obere Ecke ist daher »1.0«. Diese Zählung ist zwar nicht besonders konsequent, deckt sich aber mit den meisten Unix-Editoren.
Der Programmierer kann Positionen auch durch so genannte Marken definieren. Eigene Marken setzt er per ».text mark set Name Position« in das Widget. Beim Ändern des Textes verschieben sich die Marken wie normale Buchstaben, bleiben selbst aber unsichtbar. Zwei Marken sind in jedem Textwidget vorhanden, »insert« und »end«. Die Insert-Marke bezeichnet die aktuelle Position des Cursors, die End-Marke folgt nach dem letzten Zeichen des Textes.
« Zurück
1
2
3
4
5
Weiter »