This is a scenario I've encountered pretty regularly - and worked around it rather than try to solve it.
I have a control workbook with the following worksheets
In the workbook is a named range "myData" which is the data in sheet "Data".
The VBA gets data and pastes it in "Data" then renames the range then refreshes the pivot table which uses the named range as its source. Then the routine copies the sheets Array("Pivot", "Data", "notes") into a fresh workbook which gets saved in a different location as "NewWorkbook.xlsx"
Now if I open the NewWorkbook and look at the data source for the pivot it is referring to the original control workbook.
Is there a simple way of making sure the pivot refers to the data in the new workbook? Should I not use a named range?
You need to update the sourcedata of the pivotcache
Sheets(Array("Data", "Pivot", "notes")).Copy
With ActiveWorkbook.Sheets("Pivot").PivotTables(1)
.PivotCache.SourceData = "myData"
.RefreshTable
End With
for instance
You can also click on the Pivot table tab and redirect it's source from there using the "change source" button and then refreshing as well.enter image description here
Hope this helps.
Related
I have a macro that copies two sheets from my workbook to their own workbook. One sheet has some data defined with a named range, the second has multiple pivot tables, all with the data source as said named range candData.
Once the sheets have copied my slicers lose some of their Report Connections.
In order to reconnect them, I have to manually select each pivot table and set the data source again, even though the data source is already set. (I simply click Change Data Source and immediately click OK, without actually changing anything.)
Once I have done this for each pivot table all report connections are showing again.
I have the following macro to loop through each pivot table and re apply the data source, then reconnect each slicer connection, however even after the data source has been applied, I still have to manually select each pivot table in order to reconnect the slicers.
I am getting no errors, it steps through each pivot table as expected and resets the data source. Any clues why the report connections only work when I set the data source manually instead of through the following?
Sub setSlicerSource()
Dim MyPivot As PivotTable
Dim slCaches As SlicerCaches
Dim slCache As SlicerCache
Set slCaches = ActiveWorkbook.SlicerCaches
With ActiveWorkbook
For Each MyPivot In .Sheets("Pivots").PivotTables
MyPivot.ChangePivotCache .PivotCaches.Create(SourceType:=xlDatabase, SourceData:="candData")
Next MyPivot
For Each slCache In slCaches
For Each MyPivot In .Sheets("Pivots").PivotTables
slCache.PivotTables.AddPivotTable MyPivot
Next MyPivot
Next slCache
End With
End Sub
I'm not sure if this will actually solve your problem, but it's the first thing I'd try fixing regardless:
This line currently creates a new PivotCache for each PivotTable:
MyPivot.ChangePivotCache .PivotCaches.Create(SourceType:=xlDatabase, SourceData:="candData")
Instead, create a PivotCache for PivotTables(1) first before the loop:
.Sheets("Pivots").PivotTables(1).ChangePivotCache .PivotCaches.Create(SourceType:=xlDatabase, SourceData:="candData")
Then in the loop, set all PivotTables to use the cache of PivotTables(1)
MyPivot.ChangePivotCache .Sheets("Pivots").PivotTables(1)
I have a workbook, where there is a RawData sheet and there are 8-9 other sheets that have pivot tables that read a table from RawData. The RawData changes daily, i.e. there can be more or less number of rows in the RawData sheet's table.
Right now, I manually update DataSource property of each pivot table one each sheet using ChangeDataSource feature of Excel. However, this is painful. Crawling on web I found vba code to update all Pivot tables at once. I am not pasting the whole code, but it looks something like this.
ActiveSheet.PivotTables("PivotTable1").ChangePivotCache ActiveWorkbook.PivotCaches.Create(SourceType:=xlDatabase, SourceData:=<RawData-AddressRange>)
But what this code does is, it creates new pivot caches for each pivot table and increases the size of the file. However, I do not want the file size or number of pivot cache's to increase, but just change the dataSource of existing PivotTables/PivotCaches and refresh them.
To set a single PivotCache for all the PivotTable:
Sub UpdatePivots()
Dim ws As Worksheet, pivot As PivotTable, cache As PivotCache
' create a new pivot cache '
Set cache = ThisWorkbook.PivotCaches.Create( _
XlPivotTableSourceType.xlDatabase, _
ThisWorkbook.Sheets("Sheet1").UsedRange)
' set the pivot cache for each pivot table
For Each ws In ThisWorkbook.Worksheets
For Each pivot In ws.PivotTables
If cache.Index Then
pivot.CacheIndex = cache.Index
Else
pivot.ChangePivotCache cache
End If
Next
Next
' refresh the cache
cache.Refresh
End Sub
Just turn RawData into an Excel Table (Ctrl + T is the keyboard shortcut) and then point your PivotTables at that Table. (You'll have to use the 'Change Data Source' button one more time, to get it to change from using a hard-coded reference like $A$1:$Z$1000 to a Table reference like Table1).
From then on, any time you put new data into RawData, the Table will automatically expand (or contract) to accomodate it, and whenever you click refresh, the PivotTables will automatically reference those Tables instead of a hard-coded range.
Also note that if the PivotTables are all based on the exact same data source, refreshing one of them refreshes all of them.
You should consider using dynamic named range to define your RawData. Set the data source of all of your pivot tables to be your dynamic named range and then all you will need to do is click data>refresh all to update all pivot tables
here is a tutorial on dynamic named ranges
http://www.excel-easy.com/examples/dynamic-named-range.html
I'm facing a problem regarding creating Pivot table and chart with multiple worksheets.
I have already created a pivot table and chart using Microsoft Query. I followed the steps from this blog:
http://www.ashishmathur.com/create-a-pivot-table-from-multiple-worksheets-in-the-same-workbook/
Right now, I'm figuring out how I can add new data into pivot table.
Is it possible to add new worksheets of data into already created query and pivot table?
Or do I need to create all over again everytime I add new worksheet of data?
FYI: I'm using Excel 2007 and all my data contains same no. of columns and same column names.
Looks like you need to add just one more block of UNIONALL Select * from dummy2.
If you'd need to do it say weekly or daily I recommend getting to know basic macro editing that will enable you to pull data from numerous sheets to a summary one and base your SQL on that single sheet.
Sub loop_through_sheets()
Dim ws As Worksheet 'define a worksheet
For Each ws In ActiveWorkbook.Worksheets 'for each worksheet
If ws.Name Like "YourString" Then 'make sure you don't consolidate the summary sheet
Call DataGrab(ws)
End If
Next ws
End Sub
I am pretty new to VBA, so please excuse me if this is a simple question! I have created a template report (titled "Client_Name") that I want populated for each client - in essence all this involves is selecting the client in the PivotTable's report filter and copying the PivotTable's data values to the template. In order to automate this, I have created the following code to duplicate the template and rename it for the client currently selected in the PivotTable:
Sheet_Name_To_Create = Sheets("Pivot").Range("B1").Value
Sheets("Client_Name").Select
Sheets("Client_Name").Copy After:=Sheets(Sheets.Count)
Sheets(ActiveSheet.Name).Name = Sheet_Name_To_Create
My next step would be to go back to the PivotTable ("Pivot" worksheet) and copy the data to the newly created client worksheet. However, the worksheet's name will obviously change differ for each client. Is there a way to reference the VBA code to select the worksheet whose name is the same as the client currently shown in the PivotTables's report filter?
Sheets(ActiveSheet.Name) is an inconvenient way of saying ActiveSheet.
Just capture ActiveSheet in a variable after copying.
Dim CopiedSheet as Worksheet
Set CopiedSheet = ActiveSheet
You don't need sheet's name when you have the sheet itself.
Recommended reading: How to avoid using Select in Excel VBA macros
I am new to excel vba and I have some questions regarding referencing a worksheet
I noticed that when I used
Worksheets(3)
The worksheet would be obtained according to the sequence of the worksheet in the workbook
When I used
Worksheets("Name")
It would be retrieved according to the name of the worksheet
However, I found that both approach is troublesome because for method 1, I need to fix the sequence of the worksheet. Once I dragged the worksheet around, the reference would become incorrect.
Method 2 would need me to fix the work sheet name , which is not that flexible.
I noticed that at the left panel of VBA editor, under the Microsoft Excel Objects, whenever the worksheet is created, a new sheet like
Sheet1 (Name) would be created.
Is there any way that I could reference the worksheet based the the Sheet1 variable, which I could fixed it so that I could freely drag the sheet around or change the worksheet name?
Thanks.
The name you refer to is called the CodeName. You can refer to a sheet by this name.
Eg, for your example Sheet1 (Name) can be referenced as
Worksheets("name")
or
Sheet1
Eg Worksheets("name").Activate or Sheet1.Active would both work
Note that you can change this name to something meaningful in the Properties window of the VBA IDE, but you can't change it at run time