【问题标题】:How to hide a row if a cell in one column contains a certain string如果一列中的单元格包含某个字符串,如何隐藏一行
【发布时间】:2017-09-01 21:25:40
【问题描述】:

我有一个像日历一样设置的工作表 - 每列是一个工作日,直到月底,A 列是任务的名称,每一行是一个特定的任务(8 个任务),然后下个月使用相同的任务。

目前我们为每个任务使用一个切换按钮,并使用以下代码隐藏每一行(删除其他行以节省空间):

Private Sub ToggleButton13_Click()
If ToggleButton13.Value = True Then

        Rows(22).EntireRow.Hidden = True

    Else

        Rows(22).EntireRow.Hidden = False

    End If
End Sub

这很好,但是这个日历现在随着额外的任务不断增长,需要我们进入每个切换按钮和每一行来更改它以适应新任务。由于日历不属于我,我没有任何形式的编码经验,所以之前发现了这个,实际用户不想手动更改它(我可以理解为什么,这可能很耗时)。我想知道我们是否可以将“IF”功能与切换按钮一起使用?

如此有效:

  1. 一切都是可见的
  2. 按下切换按钮13

    IF ColumnA cell contains 'Admin' then hide the row ELSE If ColumnA cell doesn't contain 'Admin' then show the row

【问题讨论】:

  • 只需使用IFRow.Hidden。循环遍历行;查看该行是否包含Admin,如果包含,则将该行设置为Hidden。并且可以使用 Button 来触发宏。

标签: excel excel-formula vba


【解决方案1】:

我能想到的两种方法:

循环浏览每一行并设置隐藏属性。
由于代码在 ToggleButton 后面,我们不需要指定工作表名称。代码将在当前活动的工作表上运行,该工作表是正确的工作表,因为您在其上按下了切换按钮。

由于 ToggleButton 返回 TRUE 或 FALSE,我们可以将 hidden 属性设置为该值。

Private Sub ToggleButton1_Click()
    Dim rDataRange As Range
    Dim rCell As Range

    'Set rDataRange = Range("A2", Cells(Rows.Count, 1).End(xlUp))
    'Take into account hidden rows:  
    Set rDataRange = Range("A2", HiddenLastCell(ActiveSheet))

    For Each rCell In rDataRange
        If rCell = "Admin" Then
            Rows(rCell.Row).EntireRow.Hidden = ToggleButton1
        End If
    Next rCell
End Sub 

rDataRange 中设置范围使用此函数来查找最后一个单元格,即使它是隐藏的:

Public Function HiddenLastCell(wrkSht As Worksheet) As Range

    Dim rLastCell As Range
    Dim bHasHiddenData As Boolean
    Dim rSearch As Range
    Dim lLastCol As Long, lLastRow As Long
    Dim lRow As Long

    With wrkSht
        Set rLastCell = .Columns(1).Find("*", , , , xlByColumns, xlPrevious)

        If Not rLastCell Is Nothing Then
            bHasHiddenData = rLastCell.Row <> .UsedRange.Rows.Count
        Else
            bHasHiddenData = .UsedRange.Rows.Count > 1
        End If

        If bHasHiddenData Then
            Set rSearch = .Range(.Cells(1, 1), .Cells(.UsedRange.Row + .UsedRange.Rows.Count - 1, 1))
            For lRow = rSearch.Rows.Count + 1 To 2 Step -1
                If .Cells(lRow, 1) = vbNullString And .Cells(lRow - 1, 1) <> vbNullString Then
                    Set HiddenLastCell = .Cells(lRow, 1)
                End If
            Next lRow
        Else
            On Error Resume Next
            lLastCol = .Cells.Find("*", , , , xlByColumns, xlPrevious).Column
            lLastRow = .Columns(1).Find("*", , , , xlByColumns, xlPrevious).Row
            If lLastCol = 0 Then lLastCol = 1
            If lLastRow = 0 Then lLastRow = 1
            Set HiddenLastCell = wrkSht.Cells(lLastRow, lLastCol)
            On Error GoTo 0
        End If
    End With

End Function

使用自动过滤器隐藏行。
将此代码添加到按钮:

Private Sub ToggleButton1_Click()
    FilterAdmin ToggleButton1.Value
End Sub

此代码将应用或删除过滤器:

