2017-09-29 2 views
0

Mon objectif est de filtrer un tableau pivotant à l'aide d'une plage d'une autre feuille. Cette plage extrait les données d'une troisième feuille, qui est le vidage de données qui déclenche tout un ensemble de formules et change chaque fois qu'il est utilisé.Filtrage d'une table pivotante en fonction de la plage de valeurs

J'ai le code ci-dessous, mais ce que je peux le voir faire est de parcourir chaque champ Tableau croisé dynamique, en le comparant à la plage, puis en supprimant le filtre. J'ai 32 000 champs qui doivent être vérifiés pour que la macro actuelle soit trop lente à utiliser.

Quelqu'un pourrait-il m'aider à corriger le code afin qu'il ne filtre que sur la base des valeurs de la plage qui ne sont pas vides?

Sub PT() 
Dim PT As PivotTable 
Dim PI As PivotItem 
Set PT = Sheets("Pivot_Sheet").PivotTables("PivotTable2") 
With Sheets("Pivot_Sheet").PivotTables("PivotTable2").PivotFields("Product") 
.ClearAllFilters 
End With 
For Each PI In PT.PivotFields("Product").PivotItems 
PI.Visible = WorksheetFunction.CountIf(Sheets("Sheet1").Range("J2:J100"), 
PI.Name) > 0 
Next PI 
Set PT = Nothing 
End Sub 
+0

Mettez votre code dans les étiquettes de code s'il vous plaît. – Sand

+0

Désolé, Code tagué. – NMO

Répondre

0

Votre code va être lent sur beaucoup, beaucoup de comptes. Avoir une lecture de mon blogpost on this subject si vous êtes intéressé à en apprendre davantage sur les goulots d'étranglement à éviter lors du filtrage des tableaux croisés dynamiques.

Le code suivant devrait vous aider à démarrer. Si vous avez des questions, il suffit de crier.

Option Explicit 

Sub FilterPivot() 
Dim pt As PivotTable 
Dim pf As PivotField 
Dim pi As PivotItem 
Dim i As Long 
Dim vItem As Variant 
Dim vList As Variant 

Set pt = ActiveSheet.PivotTables("PivotTable2") 
Set pf = pt.PivotFields("Product") 

vList = Application.Transpose(ActiveWorkbook.Worksheets("Sheet1").Range("J2:J100")) 

pt.ManualUpdate = True 'Stops PivotTable from refreshing after each PivotItem is changed 

With pf 

    'At least one item must remain visible in the PivotTable at all times, so make the first 
    'item visible, and at the end of the routine, check if it actually *should* be visible 
    .PivotItems(1).Visible = True 

    'Hide any other items that aren't already hidden. 
    'Note that it is far quicker to check the status than to change it. 
    ' So only hide each item if it isn't already hidden 
    For i = 2 To .PivotItems.Count 
     If .PivotItems(i).Visible Then .PivotItems(i).Visible = False 
    Next i 

    'Make the PivotItems of interest visible 
    On Error Resume Next 'In case one of the items isn't found 
    For Each vItem In vList 
     .PivotItems(vItem).Visible = True 
    Next vItem 
    On Error GoTo 0 

    'Hide the first PivotItem, unless it is one of the items of interest 
    On Error Resume Next 
    If InStr(UCase(Join(vList, "|")), UCase(.PivotItems(1))) = 0 Then .PivotItems(1).Visible = False 
    If Err.Number <> 0 Then 
     .ClearAllFilters 
     MsgBox Title:="No Items Found", Prompt:="None of the desired items was found in the Pivot, so I have cleared the filter" 
    End If 
    On Error GoTo 0 

End With 

pt.ManualUpdate = False 

End Sub