VBA - 将 MS Word 表中的数据拉入 MS Excel 工作表(非特殊粘贴)
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/15789505/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
VBA - Pull data from MS Word table into MS Excel Worksheet (NOT special Paste)
提问by Ashley Niall Coutts
I have a standard word document that contains a few tables of data (name, dob, address, etc).
我有一个标准的 word 文档,其中包含一些数据表(姓名、dob、地址等)。
I am wanting to have a set up so when data is newly entered or altered within the word document it automatically filters through into my excel document. I know this can be done using "Special Paste" but am wondering if it's possible to do any other way. I know basic VBA as I can get the spreadsheet to open and save from a button within my Word doc.... but that's it.
我想要一个设置,以便在 Word 文档中新输入或更改数据时,它会自动过滤到我的 Excel 文档中。我知道这可以使用“特殊粘贴”来完成,但我想知道是否有其他方法可以做到。我知道基本的 VBA,因为我可以从 Word 文档中的一个按钮打开和保存电子表格......但就是这样。
Any advice is greatly welcome.... been struggling with this for a while now. It might just be the company I am working for being old fashioned.
非常欢迎任何建议......现在已经为此苦苦挣扎了一段时间。这可能只是我工作的公司过时了。
So to recap the word doc is the central hub of info and the excel doc needs to grab updated info from the word doc.
所以总结一下 doc 是信息的中心枢纽,excel doc 需要从 word doc 中获取更新的信息。
回答by Siddharth Rout
This is further to my above comment. What this code does is loops through each cell in the table row and extracts the text which can be directly put into the Excel cell thereby negating the need to use Copy-Paste
这是对我上述评论的进一步补充。这段代码的作用是遍历表格行中的每个单元格并提取可以直接放入 Excel 单元格的文本,从而不需要使用Copy-Paste
I have commented the code so you shouldn't have any problem understanding it. Still if you do then simply post back.
我已经注释了代码,所以你理解它应该没有任何问题。尽管如此,如果您这样做,则只需回帖即可。
You need to paste this code in a module and run it every time you want to export the Table data to Excel.
您需要将此代码粘贴到模块中,并在每次要将表数据导出到 Excel 时运行它。
It goes unsaid that I haven't completely tested this code.
不用说,我还没有完全测试过这段代码。
Sub Sample()
Dim wrdTbl As Table
Dim RowCount As Long, ColCount As Long, i As Long, j As Long
'~~> Excel Objects
Dim oXLApp As Object, oXLwb As Object, oXLws As Object
'~~> Set your table
Set wrdTbl = Selection.Tables(1)
'~~> Get the word table Row and Column Counts
ColCount = wrdTbl.Columns.Count
RowCount = wrdTbl.Rows.Count
'~~> Create a new Excel Applicaiton
Set oXLApp = CreateObject("Excel.Application")
'~~> Hide Excel
oXLApp.Visible = False
'~~> Open the relevant Excel file
Set oXLwb = oXLApp.Workbooks.Open("C:\Sample.xls")
'~~> Work with Sheet1. Change as applicable
Set oXLws = oXLwb.Sheets(1)
'~~> Loop through each row of the table
For i = 1 To RowCount
'~~> Loop through each cell of the row
For j = 1 To ColCount
'~~> This gives you the cell contents
Debug.Print wrdTbl.Cell(i, j).Range.Text
'~~> Put your code here to export the values of the Word Table
'~~> cell to Excel Cell. Use the .Range.Text to get the value
'~~> of that table cell as shown above and then simply put that
'~~> in the Excel Cell
With oXLws
'~~> EXAMPLE
' .Cells(1, 1).Value = wrdTbl.Cell(i, j).Range.Text
End With
Next
Next
'~~> Close and save Excel File
oXLwb.Close savechanges:=True
'~~> Cleanup (VERY IMPROTANT)
Set oXLws = Nothing
Set oXLwb = Nothing
oXLApp.Quit
Set oXLApp = Nothing
MsgBox "DONE"
End Sub
回答by Daniel M?ller
I did that once, here are the basics, sorry for the code is in portuguese, but I'll comment it in english. The main feature here is the easyness to get table values by their titles and names. (there's no need for code translating)
我做过一次,这是基础知识,抱歉代码是葡萄牙语,但我会用英语评论。这里的主要功能是通过标题和名称轻松获取表值。(无需代码翻译)
'opens word and loads tables
Sub AbreWordDatabase()
Set WordApp = CreateObject("Word.Application") 'creates word application in a variable declared as global outside this method
WordApp.Visible = True 'shows word
'opens dialog box
If WordApp.Dialogs(80).Show = -1 Then 'shows fileopendialog
Set Doc = WordApp.Documents(1) 'sets the open document to a previously declared variable
WordApp.WindowState = 2 'minimizes o word (2 = wdWindowStateMinimize)
LoadDataBase 'takes desired values in file
Else
MsgBox "Word file wasnt open, operation was canceled."
End If
WordApp.Quit
Set WordApp = Nothing
End Sub
Sub LoadDataBase() 'Takes values in word file
SelectTabela "Title" 'selects a table below the passed title
Plan3.Range("NamedRange").Value = PegaValor("Some variable name - Line", "Some column name") 'Puts in excel table the value of first column after the passed variable name
Plan3.Range("NamedRange2").Value = PegaValor("Another variable", "Another column name")
End Sub
'Selects in Word the table below "Titulo"
Sub SelectTabela(Titulo As String, Optional NumTabela As Integer = 1)
'Titulo = Title that comes before the desired table in word file
'NumTabela = defines if the desired table is the first below title, or second, third....
Dim i As Integer
PegaTexto(Titulo, Doc.Content, 12, True).Select 'Finds the title using the title formatting of table titles (customize this for your needs)
For i = 1 To NumTabela 'This loop finds below title the tables one by one until the desired number
WordApp.Selection.GoToNext (2) 'goes to next table (2 = wdGoToTable)
Next
End Sub
'Finds a value in table using variable name and passed column
Function PegaValor(NomeVar As String, Coluna As Variant) As String
'Parameters
'NomeVar = name of the variable in the selected table corresponding to the desired value
'Coluna = index of the column after the name of the variable, or the name of the column
Dim LinVar As Integer, ColVar As Integer 'Row and column indices to find the line based on variable name
Dim LinCol As Integer, ColCol As Integer 'Row and column indices to find the column based on column name
Dim Tabela As Object 'Word.Table object - table where the values will be searched
Set Tabela = WordApp.Selection.Range.Tables(1) 'Takes selected table
AchaLinhaColuna NomeVar, Tabela, LinVar, ColVar 'Gives LinVar and ColVar the indices of the cell where the variable name was found (NomeVar)
If LinVar = 0 Or ColVar = 0 Then ' 'If row or column are zero, variable was not found in table
MsgBox "The name """ & NomeVar & """ passed to function ""PegaValor"" wasn't found"
Exit Function
End If
If VarType(Coluna) = vbString Then 'Verifies if type of var in column is string
AchaLinhaColuna Coluna, Tabela, LinCol, ColCol, ColVar 'Gives LinCol and Colcol the indices of the cell where "Coluna" is found. Remember the searched region is after "ColVar". Colvar is for the case there are repeated names in different columns, we want the values only after the desired name
If LinVar = 0 Or ColVar = 0 Then 'If line or column are zero, column wasn't found by name.
MsgBox "The name of the column """ & Coluna & """ passed to the function ""PegaValor"" wasn't found"
Exit Function
End If
Else
ColCol = ColVar + Coluna 'The value of the searched column is the column containing the variable name plus the quantity of columns after that, passed to this function
End If
PegaValor = Tabela.Cell(LinVar, ColCol).Range.Text 'Takes the text of the cell of row corresponding to var name and column corresponding to the passed column name or index
PegaValor = Left(PegaValor, Len(PegaValor) - 2) 'Eliminates the two last characters, they are special characters coming from word table.
End Function
'Returns line and column in a table where given text is found
Sub AchaLinhaColuna(ByVal Texto As String, ByVal Tabela As Object, ByRef L As Integer, ByRef C As Integer, Optional ByVal StartC As Integer = 1)
'Parameters consumed
'Texto = desired text to be found in table
'Tabela = table where text will be searched (Word.Table)
'StartC = Start column from where value will be searched (for tables with repeated columns, starts the search in the desired column)
'Parameters passed as results (marked byref)
'L = line of the cell where text has been found
'C = column of the cell where text has been found
Dim j As Integer 'Loop indices
Dim Linha As Object 'Table row (Word.Row)
For Each Linha In Tabela.Rows 'For each table line
For j = StartC To Linha.Cells.Count 'For each cell in that line starting from desired column (StartC)
With Linha.Cells(j) 'With cell in row "Linha" and column j
If UCase(PegaTexto(Texto, .Range).Text) = UCase(Texto) Then 'If text in cell is the desired text returns line and column
L = .Row.Index 'Row index
C = .Column.Index 'Column Index
Exit Sub
End If
End With
Next
Next
End Sub
'Finds and returns any text in Word file. May use formatting.
Function PegaTexto(Texto As String, FindWhere As Object, Optional FontSize As Integer = 0, Optional Negrito As Boolean = False) As Object '(Word.Range)
'Parameters consumed
'Texto = Desired text to find
'FindWhere = Range of the word file where text will be searched. (Range: Word's API object containing parts of the document, beware, there are ranges in excel, they are different) (Word.Range)
'FontSize = desired font size (if no value is passed, assume any size)
'Negrito = defines if desired text is bold (if no value is passed, assumes any formatting)
With FindWhere.Find 'Find: Word's API object that finds text
.ClearFormatting 'At start clears all formatting
.Text = Texto 'Sets the desired text to be found
With .Font 'WIth the font of the Find object - sets the font and bold formatting
If FontSize <> 0 Then
.Size = FontSize
End If
If Negrito Then
.Bold = True
End If
End With
.Execute 'Executes the Find object
End With
Set PegaTexto = FindWhere 'The Find object transforms the FindWhere range, making it contain only the found text
End Function