luca345
asked on
Force to close Excel process thread
Hi ,
I have this routine that force to closing an excel instance thread:
/////////
Public Sub Excel_Chiudi(ByVal objExcel, ByVal objWorkBook, ByVal objWorksheet)
Dim WMI
Dim strQuery
Dim objProcesses
Dim objProcess
Dim Handle_Excel As Long
Try
1: GetWindowThreadProcessId(o bjExcel.hw nd, Handle_Excel)
2: objExcel.ActiveWorkbook.Cl ose()
3: objExcel.DisplayAlerts = True
4: objExcel.Quit()
5: objWorksheet = Nothing
6: objWorkBook = Nothing
7: objExcel = Nothing
8: WMI = GetObject("winmgmts:")
9: strQuery = "SELECT * FROM win32_process WHERE Name = 'EXCEL.EXE'"
10: objProcesses = WMI.execquery(strQuery)
For Each objProcess In objProcesses
11: If objProcess.Handle = Handle_Excel Then
' On Error Resume Next
12: objProcess.Terminate()
End If
13: Next
Catch Ex As System.Exception
Error_Handler(Ex)
End Try
End Sub
//////
This routine work fine but I need to remove the dipendence from the old Api instruction:
GetWindowThreadProcessId
In other word, I need to write only code that use .Net framework and not old win32 api like this.
Sameone can help me please to re-write this routine ?
I have this routine that force to closing an excel instance thread:
/////////
Public Sub Excel_Chiudi(ByVal objExcel, ByVal objWorkBook, ByVal objWorksheet)
Dim WMI
Dim strQuery
Dim objProcesses
Dim objProcess
Dim Handle_Excel As Long
Try
1: GetWindowThreadProcessId(o
2: objExcel.ActiveWorkbook.Cl
3: objExcel.DisplayAlerts = True
4: objExcel.Quit()
5: objWorksheet = Nothing
6: objWorkBook = Nothing
7: objExcel = Nothing
8: WMI = GetObject("winmgmts:")
9: strQuery = "SELECT * FROM win32_process WHERE Name = 'EXCEL.EXE'"
10: objProcesses = WMI.execquery(strQuery)
For Each objProcess In objProcesses
11: If objProcess.Handle = Handle_Excel Then
' On Error Resume Next
12: objProcess.Terminate()
End If
13: Next
Catch Ex As System.Exception
Error_Handler(Ex)
End Try
End Sub
//////
This routine work fine but I need to remove the dipendence from the old Api instruction:
GetWindowThreadProcessId
In other word, I need to write only code that use .Net framework and not old win32 api like this.
Sameone can help me please to re-write this routine ?
There doesn't seem to be a replacement for GetWindowThreadProcessId and I'd guess you'd otherwise have to use a lower level language to get at the processes.
Since we only have the code and no explanation of what you try to do or what the problem is, this is only a guess. Looks like you have problem with Excel instances being stuck running. Is that it?
Moving lines 5 and 6 before line 4 might do it, since you are releasing the worksheet and workbook before quitting. However, if there are other Excel objects referenced somehwere else, Quit might still do not do the job. All the objects referenced through a variable need to be released before Quit will work. You might have to deal with those in the calling methods.
Setting a variable to Nothing is usually sufficient in VBA, but since .NET and COM (Excel) are using different memory models, this is not always sufficient when working Excel from .NET code.
The way to resolve that problem is to use the ReleaseComObject method. This is not as straightforward as simply terminating a process, but this is the way for .NET applications to release the memory and enable old COM application (such as Excel) to terminate when you are done with them and they do no want to react to Quit.
Look for ReleaseComObject in the documentation and in other posts. It will probablyl solve your problem.
Moving lines 5 and 6 before line 4 might do it, since you are releasing the worksheet and workbook before quitting. However, if there are other Excel objects referenced somehwere else, Quit might still do not do the job. All the objects referenced through a variable need to be released before Quit will work. You might have to deal with those in the calling methods.
Setting a variable to Nothing is usually sufficient in VBA, but since .NET and COM (Excel) are using different memory models, this is not always sufficient when working Excel from .NET code.
The way to resolve that problem is to use the ReleaseComObject method. This is not as straightforward as simply terminating a process, but this is the way for .NET applications to release the memory and enable old COM application (such as Excel) to terminate when you are done with them and they do no want to react to Quit.
Look for ReleaseComObject in the documentation and in other posts. It will probablyl solve your problem.
ASKER
Hi James,
The problem is a bug of microsoft:
When you do this:
objExcel.ActiveWorkbook.Cl ose()
3: objExcel.DisplayAlerts = True
4: objExcel.Quit()
5: objWorksheet = Nothing
6: objWorkBook = Nothing
7: objExcel = Nothing
The Excel applicaion still active, and actually the only way that I known to close the excel instance is terminate the Thread process.
Do you known a way to solve this problem ?
The problem is a bug of microsoft:
When you do this:
objExcel.ActiveWorkbook.Cl
3: objExcel.DisplayAlerts = True
4: objExcel.Quit()
5: objWorksheet = Nothing
6: objWorkBook = Nothing
7: objExcel = Nothing
The Excel applicaion still active, and actually the only way that I known to close the excel instance is terminate the Thread process.
Do you known a way to solve this problem ?
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
ASKER
Excellent !
ASKER
Hi James ,
I was try with ReleaseComObject and work fine !!
I need an excact clone in VB.net of the Old Format VB6 instruction.
If I open a new Thread are you interested ?
I was try with ReleaseComObject and work fine !!
I need an excact clone in VB.net of the Old Format VB6 instruction.
If I open a new Thread are you interested ?
I suggest that you use the formatting functions in .NET. There are many of those that are adapted to different needs, so they are a lot more versatile. They are also more apt to work will in a multilingual environement if this is something that concerns your work.
String.Format is very close to the one that was used in VB6.
String.Format is very close to the one that was used in VB6.
ASKER
Hi James,
I need a function that is a clone of the old format because this function was called 50-100 times and I can't risk the insert only similar.
I was try to use the equivalent format method of vb.net but there is some difference and return something like ####,#### and not the value of the VB6 instruction.
Do you have the possibility to write a new function called S_Format that is a clone of the old VB6 format ?
If you can do it , I like to give you other 500 points in another post.
I need a function that is a clone of the old format because this function was called 50-100 times and I can't risk the insert only similar.
I was try to use the equivalent format method of vb.net but there is some difference and return something like ####,#### and not the value of the VB6 instruction.
Do you have the possibility to write a new function called S_Format that is a clone of the old VB6 format ?
If you can do it , I like to give you other 500 points in another post.
If I already had that function, I would give it to you, but I don't.
Sorry, but it would require too much time to write one and I do not have that time.
Good luck.
Sorry, but it would require too much time to write one and I do not have that time.
Good luck.