非活动工作表应用AutoFilter后避免整表选中,如何获取其‘活动单元格’?
问题解决方案
Excel本身没有原生属性可直接获取非活动工作表的“活动单元格”(即该工作表上次处于激活状态时的选中单元格),但可以通过提前记录的方式实现需求,以下是两种可行方案:
方案1:利用工作表隐藏名称记录最后活动单元格
- 为每个包含ListObject的工作表添加激活事件代码,记录当前活动单元格:
Private Sub Worksheet_Activate() On Error Resume Next Me.Names("LastActiveCell").Delete On Error GoTo 0 Me.Names.Add Name:="LastActiveCell", RefersTo:=ActiveCell End Sub
- 修改你的宏代码,调用该名称获取目标工作表的最后活动单元格,替代原选中第一个单元格的逻辑:
Dim lo As ListObject ' lo 是目标ListObject对象 Dim rg As Range Set rg = ActiveCell ' 执行数据处理操作 lo.Sort.Apply ' 表格排序,数据处理最后一步 ' 处理非活动工作表的选中状态 If rg.Parent.Name = lo.Parent.Name Then ' 活动工作表无需处理 Else Dim lastActiveRg As Range On Error Resume Next Set lastActiveRg = lo.Parent.Range("LastActiveCell") On Error GoTo 0 ' 若未记录过则 fallback 到表格第一个单元格 If lastActiveRg Is Nothing Then Set lastActiveRg = lo.DataBodyRange(1, 1) End If lo.Parent.Activate lastActiveRg.Select rg.Parent.Activate rg.Select End If
方案2:使用全局字典存储所有工作表的最后活动单元格
- 在标准模块中声明全局字典变量:
Public lastActiveCells As New Dictionary
- 为每个目标工作表添加激活和选区变化事件,更新字典中的记录:
Private Sub Worksheet_Activate() Set lastActiveCells(Me.Name) = ActiveCell End Sub Private Sub Worksheet_SelectionChange(ByVal Target As Range) Set lastActiveCells(Me.Name) = Target End Sub
- 修改宏代码,通过字典获取目标工作表的最后活动单元格:
Dim lo As ListObject ' lo 是目标ListObject对象 Dim rg As Range Set rg = ActiveCell ' 执行数据处理操作 lo.Sort.Apply ' 表格排序,数据处理最后一步 ' 处理非活动工作表的选中状态 If rg.Parent.Name = lo.Parent.Name Then ' 活动工作表无需处理 Else Dim lastActiveRg As Range If lastActiveCells.Exists(lo.Parent.Name) Then Set lastActiveRg = lastActiveCells(lo.Parent.Name) Else Set lastActiveRg = lo.DataBodyRange(1, 1) End If lo.Parent.Activate lastActiveRg.Select rg.Parent.Activate rg.Select End If
以上两种方案均可替代原代码中的lo.DataBodyRange(1,1).Select语句,实现返回非活动工作表时选中其上次激活的活动单元格。
内容的提问来源于stack exchange,提问作者Charlio
相关产品推荐
相关产品推荐

