Reputation: 1964
There is ABC.xls
file which has the macro. Now, the macro has a sub which is getting called when I press Ctrl + M
.
This sub will open a Open File Dialog where the user can choose a CSV
file. So basically, this macro is used for processing and saving CSV
file.
Below is the code which gets called on pressing Ctrl + M
.
Sub runProperChangeSubroutine() ' Assigned to shortcut key CTRL + M.
file_name = ActiveWorkbook.Name ' Gets the file name.
Application.Run file_name & "!ChangeSub"
End Sub
When the user closes the workbook, I have to test for a condition like each row in the CSV
has a termination string. If that termination string is not
present, I should popup a message box to the user and prevent the closing of workbook.
So I did the following...
Private Sub Workbook_BeforeClose(Cancel As Boolean)
Dim improperRowNumber As Integer
Dim BlnEventState As Boolean
improperRowNumber = returnImproperRow()
BlnEventState = Application.EnableEvents
Application.EnableEvents = True
If improperRowNumber <> -1 Then
Cancel = True
MsgBox "The row number " & improperRowNumber & " is not ending with '@/#'. Please correct the row before closing."
Else
Call saveCSV
End If
Application.EnableEvents = BlnEventState
End Sub
On clicking of the close (X mark on top right corner, closing of workboox. I am not closing the excel.) button, I am able to see the message box but the workboox closes. I want user to make some edit if the row is not properly ended. Please suggest.
Edited:
As the above code is not working, I used ThisWorkbook.Saved = False
after the message box as shown below...
If improperRowNumber <> -1 Then
MsgBox "The row number " & improperRowNumber & " is not ending with '@/#'. Please correct the row before closing."
Application.DisplayAlerts = False
ThisWorkbook.Saved = False
Cancel = False
Else
Now it displays the "Do you want to save the changes....
" message box. If I click on Cancel
button on message box, the workbook is not closed.
Is there a way to customize the message box text or buttons or hide this Save
message box?
Upvotes: 7
Views: 7499
Reputation: 1395
You can use this code in the workbook macro
Private Sub Workbook_BeforeClose(Cancel As Boolean)
ActiveWorkbook.Save
Workbooks.Open Application.ActiveWorkbook.FullName
End Sub
As you can see it basically saves and open the workbook when it close
Upvotes: 0
Reputation: 2849
If you must monitor the closing of workbooks other than the one containing the macros, you can intercept application-level events from your macro-enabled workbook as follows:
Add (or adapt) this code behind ThisWorkbook:
Option Explicit
Private m_CloseHelper As CloseHelper
Private Sub Workbook_Open()
Set m_CloseHelper = New CloseHelper
End Sub
Add a new Class Module named CloseHelper:
Option Explicit
Private WithEvents m_App As Excel.Application
Private Sub Class_Initialize()
Set m_App = Excel.Application
End Sub
Private Sub Class_Terminate()
Set m_App = Nothing
End Sub
Private Sub m_App_WorkbookBeforeClose(ByVal Wb As Workbook, Cancel As Boolean)
'Logic goes here, e.g. the code below will prevent the user from closing
'any workbook other than this one, for as long as this workbook is open.
If Not Wb Is ThisWorkbook Then
Cancel = True
MsgBox "Hello from m_App_WorkbookBeforeClose"
End If
End Sub
The important keyword is WithEvents, and the principle is that events raised by the Excel application can now be coded against within the CloseHelper class.
You'll find a more in-depth article here: Application Events
Upvotes: 6
Reputation: 4129
Have you tried closing all your add-ins (or run Excel in Safe Mode)?
I'm asking because this problem could be due to the fact that one of your add-ins contains an Application Level Event like the one described in Excelosaurus' answer. And it could contain Application.EnableEvents = False
or even Cancel = False
and interfere with your code.
EDIT: This would be especially hard to detect with an add-in that is protected since the code would run after Workbook_BeforeClose and you won't be able to know what it's doing even if you were debugging line by line using F8.
Upvotes: 0
Reputation: 4858
The Workbook_BeforeClose event only applies to the workbook in which the code is located. It runs when you try to close the macro workbook and setting its parameter Cancel to TRUE only cancels the closure of the macro workbook when you close Excel. The csv file that is open is a separate workbook and Excel tries to close that separately, generating a separate message about saving the csv file.
To automatically prevent the csv file from being closed, you need to use extensibility programming to add a Workbook_BeforeClose event to the csv file while it is open in Excel. Obviously you can't save the file with the event in place, but you don't need to. The code sitting in the module will run while the workbook is still open preventing closure when your conditions are not met; and a successful save allowed after conditions are met will be in the .csv format which will wipe the temporarily added code.
http://www.cpearson.com/excel/vbe.aspx
Upvotes: 0
Reputation: 14383
Pressing the X-button in the top right quits the Excel application. You shouldn't expect the workbook to remain open when the application is closed. You could write an application-event procedure preventing Excel from quitting, but the better way might be to simply get rid of the bad habit of using that button. Find another way to close the workbook.
Upvotes: 0