Tcl vwait Command
last modified October 20, 2026
The Tcl vwait command is used to wait for variable modifications
in the event loop. It's essential for event-driven programming in Tcl.
Basic Definition
The vwait command enters the event loop and waits until a specified
variable is modified. It processes events while waiting for the change.
Syntax: vwait varName. The command blocks until varName
is written or unset. Setting the variable to the value it already has also
counts. The code that follows the vwait does not run until then,
but other events (timers, file events, GUI events) are processed meanwhile. If
nothing ever modifies the variable, vwait waits forever.
Simple vwait Example
This demonstrates the basic usage of vwait to wait for a variable
change.
set done 0
after 1000 {set done 1}
puts "Waiting for variable change..."
vwait done
puts "Variable changed, continuing execution"
This script sets a timer to modify done after 1 second. The
vwait blocks until this change occurs, then continues execution.
vwait with User Input
vwait can be used to wait for user input in console applications.
set input ""
puts "Enter some text and press Enter:"
fileevent stdin readable {set input [gets stdin]}
vwait input
puts "You entered: $input"
This example sets up a file event handler for stdin. vwait waits
until the user enters text and presses Enter, storing the input in the variable.
When standard input is empty or closed, as in this run, the handler fires at
once with end-of-file and stores an empty string.
vwait with Socket Communication
vwait is commonly used in network programming to wait for data.
set response ""
set sock [socket -async www.example.com 80]
fconfigure $sock -buffering none
fileevent $sock readable {set response [read $sock 4096]}
puts -nonewline $sock "GET / HTTP/1.1\r\nHost: www.example.com\r\nConnection: close\r\n\r\n"
vwait response
puts "Received [string length $response] bytes"
close $sock
This creates an asynchronous socket connection and stores its channel in
sock. The request is sent and vwait blocks until
data is received and stored in response. The event loop processes
network events while waiting.
vwait in GUI Applications
In Tk applications, vwait can be used to wait for GUI events.
package require Tk
set clicked 0
button .btn -text "Click Me" -command {set clicked 1}
pack .btn
puts "Waiting for button click..."
vwait clicked
puts "Button was clicked!"
This creates a simple Tk button. The script waits with vwait until
the button is clicked, which sets the clicked variable to 1.
Sequential vwait Commands
Several vwait commands can follow each other to wait for a series
of events.
set step1 0
set step2 0
after 500 {set step1 1}
after 1000 {set step2 1}
puts "Waiting for first event..."
vwait step1
puts "First event received, waiting for second..."
vwait step2
puts "Both events received"
This demonstrates vwait commands waiting for sequential
events. Each vwait processes events until its variable is set.
These calls are not nested; they run one after the other. If a
vwait were started inside an event handler while another
vwait is waiting, the inner one would have to return before the
outer one could.
vwait with Multiple Variables
In Tcl 8.6 vwait takes just one variable. To wait for any of
several variables, a trace on each of them can set one common variable.
set event1 0
set event2 0
after 800 {set event1 1}
after 1200 {set event2 1}
proc wakeUp {args} {
set ::waiting 1
}
proc waitForAny {vars} {
global waiting
set waiting 0
foreach var $vars {
trace add variable ::$var write wakeUp
}
vwait waiting
foreach var $vars {
trace remove variable ::$var write wakeUp
}
}
puts "Waiting for either event..."
waitForAny {event1 event2}
puts "An event occurred: event1=$event1, event2=$event2"
This advanced example shows how to wait for changes to any of several variables.
It uses write traces on the watched variables; each trace sets the global
variable waiting, which is the one vwait waits for.
The traces are removed afterwards. The script continues as soon as
event1 changes after 800 ms, so event2 is still 0 when
the message is printed.
Best Practices
- Event Loop: Remember vwait enters the event loop.
- Nesting: Avoid calling
vwaitinside event callbacks; nested waits must finish in reverse order, and an outer wait can be held up by an inner one. - Timeouts: Consider adding timeout mechanisms for robustness.
- GUI: In Tk,
vwaitkeeps the interface responsive, but the code after it is suspended; Tk'stkwaitis the equivalent for windows. - Alternatives: For complex cases, consider coroutines.
This tutorial covered the Tcl vwait command with practical
examples showing its usage in different scenarios.
Author
List all Tcl Tutorials.