For a former-insider's point of view on General Electric's announcement to create new GIS applications on the Oracle stack, see Peter Batty 's Thoughts on GE's next generation system based on Oracle - part 1.
I plan to write some more about this myself in the coming weeks, particularly as it relates to a recent demo I saw of the system running on Oracle.
Dedicated to sharing interesting news and innovations related to GE Smallworld GIS software. This blog is not related to, endorsed by or supported by General Electric.
Wednesday, June 27, 2007
Friday, June 22, 2007
progress counters and dialogs
I recently had a colleague ask me how to pop up a progress bar dialog to indicate to a user the percentage complete of a process. I did not know how to answer that at first... Smallworld has historically not used progress bar dialogs as much as some users would expect. So I will present two options for showing progress status.
Text-based process
If you have some kind of text based process use progress_counter...
... you can also ask the progress_counter to report at a given time interval...
If you want to use a more user-friendly indicator, use the progress_indicator_dialog. It is loaded into the core 4.1 image and you can find details about it in the header of product/modules/sw_core/progress_manager/source/progress_indicator_dialog.magik

And there you have it... easy ways to let your users know the progress of a process.
Text-based process
If you have some kind of text based process use progress_counter...
_block
_local some_collection << rope.new(20)
# create a progress_counter class that reports every 5
# increments. Because we know some_collection.size we can also
# estimate completion time
_local pc << progress_counter.new_on_count(5,some_collection.size)
_for idx,an_el _over some_collection.fast_keys_and_elements()
_loop
# the write() and sleep() statements are here to make a simple
# example...
write(an_el)
_thisthread.sleep(1000)
# ... but the :next() method is important to let the
# progress_counter (aka PC) know that you have completed one
# iteration of the loop.
pc.next()
_endloop
_endblock
$
unset
unset
unset
unset
unset
Done 5 (15 left) time taken 5 seconds 297 milliseconds (ETC. 15 seconds 891 milliseconds ) average rate 0.9439305267
unset
unset
unset
unset
unset
Done 10 (10 left) time taken 10 seconds 625 milliseconds (ETC. 10 seconds 625 milliseconds ) average rate 0.9411844826
unset
unset
unset
unset
unset
Done 15 (5 left) time taken 15 seconds 812 milliseconds (ETC. 5 seconds 270 milliseconds ) average rate 0.9487724325
unset
unset
unset
unset
unset
Done 20 (0 left) time taken 21 seconds 15 milliseconds (ETC. 0 milliseconds ) average rate 0.9562876356
... you can also ask the progress_counter to report at a given time interval...
_block
_local some_collection << rope.new(20)
# create a progress_counter class that reports every 2
# seconds. Because we know some_collection.size we can also
# estimate completion time
_local pc << progress_counter.new_on_time(3,some_collection.size)
_for idx,an_el _over some_collection.fast_keys_and_elements()
_loop
# the write() and sleep() statements are here to make a simple
# example...
write(an_el)
_thisthread.sleep(1000)
# ... but the :next() method is important to let the
# progress_counter (aka PC) know that you have completed one
# iteration of the loop.
pc.next()
_endloop
_endblock
$
unset
unset
unset
Done 3 (17 left) time taken 3 seconds 125 milliseconds (ETC. 17 seconds 708 milliseconds ) average rate 0.9600000000
unset
unset
unset
Done 6 (14 left) time taken 6 seconds 250 milliseconds (ETC. 14 seconds 583 milliseconds ) average rate 0.9600000000
unset
unset
unset
Done 9 (11 left) time taken 9 seconds 359 milliseconds (ETC. 11 seconds 439 milliseconds ) average rate 0.9616468318
unset
unset
unset
Done 12 (8 left) time taken 12 seconds 453 milliseconds (ETC. 8 seconds 291 milliseconds ) average rate 0.9648530373
unset
unset
unset
Done 15 (5 left) time taken 15 seconds 578 milliseconds (ETC. 5 seconds 199 milliseconds ) average rate 0.9616468318
unset
unset
unset
Done 18 (2 left) time taken 18 seconds 703 milliseconds (ETC. 2 seconds 81 milliseconds ) average rate 0.9612351238
unset
unset
Done 20 (0 left) time taken 20 seconds 765 milliseconds (ETC. 0 milliseconds ) average rate 0.9612351238
If you want to use a more user-friendly indicator, use the progress_indicator_dialog. It is loaded into the core 4.1 image and you can find details about it in the header of product/modules/sw_core/progress_manager/source/progress_indicator_dialog.magik
_block
_local q << progress_indicator_dialog.new ( "Generating" )
q.interrupt_handler << handler.new ( _unset, _unset )
q.info_string << "The current series will contain approx 10 frames."
q.bar_label << "Generating frames..."
q.image << { :help, _unset }
q.activate ()
q.max_count << 10
_for n _over range(1,10,1)
_loop
_thisthread.sleep(1000)
q.progress_changed(n)
_endloop
_endblock
$

And there you have it... easy ways to let your users know the progress of a process.