You might be able to avoid all this and use the PivotTable.ShowPages Method
. It is optimized for this sort of operation.
Note:
"Owner: Full Name"
must be in the page field area at the top.
- You probably want to check the sheet names don't already exist. You could do an initial loop of sheet names that will be generated from pivot and try deleting them (wrapping inside an
On Error Resume Next, attempt delete, On Error GoTo 0
) to ensure they don't exist first. I have shown how to do this in the second example.
Info: PivotTable.ShowPages Method
Creates a new PivotTable report for each item in the page field. Each
new report is created on a new worksheet.
Syntax expression . ShowPages( PageField )
expression A variable that represents a PivotTable object.
[Optional parameter of pageField.]
Code:
ThisWorkbook.Worksheets("Copy").PivotTables("PivotCopy").ShowPages "Owner: Full Name"
This will produce a sheet for each possible value in the page field "Owner: Full Name"
. If you don't want all of them, simply hold a list of sheet names for sheets to keep, in an array, and loop over all sheets in workbook and if not in array then delete as shown below:
① Example of looping sheets and deleting if not in array:
Option Explicit
Public Sub GeneratePivots()
Dim keepSheets(), ws As Worksheet
keepSheets = Array("FilterValue1", "FilterValue2","Lookup","Copy") '<== List of sheet names to keep
Application.ScreenUpdating = False
Application.DisplayAlerts = False
On Error GoTo errHand
ThisWorkbook.Worksheets("Copy").PivotTables("PivotCopy").ShowPages "Owner: Full Name"
For Each ws In ThisWorkbook.Worksheets
If IsError(Application.Match(ws.Name, keepSheets, 0)) And ThisWorkbook.Worksheets.Count > 1 Then
ws.Delete
End If
Next ws
errHand:
Application.DisplayAlerts = True
Application.ScreenUpdating = True
End Sub
② Using a lookup sheet:
If you do want to still read in the sheets to keep from the Copy
sheet then you can use the following (but be sure to include in the list in column B the sheet names Copy
,Lookup
, the filter values of interest, and any other sheet names you don't want deleted):
Code:
Option Explicit
Public Sub GeneratePivots()
Dim ws As Worksheet, lookups As Range
Application.ScreenUpdating = False
Application.DisplayAlerts = False
With ThisWorkbook.Worksheets("Lookup")
Set lookups = .Range(.Range("B2"), .Range("B2").End(xlDown))
If Application.WorksheetFunction.CountA(lookups) = 0 Then Exit Sub
keepSheets = lookups.Value
End With
Dim rng As Range
For Each rng In lookups
On Error Resume Next
Select Case rng.Value
Case "Lookup", "Copy" '<=Extend for sheets to keep listed in lookups that aren't generated by the pivot filtering
Case Else
ThisWorkbook.Worksheets(rng.Value).Delete
End Select
On Error GoTo 0
Next rng
On Error GoTo errHand
ThisWorkbook.Worksheets("Copy").PivotTables("PivotCopy").ShowPages "Owner: Full Name"
For Each ws In ThisWorkbook.Worksheets
If IsError(Application.Match(ws.Name, Application.WorksheetFunction.Index(keepSheets, 0, 1), 0)) And ThisWorkbook.Worksheets.Count > 1 Then
ws.Delete
End If
Next ws
errHand:
Application.DisplayAlerts = True
Application.ScreenUpdating = True
End Sub
Example run:
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…