ulis, 2003-07-02: How to scroll two widgets at the same time. Or: synchronized listboxes.
Also see mention of the same subject in the FAQ for Tk.
# --------------- # multi scrolling # --------------- # creating the widgets frame .f foreach n {0 1 2 3 4 5 6 7 8 9} { lappend list1 item1-$n } foreach n {0 1 2 3 4 5 6 7 8 9} { lappend list2 item2-$n } listbox .f.lb1 -list ::list1 -height 8 -yscrollc yset listbox .f.lb2 -list ::list2 -height 8 -yscrollc yset scrollbar .f.sb -command yview # placing & showing the widgets pack .f grid .f.lb1 -row 0 -column 0 grid .f.lb2 -row 0 -column 1 grid .f.sb -row 0 -column 2 -sticky ns # the scroll procs # called by a listbox proc yset {args} { eval [linsert $args 0 .f.sb set] yview moveto [lindex [.f.sb get] 0] } # called by the scroll bar proc yview {args} { eval [linsert $args 0 .f.lb1 yview] eval [linsert $args 0 .f.lb2 yview] }
Or rewritten to use {*}:
# called by a listbox proc yset {args} { .f.sb set {*}$args yview moveto [lindex [.f.sb get] 0] } # called by the scroll bar proc yview {args} { .f.lb1 yview {*}$args .f.lb2 yview {*}$args }
JMD, 2006-06-13, Just to clarify, this technique does work with other widgets, such as horizontally scrolling a text box and an entry field (using xview and xset, of course).
ulis, 2003-08-05: Better to have the selection synchronized.
# --------------- # multi selecting # --------------- # creating the widgets foreach n {0 1 2 3 4 5 6 7 8 9} { lappend list1 item1-$n } foreach n {0 1 2 3 4 5 6 7 8 9} { lappend list2 item2-$n } frame .f -relief sunken -bd 2 -highlightt 0 listbox .f.lb1 -list ::list1 -height 8 -yscrollc yset \ -relief flat -selectbord 0 -highlightt 0 -bd 0 \ -exportselection 0 listbox .f.lb2 -list ::list2 -height 8 -yscrollc yset \ -relief flat -selectbord 0 -highlightt 0 -bd 0 \ -exportselection 0 canvas .f.c -width 1 -height 0 -relief flat -selectbord 0 -highlightt 0 -bd 0 scrollbar .f.sb -command yview # placing & showing the widgets pack .f grid .f.lb1 -row 0 -column 0 grid .f.c -row 0 -column 1 grid .f.lb2 -row 0 -column 2 grid .f.sb -row 0 -column 3 -sticky ns # the scroll procs # called by a listbox proc yset {args} { eval [linsert $args 0 .f.sb set] yview moveto [lindex [.f.sb get] 0] } # called by the scroll bar proc yview {args} { eval [linsert $args 0 .f.lb1 yview] eval [linsert $args 0 .f.lb2 yview] } # bind to the select events bind .f.lb1 <<ListboxSelect>> { synchro .f.lb1 .f.lb2 } bind .f.lb2 <<ListboxSelect>> { synchro .f.lb2 .f.lb1 } proc synchro {w1 w2} { set sel [$w1 cursel] $w2 selection clear 0 end foreach item $sel { $w2 selection set $item } }