I have multiple simple calculated measures, which I would like to combine into categories, so that one could use this "category measure" in matrix visual.
Each measure basically counts data with some filter(s), like:
Blue =
CALCULATE(
COUNT(data[Full name]),
FILTER(data, data[White/Blue] = "Blue")
)
My attempt to this, was to create a table for measures categories, and then measure indexed accordingly.
Table:
Measures categories =
DATATABLE (
"Category", STRING,
"Sub-Category", STRING,
"Index", INTEGER,
{
{ "Direct/Indirect", "Direct", 1},
{ "Direct/Indirect", "Indirect", 2},
{ "White/Blue", "White", 3},
{ "White/Blue", "Blue", 4}
}
)
Measure:
Categories measure =
VAR SelectedMeasure_ =
SELECTEDVALUE('Measures categories'[Index])
RETURN
IF(HASONEVALUE('Measures categories'[Index]),
SWITCH(
SelectedMeasure_,
1, [Direct],
2, [Indirect],
3, [White],
4, [Blue]
)
)
This seems to work fine, however I'm missing Totals in Matrix visual, how do I get sum of measures per category/subcategory and total? I can workaround this by adding additional Total fields with corresponding sums, but there must be a better way.
One possible solution, is to create another measure, which sums value of Categories measure.
Your hasonevalue() looks like the problem. You need to rethink your approach to use values() but hard to advise further without a .pbix or full sample data to work from.
Related
What I want to achieve is to create table where I can display a list of items with max values, but grouped with another dimension.
Here is the example:
[
Have tried this, but the result is wrong
sum_of_max = SUMX(VALUES(T1[dimension1]),CALCULATE(MAX(T1[Value])))
Use this measure instead:
sum_of_max =
CALCULATE(
SUM(T1[value]),
T1[value] = MAX(T1[value])
)
I have the following Table:
BaseTable
It represents processes with a certain category.
And there is also a Date Table over column TIMESTAMP.
I would like to show a Measure based on another Measure that calculates the Date-Difference until the selected Date.
So first this is how I calculate the Date-Difference:
AGE =
VAR SELECTED_DATE = CALCULATE(MAX(DATUM[Date]), ALLSELECTED(DATUM))
VAR STARTDATE_PROCESS = Calculate(MAX(Workflow[MIN_TIMESTAMP]),DATUM[Date]<=MAX(DATUM[Date]), ALL(DATUM[Date]))
RETURN
DATEDIFF(STARTDATE_PROCESS,SELECTED_DATE,DAY)
Now I want to use a Measure which depends on the result of AGE, like
NEW = IF([AGE]<=3,CALCULATE(COUNT(Workflow[PROCESS]),DATUM[Date]<=MAX(DATUM[Date]),ALL(DATUM)))
or
OLD = IF([AGE]>3,CALCULATE(COUNT(Workflow[PROCESS]),DATUM[Date]<=MAX(DATUM[Date]),ALL(DATUM)))
The Measures AGE, OLD and NEW look like that with the Base Table:
Measures
As you can see the aggregation is not working correctly:
Result_Wrong
But it should be like that
Result_Correct
Any idea how to fix that?
Thank you!
So the problem is that the subtotal is calculated at a whole different context, and because your Age measure is based on the MAX(Workflow[MIN_TIMESTAMP]) that won't take into account that there can be multiple processes.
To do what you want, you need to change the New and Old measures to perform an aggregation per process and then return the result of that. Something like this:
New_agg =
VAR tbl = ADDCOLUMNS(CALCULATETABLE(VALUES(Workflow[Process]), ALL('Date')), "age", [Age], "count_process", CALCULATE(COUNT(Workflow[Process]), ALL('Date')))
RETURN SUMX(tbl, IF([age]<=3, [count_process]))
Demo File
Let me know if below solution is working
Unfortunately I am unable to generate the dummy data that you have been using, so Created my own data for developing the solution.
Now from this data I have calculated the difference of dates and put it as Age
Now to get the count of process for the condition like yours, I have created two formulas and the result is:
Logic I followed here is, instead of creating measure I have created columns and took the sum of those columns which will give the data you need as sum of those columns.
Column for New:
New = IF((Sheet1[Age]) > 20, 1,0)
Column for Old:
Old = IF((Sheet1[Age]) < 20, 1,0)
Now place both formulas in "Values" and take sum as the aggregation.
Final result is
I have created this table in Power BI:
DimProduct = UNION(
ROW("ProductId", 1, "Product", "AB","ProductType","A"),
ROW("ProductId", 2, "Product", "AC","ProductType","A"),
ROW("ProductId", 3, "Product", "AD","ProductType","A"),
ROW("ProductId", 4, "Product", "BB","ProductType","B"),
ROW("ProductId", 5, "Product", "BC","ProductType","B")
)
Then I created this table:
DimProductSelectedType =
VAR vSelectedProduct=
SELECTEDVALUE('DimProduct'[Product])
RETURN
ROW("Col1",vSelectedProduct)
I dropped DimProduct[Product] into a slicer
I dropped DimProductSelectedType into a list
I expect that when I pick one product from the product slicer, it will appear in the list. But the list always remains blank.
I had thought that SELECTEDVALUE would reflect any single value picked in a slicer
That's my immediate problem, and this can be summarized as
Table columns that use DAX calcs are evaluated at import time. Measure are evaluated at runtime
What I'm actually working towards is:
Pick a product in a slicer
Identify that products product type
Show visualisations comparing selected product compared to all other products within that product type
I actually started with this and now I'm working my way back.
DimProductTypeSelected =
VAR vSelectedProduct=
SELECTEDVALUE('DimProduct'[Product])
VAR vSelectedProductType=
SUMMARIZE(
FILTER(
ALLSELECTED(DimProduct),
DimProduct[Product]=vSelectedProduct
),
DimProduct[ProductType]
)
RETURN
FILTER(
ALLSELECTED(DimProduct),
DimProduct[ProductType]=vSelectedProductType
)
When you select item in a slicer it already creates fitler context on other visuals, so there is no need to overwrite it manually. What you would need to do is to create a fitler context for all products, e.g. by using ALL or ALLSELECTED for the comparators. But in order for this to be dynamic you need to use measures, tables are static and do not recalculate with UI changes.
To explain why you get your results with your current approach - tables are refreshed once and do not change afterwards. Therefore vSelectedProduct always returns blank, as at the moment of refreshing this table there is no filter context on the DimProduct[Product], so it defaults to blank
If you create a measure Measure = SELECTEDVALUE('DimProduct'[Product]) and put DimProduct[Product] into a slicer it will show the selected product for a single select and blank for multiselect (or all values)
EDIT
Regarding the second part of your question - selecting a product will create a filter context only for that product in the other visuals. Then you could use e.g.:
CountRowsPerType =
VAR vSelectedType =
SELECTEDVALUE('DimProduct'[ProductType])
RETURN
CALCULATE( COUNTROWS(DimProduct), ALL(DimProduct[Product]), 'DimProduct'[ProductType] = vSelectedType )
which will return count for all the products of that type even though the visual will only show the selected product
I want to count records in a certain condition and allow people to filter down to the relevant records, but selecting a measure value (which filters so it only counts certain rows) isn't cross-filtering others as I'd expect. Maybe ths isn't possible or maybe I'm just doing it wrong, but I'd appreciate help.
I have a single table:
let
Source = Table.FromRows(Json.Document(Binary.Decompress(Binary.FromText("i45Wci4tLsnPTS1SMFTSUTJUitVBEjICChmgChljCplgajSFCMUCAA==", BinaryEncoding.Base64), Compression.Deflate)), let _t = ((type text) meta [Serialized.Text = true]) in type table [#"Customer Name" = _t, #"Ordered Recently" = _t]),
#"Change to INT" = Table.TransformColumnTypes(Source,{{"Ordered Recently", Int64.Type}}),
#"Change to T/F" = Table.TransformColumnTypes(#"Change to INT",{{"Ordered Recently", type logical}})
in
#"Change to T/F"
The result looks like this:
Customer Name Ordered Recently
Customer 1 True
Customer 2 False
Customer 3 False
Customer 4 True
Customer 5 True
I added two measures:
Count Total = COUNTROWS(Customers)
Count Recent = CALCULATE([Count Total], filter(Customers, Customers[Ordered Recently]))
If I put both measures in a bar chart and highlight the "Count Recent" measure, I'd expect it to know to filter other visuals based on the FILTER statement present in the measure, but that doesn't happen. Selecing this value doesn't impact anything else on my page (including just a count of rows).
The goal is to allow people to select a measure that counts rows and then to see the makeup of the data in those rows (select a count of late projects and filter other visuals to describe those late projects).
Is this possible or am I doing something wrong?
EXAMPLE:
Here's what it looks like now, with nothing selected:
When I select the black bar (the "Ordered Recently" measure), nothing changes right now - but here's what I want to happen (actually achieved with a slicer off screen on the T/F field):
I understand if my measure is a SUM of an integer field, it includes every row in the calculation - even when the row value is zero - and there's no way to filter my dataset based on that. However, in this case, my measure is actually using a FILTER on the dataset so that it only counts rows with a certain criteria set - given that, it should be able to filter the requested table, and then flow that filter through the rest of my dataset (the same way it would if I selected a bar from a chart where I had used that same field as the series - exactly how it works when I do this:
PBIX file to download as an example
No, I don't believe it's possible to make a measure value cross-filter other visuals based on filters within the measure definition.
You can, however, click on i.e. row header Customer 3 and it should cross-filter the other visuals to only include that customer. Any table column you set for the rows or columns of a matrix visual should behave this way.
Here's a hacky workaround:
Create a measure that shows the right values when you use the column you want to use as a filter as the Legend or Axis (like in your last image). For example, in this case, you could do this:
Total Customers =
VAR TF = SELECTEDVALUE ( Customers[Ordered Recently] )
RETURN
COUNTROWS (
FILTER (
ALLSELECTED ( Customers ),
IF ( TF, TF, TF || Customers[Ordered Recently] )
)
)
This behaves how you want, but isn't labeled as you want. To achieve that create a calculated column with the labels you want. For example,
Label = IF(Customers[Ordered Recently], "Ordered Recently", "Total Customers")
Then take Ordered Recently off the axis and put the Label column in the Legend box to get this:
Your Filter argument is really Filter(All(Customers, Customers[Ordered Recently])
You remove all filters on the Customer Table, and then specify Ordered Recently Column as the filter.
Try
[MeasureName] =Calculate([Count Total], All(Customer), Values(Customer[Recently Ordered]), Customer[Recently Ordered] = “True”)
My goal is to aggregate values in a single column based on groups of other columns.
For example my table looks like:
https://imgur.com/YbTFDh2
and the desired output would be something like this:
https://imgur.com/5It0KgW
I can do this on the same table or create a new table.
I have attemped this:
SUMMARIZECOLUMNS (
'Sheet1 (2)'[Item],
'Sheet1 (2)'[Name],
"Total", SUM([Money])
)
but the error returned is: *The expression refers to multiple columns. Multiple columns cannot be converted to a scalar value.*z
EDIT
Ultimately my end goal is to create a calculated column to round the dollar up based on a series of ranges using SWITCH function.
=SWITCH(TRUE(),[Money] <= 10, 0, [Money] <= 20, 10)
...something like that.
The easiest thing to do would be create a simple measure:
Total=SUM([Money])
Then, you can view this in Power BI by putting the Name on an axis:
Like this...
Table Example
Or this...
Bar Chart Example
In Excel, you could use Pivot Tables to show the same thing.
You can achieve a sum of each group rounded down to the nearest 10 using the following:
Answer =
FLOOR ( SUM ( 'Sheet1 (2)'[Money] ), 10 )
FLOOR() takes the Sum of your "Money" column as the first argument, and your required multiple (in this case 10) as the second. CEILING() and MROUND() can be used alternatively if you want to round up, or to the nearest value.
EDIT:
Based on your recent comments, perhaps something like this would be more appropriate:
Answer =
IF(SUM('Sheet1 (2)'[Money]) < 10, 0,
IF(SUM('Sheet1 (2)'[Money]) < 20, 10,
IF(SUM('Sheet1 (2)'[Money]) < 25, 20, BLANK())))
SWITCH can only be used with constants, so you'll need to chain together some IF statements to get what you're looking for.