Question:
How could I repeatedly refresh a progress bar in visual basic while a function is running?
fortebass1
2010-07-06 07:03:02 UTC
I have a function that tests a connection to a SQL server with the parameters given by the user. If the parameters are correct, the connection test takes very little time to complete, but if the parameters are incorrect, my program pretty much locks up and takes around 15-20 seconds before my error message tells the user that the parameters are wrong. So I want to add a progress bar so that the user knows that the program is working. Since it can take any amount of time and it varies, I'm going to use a marquee style progress bar and just change the 'visible' property as needed.

So I want to show the progress bar before I attempt the connection test, which is a function that I call, and hide the progress bar after the function is complete. But since the form locks up when the function is working, the progress bar does not show until the error message is displayed. So is there a way for me to refresh the progress bar to the point that it moves while it's visible? Below is my snippet of code, pbarProgress is my progress bar.

pbarProgress.Visible = True

'checks the connection for integrity
Try
If connCheck(BackupPath, ServerName, ServerUserID, ServerPassword) = 0 Then
txtBackupPath.Focus()
Exit Sub
End If
'MsgBox("Connection confirmed")
pbarProgress.Visible = False
Try
'creates an .xml that holds the configuration data
writeConfigurations(BackupPath, ServerName, ServerUserID, ServerPassword, NewDBName)
MsgBox("Configuration Completed")

frmMain.Visible = True
Me.Visible = False
Catch ex As Exception
MsgBox("Failed to create configuration" & vbCrLf & ex.Message)
Exit Sub
End Try
Five answers:
?
2010-07-06 11:12:28 UTC
When your computer is running a procedure (Subroutine or Function) any events that are triggered while its running are placed into a cue and will run in the order they were called AFTER the procedure completes.



When you set the progress bar visible property to true you end up triggering several events which relate to redrawing / repainting the form and its controls on the screen. As you have found out these events are not run until the current procedure finishes and allows the code to branch away and execute the next waiting procedure..



You have two options.



1.) Call the My.Application.DoEvents method periodically from within your running procedure. Upon calling this method you will allow the code execution to branch away and execute another procedure (such as refreshing the screen via a repaint) if one or more are awaiting execution. Upon completion of these outstanding events control is returned to your procedure where it continues to run to completion or handline of another DoEvents call.



To allow the animation of the progress bar to function you would also have to periodacially call DoEvents from within a loop. A Do/While Loop that loops while the connection is NOT open and has a means of terminating the loop via a counter is very easy to code.



2.) The other way is to start another thread that runs independently of the main program. This new thread will handle the display of a progress bar on a new form.







edit:



Here is an example of using a timer to update a counter variable which in turn is used to control a Do/While Loop.

The code would other wise enter an infinite loop were it not for the use of a DoEvents call which allows the code to branch away and handle the timer TICK event which increments the counter variable .



To make this loop more effective for your code you would exit this loop when the connect becomes open OR when the loop times out .



Public Class Form1

Private m_cntLimit As Integer



Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

Dim TimeLimit As Integer



pbarProgress.Visible = True

m_cntLimit = 0

TimeLimit = 120



Do While m_cntLimit < TimeLimit

My.Application.DoEvents()

Label1.Text = m_cntLimit

Loop



MsgBox("end")

pBarProgress.Visible = False



End Sub



Private Sub tmrLimit_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles tmrLimit.Tick

'timer is enabled and set for an interval of 250

m_cntLimit = m_cntLimit + 1



End Sub

End Class
Pfo
2010-07-06 10:28:50 UTC
Since you know the operation takes 15-20 seconds, spawn off a thread that updates every second or so and updates the progress bar. Testing a SQL connection is a blocking call, so another thread is going to have to update the progress bar.
yamamoto
2016-12-10 22:20:23 UTC
Vb6 Progress Bar
2016-04-12 04:26:16 UTC
No progress bars in VB 6. Not portable edition, at least.
2010-07-06 07:22:15 UTC
Try using pbarProgress.update after you change the visibility, before starting the connection check.


This content was originally posted on Y! Answers, a Q&A website that shut down in 2021.
Loading...