2016-07-15 193 views
2

我希望在VBA腳本開始修改內容之前提示用戶保存工作簿。當SaveAs對話框出現時,如果用戶單擊取消,則引發自定義錯誤並停止腳本。如果他們點擊保存並且文件名已經存在,我希望他們被問到是否覆蓋。如何處理Workbook.Save上的「否」或「取消」覆蓋確認?

這裏是我的代碼:

Function SaveCurrentWorkbook(wkbSource As Workbook, strNewFileName As String) As Variant 
    If Not bolDebug Then On Error GoTo errHandler 
    Dim varSaveName As Variant 

SaveAsDialog: 
    varSaveName = Application.GetSaveAsFilename(InitialFileName:=strNewFileName, FileFilter:="Excel Files (*.xls), *.xls") 
    If varSaveName <> False Then 
     wkbSource.SaveAs Filename:=varSaveName, ConflictResolution:=True, Addtomru:=True 
     Set SaveCurrentWorkbook = wkbSource 
    Else 
     SaveCurrentWorkbook = False 
     Err.Raise 11111, , "Save Canceled" 
    End If 

exitProc: 
    Exit Function 

errHandler: 
    Select Case Err.Number 
     Case 1004 'Clicked "No" or "Cancel" - can't differentiate 
      Resume SaveAsDialog 
     Case esle 
      MsgBox "File not saved. Stopping script.", vbOKOnly, Err.Description 
      Resume exitProc 
    End select 

End Function 

如果他們點擊 '是',它會覆蓋它。如果他們點擊「否」,我希望SaveAs對話框出現,以便他們可以選擇一個新的文件名,但相反,我得到一個錯誤。如果他們點擊「取消」,我想要發生錯誤並停止腳本。問題是我無法區分「否」和「取消」之間觸發的錯誤。

任何建議如何處理? (請原諒任何窮人使用的錯誤處理 - 它已經有一段時間。)

附:此功能由另一個過程調用,因此如果用戶在SaveAs對話框或ResolveConflict對話框中單擊「取消」,我希望調用過程也停止。我想我可以通過檢查SaveCurrentWorkbook返回的內容(Workbook對象或False)來做到這一點。

回答

1

您可以簡單地創建自己的「覆蓋?」 - 問題是這樣的:

Function SaveCurrentWorkbook(wkbSource As Workbook, strNewFileName As String) As Variant 
    If Not bolDebug Then On Error GoTo errHandler 
    Dim varSaveName As Variant 

SaveAsDialog: 

    varSaveName = Application.GetSaveAsFilename(InitialFileName:=strNewFileName, FileFilter:="Excel Files (*.xls), *.xls") 
    If varSaveName <> False Then 
     If Len(Dir(varSaveName)) Then 'checks if the file already exists 
     Select Case MsgBox("A file named '" & varSaveName & "' already exists at this location. Do you want to replace it?", vbYesNoCancel + vbInformation) 
     Case vbYes 
      'want to overwrite 
      Application.DisplayAlerts = False 
      wkbSource.SaveAs varSaveName, ConflictResolution:=2, Addtomru:=True 
      Application.DisplayAlerts = True 
      Set SaveCurrentWorkbook = wkbSource 
     Case vbNo 
      GoTo SaveAsDialog 
     Case vbCancel 
      SaveCurrentWorkbook = False 
      Err.Raise 11111, , "Save Canceled" 
     End Select 
     Else 
     wkbSource.SaveAs varSaveName, ConflictResolution:=True, Addtomru:=True 
     Set SaveCurrentWorkbook = wkbSource 
     End If 
    Else 
     SaveCurrentWorkbook = False 
     Err.Raise 11111, , "Save Canceled" 
    End If 

exitProc: 
    Exit Function 

errHandler: 
    Select Case Err.Number 
    Case 1004 'Clicked "No" or "Cancel" - can't differentiate 
     Resume SaveAsDialog 
    Case Else 
     MsgBox "File not saved. Stopping script.", vbOKOnly, Err.Description 
     Resume exitProc 
    End Select 

End Function 

正如你已經注意到了,有(與「否」和「取消」沒什麼區別了該應用程序,因爲它不會停止保存本身)。 Excel中簡單地在於把自己說:「我不能在這裏保存」並彈出同樣的錯誤,這兩種情況......所以唯一的真正解決方案是創建你自己的msgbox :(

+0

這是偉大的,謝謝! – MJA

1

我會讓SaveCurrentWorkbook返回真或假,並使用Msgboxes處理保存爲strNewFileName。

然後在調用SaveCurrentWorkbook腳本,你可以做一個簡單的布爾評估。

 
    If SaveCurrentWorkbook(wkbSource, "C:\...\SomeFile.xls") then 
     'Do Something 
    Else 
     'Do Something else 
    End If 
Function SaveCurrentWorkbook(wkbSource As Workbook, strNewFileName As String) As Boolean 
    Dim iResult As VbMsgBoxResult 

    Dim varSaveName As Variant 

    If Dir(strNewFileName) <> "" Then 
     iResult = MsgBox("Press [Yes] to overwite " & strNewFileName & " or [No] to choose a new filename.", vbInformation + vbYesNo, "Save File") 
    Else 
     iResult = MsgBox("Press [Yes] to save as " & strNewFileName & " or [No] to choose a new filename.", vbInformation + vbYesNo, "Save File") 
    End If 

    If iResult = vbYes Then 
     SaveCurrentWorkbook = True 
    Else 
     varSaveName = Application.GetSaveAsFilename(FileFilter:="Excel Files (*.xls), *.xls") 
     If CStr(varSaveName) <> "False" Then 
      wkbSource.SaveAs Filename:=varSaveName, ConflictResolution:=True, Addtomru:=True 
      SaveCurrentWorkbook = True 
     End If 
    End If 

End Function 

你不需要使用另存爲的時候,因爲你原來被關閉(不保存),並參考自動更新到新的文件設置一個參考。如果您使用的是SaveCopyA,則您的原始文件保持打開狀態,並創建當前文件的副本(包括任何未保存的數據)。在下面的測試

注意,當我們使用另存爲的refernce更新到另存爲名稱。當我們使用SaveCopAs時,名稱不會更改,因爲原始文件仍處於打開狀態。

enter image description here

+0

我想新的工作簿引用所以我可以繼續修改它,而不是True/False,我會看看我是否可以返回Nothing並只是測試它。 – MJA

+1

我更新了我的答案,並解釋了爲什麼不需要返回對工作簿的引用。 – 2016-07-15 20:49:04

+0

感謝托馬斯,我能夠證實這個作品,它幫助我收拾我的代碼。+1 – MJA