【问题标题】:vba Range.Autofilter fails on Excel 2011 (Mac)vba Range.Autofilter 在 Excel 2011 (Mac) 上失败
【发布时间】:2011-07-28 14:09:41
【问题描述】:

我的代码中有一个公共的关注子,如下所示:

Public Sub ResetFilters(ByRef tbl As ListObject)
    With tbl

        '// If Filter Arrows are OFF - turns them on
        '// If Filter Arrows are ON - turns them off and resets filter
        .Range.AutoFilter

        '// Always turns filter arrows to on and sorts table by first field
        .Range.AutoFilter Field:=1
    End With
End Sub

如您所见,我使用 Excel 表格(vba 中的ListObjects),因此我将引用传递给子,它应该将表格重置为未过滤状态。它在装有 Excel 2007 的 PC 上运行良好,但在 Mac 上的 Excel 2011 上却失败了:

对象“范围”的方法“自动过滤器”失败

Excel 2011 VBA Reference 的以下链接显示了 Range 对象的 AutoFilter 方法,它与我在 Excel 2007 VBA 参考中看到的内容相匹配。

那么任何人都知道为什么会失败吗?

【问题讨论】:

    标签: excel vba macos


    【解决方案1】:

    我无法让您的ListObject.ShowAutoFilter 解决方法为我工作,尤其是因为我不仅需要关闭自动过滤器,而且在我的代码完成后以编程方式恢复过滤器。

    我在 Mac 上进行了一些宏录制,发现即使 Range.AutoFilter 抛出错误 Selection.AutoFilter 也不会。所以我可以只选择我想要过滤的范围,然后将我的过滤器应用于选择。

        ws.Range(currentFiltRange).Select
        Selection.AutoFilter
    

    如果您需要保留用户的选择,您也可以轻松地恢复它,这是我保存自动过滤状态的完整子例程,运行您自己的代码,然后恢复自动过滤状态,它适用于 PC 和 Mac。

    Private Sub saveAndRestoreAutoFilterPCandMAC()
    
    
        Application.ScreenUpdating = False
    
        'START SAVING AUTOFILTER STATE
        Dim ws As Worksheet
        Dim filterArray()
        Dim currentFiltRange As String
        Dim col As Integer
        Dim usingAutoFilter As Boolean
        Dim userSelection As String
    
        usingAutoFilter = False      
        Set ws = ActiveSheet
    
        'Capture AutoFilter settings
        If ws.AutoFilterMode = True Then
            With ws.AutoFilter
                currentFiltRange = .Range.Address
                If ws.FilterMode = True Then
                    usingAutoFilter = True
                    With .Filters
                        ReDim filterArray(1 To .count, 1 To 3)
                        For col = 1 To .count
                            With .Item(col)
                                If .On Then
                                    filterArray(col, 1) = .Criteria1
                                    If .Operator Then
                                        filterArray(col, 2) = .Operator
                                        If .Operator = xlAnd Or .Operator = xlOr Then
                                            filterArray(col, 3) = .Criteria2
                                        End If
                                    End If
                                End If
                            End With
                        Next col
                    End With
                End If
            End With
        End If
        'END SAVING AUTOFILTER STATE
    
        'Remove AutoFilter
        ws.AutoFilterMode = False
    
        'Start Your code here
    
        'End of your code
    
        'START RESTORE FILTER SETTINGS
        If Not currentFiltRange = "" Then
            userSelection = Selection.Address
            ws.Range(currentFiltRange).Select
            Selection.AutoFilter
            If usingAutoFilter Then
                For col = 1 To UBound(filterArray(), 1)
                    If Not IsEmpty(filterArray(col, 1)) Then
                        If filterArray(col, 2) Then
                            'check if Criteria2 exists and needs to be populated
                            If filterArray(col, 2) = xlAnd Or filterArray(col, 2) = xlOr Then
                                ws.Range(currentFiltRange).Select
                                Selection.AutoFilter Field:=col, _
                                    Criteria1:=filterArray(col, 1), _
                                    Operator:=filterArray(col, 2), _
                                    Criteria2:=filterArray(col, 3)
                            Else
                                ws.Range(currentFiltRange).Select
                                Selection.AutoFilter Field:=col, _
                                    Criteria1:=filterArray(col, 1), _
                                    Operator:=filterArray(col, 2)
                            End If
                        Else
                            ws.Range(currentFiltRange).Select
                            Selection.AutoFilter Field:=col, _
                            Criteria1:=filterArray(col, 1)
                        End If
                    End If
                Next col
            End If
        End If
        ws.Range(userSelection).select
    
        'END RESTORE FILTER SETTINGS
    
        Application.ScreenUpdating = True
    
    End Sub
    

    【讨论】:

      【解决方案2】:

      似乎没有很多人回答这个问题...无论如何,如果其他人有兴趣,我想我找到了使用ListObject.ShowAutoFilter 属性的解决方法。它是一个读/写布尔属性,当关闭时,它将重置 ListObject 中的过滤器。它还有一个额外的好处是可以在 PC 上同时使用 Excel 2011 for Mac 和 Excel 2007(以及 2010)。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2013-08-19
        • 1970-01-01
        • 2016-09-29
        • 1970-01-01
        • 1970-01-01
        • 2014-12-10
        相关资源
        最近更新 更多