How do I use a Progress Bar?

Learn how to use a progress bar while importing or exporting a file. Sample code is provided.

Introduction

Progress bars are often used to provide a graphical indication of an action measured against time for an ongoing process, such as when transferring files. Here we demonstrate how to implement a progress bar that can be used when importing and exporting a file.

Creating the Interface

Creating the Interface

Create a new main stack with two buttons. One button should be labeled Import, the other button should be labeled Export. Then add the progress bar. In a working application, it may be more appropriate to add the file selection dialog, rather than the Import and Export buttons.

The properties of the progress bar are widely configurable. By default the range is set from 0 to 100, with the current value set to 50. For the purpose of this lesson, set the current value to 0. This allows the progress bar to be updated with percentiles.

Note: A range from 0 to 100 is convenient if the percentage values are to be displayed in numerical terms next to the progress bar.

The Import Button

Much of the code in this example is used to determine the size of the file. The repeat loop then reads in the file in 1024 character chunks until the end of file (eof) marker is reached. As the file is read, a counter is incremented to keep track of the amount of data transferred. That value is then used to update the current value of the progress bar.

on mouseUp
	global gFileContents
	# the location of the source file
	# update this line as required
	local tImportFileName = "C:/Users/DaveC/Documents/import_me.txt"
	put empty into gFileContents
	set the thumbPosition of scrollbar "Progress Scrollbar" to 0
	# this section of code is used to find the file size and track
	# the progress while reading in the file
	set the itemDel to slash
	put item 1 to -2 of tImportFileName into tPath
	put item -1 of tImportFileName into tFileName
	set the directory to tPath
	put the detailed files into tFiles
	# the file name is URL-encoded when using the detailed files 
	# we have to match the encoding here
	filter tFiles with URLEncode(tFileName) & "*"
	set the itemDel to comma
	put item 2 of line 1 of tFiles into tFileSize
   
	open file tImportFileName for read
	put empty into tReadResult
	put 0 into tAmountRead
	repeat while tReadResult is not "eof"
		read from file tImportFileName for 1024 # read 1k characters
		put the result into tReadResult
		put it after gFileContents
		add length(it) to tAmountRead
		# the following line updates the current position of the progress bar
		set the thumbPosition of scrollbar "Progress Scrollbar" to (tAmountRead/tFileSize)*100
	end repeat
	# if the file uses LF + CR to mark EOL it will be converted to just one of these
	# characters here
	# this means that tAmountRead is slightly smaller than tFileSize
	# compensate for this mismatch by setting the progress bar to 100
	set the thumbPosition of scrollbar "Progress Scrollbar" to 100
	close file tImportFileName
end mouseUp

The Export Button

As the file is already in memory, it is not necessary to calculate the download size. The export process writes to the file line by line from the internal memory buffer.

on mouseUp
	global gFileContents
	# the location of the target file
	# update this line as required
	local tExportFileName = "C:/Users/DaveC/Documents/export_me.txt"
	open file tExportFileName for write
	set the thumbPosition of scrollbar "Progress Scrollbar" to 0
	put number of lines of gFileContents into tNumLines
	put 0 into tLineCounter
	repeat for each line tLine in gFileContents
		add 1 to tLineCounter
		write tLine & return to file tExportFileName
		# the following line updates the current position of the progress bar
		set the thumbPosition of scrollbar "Progress Scrollbar" to (tLineCounter/tNumLines)*100
	end repeat
   
	close file tExportFileName
end mouseUp

Progress Bar Operation

The progress bar should be working now. Use the Import button to load a file into memory and use the Export button to write the file back out to the file system.

If you get an error something like

button "Import": execution error at line 30 (Operators /: divide by zero), char 1

check that you changed the filepath to the file you are importing to something valid on your computer. You can't import Dave's actual file :).

7 Comments

Regan

This is helpful but the code in the input button doesnt work properly, it keeps telling me to debugg this
" set the thumbPosition of scrollbar "Progress Scrollbar" to (tAmountRead/tFileSize)*100 " im not the greatest at codeing and have just started using live code at school, could you tell me what im doing wrong

Hanson Schmidt-Cornelius

Hi Regan,

you are getting this error message because tFileSize is not set. You need to specify the input file you want to load. You have to change the following lines in the code to point to a text file on your filesystem:

local tImportFileName = "C:/Users/DaveC/Documents/import_me.txt"

The following line has to be updated to point to a file you want to write:

local tExportFileName = "C:/Users/DaveC/Documents/export_me.txt"

Kind Regards,

Hanson

Francis Nugent Dixon

Great Stuff - takes the mystery out of file copies with a progress bar. Allows us to give that professional look to a file copy.

Thanks !

Ross Waumsley

When I test the import button this error comes up in the script window

button "Import": execution error at line 32 (Operators /: divide by zero), char 69

what do i need to do to fix the problem and what is the problem. I am new to coding and am struggling to fix it on my own.

Mark Wieder

See the comment about needing to select a file - what's happening is that the fileSize is 0, and so you're getting an error on the division. There are a few ways to do defensive coding to handle this situation. The easiest is to insert a line
after the line

put item 2 of line 1 of tFiles into tFileSize
-- insert this line
if tFileSize is 0 then exit mouseUp

Torsten Holmer

How can I find out the size of a file which is on the web? I need a classical download indicator like in Firefox

Elanor Buchanan

Hi Torsten

If you use libURLDownloadToFile to download your file you can use libURLSetStatusCallback to set a status message to be sent periodically while the file downloads. This message is sent with a parameter that inlcudes the status, downloaded bytes and total bytes which you can use to update a scrollbar.

Something along the lines of

on mouseUp pMouseButton
libURLSetStatusCallback "downloadUpdate", the long id of me
libURLDownloadToFile , , "DownloadComplete"
end mouseUp

on downloadUpdate pUrl, pStatus
set the endValue of scrollbar "progress" to item 3 of pStatus
set the thumbPosition of scrollbar "progress" to item 2 of pStatus
end downloadUpdate

Kind regards

Elanor

Add your comment

E-Mail me when someone replies to this comment