I am a newbie, and I am sort of a enthusiastic learner, a beginner who is making many mistakes. On my pivot table which is picking up two years worth of dates, I am keen to only choose the first two most recent dates, rather than using a slicer. I have tried to make it a little bit dynamic, but I am constantly getting error messages,
I was trying to have cells in my spreadsheet which is from date and a two date, or a code that picks the first two most recent dates. I really want the code to work and pulling my hair out, as I have few other pivot tables. Every time I put the cell reference in between, where the dates are I keep getting coding errors.
I want the pivot items more dynamic as like before, I will try to add a validation on the date from and date to make it lot more dynamic.
I want the pivot items to be x first date and y as the second date referring to two cells on the sheet, which I can amend on the sheet, and another code that just picks the first two most recent dates.
Sub DateSlection ()
With ActiveSheet
.PivotTables("PivotTable4").PivotFields("Date")
.PivotItems("11/2/2016").Visible = True
.PivotItems("10/26/2016").Visible = True
End With
End Sub
kind regards
Ali
For the dynamic filter you could do something like this:
Sub DateSlection ()
Dim startDate As String
Dim endDate As String
With ActiveSheet
'Set your date parameters in the required date format
'- looks like you need US
startDate = Format(.Range("A1").Value, "mm/dd/yyyy")
endDate = Format(.Range("A2").Value, "mm/dd/yyyy")
'clear the existing filter and add the new
.PivotTables("PivotTable4").PivotFields("Date").ClearLabelFilters
.PivotTables("PivotTable4").PivotFields("Date").PivotFilters.Add Type _
:=xlDateBetween, Value1:=startDate, Value2:=endDate
End With
End Sub
I also understand you want to get the first two dates in the pivot table? If so you can do this:
ActiveSheet.PivotTables("PivotTable4").PivotFields("Date").PivotItems(1)
ActiveSheet.PivotTables("PivotTable4").PivotFields("Date").PivotItems(2)
To get the last two dates you can do:
With ActiveSheet.PivotTables("PivotTable4").PivotFields("Date")
ptCount = .PivotItems.Count
last = .PivotItems(ptCount)
secondLast = .PivotItems(ptCount - 1)
End With
Related
I have a Table with a column that I added, that checks the date of that row against a formula.
The result of that formulae is TRUE or FALSE and a subsequent Pivot Table Sums a value in the TRUE rows. I Introduced it to get what is called a Rolling Total Income.
There are two formula and I want to swap from one to another using VBA.
The formula are:
=IF([#Date] = "", "", AND([#Date]>=EOMONTH(TODAY(),-13)+1,[#Date]<EOMONTH(TODAY(),-1)))
for the Rolling data.
=IF(AND([#Date] >=G1,[#Date] <=H1),"TRUE","FALSE")
for the Sum of Income between G1 and H1, the financial year start and end dates.
The VBA I have tried is as follows:
Set lo = Sheet2.ListObjects(1) 'Sheet2 is the Income sheet see Project list
lo.Parent.Activate 'Activate sheet that Table is on
Set lColName = lo.ListColumns(9)
lColName.DataBodyRange.Cells(1).Formula = [=IF(AND([#Date] >=G1,[#Date] <=H1),"TRUE","FALSE")]
Running the above errors and gives #VALUE in the first cell in that column, and doesn't ripple through the rest of the column.
What have I done wrong?
Try
lColName.DataBodyRange.Formula = "=IF(AND([#Date] >=$G$1,[#Date] <=$H$1),""TRUE"",""FALSE"")"
Thanks, those changes have sorted it.
One more refinement I am struggling with.
The IF test statement is testing a date against cells, $G1 and $H1 which I set up for ease of debugging. However I have another worksheet in the workbook where I store all the references/static data I use in the various Sheets and I have placed those dates there. In this Module, before the IF statement, I have set those dates against two variables.
startdate = Range("I2").Value
enddate = Range("J2").Value
I now want to use those in the IF statement but cannot get the correct syntax!
This just errors:
"=IF(AND([#Date] >= startdate,[#Date] <= enddate),""TRUE"",""FALSE"")"
How should I write it?
Thanks
I have a form that is supposed to show the total sum of different numeric values between two dates, a start date and a finish date. For this, I thought the best option would be to use the SumIfs WorkSheetFunction. However, after trying to code this, the function is not working properly. I am not sure of what is wrong. If I type the exact same formula on the worksheet that has the table with my sample data, it works perfectly.
So, the form I designed is the following:
A second label and textbox will be added for the finish (or end) date. However, I thought it would be better to do that once I get the code to work with a single date in the beginning. The textbox where the user will insert the start date is called tbxDate and the textbox that will show the resulting sum is called tbxBalance. The button that triggers the SumIfs functions is called cmdCalculate.
Also, the table that stores the data (which only has one row of data so far for testing purposes) is this one:
The table name is Sales, and the worksheet name is SalesWS. I thought the code should be pretty simple, unless there is something I am missing. What I did was:
Private Sub cmdCalculate_Click()
Set SalesRange = Worksheets("SalesWS").Range("Sales[TOTAL]")
Set DatesRange = Worksheets("SalesWS").Range("Sales[DATE]")
tbxBalance = Application.WorksheetFunction.SumIfs(SalesRange , DatesRange , ">=" & tbxDate)
End Sub
The issue is that the >= part of the criteria is failing. I only get proper results using only the greater than or less than conditions. For example, if I enter the date 09/08/2020 in the textbox the result in the balance textbox is 0, but if I enter the date 08/08/2020 or anything before it works. It just ignores the condition to sum the values if the date is equal to what is entered. It only works with dates greater or less than what the user inputs in the textbox, excluding the chosen date.
I already checked that the column with the dates in the table is formatted properly.
The version of your code given below should work provided your DATE range contains true dates and tbxDate contains a string VBA can recognise as a date.
Private Sub cmdCalculate_Click()
Dim Fun As Double
Set SalesRange = Worksheets("SalesWS").Range("Sales[TOTAL]")
Set DatesRange = Worksheets("SalesWS").Range("Sales[DATE]")
Fun = Application.WorksheetFunction.SumIfs(SalesRange, DatesRange, ">=" & CLng(CDate(tbxDate.Value)))
tbxBalance = Format(Fun, "#,##0.00")
End Sub
Remember that tbxBalance will cotnain a text string, not a number. Use Excel's NUMBERVALUE function to convert the formatted number you have in tbxBalance after the above code back to a number you can calculate with.
I have a refreshable table in excel and I want to filter the rows by a couple of date ranges. Each row has a date and other information.
I want to find the rows that are in the first date range (F1:F2) and are not in the second date range (H1:H2).
The table is refreshable, and can change size. It currently spans A3:X6146. The table is a query, so it will change sizes when a separate date range is used to find the table values.
I don't have much VBA experience, so this problem is tripping me up. Any ideas?
Thanks
EDIT:
I'll try to make the issue clearer.
I have a table that is created via a query that pulls in data that falls between the Starting Date and the Ending Date, 1/1/2016 and 12/31/2017 here. It lists each time an item was purchased, so each one can be listed multiple times.
I want to find which items were purchased (listed in the table) between the Active Date Range start and end dates (cells F1 and F2), and NOT purchased between the Inactive Date range (cells H1 and H2).
Starting Date: 1/1/2016 Active Date Range Start: 3/1/2016 Inactive Date Start: 3/2/2017
Ending Date: 12/31/2017 Active Date Range End: 3/1/2017 Inactive Date End: 9/22/2017
item date
1 9/21/2017
2 9/20/2017
3 9/20/2017
Yes, I can say to you what I would do.
Create one additional column to keep the result value, if is in or out of the date range. Then
dim t() as string, lin as long, linf as long
linf=Range("F65536").End(xlUp).Row 'or any other more precise way to get the final line
redim t(1 to linf-2,1 to 1)
'range dates - are they on the worksheet?
dim rg_dates as Range,r as range,b as boolean
set rg_dates=Sheets("xxxx").Range("B1:B4") ' just an example, the range would be B1:C4 but use only the first column - see below
For lin=3 to linf
b=False
For each r in rg_dates
If cells(lin,"F").value>= r.Cells(1,1) and cells(lin,"G").Value<=r.Cells(1,2).value then
b=true
Exit for
End If
Next r
If b then t(lin-2,1)="Y" else t(lin-2,1)="N"
Next l
Range("Z3:Z" & linf).Value = T
'Then just filter the table.
There would be then many things to do to keep it error free, and how to apply it at the concrete situation. Hopefully with what I wrote above you can get an idea about things you can do using VBA. If you are using code to filter the table you can do all this invisible to the user, creating an extra column for the filter criteria, filtering, and then deleting the whole column..
I'm not even looking for a solution as much as I am some guidance on how best to even begin tackling this. Thanks in advance for reading.
To start off with, I find it difficult to describe my goal with words, so I created a picture which I hope will make it clear when paired with my words:
I'll try and describe what I'm trying to do as simply as possible:
I have a resource forecasting sheet which lists employees, the projects they're working on, and then features a "calendar" where the employees' estimated hours per project are shown for specific date periods in each month. (In this case, the date periods are each week in a month, plus the last day in each month if it falls in between a week.)
Next, each project that has employees assigned to it has its own tab. These project tabs list the employees working on the specific project, and feature estimates and actuals of both billable and non-billable hours. In any case, the classification of billable or non-billable is irrelevant except to say that each employee may or may not be listed twice in each project sheet. Finally, one employee may have hours logged in multiple sheets, and each sheet features the same calendar view as the resource forecasting sheet. What I'd like to do in pseudo-code would be:
SUM the billable and non-billable estimated hours of all projects where:
The employee name is the same in any project tab as the resources sheet,
The project name in the resources sheet is the same as the name of the project tab,
The date range in the resourcing sheet matches the date range in any project tab
It would be amazing if I could do the majority of this stuff using formulas, but I imagine I'll need to use some vba as well, which I have a little experience with, but not much at all.
If anyone could take a look at the image I've posted and give me some ideas as to a.) whether this can even be done, b.) how to start to think about doing it logic-wise and c.) whether this can be done with formulas, vba or a combination of the two, I'd be very grateful.
Thanks again,
Steve
Since you have a lot of merged cells, I found the simpliest way is to use UDF:
Function getData(targetName As String, targetSheet As String, targetDate)
Dim res As Double
Dim col As Integer
Dim cell As Range
Dim names As Range
Dim lastrow As Long
With ThisWorkbook.Worksheets(targetSheet)
lastrow = .Cells(.Rows.Count, "A").End(xlUp).Row
col = Application.Match(targetDate, .Range("4:4"), 0)
If col = 0 Then
getData = CVErr(xlErrNA)
Exit Function
End If
Set names = .Range(.Cells(4, "A"), .Cells(lastrow, "A"))
For Each cell In names
If cell = targetName Then
res = res + cell.Offset(, col - 1)
End If
Next cell
End With
getData = res
End Function
I've changed formulas on your 4th row in each sheet (with dates that was stored as text). Now they are stored dates and has format "mmm-dd". It is more correct approach, because if you're using =Text(date,"mmm-dd") you could have two identical columns for different years which is uncorrect (i.e. jan-11 for 2013 and jan-11 for 2014).
One more thing: this line res = res + cell.Offset(, col - 1) gets EST column. If you need ACT column, use res = res + cell.Offset(, col)
P.S. if you'd like to use plain formulas - look into INDIRECT function, but I don't suggest you to go this way, because your data structure and merged cells would make formulas very complex.
Here is test workbook.
I have created a pivot table that lists the number of visitors to a store on a given date. There are 3 columns of data, the date column and two columns of numbers representing the visitors. When I create a chart from this data I get a bar of data that represents dates before and after the range of dates that make up the data. I can suppress all dates that occur prior to the dates I want to view by using the command:
With Worksheets("Pivot Tables").PivotTables("Weekly Statistics").PivotFields("Date")
.PivotItems.Item(1).Visible = False
However, I can't find a way to suppress the dates that occur after today's date. This leaves me with a column on my bar chart that is blank and has the axis value ">3/27/2013". I can suppress it by actually typing this line:
.PivotItems.Item(">3/27/2013").Visible = False
but having to manually do this every time I update the sheet is laborious and makes the sheet unusable to anyone else.
I tried to create a variable that would update the value inside the () but I can't get it to work.
Dim t
t = Worksheets("Data").Range("i3").Value
.PivotItems.Item(t).Visible = False
(where i3 is a cell in the Worksheet("Data") that is a concatenation of the date; in this case the cell contents are ">3/27/2013" )
Thanks
You could try to use alternative filtering technique:
t="3/27/2013"
Worksheets("Pivot Tables").PivotTables("Weekly Statistics").PivotFields("Date").PivotFilters.Add Type:=xlBefore, Value1:=t
However, it is used as of Excel 2007.
If not working try to start with:
Worksheets("Pivot Tables").PivotTables("Weekly Statistics").PivotFields("Date").ClearAllFilters