Pivottable' s content format - excel

everyone,
In this pivottable I'm working on, the source data has money values and quantities. I have a filter in my pivottable in order to choose what type of data I want to see in my pivottable, whether is "V" or "Q".
My problem is that I need to format the contents of the pivottable accordingly to the type of information I'm seeing: for money values, I need to see the contents in "# ###.00 €" format; for quantity values, in "#,##0".
I already tried to use a DataRange property for the pivotfields (as you can see in the code) and even tried using NumberFormat directly on the pivotfields, but none of these worked.
Do you suggest anything to solve this?
Dim vp As Workbook
Dim type_qv As String
Dim chart_pt As PivotTable
Dim pf As PivotField
Set vp = ThisWorkbook
Set chart_pt = vp.Sheets("Chart").PivotTables("VP_table")
'this detects what type of data is being used
type_qv = vp.Sheets("Chart").Range("B2").Value
If type_qv = "Q" Then
For Each pf In chart_pt.RowFields
pf.DataRange.NumberFormat = "#,##0"
Next
End If
If type_qv = "V" Then
For Each pf In chart_pt.RowFields
pf.DataRange.NumberFormat = "# ###.00 €"
Next
End If

It's "Sum of Q" but you don't want to look at the description because they can change it and they can move the table and they can show both fields.
Dim chart_pt As PivotTable, df As PivotField
Set chart_pt = ActiveSheet.Range("A3").PivotTable
For Each df In chart_pt.DataFields
Select Case True
Case df.Name Like "*Q"
df.DataRange.NumberFormat = "#,##0"
Case df.Name Like "*V"
df.DataRange.NumberFormat = "# ###.00 €"
Case Else
df.DataRange.NumberFormat = "# ###.00"
End Select
Next

Related

I get an error while adding value fields to pivot

G'day,
I have an excel macro where i combine my data at the end into a pivot table. However i also have a sub that adds a value field to the table. It looks like this:
Sub AddValuesField()
Dim pvt As PivotTable
Dim pf As String
Dim pf_Name As String
Dim sDatasheet As String
Dim sPivotName As String
sPivotName = "Pivot1"
sDatasheet = "Documents with extracted fields"
Sheets(sPivotName).Select
Set pvt = Sheets(sPivotName).PivotTables("PivotTable1")
pf = Sheets(sDatasheet).Range("A1").Value
pvt.AddDataField pvt.PivotFields(pf), pf, xlSum
End sub
The name of the column is stored in pf(pivotfield). I however get the most descriptive error i dream of receiving: "1004 object defined error"
I hope that someone here can help me out :)
gr,
Menno
When adding a field as Sum to your Pivot-Table, you need to add the words "Sum of" before the PivotField name.
Change your line:
pvt.AddDataField pvt.PivotFields(pf), pf, xlSum
to:
pvt.AddDataField pvt.PivotFields(pf), "Sum of " & pf, xlSum
Note: you don't need to Select your worksheet, you can simply use Set pvt = Sheets(sPivotName).PivotTables("PivotTable1") without selecting it first.

Rename filter values

