One of our clients had a specific requirement: they wanted to view progress per task and per unit on the same page.
The apparent solution was a Power BI matrix.
We quickly encountered some limitations. There is a maximum limit of 100 columns, which is a constraint for us. Moreover, the appearance of 3 scrolls makes it difficult to view all the data in a single frame. Additionally, the width of each column needs to be set manually, which results in differences.
Alongside and below it, we try to add a bar chart to display progress percentages. We encountered a bigger challenge: having three visuals on the same page made it difficult to perfectly align the matrix's rows and columns with the bar charts, resulting in a less-than-ideal presentation.
Thus, we began exploring a custom solution to achieve the desired outcome.
We started with the idea inspired by Kerry Kolosko's Deneb heatmap.
So, we chose Deneb's custom visual for this task. We have effectively organized all tasks within this visual, offering a streamlined user experience with a single scroll. The addition of progress bars on rows and columns provides a straightforward way to track project progress. This update ensures a clear and concise overview of the entire project. We liked the outcome, and the client was satisfied with the result.
{
"data": {"name": "dataset"},
"spacing": 10,
"bounds": "full",
"vconcat": [
{
"spacing": 5,
"bounds": "full",
"hconcat": [
{
"width": 1050,
"height": 550,
"mark": {
"type": "rect",
"stroke": "white",
"tooltip": true
},
"encoding": {
"y": {
"field": "Task",
"type": "ordinal",
"title": null,
"axis": {
"domain": false,
"ticks": false,
"labels": true,
"labelFontSize": 10,
"labelAngle": 0,
"labelPadding": 5
},
"sort": {
"op": "max",
"field": "Sort Column"
}
},
"x": {
"field": "Building",
"type": "ordinal",
"title": null,
"axis": {
"domain": false,
"ticks": false,
"labels": true,
"labelAngle": 320,
"labelFontSize": 10,
"orient": "top"
},
"sort": {
"op": "max",
"field": "Building"
}
},
"color": {
"field": "First Status Matrix",
"type": "nominal",
"title": "Status Matrix",
"scale": {
"domain": [
"1",
"2",
"3"
],
"range": [
"#04A146",
"#D9B300",
"#E8EAFA"
]
},
"legend": null
},
"tooltip": [
{
"field": "Building",
"type": "nominal",
"aggregate": "max"
},
{
"field": "First Status Matrix",
"type": "nominal",
"aggregate": "max"
},
{
"field": "Task",
"type": "nominal",
"aggregate": "max"
}
]
}
},
{
"width": 30,
"height": 550,
"layer": [
{
"mark": {
"type": "bar",
"stroke": null,
"cornerRadiusEnd": 2,
"tooltip": true,
"color": "lightgrey"
},
"encoding": {
"y": {
"field": "Task",
"type": "nominal",
"axis": null,
"sort": {
"op": "max",
"field": "Sort Column"
}
},
"x": {
"field": "AVG of Progress %",
"type": "quantitative",
"aggregate": "mean",
"axis": null
},
"text": {
"field": "AVG of Progress %",
"type": "quantitative",
"aggregate": "mean",
"format": ".1%"
}
}
},
{
"mark": {
"type": "text",
"align": "left",
"baseline": "middle",
"dx": 1,
"dy": -1,
"fontSize": 7,
"tooltip": true,
"color": "black"
},
"encoding": {
"x": {
"field": "AVG of Progress %",
"type": "quantitative",
"aggregate": "mean"
},
"y": {
"field": "Task",
"type": "nominal",
"title": "Task",
"sort": {
"op": "max",
"field": "Sort Column"
}
},
"text": {
"field": "AVG of Progress %",
"type": "quantitative",
"aggregate": "mean",
"format": ".1%"
}
}
}
]
}
]
},
{
"height": 50,
"width": 1050,
"layer": [
{
"mark": {
"type": "bar",
"stroke": null,
"cornerRadiusEnd": 2,
"tooltip": true,
"color": "lightgrey"
},
"encoding": {
"x": {
"field": "Building",
"axis": null,
"sort": {
"op": "max",
"field": "Building"
}
},
"y": {
"field": "AVG of Completion %",
"type": "quantitative",
"aggregate": "mean",
"axis": null
}
}
},
{
"mark": {
"type": "text",
"align": "left",
"baseline": "middle",
"angle": 270,
"dx": 1,
"dy": -1,
"fontSize": 10,
"tooltip": true,
"color": "black"
},
"encoding": {
"x": {
"field": "Building",
"sort": {
"op": "max",
"field": "Building"
}
},
"y": {
"field": "AVG of Completion %",
"type": "quantitative",
"aggregate": "mean",
"axis": null
},
"text": {
"field": "AVG of Completion %",
"aggregate": "mean",
"type": "quantitative",
"format": ".1%"
}
}
}
]
}
]
}