问题描述
主要的 VBA 过程计算 Word 文档中表格单元格中的字符数。因为它可以用不同的方式计算字符:
- 计算所选表格的“目标”文本
- 计算所选表格的“完成”文本
- 计算每个表中的 Obj 和 Acc 文本(循环),对于所有表(另一个循环)
我为上面调用主过程的每个选项创建了调用过程。通过这种方式,我将变量从调用 Sub 传递到主 Sub。这些变量 (1) 告诉主 Sub 是否要计算第 3 行(目标)或第 5 行(成就)或两者中的内容,以及 (2) 在主 Sub 中输入 If/then 行以确保计算右行。 事后看来,当时它看起来很优雅 - 不是那么优雅。
O1 中会有文本,VBA 会对其进行计数(字符、空格 + 段落)并在 C1 中输出,如果超过/低于字符限制,C1 填充会变为红色或绿色。对于以下任意数量的表格,A1 和 C2 都是相同的。
问题描述
当我将行/列硬编码到代码中的各个位置时,VBA 正在为上述操作工作。如果从表中添加/删除行/列,它们将不得不在多个位置更新。如果行/列号在一个地方并被称为变量会更简单,所以我将行/列#s 更改为公共变量。然后问题就开始了。
在代码中,我跟踪 (debug.print) oRow
(输出行)和 chcct
(字符数列)的变化,并且在主要 Sub 运行时两者都是 0,尽管两者都是在下面的公共 Sub Row_Col_Num() 中初始化为 3。
我的公共变量位于第一个 Sub() 之前的模块顶部,并表示为 Public
。包含变量赋值的 Sub Row_Col_Num() 也是 Public
。所有 Sub 都在同一个标准模块中。
Option Explicit
Public oRow As Integer 'row with "Objectives" text
Public aRow As Integer 'row with "Accomplishments" text
Public cOnA As Integer 'column that both obj and accmp text are in
Public cChCt As Integer 'column that the char count is output to
Public Sub Row_Col_Num()
oRow = 3
aRow = 5
cOnA = 1
cChCt = 3
Debug.Print "cchct pub sub: " & cChCt
End Sub
尝试解决问题和结果
- 我通常使用变量并将其保留为
Public
以及分配变量 (oRow =3
) 值的 Sub。
Sub TableCharCount_Obj()
'Run character count for the "Objectives" in the SELECTED table
Debug.Print "orow = " & oRow
Call TableCharCount(oRow,oRow) 'provide it 2x to make IF and FOR loop
End Sub
-
我尝试在使用变量时将 Sub() 名称放在变量前面,例如Row_Col_Num.orow,在上面的 Sub 中。
Call TableCharCount(Row_Col_Num.oRow,Row_Col_Num.oRow)
-
我也尝试了变量前面的模块名称,例如Module1.orow。
Call TableCharCount(Module1.oRow,Module1.oRow)
结果
#1 & #3 导致宏计算错误的行并输出到错误的单元格。
#2 导致错误“预期函数或变量”在行:Call TableCharCount(Row_Col_Num.oRow,Row_Col_Num.oRow)
所有 3 个案例 orow
和 cchct
在整个运行过程中都继续为 0。
问题/解决方案
a) 是否可以将公共变量 (oRow
) 用作从调用 Sub 传递给被调用 Sub 的参数 ByVal a As Integer
?
b) 为公共变量赋值的 Public Sub Row_Col_Num() 是否必须显式运行或调用以使用正确的值填充其他 Sub 中的变量?
c) 在调用主 Sub 之前,我应该在每次调用 Sub 中调用 Public Sub Row_Col_Num() 吗?
Sub TableCharCount_Obj()
Call Public Sub Row_Col_Num() '<<< add this call
Call TableCharCount(oRow,oRow) 'provide it 2x to make IF and FOR loop
End Sub
这个选项看起来很糟糕。
如果不是很明显,我添加了更多功能时会出现一些任务蠕变现在,如果我可以让公共变量工作,它就会完成。感谢任何使这些变量起作用的建议。对于这个问题,我只留下了变量 Sub、第一个调用 Sub 和主 Sub 的代码。下面的 VBA:
'#0 -- This creates variables for column and row number used in all the macros. Only need to change row/col number here if row/col are added/deleted
Option Explicit
Public oRow As Integer 'row with "Objectives" text
Public aRow As Integer 'row with "Accomplishments" text
Public cOnA As Integer 'column that both obj and accmp text are in
Public cChCt As Integer 'column that the char count is output to
'This assigns row/column numbers to the variables
Public Sub Row_Col_Num()
oRow = 3
aRow = 5
cOnA = 1
cChCt = 3
Debug.Print "cchct pub sub: " & cChCt End Sub
'#2
Sub TableCharCount_Obj() 'Run character count for the "Objectives" in the SELECTED table
Debug.Print "orow = " & oRow
Call TableCharCount(oRow,oRow) 'provide it 2x to make IF and FOR loop
End Sub
'other calling procedures removed
'#5
Option Explicit
Sub TableCharCount(ByVal a As Integer,ByVal b As Integer)
'Counts total characters in a cell w/in a table and outputs the number to a different cell,and colors the cell red or green if over/under the maximum number of characters.
Dim charCount,charWSCount,paraCount,charTot As Double
Dim iRng,oRng,txtRng As Word.Range
Dim i,max,s,t,x As Integer
Dim tcount,tbl As Integer
Dim DocT As Table 'for active doc tables
Debug.Print "cchct1= " & cChCt 'Debug.Print vbCr & "-----START-------" & vbCr Application.ScreenUpdating = False
If a <> b Then
tcount = ActiveDocument.Tables.Count
tbl = 1 'used in FOR loop,start w/ table #1
s = b - a '"STEP" used in FOR loop = # of rows between objectives text and accomplishments text Else
On Error GoTo ErrMsg 'handles expected user error of not selecting a table to execute on
tbl = ActiveDocument.Range(0,Selection.Tables(1).Range.End).Tables.Count 'ID the table that is selected
tcount = tbl 'prevents FOR loop from trying to run again
s = 1 '"STEP" used in FOR loop = # of rows between objectives text and accomplishments text / do not set to zero = infinite loop End If
'Debug.Print "# of Tables: " & tcount
For t = tbl To tcount 'loops thru the tables
Set DocT = ActiveDocument.Tables(t)
For x = a To b Step s 'loops thru the applicable row(s) in the table
'Debug.Print "x @ start = " & x
'Debug.Print "table " & t
iRng = DocT.Cell(x,cOnA)
iRng.Select
'Count used in output
Selection.MoveLeft wdCharacter,1,wdExtend 'computerstats requires the text itself selected,characters.count can use the whole cell selected
charWSCount = Selection.Range.ComputeStatistics(Statistic:=wdStatisticCharactersWithSpaces) 'counts bullets & space after bullet / not line breaks (paragraphs)
'Debug.Print "Comp statchar# " & charWSCount
'---------
paraCount = Selection.Range.ComputeStatistics(Statistic:=wdStatisticParagraphs)
'Debug.Print "#paras = " & paraCount
'----------
charTot = charWSCount + paraCount
'Output to table cell
i = x - 1 'output cell is 1 row above cell that is counted
Set oRng = DocT.Cell(i,cChCt).Range 'Char count ouput row,column
Debug.Print "cchct2= " & cChCt
oRng.Text = charTot
Set txtRng = DocT.Cell(i,cChCt - 1).Range '"# Char:" location row,column
txtRng.Text = "# Char:"
'Maximum # of char allowed in a cell. Used to change cell fill red or green.
max = 2000 '"Accomplishment" row (row 5) has a max of 2000
If i = 2 Then max = 1500 '"Objective" row (row 3) has a max of 1500
'Change color of cell to indicate over/under max # of characters
If charCount < max Then
oRng.Shading.BackgroundPatternColor = wdColorBrightGreen
Else: oRng.Shading.BackgroundPatternColor = wdColorRed
End If
'Debug.Print "x @ end = " & x
'Debug.Print "--------Next x--------------"
Next x
'Debug.Print "------Next Table------"
Next t
ActiveDocument.Tables(tbl).Select 'attempt to move to top of 1st table if using CharCount_AllTab() or just to the top of the selected table for the other macros
Selection.GoTo What:=wdGoToBookmark,Name:="\Page" Selection.StartOf
Application.ScreenUpdating = True
Exit Sub
ErrMsg: MsgBox "Select a table by placing the cursor anywhere in the table. Press OK and try the macro again numnuts!",_
vbOKOnly,"Table not selected"
End Sub
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)