I have a macro that is supposed to change the "WEEK"-filter on 5 pivot tables on the sheet "veckorapport".
This macro somehow changes "name" on the weeks to the number/text i put in the input box. See first picture, this numbers should be in descending order.
My code:
Sub Veckorapport_filter()
Dim num As String
Dim sht As Worksheet
Set sht = Sheets("Veckorapport")
num = InputBox(Prompt:="Vecka", Title:="ENTER WEEK")
sht.PivotTables("PivotTable1") _
.PivotFields("WEEK").CurrentPage = num
sht.PivotTables("PivotTable2") _
.PivotFields("WEEK").CurrentPage = num
sht.PivotTables("PivotTable3") _
.PivotFields("WEEK").CurrentPage = num
sht.PivotTables("PivotTable4") _
.PivotFields("WEEK").CurrentPage = num
sht.PivotTables("PivotTable5") _
.PivotFields("WEEK").CurrentPage = num
End Sub
I need help with two things: How can i write this code so it doesn't change "name" on the Weeks in the filter?
And 2nd: How can i change back the names to the proper names in the filter-list?
Link to picture: https://imgur.com/kndEnm6
EDIT: Picture how it should look: https://imgur.com/CU9fWex
EDIT 2: Those two weeks have switched places. It should be in descending order: https://imgur.com/PVS3JMf
If you change the .CurrentPage to something that does not exist, then it will instead rename the currently selected page/item. (If you do this manually, instead of via VBA, then you will get a confirmation box, "No item of this name exists in the PivotTable report. Rename 'Old_Name' to 'New_Name'?" with an "OK" and "Cancel" button)
You can partially prevent this by ensuring that "Show Items without Data" is turned on for that field, and/or you can use WorksheetFunction.CountIf to check if that value exists before changing the .CurrentPage
As for resetting the items: Set the .Name, .Value or .Caption of the PivotItem back to the SourceName:
Dim piTMP AS PivotItem, pfTMP AS PivotField
Set pfTMP = sht.PivotTables("PivotTable1").PivotFields("WEEK")
For Each piTMP In pfTMP.PivotItems
piTMP.Name = piTMP.SourceName
Next piTMP
If the names have been switched for 2 items, you will run into an issue (the same name cannot exist twice), so you either need to check for the name being in use, or to just brute-force it with 2 loops - which is probably the simpler solution to write:
Dim piTMP AS PivotItem, pfTMP AS PivotField
Set pfTMP = sht.PivotTables("PivotTable1").PivotFields("WEEK")
'Once through
For Each piTMP In pfTMP.PivotItems
piTMP.Name = piTMP.SourceName & "_AndSomeTextThatYouNeverUse"
Next piTMP
'Twice through
For Each piTMP In pfTMP.PivotItems
piTMP.Name = piTMP.SourceName
Next piTMP
To loop through all pivot tables on the sheet:
Sub Veckorapport_filter()
Dim num As String
Dim sht As Worksheet
Set sht = Sheets("Veckorapport")
num = InputBox(Prompt:="Vecka", Title:="ENTER WEEK")
If len(num) <> 0 then
dim pt as pivottable
for each pt in sht.pivottables
with pt.PivotFields("WEEK")
.clearallfilters
.CurrentPage = num
end with
next pt
end if
End Sub

Excel VBA - Filter specific data in Pivot Table

I tried using the code that appeared to have helped the poster at
Excel VBA - Privot table filter multiple criteria
But I keep on getting the following error: Unable to get the PIvtoFields property of the PIvotTable Class.
Sub FilterPivotItems()
Dim PT As PivotTable
Dim PTItm As PivotItem
Dim FiterArr() As Variant
' use an array to select the items in the pivot filter you want to keep visible
FiterArr = Array("MC. Santa Clara", "MC. Plaza Américas", "MC. El Frutal")
' set the Pivot Table
Set PT = ActiveSheet.PivotTables("PivotTable4")
' loop through all Pivot Items in "Value" Pivot field
For Each PTItm In PT.PivotFields("Value").PivotItems
If Not IsError(Application.Match(PTItm.Caption, FiterArr, 0)) Then ' check if current item is not in the filter array
PTItm.Visible = True
Else
PTItm.Visible = False
End If
Next PTItm
End Sub
What can I do?
After reading about the properties of the class, I finally got to what I wanted.
Sub filterpivot()
Dim pi As PivotItem
Dim pt As PivotTable
Dim first As String
Dim second As String
Dim third As String
Dim fourth As String
first = Range("a26").Value
second = Range("a27").Value
third = Range("a28").Value
fourth = Range("a29").Value
Set pt = Worksheets("Lowest Scores").PivotTables("PivotTable4")
With pt.PivotFields("Nombre conjunto")
For Each pi In pt.PivotFields("Nombre conjunto").PivotItems
If pi.Name = first Or pi.Name = second Or pi.Name = third Or pi.Name = fourth Then
pi.Visible = True
Else
pi.Visible = False
End If
Next pi
End With
End Sub
This bases the applied filter on specific cell values. My apologies if anyone was working on this already, I was on a crunch at work and needed the answer.

How do I loop through the filter items and hide items in an Excel PivotTable using the Data Model?

