Building User Interfaces With Tcl And Tk John Ousterhout
Tcl/Tk Tutorial, Part III
Outline
Structure Of A Tk Application
Frame Menubutton Canvas
Label Menu Scrollbar
Button Message Scale
Checkbutton Entry Listbox
Radiobutton Text ToplevelThe Widget Hierarchy [A series of images are missing here] ---
Types Of Windows [A series of images are missing here] ---
Creating Widgets
button .a.b -text Quit -command exit
scrollbar .x -orient horizontal
^ ^ ^ ... ^
class name | |
window name |
configuration optionsConfiguration Options
-activebackground -disabledforeground -justify -underline
-activeforeground -font -padx -width
-anchor -foreground -pady -wraplength
-background -height -relief
-bitmap -highlightbackground -state
-borderwidth -highlightcolor -takefocus
-command -highlightthickness -text
-cursor -image -textvariable - Loaded from ''RESOURCE_MANAGER'' property or ''.Xdefaults'' file.
- May be set, queried with ''option'' command.Widget Commands
button .a.b
.a.b configure -relief sunken
.a.b flash
scrollbar .x
.x set 0.2 0.7
.x getGeometry Management
[Missing graphic here showing relationship between a geometry manager and various inputs and outputs] ---
The Placer
place .x -x 0 -y 0
[missing graphic here]
place .x -x 1.0c -rely 0.5 -anchor w
[missing graphic here]
place .x -relx 0.5 -rely 0.5 -height 2c -anchor center
[missing graphic here]
place .x -relheight 0.5 -relwidth 0.5 -relx 0 -rely 0.5
[missing graphic here]
The Packer
[missing graphics showing how use of the packer allows you to pick cavity, slice off parcels for slave, grow slaves, and position slave]
The Packer: Choosing Sides
button .ok -text OK
button .cancel -text Cancel
button .help -text HElp
pack .ok .cancel .help '''-side left'''[missing graphic]
.cancel configure -text "Cancel Command"
[missing graphic]
pack .ok .cancel .help '''-side top'''
[missing graphic]
The Packer: Padding
pack .ok .cancel .help -side left '''-padx 2m -pady 1m'''
[missing graphic]
pack .ok .cancel .help -side left '''-ipadx 2m -ipady 1m'''
[missing graphic]
pack .ok .cancel .help -side left '''-padx 2m -pady 1m -ipadx 2m -ipady 1m'''
[missing graphic]
The Packer: Filling
Stretch widgets to fill parcels:
pack .ok .cancel .help -side top
[missing graphic]
pack .ok .cancel .help -side top '''-fill x'''
[missing graphic]
pack .menu -side top
pack .scrollbar -side right
pack .listbox[missing graphic]
pack .menu -side top '''-fill x'''
pack .scrollbar -side right '''-fill y'''
pack .listbox[missing graphic]
The Packer: Expansion
Increase parcel size to absorb extra space in master:
pack .okay .cancel .help -side left
[missing graphic]
pack .ok .cancel -side left
pack .help -side left '''-expand true'''[missing graphic]
pack .ok .cancel -side left
pack .help -side left '''-expand true -fill x'''[missing graphic]
pack .ok .cancel .help -side left '''-expand true'''
[missing graphic]
pack .ok .cancel .help -side left '''-expand 1 -fill both'''
[missing graphic]
Hierarchical Packing
Use additional frames to create more complex arrangements:
frame .left
pack .left -side left -padx 3m -pady 3m
frame .right
pack .right -side right -padx 3m -pady 3m
foreach size {8 10 12 18 24} {
radiobutton .pts$size -variable pts \
-value $size -text "$size points"
}
pack .pts8 .pts10 .pts12 .pts18 .pts24 \
-in .left -side top -anchor w
checkbutton .bold -text Bold \
-variable bold
checkbutton .italic -text Italic \
-variable italic
checkbutton .underline -text Underline \
-variable underline
pack .bold .italic .underline \
-in .right -side top -anchor w[missing graphic]
Connections
button .a.b -command exit
At the button release, exit the application scrollbar .s -command ".text yview"
Upon a click on the scrollbar arrow, invoke the command:
.text yview scroll 1 unitBindings
bind .b <Control-h> {backspace .t}
^ ^ ^
| | |
window(s) Event Script - Name of window: .b
- Widget class: Text
- All windows: all
- Arbitrary string: foo, bar, ...Bindings: Specifying Events
a
<3>
<KeyPress>
<Double-Control-ButtonPress-1>
^ ^ ^ ^
| | | |
Modifiers Event type |
Button or KeysymBindings: Substitutions
- Coordinates from event: %x and %y.
- Window: %W.
- Character from event: %A.
- Many more... bind .c <B1-Motion> {move %x %y}
bind .t <KeyPress> {insert %A}
bind all <Help> {help %W}Binding Order
bind .t a ...
bind all <KeyPress> ... bindtags .b {MyButton .b foo all}More On Bindings
- Associate tags with text or graphics:
.t tag add foo 1.0 2.0
.c create rect 1c 1c 2c 2c -tags foo
- Associate bindings with tags:
.t bind foo <1> {...}
.c bind foo <Enter> {...}- If binding created in procedure, procedure's local variables aren't available at event- time.
Quoting Hell
bind .x <1> {set y [expr $a + $b]}
bind .x <1> "set y [expr $a + $b]"
proc sety a {
global b y
set y [expr $a + $b]
}
bind .x <1> [list sety $a]Other Tk Commands
selection get selection get FILE_NAME
send tgdb "break tkEval.c:200" winfo interps
winfo width .x winfo children . winfo containing $x $y
Access To Other X Facilities
focus .x.y
wm title . "Editing main.c" wm geometry . 300x200 wm iconify .
destroy .x
grab .x grab release .x
Example #1: showVars
showVars .vars name age ssn phone
proc showVars {w args} {
toplevel $w
wm title $w "Variable values"
frame $w.menu -relief raised -bd 2
pack $w.menu -side top -fill x
menubutton $w.menu.file -text File \
-menu $w.menu.file.m -underline 0
pack $w.menu.file -side left
menu $w.menu.file.m
$w.menu.file.m add command -label Quit \
-command "destroy $w" -underline 0
...
}
proc showVars {w args} {
...
frame $w.bot -relief raised -bd 2
pack $w.bot -side bottom -fill both
label $w.bot.title -width 20 -anchor center \
-text "Variable values:" -font \
-Adobe-Helvetica-Medium-r-normal--*-180-*-*-*-*-*-*-
pack $w.bot.title -side top -fill x
...
}
proc showVars {w args} {
...
foreach i $args {
frame $w.bot.$i
pack $w.bot.$i -side top -anchor w
label $w.bot.$i.name -text "$i: "
label $w.bot.$i.value -textvariable $i
pack $w.bot.$i.name -side left
pack $w.bot.$i.value -side left
}
}
showVars .vars name age ssn phoneExample #2: mkDialog Creates dialog box, waits until button pressed, returns index.
mkdialog .d "File Modified" $msg warning \
"Save File" "Discard Changes" "Return To Editor"
proc mkDialog {w title text bitmap args} {
toplevel $w
wm title $w $title
wm protocol $w WM_DELETE_WINDOW { }
frame $w.top -relief raised -bd 1
pack $w.top -side top -fill both
frame $w.bot -relief raised -bd 1
pack $w.bot -side bottom -fill both
label $w.msg -wraplength 3i -text $text \
-justify left -font \
-Adobe-Times-Medium-R-Normal--*-180-*-*-*-*-*-*
pack $w.msg -in $w.top -side right \
-expand 1 -fill both -padx 3m -pady 3m
...
}
proc mkdialog {w title text bitmap args} {
...
if {$bitmap != ""} {
label $w.bitmap -bitmap $bitmap
pack $w.bitmap -in $w.top -side left \
-padx 3m -pady 3m
}
...
}
proc mkDialog {w title text bitmap args} {
...
set i 0
foreach but $args {
button $w.button$i -text $but \
-command "set button $i"
pack $w.button$i -in $w.bot -side left \
-expand 1 -padx 3m -pady 2m
incr i
}
...
}
proc mkDialog {w title text bitmap args} {
global button
...
grab $w
set oldFocus [focus]
focus $w
tkwait variable button
destroy $w
focus $oldFocus
return $button
}Summary
- Create widgets.
- Arrange with geometry managers.
- Connect to application, each other. - For specifying user interface.
- For widgets to invoke application.
- For widgets to communicate with each other.
- For communicating with outside world.
- For changing anything dynamically.