VBA~how to quit all Word applications

ron2

Registered User.
Local time
Today, 01:25
Joined
Sep 8, 2002
Messages
12
I'm outputting several report from Access >> Word but find my client reporting
that the template I insert them into is not closing but reporting locking.

So I've devised this code but find it usually only quits one instance of Word
at a time unless I step through the code when it closes all.
(I judge this using windows task manager and look for Processes = WINWORD.EXE)

Can anyone advise whats wrong here or another way of closing all Word.Applications ??

Public Function fgetwordandquit() As String
'test for open word apps and closes them
On Error Resume Next
Dim myword As Word.Application, wordisrunning As Boolean, C As Byte

wordisrunning = -1
'closes all word applications that are running
Do While wordisrunning = -1
'tests to see if any word application is open
Set myword = GetObject(, "Word.Application")
If Err.Number <> 0 Then 'cannot get application object so err 429
Err.Clear 'Clear Err object
wordisrunning = 0 'all closed so will now quit loop
End If
If wordisrunning = -1 Then
myword.Application.Quit
C = C + 1
End If
Set myword = Nothing
Loop
'MsgBox C


Exit_getthisdoc:
Exit Function

End Function
 
Just make a module and put the code bellow.

Then use this:
call KillProcess("Winword.exe")


Code:
Option Compare Database

Type PROCESSENTRY32
    dwSize As Long
    cntUsage As Long
    th32ProcessID As Long
    th32DefaultHeapID As Long
    th32ModuleID As Long
    cntThreads As Long
    th32ParentProcessID As Long
    pcPriClassBase As Long
    dwFlags As Long
    szexeFile As String * 260
End Type
'-------------------------------------------------------
Declare Function OpenProcess Lib "kernel32.dll" (ByVal dwDesiredAccess As Long, _
ByVal blnheritHandle As Long, ByVal dwAppProcessId As Long) As Long

Declare Function ProcessFirst Lib "kernel32.dll" Alias "Process32First" (ByVal hSnapshot As Long, _
uProcess As PROCESSENTRY32) As Long

Declare Function ProcessNext Lib "kernel32.dll" Alias "Process32Next" (ByVal hSnapshot As Long, _
uProcess As PROCESSENTRY32) As Long

Declare Function CreateToolhelpSnapshot Lib "kernel32.dll" Alias "CreateToolhelp32Snapshot" ( _
ByVal lFlags As Long, lProcessID As Long) As Long

Declare Function TerminateProcess Lib "kernel32.dll" (ByVal ApphProcess As Long, _
ByVal uExitCode As Long) As Long

Declare Function CloseHandle Lib "kernel32.dll" (ByVal hObject As Long) As Long

Public Sub KillProcess(NameProcess As String)
Const PROCESS_ALL_ACCESS = &H1F0FFF
Const TH32CS_SNAPPROCESS As Long = 2&
Dim uProcess  As PROCESSENTRY32
Dim RProcessFound As Long
Dim hSnapshot As Long
Dim SzExename As String
Dim ExitCode As Long
Dim MyProcess As Long
Dim AppKill As Boolean
Dim AppCount As Integer
Dim i As Integer
Dim WinDirEnv As String
        
       If NameProcess <> "" Then
          AppCount = 0

          uProcess.dwSize = Len(uProcess)
          hSnapshot = CreateToolhelpSnapshot(TH32CS_SNAPPROCESS, 0&)
          RProcessFound = ProcessFirst(hSnapshot, uProcess)
  
          Do
            i = InStr(1, uProcess.szexeFile, Chr(0))
            SzExename = LCase$(left$(uProcess.szexeFile, i - 1))
            WinDirEnv = Environ("Windir") + "\"
            WinDirEnv = LCase$(WinDirEnv)
        
            If Right$(SzExename, Len(NameProcess)) = LCase$(NameProcess) Then
               AppCount = AppCount + 1
               MyProcess = OpenProcess(PROCESS_ALL_ACCESS, False, uProcess.th32ProcessID)
               AppKill = TerminateProcess(MyProcess, ExitCode)
               Call CloseHandle(MyProcess)
            End If
            RProcessFound = ProcessNext(hSnapshot, uProcess)
          Loop While RProcessFound
          Call CloseHandle(hSnapshot)
       End If

End Sub
'-------------------------------------------------------
 
thanks for that will try
 
This is same thing as CTRL-ALT-DELing every instance of Word, which may not be appropriate.

I would think it much more easier and safer to check if a instance of Word is already, and if so, use that instance to do automation, or otherwise create a new instance, and when you're done, check if the code has created an instance and destroy that instance ONLY.
 
thanks for your interest
my code creates new instances of Word then always does .Quit at end of each process
it 1st bungs reports into a template(.doc) Saves as new .Doc and Quits template then
either Opens and is Visible, or Prints then Quits.
I find that when testing I get no problems, but my client reports locking errors when using same. So I assume the .Quits are not always being done.
Hence I thought good idea to Quit all Word applications just in case ~ a sort of belt and braces approach.
I am some miles away from my Client and rarely visit so difficult to investigate fully the reasons for this problem.

When you say "destroy that instance" is there another way of doing that appart from
my mywordapp.application.Quit followed by mywordapp = Nothing approach?
 
yeh ~there they have only used .Close method and not .Quit (see the replies)
My .Quit should close the Application ,this includes closing all its .docs (so you don't need to .Close them separately)

I think my issue is that it must be skipping the .Quit for some reason on my clients machine> I'm wondering if some other process on their PC is interfering with VBA running?

I know in from experience that if VBA is running and user eg opens Outlook then that can stop the code running successfully.
 
I just came across this thread via a Google search.

ron2's code did the job for me that I was looking for.
 
in VBA language .Quit means close a instance of the whole application (Word) that is currently running

the answer lies either with my initial code example or with the replies
this thread is now closed
 

Users who are viewing this thread

Back
Top Bottom