I have been working with normal PivotTables in VBA, but I recently found some features on the Pivot Tables using the Data Model that I really like--mainly 'Distinct Count'. I have some code in a normal pivot table which filters the table for records 'Like' a string, and it works perfectly. How might I convert this code to the Pivot Table using the Data Model?
With ActiveSheet.PivotTables("Metrics").PivotFields("Reference number")
.Orientation = xlPageField
.Position = 1
.EnableMultiplePageItems = True
For i = 1 To .PivotItems.Count
If .PivotItems(i).Name Like "*oran*" Then
.PivotItems(i).Visible = False
End If
Next i
End With
Here is the code that is created when I record a macro and select the items to display manually under the Data Model:
ActiveSheet.PivotTables("Metrics").PivotFields("[RawData].[Status].[Status]"). _
VisibleItemsList = Array("[RawData].[Status].&[apple_434]", _
"[RawData].[Status].&[banana_689]", _
"[RawData].[Status].&[orange_1346]", _
"[RawData].[Status].&[orange_1454]")
This is the direction I am heading, but I am having some trouble accessing the VisibleItemsList Array:
With ActiveSheet.PivotTables("Metrics").PivotFields("[RawData].[Status].[Status]")
For i = 0 To UBound(.VisibleItemsList)
If i Like "*oran*" Then
i = ""
Debug.Print i
End If
Next i
End With
The output i is numeric 0,1,2,3,4 --not text, and the numbers do not seem to correspond to the number of items in the filter list. I can't figure out how to access the items, so I can show or hide the ones I want using code. I will be honest that I have not been working with arrays for very long.
I ended up using slicers to filter the data.
Dim sC As SlicerCache
Dim sL As SlicerCacheLevel
Dim aArray() As Variant
'create a slicer cache. I just used a recorded macro to get the cache code
ActiveWorkbook.SlicerCaches.Add2(ActiveSheet.PivotTables("Metrics"), _
"[RawData].[Status]").Slicers.Add ActiveSheet, "[RawData].[Status].[Status]", _
"Status", "Status", 141.75, 424.5, 144, 198.75
Set sC = ActiveWorkbook.SlicerCaches("Slicer_Status")
Set sL = sC.SlicerCacheLevels(1) 'this will start with the first item in the slicer
With sL
For i = 1 To .Count
If sL.SlicerItems.Item(i).Name Like "*oran*" Then
GoTo nextiteration 'this will skip over anything
'like oran when saving to the array
End If
ReDim Preserve aArray(0 To i) As Variant
aArray(i) = sL.SlicerItems.Item(i).Name
nextiteration:
Next i
sC.VisibleSlicerItemsList = aArray 'this set the visible items
'= to the array you just created
'ActiveSheet.Shapes("Status").Visible = False
'to hide this slicer, uncomment the line above
End With
This Post by Paul te Braak provided the bulk of the solution. I also used this tutorial for some help with saving items to arrays. This stackoverflow answer also helped me when I needed to work with dynamic arrays. Thanks to -GregGalloway and -jeffreyweir: when looking through the links you provided, I got the idea to search for solutions using slicers.
Hey I know this is an old question, but I recently came up with a good solution for this:
<your other code goes here>
dim v as Variant, xlPT as Excel.PivotTable, str as String
str = vbNullString
set xlPT = xlBook.PivotTables("MyPivot")
with xlPT
for each v in .PivotFields("[table].[field]").PivotItems
select case Right(Left(v.Name, Len(v.Name) - 1), 4) 'my variables are 4-char strings
' But you can manipulate this piece to match your need
case "1234", "4312", "4321", "7462", "etc."
str = str & v.Name & ";"
end select
next v
.CubeFields("[table].[field]").PivotFields(1).VisibleItemsList = Split(str, ";")
end with
<the rest of your code goes here>
The key bit of knowledge here was that the CubeField object contains a PivotFields collection with just 1 member, and we can work with the VisibleItemsList in it.
Hope this helps someone in the future. Happy SO'ing

Trying to pull DataField from PivotTable using VBA in Excel

I am trying to pull both a column value and a data value out of a pivot table, using Excel.
For j = 1 To 1 'pt.RowFields(i).PivotItems.Count
sum = pt.DataFields(2).PivotItems(j)
Client = pt.RowFields(1).PivotItems(j)
Sheets("InvoiceTemplate").Range("c7").Value = Client
Sheets("InvoiceTemplate").Range("i13").Value = sum
Next
The Client value comes back exactly as expected. However, the sum value throws the error:
Unable To Get PivotItems Property from PivotField class.
With a PivotTable that looks like the below, I would expect results of Contoso and £60.50
net gross
Contoso £50.00 £60.50
Adventureworks £100 £110.00
Any idea as to what I am doing wrong? By the way, I know I have a 1 TO 1 loop, but this will be modified once this is working.
I think this does what you want:
Sub PrintPivotFields()
Dim pvt As Excel.PivotTable
Dim pvtAcctField As Excel.PivotField
Dim pvtNetField As Excel.PivotField
Dim pvtItem As Excel.PivotItem
Set pvt = ActiveCell.PivotTable
Set pvtAcctField = pvt.RowFields(1)
Set pvtNetField = pvt.DataFields(1)
For Each pvtItem In pvtAcctField.PivotItems
Debug.Print pvtItem.Name
Debug.Print Intersect(pvtItem.DataRange.EntireRow, pvtNetField.DataRange).Value
Next pvtItem
End Sub
I didn't refer to this great VBA pivot table reference by Jon Peltier, but if you do you may find a better way.

Resources