Sub FilterAdmin(ToggleOn As Boolean)

    Dim rDataRange As Range
    Dim rLastCell As Range

    With ThisWorkbook

        If ToggleOn Then
            Set rLastCell = LastCell(.Worksheets("Sheet1"))
            With .Worksheets("Sheet1")
                'Get reference to data range (A1 to last used cell).
                'Or you can manually set the range.
                Set rDataRange = .Range(.Cells(1, 1), rLastCell)

                'If auto-filter isn't turned on then turn it on.
                If Not .AutoFilterMode Then rDataRange.AutoFilter

                'Remove any applied filters.
                If .FilterMode Then .ShowAllData

                rDataRange.AutoFilter Field:=1, Criteria1:="<>Admin", Operator:=xlAnd
            End With
        Else
            If .Worksheets("Sheet1").FilterMode Then .Worksheets("Sheet1").ShowAllData
        End If
    End With

End Sub  

此函数将返回包含数据并用于上述过程的最后一个单元格:

Public Function LastCell(wrkSht As Worksheet, Optional Col As Long = 0) As Range

    Dim lLastCol As Long, lLastRow As Long

    On Error Resume Next

    With wrkSht
        If Col = 0 Then
            lLastCol = .Cells.Find("*", , , , xlByColumns, xlPrevious).Column
            lLastRow = .Cells.Find("*", , , , xlByRows, xlPrevious).Row
        Else
            lLastCol = .Cells.Find("*", , , , xlByColumns, xlPrevious).Column
            lLastRow = .Columns(Col).Find("*", , , , xlByColumns, xlPrevious).Row
        End If

        If lLastCol = 0 Then lLastCol = 1
        If lLastRow = 0 Then lLastRow = 1

        Set LastCell = wrkSht.Cells(lLastRow, lLastCol)
    End With
    On Error GoTo 0

End Function  

您可以将代码中的工作表引用更改为使用ActiveSheet 而不是Sheet1(同样,当您按下切换按钮时,正确的工作表将处于活动状态)。

【讨论】:

  • 谢谢达伦·巴特鲁普-库克!我已经使用了您的第一个建议,这已经解决了我遇到的问题,我现在唯一的问题是,如果按下了我拥有的所有切换按钮并且隐藏了任务,那么即使它们也无法取消隐藏拨动开关被压下。不要以为您对此有任何指示吗?我正在考虑创建另一个 ToggleButton 来取消隐藏所有行。
  • 隐藏所有任务的声音隐藏了所有行,因此列 A 似乎是空的,设置 rDataRange 的行将返回对单元格 A1:A2 的引用。我将更新代码以考虑到这一点 - 这可能不是找到最后一行的最佳方法(考虑到隐藏行),但它可以工作。
【解决方案2】:

假设:A 列中的条目是连续的……随着您的工作表不断增长,它会派上用场,因此只需要遵循一种格式。

     Private Sub ToggleButton13_Click()

        Dim indexCol, indexRow as Integer
        dim myKey as String

        myKey = "Admin"


        indexCol = 1 ' For Column A
    indexRow = 2 'row index from where the first entry starts in the Column


    ' loop will traves each row utill columnA entry correspondig to that row is not empty
    Do While IsEmpty(ActiveSheet.Cells(indexRow, indexCol)) = False 

    If ActiveSheet.Cells(indexRow, indexCol).Value = myKey Then

            Rows(indexRow).EntireRow.Hidden = True

        Else

            Rows(indexRow).EntireRow.Hidden = False

        End If

        indexRow = indexRow + 1

    Loop    

    End Sub

【讨论】:

    【解决方案3】:

    尝试一个通用循环,类似于 Ron Rosenfield 在 cmets 中建议的循环。因为你说你没有编码经验,所以会评论它:

    Dim i, LR as Integer 'i will be variable for row in the loop, LR as variable for last row
    LR = Cells(Rows.Count,1).End(xlUp).Row 'Determines the last row based on contiguous cells in column 1, aka column A
    For i = 2 to LR 'Starting at Row 2 with the assumption that you have headers
        If Cells(i,1).Value="Admin" Then 'Cells(row,column) here is column 1, aka column A.  
            Rows(i).EntireRow.Hidden=True 'Hides row if true
        Else
            Rows(i).EntireRow.Hidden=False 'Ensure row is not hidden if false.
        End If
    Next i
    

    这将在您的按钮单击宏中。

    【讨论】:

      猜你喜欢
      • 2012-08-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-06-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多