Pivoting
Column Pivoting
Column pivoting uses the values of cells in a particular column
to create new columns. In Graphite Grid, column pivots are a
separate set of column definitions that can be toggled on or off
using the pivotModeIsOn
property. However, the definitions are not
provided directly to the grid but are created via the pivotColumnSource
property.
The pivotColumnModel
is used by Graphite Grid to determine which columns have
been pivoted. Columns used in the pivotColumnModel
must have the
pivotColumnKey
property set in their definition. Generally, for pivot columns
to make sense, there should also be some measures used for the pivot. The
measureModel
is used by Graphite Grid to determine which columns should be
used as measures for pivots.
In summary:
pivotModeIsOn
: used to switch between column pivot mode and normal column display.pivotColumnSource
: used by Graphite Grid for the creation of pivot columns.pivotColumnModel
: determines which columns have been pivoted. These columns must have apivotColumnKey
defined in their definition.measureModel
: determines which columns should be used as measures for pivots.
These properties form the starting point for column pivots in Graphite Grid. A basic example is shown below:
export function ColumnPivotingBasic() {
const grid = useGraphiteGrid({
initial: {
columnDefinitions: financeColumns,
pivotColumnModel: ["exchange"],
measureModel: ["volume"],
pivotModeIsOn: true,
pivotColumnSource: "client",
baseColumnDefinition: {
freeWidthRatio: 1,
},
rowDataSource: { kind: "client", data: financeData },
},
});
return (
<WindowContainer className="h-[400px]">
<div className="border border-border h-full">
<GraphiteGridDom state={grid} />
</div>
</WindowContainer>
);
}
Tip
You may notice that row pivots are not required for column pivots.
This is intentional. Column pivots may be defined arbitrarily (depending
on the pivotColumnSource
). The default "client"
source creates new columns
where the values are the constituent parts of a measure for a particular row.
The Pivot Column Source
The pivotColumnSource
is required to create pivot column definitions.
It may be one of the following:
"client"
: for use with a client row data source, Graphite Grid will use its default settings for creating column pivots.pivotColumnSourceClient
: allows you to modify the pivot columns generated by Graphite Grid when using client column pivots.pivotColumnSourceControlledi
: a controlled pivot column source that should return a set of pivot column definitions. Definitions may be returned asynchronously.null
: indicates a data set does not support column pivots.
Client Pivot Column Source
When the pivotColumnSource
is set to "client"
, Graphite Grid
will create its default pivotColumnSourceClient
value for column pivots.
This default will use the pivotColumnModel
to generate pivot definitions,
which is usually sufficient for client column pivoting.
Depending on the columns being pivoted, adjusting the columns created
by Graphite Grid's client source is sometimes helpful. A
pivotColumnSourceClient
may be provided instead of the
"client"
value in such cases. The
pivotColumnSourceClient
has a postProcessColumnPivotDefinitions
callback that may be
used to alter the generated pivot column definitions. For example, we
could omit the total
column that is generated by pivots:
export function ColumnPivotingClient() {
const grid = useGraphiteGrid({
initial: {
pivotColumnSource: {
kind: "client",
postProcessColumnPivotDefinitions: ({ definitions }) => {
return definitions.filter((def) => !def.id.includes("total"));
},
},
// other properties
},
});
// ...
}
The postProcessColumnPivotDefinitions
callback must return an array of
Column Definitions.
Furthermore, every pivot column must begin with a pivotColumnIdPrefix
.
The pivotColumnIdPrefix
is a prefix on every pivot column. Graphite Grid uses it
to differentiate between pivot columns and normal columns.
Graphite Grid uses a default value for this prefix, but the default may be
changed by providing a value for the pivotColumnIdPrefix
property on the grid
state.
const grid = useGraphiteGrid({
initial: {
pivotColumnIdPrefix: "Pivot:",
// other properties
},
});
Controlled Pivot Column Source
The controlled pivot column source delegates full control of generating pivot column definitions to the column source. Unlike the "client" source, the controlled pivot column source can asynchronously generate pivot columns.
The example below shows a contrived example of a controlled pivot
source. Notice the getColumnPivotDefinitions
function is an async
function - but it may also be a synchronous function if necessary.
Furthermore, unlike the "client"
source, how pivot columns are defined
and created is entirely up to the source. Hence, a valid
measure model is not required.
export function ControlledPivotColumnSource() {
const grid = useGraphiteGrid({
initial: {
pivotColumnModel: ["exchange", "sector"],
pivotModeIsOn: true,
pivotColumnSource: {
kind: "controlled",
getColumnPivotDefinitions: async ({ api }) => {
const model = api.getPivotColumnModel();
const idPrefix = api.getPivotColumnIdPrefix();
return model.map((id) => {
const column = api.getColumnById(id)!;
return {
...column,
id: `${idPrefix}:${column.id}`,
field: ({ data }) => `${data[id]}`.length,
};
});
},
},
},
});
return (
<div style={{ height: 400 }}>
<GraphiteGridDom state={grid} />
</div>
);
}
Graphite Grid will call the getColumnPivotDefinitions
whenever the following
properties change:
pivotColumnSource
pivotColumnModel
rowDataSource
measureModel
markerColumnDefinition
markerColumnEnabled
Tip
The controlled pivot column source may load definitions asynchronously.
Columns can be in a loading state. The arePivotcolumnsPending
API
method returns true
whenever columns are pending. It can be used to display loading indicators.
Column Pivots and Row Pivots
The column definitions created via pivot columns work the same way as normal column definitions. Hence, row pivots with aggregations will work as expected.
export const columns: ColumnDefinition<any>[] = [
{ id: "exchange", rowPivotKey: "exchange", pivotColumnKey: "exchange" },
{ id: "symbol" },
{ id: "currency" },
{ id: "sector", rowPivotKey: "sector", pivotColumnKey: "sector" },
{ id: "industry" },
{ id: "price", aggregation: "sum", measure: "sum" },
{ id: "volume", aggregation: "avg", measure: "sum" },
];
export function ColumnPivotsWithRowPivots() {
const grid = useGraphiteGrid({
initial: {
columnDefinitions: columns,
pivotColumnModel: ["exchange"],
rowPivotModel: ["sector"],
measureModel: ["price"],
pivotModeIsOn: true,
pivotColumnSource: "client",
// other props
},
});
const isPivotModeOn = grid.api.useApiSlice((s) => s.isPivotModeOn());
return (
<div>
<div>
<button onClick={() => grid.api.togglePivotMode()}>
Pivot Mode: {isPivotModeOn ? "Yes" : "No"}
</button>
</div>
<div style={{ height: 400 }}>
<GraphiteGridDom state={grid} />
</div>
</div>
);
}