Search code examples
vb.netmultithreadingbackgroundworker

Main form freezing due to backgroundwork


Scenario: I am making a login form which connects to a MySQL database for account and password confirmation.

Trying: I am trying to show an animated loading gif and a loading text while the form is connecting and getting the result from the database.

Did so far: So I used background worker: The Login button:

Private Sub LoginBtn_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles LoginBtn.Click
    PictureBox2.Visible = True
    Label6.Visible = True
    BackgroundWorker1.RunWorkerAsync()
End Sub

Background worker DoWork:

 Private Sub BackgroundWorker1_DoWork(sender As Object, e As DoWorkEventArgs) Handles BackgroundWorker1.DoWork
    AccessControl()
End Sub


Private Sub AccessControl()
    If Me.InvokeRequired Then
        Me.Invoke(New MethodInvoker(AddressOf AccessControl))
    Else
        con.Open()
        Dim user, pass As String
        user = UserNameBox.Text
        pass = Crypt(PasswordBox.Text)
        cmd = New MySqlCommand("SELECT * FROM users WHERE Name ='" + user + "' And Password ='" + pass + "'", con)
        dr = cmd.ExecuteReader
    End If
End Sub

Background RunWorkerCompleted:

 Private Sub backgroundWorker1_RunWorkerCompleted(sender As Object, e As RunWorkerCompletedEventArgs) Handles BackgroundWorker1.RunWorkerCompleted
    If (dr.Read()) Then
        FadingForm()

    Else
        PictureBox2.Visible = False
        Label6.Visible = False
        WrnPnl.Visible = True
        WrnLbl.Visible = True
        WrnPnlImg.Visible = True
        PasswordBox.Text = ""
        UserNameBox.Text = ""
        UserNameBox.Focus()
    End If

    con.Close()
End Sub

What should happen: After entering the credentials when the user clicks the login button the animated loading gif and the loading text should appear and the background process should start, if the credentials are right FadingForm() should be fired or if not then the else part should.

Problem: The problem is When I press the Login button after entering the corrent credentials, the loading gif and text shows up but the form freezes. And after the process is completed the main form gets back to normal. I am sure the form freezes as the animated gif stops animating and non of the controls are usable. I have no idea what could be the possible reason or how it can be fixed.

Any help would be appreciated. Thanks a ton!


Solution

  • The very first thing you do inside your background worker is force all the work back to the UI thread. This is why it's hanging your UI.

    If Me.InvokeRequired Then
        Me.Invoke(New MethodInvoker(AddressOf AccessControl))
    

    You should only invoke the access to the UI, not the sql work. Since you need access to the username and password fields you should pass them as arguments, or pull them out of the their controls and in to local variables BEFORE the background worker begins. That way you can access their values without having to invoke anything.

    Declare user and pass at the form level and, do this inside the click event.

        user = UserNameBox.Text
        pass = Crypt(PasswordBox.Text)