Simple Example

Some long-running database operations can periodically execute a callback function to inform the caller about the progress of the operation.

The typical usage is:

proc myProgress {w percent info} {
    puts "$w $percent $info"
    return 0
}
zprogress init myProgress .progress
zprogress begin
... zdb operation ...
zprogress end
zprogress finit

The initial zprogress init registers "myProgress" as callback function with ".progress" as first argument. The next zprogress begin enables progress calls for the following zdb operation. Here, the "…​zdb operation…​" will call myProgress with $w = ".progress" and two additional arguments $percent and $info. The 'percent' argument is set to a floating number between 0.0 and 1.0 (representing the progress done so far) and the 'info' argument is set to a text message that gives some hint about what the database is currently doing. The terminating zprogress end executes a final call to myProgress with percent = "END" and then resets the internal state.

Nested Example

If a combination of multiple database operations and a long running custom procedure should appear as one progress bar, then the typical usage is (assuming 4 operations, the first takes 60%, the second and the third take 20%):

zprogress begin
zprogress push "operation 1" 0.60
... zdb operation #1 ...
zprogress pop
if {![zprogress isinterrupted]} {
    zprogress push "operation 2"  0.80
    ... zdb operation #2 ...
    zprogress pop
    if {![zprogress isinterrupted]} {
        zprogress push "operation 3"  1.00
        set count 1000
        for {set i 0} {$i < $count} {incr i} {
            zprogress update "" $i $count
            # Do something
        }
        zprogress pop
    }
}
zprogress end
zprogress finit

The user can interrupt the current database operation. An interrupt is released if the callback procedure returns "1" (instead of "0"). If so, then the database operation will return with an error. The isinterrupted subcommand checks for this special condition. Please check out a full example here: demo/api/oem/interrupt.tcl.

API Commands

To manage progress callbacks the following API commands are supported.

zprogress begin

Enable progress calls for the following operation.


Usage:

zprogress begin


Parameters:

No parameters.


Example:

zprogress begin
# ...
zprogress end

zprogress check

Return true if the interrupted flag is set. Alias for zprogress isinterrupted.


Usage:

zprogress check ?setLastErrorMsg?


Parameters:

setLastErrorMsg (optional)

Write the text "interrupted" in the last error message.


Example:

if {[zprogress check]} {
    # the current progress has been interrupted by the user
}

zprogress end

Call progress callback with end mark and disable the progress bar.


Usage:

zprogress end


Parameters:

No parameters.


Example:

zprogress begin
# ...
zprogress end

zprogress finit

Delete registered progress callback.


Usage:

zprogress finit


Parameters:

No parameters.


Example:

proc my_callback {w ratio message} {
    puts "$w $ratio $message"
    return 0
}
zprogress init my_callback .progress 10 2
# ...
zprogress finit

zprogress init

Register a progress update callback procedure.


Usage:

zprogress init progressCallback pathName ?cbPerSec? ?firstDelay?


Parameters:

cbPerSec (optional)

Number of callback calls per second.

firstDelay (optional)

The number of first calls which where suppressed.

pathName

The widget path of the progress bar. This is appended as the first parameter to the progressCallback. May be the empty string if not needed.

progressCallback

The name of the progress callback procedure. When calling the callback, pathName, the current progress ratio (or END), and the current progress message are appended as parameters. If the callback returns 1/true the progress is interrupted.


Example:

proc my_callback {w ratio message} {
    puts "$w $ratio $message"
    return 0
}
zprogress init my_callback .progress
# ...
zprogress finit

zprogress isinterrupted

Return true if the interrupted flag is set.


Usage:

zprogress isinterrupted ?setLastErrorMsg?


Parameters:

setLastErrorMsg (optional)

Write the text "interrupted" in the last error message.


Example:

if {[zprogress isinterrupted]} {
    # the current progress has been interrupted by the user
}

zprogress istimeoutreached

Return true if the timeoutreached flag is set.


Usage:

zprogress istimeoutreached ?setLastErrorMsg?


Parameters:

setLastErrorMsg (optional)

Write the text "timeout reached" in the last error message.


Example:

if {[zprogress istimeoutreached]} {
    # the current progress has timeoutreached
}

zprogress pop

Pop range from the stack.


Usage:

zprogress pop ?-nocallback?


Parameters:

-nocallback (optional)

Do not run the registered progress callback.


Example:

zprogress push "progress at 10%" 0.1
# do some work
zprogress pop

zprogress push "progress at 50%" 0.5
# do some work
zprogress pop -nocallback

zprogress push

Push a new progress bar range to the stack.


Usage:

zprogress push msg ratio


Parameters:

msg

The push message to display.

ratio

The amount to push on the stack (0.0 …​ 1.0).


Example:

zprogress push "progress at 10%" 0.1
# do some work
zprogress pop

zprogress push "progress at 50%" 0.5
# do some work
zprogress pop

zprogress settimeout

Set the timeout period in msec. 0 = disable.


Usage:

zprogress settimeout timeout


Parameters:

timeout

timeout in msec. 0 = disable.


Example:

zprogress settimeout 10

zprogress timestep

Toggle runtime statistics.


Usage:

zprogress timestep enable


Parameters:

enable

Enable or disable the runtime statistic.


Example:

# enable runtime statistics (printed via `zmessage print DBG ...`)
zprogress timestep 1

# disable statistics
zprogress timestep 0

zprogress update

Update the progress bar (same as push/pop).


Usage:

zprogress update ?-nocallback? msg curItem totalItems


Parameters:

-nocallback (optional)

Do not run the registered progress callback.

curItem

The current processed item.

msg

The update message to display.

totalItems

The total number of items.


Example:

zprogress update "at item 17/100" 17 100
zprogress update -nocallback "at item 18/100" 18 100