Background Processing in VB

Posted on 1998-10-22
Last Modified: 2008-02-01
How do you code background processing in VB5?

I am designing an app where part of the app runs some serious mathematical code and takes hours to run.  I would like to place this processing in the background enabling the user to continue using the app.  I tried using an ActiveX EXE but am unable to return control back to the main app.

Can you please provide some example code?
Question by:sadkat

Expert Comment

ID: 1441237
McIx is better at this than I am, but this is how I understand how it works.  You create an object that runs on the server asyncronously.  You create this object where it has an event.  When it is done it raises an event.  The program that called it 'Dim'ed it with events.  So, when the object raises the event, the processing object can process the fact that it is done.  MTS or 'Remote Automation Manager' help you manage remote executing events.

Good Luck,

Expert Comment

ID: 1441238
Assuming he has a server?
LVL 14

Expert Comment

ID: 1441239
You could launch some threads to do the work.
MIM Survival Guide for Service Desk Managers

Major incidents can send mastered service desk processes into disorder. Systems and tools produce the data needed to resolve these incidents, but your challenge is getting that information to the right people fast. Check out the Survival Guide and begin bringing order to chaos.


Expert Comment

ID: 1441240

Waty is right for the threads,
but what I found quite effective is the good old shell
Shell is multithreaded, therefore pass the parameters
to your exe when you shell it.

Downside, what was 1 app, now becomes 2.
A shells B, B never works alone.

But in your case,
it is not that bad, A will contine to run letting the user
continue while B is calculating.


Expert Comment

ID: 1441241
With VB5 it is easy to your own ActiveX objects. These run in a separate thread from the main program. I personally think that the are usually the easiest way to get VB to do multithreading. If you create one that does the lengthy process then you will be able to leave it running. You could even have an event that the object can drive to tell you it has finished. I think this is probably what mkmccreary was referring to. Let me know if you need any help.

Author Comment

ID: 1441242
The Shell function is OK, but it does not allow me to pass variables and other infromation to the calculation app.  The variables passed come from the main app and will be different each time the calculation app is called.

LVL 13

Accepted Solution

Mirkwood earned 200 total points
ID: 1441243
Start a timer in your ActiveX server. This timer can be on a invisible form.
So the activeX server has a method DoSomething. DoSomething enables the timer. On the timer event you can do your stuff.
The server can launch an event when it is finished.

   Dim withevents myServer as MyActiveXServer
sub form_load
   set   myServer = new MyActiveServer
end sub

sub command1_click
end sub

sub myServer_Finished
   msgbox "Finished"
end sub

event Finished

public sub DoSomething
   timer1.enabled = true  
end sub

sub timer1_click
  timer1.enabled = false
  <Do your stuff>
  raiseevent Finished
end sub


Author Comment

ID: 1441244
Thank's for your help so far.  The code is working OK.


In the ActiveX server I want to minimize a form (already coded) and show the progress of the calc (% complete like an internet download) in the form's caption.

It seems once the focus is given back to the client I cannot update the ActiveX server form's caption.

Any ideas or code.  Thanks for your help!!

Author Comment

ID: 1441245
I'm able to set multiple calls of the calc app.  BUT the calls are working sequentially.  Call 2 must finish before call 1 finishes etc.


In Client :-

Private Sub mnuRun_Click()
  Dim myServer As TestActiveX.TestDCG
  Set myServer = New TestActiveX.TestDCG
End Sub

In Server :-

In Class Module:

Dim frm As New TestForm

Public Sub DoSomething()
  frm.Show vbModeless
  frm.WindowState = vbMinimized
  frm.Timer1.Enabled = True
End Sub

In Form:
Private Sub Timer1_Timer()
  Timer1.Enabled = False
  Unload Me
End Sub

Private Sub DoSims()
  Dim i As Long
  For i = 1 To 10000
    Caption = i
  Next i
End Sub

LVL 13

Expert Comment

ID: 1441246
The server still has one threat and can only handle one call at the time.

So you cannot start the next DoSomething until the previous one is finished.

Here are some things to think about.
1) Dim myServer As TestActiveX.TestDCG is declared local.
That means that it is immediatelly destroyed after you start DoSomething. Your DoSims is never executed. Make this a global variable.

2) Make sure that the timer is enabled = false and interval = 50
Otherwise your timer is already started before you give the command or is not started at all.

3) Here is a more elaborate example.
---- CLIENT FORM ----
Option Explicit
Dim WithEvents m_myserver As ActiveXExe ' Global declaration of the exe

Private Sub Command1_Click()
    On Error GoTo leave
    m_myserver.DoSomething   'Start exe, second call while busy will raise error
    Select Case Err.Number
        Case 0
        Case -1
            MsgBox "The server is busy, please wait"
        Case Else
            MsgBox Err.Description
    End Select
End Sub

Private Sub Form_Load()
    Set m_myserver = New ActiveXExe 'Create the server
End Sub

Private Sub Form_Unload(Cancel As Integer)
    Set m_myserver = Nothing 'Destroy the server
End Sub

Private Sub m_myserver_Finished(ByVal OK As Boolean)
    MsgBox IIf(OK, "Finished", "Aborted at " & m_myserver.progress) 'Notify user about server state
End Sub

Option Explicit

Dim WithEvents frm As Form
Dim WithEvents frmtimer As Timer
Dim fBusy As Boolean
Dim m_prg As Long

Public Event Finished(ByVal OK As Boolean)

Public Property Get Progress() As Integer
    Progress = m_prg
End Property

Public Sub DoSomething()
    If (fBusy = True) Then
        Err.Raise -1, , "Exe is Busy"
    End If
    fBusy = True
    frm.Show vbModeless
    frm.WindowState = vbMinimized
    frmtimer.Enabled = True
End Sub

Private Sub Class_Initialize()
    m_prg = 0
    Set frm = New Form1
    Set frmtimer = frm.Timer1
End Sub

Private Sub Class_Terminate()
    Unload frm
    Set frmtimer = Nothing
    Set frm = Nothing
End Sub

Private Sub frm_Unload(Cancel As Integer)
    RaiseEvent Finished(Not fBusy) 'raise event
    If (fBusy) Then fBusy = False  ' abort
    m_prg = 0
End Sub

Private Sub frmtimer_Timer()
    frmtimer.Enabled = False
    Unload frm
End Sub

Private Sub DoSims()
    For m_prg = 1 To 10000
        If Not fBusy Then Exit Sub 'aborted
        frm.Label1.Caption = m_prg
    Next m_prg
    fBusy = False
    m_prg = 0
End Sub


Featured Post

Master Your Team's Linux and Cloud Stack

Come see why top tech companies like Mailchimp and Media Temple use Linux Academy to build their employee training programs.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

I’ve seen a number of people looking for examples of how to access web services from VB6.  I’ve been using a test harness I built in VB6 (using many resources I found online) that I use for small projects to work out how to communicate with web serv…
You can of course define an array to hold data that is of a particular type like an array of Strings to hold customer names or an array of Doubles to hold customer sales, but what do you do if you want to coordinate that data? This article describes…
As developers, we are not limited to the functions provided by the VBA language. In addition, we can call the functions that are part of the Windows operating system. These functions are part of the Windows API (Application Programming Interface). U…
Get people started with the process of using Access VBA to control Excel using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Excel. Using automation, an Access application can laun…

825 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question