目录
在 VBA 中,打开文件的方式有几种,每种方式适用于不同的情况:
1 Application.GetOpenFilename
- Application.GetOpenFilename 方法:
- 适用于需要让用户手动选择文件的情况。
- 优点是简单易用,不需要引用其他对象或库。
- 缺点是无法直接通过 VBA 程序打开文件,需要用户手动选择。
filePath = Application.GetOpenFilename("Excel Files (*.xls; *.xlsx), *.xls; *.xlsx")
2 Application.GetOpenFilename 方法 + Workbooks.Open 方法
- Application.GetOpenFilename 方法 + Workbooks.Open 方法:
- 适用于需要在 VBA 程序中打开用户手动选择的文件的情况。
- 可以在用户选择文件后,直接通过 VBA 代码打开所选文件。
- 优点是灵活,能够在程序中自动处理文件的打开。
- 缺点是需要用户手动选择文件,不够自动化。
filePath = Application.GetOpenFilename("Excel Files (*.xls; *.xlsx), *.xls; *.xlsx")
If filePath <> "False" Then
Workbooks.Open filePath
End If
2.1 用户选择打开文件
由于打开文件的时候如果已经被打开会弹窗是否需要重新打开,所以为了避免每次点弹窗选择,我们可以在代码中添加逻辑判断工作簿是否被打开,被打开了就直接获取,没被打开就重新打开。打开拿完对象后 使用完工作表可以直接Close。
'选择SIP文件
Function OpenSIP_WorkBook() As Workbook
Dim filePath As String
Dim fileName As String
Dim wb As Workbook
Dim wbIsOpen As Boolean
' 使用文件对话框选择文件
filePath = Application.GetOpenFilename("Excel Files (*.xls; *.xlsx), *.xls; *.xlsx")
' 检查是否选择了文件
If filePath <> "False" Then
' 获取文件名
fileName = Right(filePath, Len(filePath) - InStrRev(filePath, "\"))
' 检查工作簿是否已经打开
For Each wb In Workbooks
If wb.name = fileName Then
wbIsOpen = True
Exit For
End If
Next wb
' 如果工作簿已经打开,则直接返回
If wbIsOpen Then
Set OpenSIP_WorkBook = Workbooks(fileName)
Else
' 否则打开选定的工作簿并返回
Set OpenSIP_WorkBook = Workbooks.Open(filePath)
End If
Else
' 如果用户取消了选择,则返回空
Set OpenSIP_WorkBook = Nothing
End If
End Function
2.2 设置文件路径操作文件
下面是一个使用设置源文件和目标文件路径,以及需要操作源文件工作表和目标文件工作表的使用案例。
功能为 从源文件的源工作表,复制到目标文件的目标工作表,因为需要选择的路径和文件很多,所以直接固定在代码比用户选择文件夹路径和工作表方柏霓很多。
打开文件和表格失败主动抛出异常 是一个很好的编程习惯
因为工作表名称比较固定,所以工作表路径写在了函数里。
’ 获取源工作表和目标工作表
On Error Resume Next
Set sourceSheet = sourceWorkbook.Sheets(“Sheet1”)
Set targetSheet = targetWorkbook.Sheets(“考勤明细”)
On Error GoTo 0
Sub 一键操作()
'===========================================================考勤表操作============================================================
Dim sourcePath As String
Dim targetPath As String
Dim result As Boolean
' 定义 打卡 源文件和目标文件的路径
sourcePath = "C:\Users\Administrator\Desktop\3月打卡.Xls"
targetPath = "C:\Users\Administrator\Desktop\人工成本核算.xls"
result = AttendanceSheet(sourcePath, targetPath)
If result Then
MsgBox "考勤表数据已成功从源文件复制到目标文件。"
Else
MsgBox "复制考勤表数据失败。"
End If
End Sub
'复制操作考勤 文件函数
Function AttendanceSheet(sourceFilePath As String, targetFilePath As String) As Boolean
Dim sourceWorkbook As Workbook
Dim targetWorkbook As Workbook
Dim sourceSheet As Worksheet
Dim targetSheet As Worksheet
Dim success As Boolean
' 尝试打开源文件和目标文件
On Error Resume Next ' 忽略错误
Set sourceWorkbook = Workbooks(GetFileNameWithoutExtension(sourceFilePath))
Set targetWorkbook = Workbooks(GetFileNameWithoutExtension(targetFilePath))
On Error GoTo 0 ' 恢复错误处理
' 如果源文件未打开,则打开它
If sourceWorkbook Is Nothing Then
Set sourceWorkbook = Workbooks.Open(sourceFilePath)
End If
' 如果目标文件未打开,则打开它
If targetWorkbook Is Nothing Then
Set targetWorkbook = Workbooks.Open(targetFilePath)
End If
' 检查文件是否成功打开
If sourceWorkbook Is Nothing Or targetWorkbook Is Nothing Then
MsgBox "无法打开源文件或目标文件。"
AttendanceSheet = False
Exit Function
End If
' 获取源工作表和目标工作表
On Error Resume Next
Set sourceSheet = sourceWorkbook.Sheets("Sheet1")
Set targetSheet = targetWorkbook.Sheets("考勤明细")
On Error GoTo 0
' 检查工作表是否存在
If sourceSheet Is Nothing Or targetSheet Is Nothing Then
MsgBox "源工作表或目标工作表不存在。"
AttendanceSheet = False
Exit Function
End If
' 复制源工作表的内容
sourceSheet.Cells.Copy
' 尝试粘贴到目标工作表
On Error Resume Next
targetSheet.Cells(1, 1).PasteSpecial Paste:=xlPasteValues ' 使用xlPasteValues来粘贴值
If Err.Number <> 0 Then
MsgBox "粘贴操作失败: " & Err.Description
Err.Clear ' 清除错误
AttendanceSheet = False
Else
Application.CutCopyMode = False ' 清除剪贴板引用
AttendanceSheet = True
End If
On Error GoTo 0
' 保存并关闭工作簿
targetWorkbook.Save
'targetWorkbook.Close
'sourceWorkbook.Close False ' 不保存更改关闭源文件
End Function
只读方式打开文件 Set wb = Workbooks.Open(filePath, ReadOnly:=True)
要以只读方式打开文件,可以使用 Workbooks.Open 方法的 ReadOnly 参数。设置 ReadOnly 参数为 True 即可以只读方式打开文件
Sub OpenReadOnlyWorkbook()
Dim filePath As String
Dim wb As Workbook
' 使用文件对话框选择文件
filePath = Application.GetOpenFilename("Excel Files (*.xls; *.xlsx), *.xls; *.xlsx")
' 检查是否选择了文件
If filePath <> "False" Then
' 以只读方式打开选定的工作簿并返回工作簿对象
Set wb = Workbooks.Open(filePath, ReadOnly:=True)
' 在这里可以对只读的工作簿进行操作
' 关闭工作簿
wb.Close False
Else
' 如果用户取消了选择,则输出消息
MsgBox "未选择文件。"
End If
End Sub
3 FileSystemObject(Scripting.FileSystemObject)
- FileSystemObject(Scripting.FileSystemObject):
- 适用于需要在 VBA 程序中对文件系统执行操作的情况,例如获取文件夹中的文件列表、创建文件、删除文件等。
- 可以使用 FileSystemObject 对象执行多种文件和文件夹操作。
- 优点是能够方便地执行文件和文件夹操作,具有较高的灵活性。
- 缺点是在某些情况下可能需要处理文件系统对象的权限问题。
Set fs = CreateObject("Scripting.FileSystemObject")
Set folder = fs.GetFolder(folderPath)
选择哪种方式取决于你的需求。如果需要用户手动选择文件,可以使用第一种或第二种方法。如果需要在 VBA 中执行文件系统操作,则需要使用 FileSystemObject。
4 Application.FileDialog 方法(msoFileDialogFolderPicker)
- Application.FileDialog 方法(msoFileDialogFolderPicker):
- 适用于需要让用户选择文件夹的情况。
- 提供了对话框,允许用户直接选择文件夹而不是单个文件。
- 优点是可以直接选择文件夹,方便用户快速定位所需文件夹。
- 缺点是无法直接选择文件,只能选择文件夹,不适用于需要选择具体文件的情况。
选择使用 Application.FileDialog 方法时,需明确用户需求是否为选择文件夹。如果需要选择文件夹,则此方法是很好的选择,能够满足用户的需求,并提供友好的交互界面。
Dim folderPath As String
With Application.FileDialog(msoFileDialogFolderPicker)
.Title = "Select a Folder"
.AllowMultiSelect = False
If .Show = -1 Then
folderPath = .SelectedItems(1)
Else
MsgBox "No folder selected.", vbExclamation
Exit Sub
End If
End With
Application.FileDialog(msoFileDialogFolderPicker)踩坑记录
Debug 发现
Application.FileDialog 方法在Office Excel的宏指令能运行,但是在WPS使用这个代码打开文件会报错,只有第一次运行的程序的时候能够弹出文件夹选择框。甚至在WPS有其他工作簿(文件)打开的时候,直接folderDialog.Show 就不等于-1 跳出判断,直接结束了程序。
If folderDialog.Show = -1 Then:
这行代码显示了文件夹选择对话框,并在用户选择文件夹后进行判断。folderDialog.Show 会显示对话框,用户选择文件夹后,返回值为 -1。因此,通过 If folderDialog.Show = -1 Then 判断用户是否选择了文件夹。