Value Formatter
The valueFormatter
function
- After the cell value is known, the optional
valueFormatter()
callback function enables us to format the value. - The
valueFormatter
function is invoked by AG Grid for each cell. - The function is invoked with the
ValueFormatterParams<TData, TValue>
object.
Before we dive into using the valueFormatter
, let's look at the ValueFormatterParams<TData, TValue>
interface.
export interface ValueFormatterParams<TData = any, TValue = any> {
api: GridApi<TData>;
colDef: ColDef<TData>;
column: Column;
columnApi: ColumnApi;
context: any;
data: TData | undefined;
node: RowNode<TData> | null;
value: TValue;
}
The main difference between the ValueFormatterParams
and the ValueGetterParams
interfaces are:
- The
getValue()
utility method is not available. - Rather, we are provided with the
value
of the cell to be formatted.
Let's look at an example:
export default function Grid() {
const [columnDefs] = useState<ColDef<RowData>[]>([
{
headerName: 'price',
valueFormatter: (params) => {
const formatter = new Intl.NumberFormat('en-US', {
minimumFractionDigits: digits,
maximumFractionDigits: digits,
});
if (params.value === undefined) {
return formatter.format(0);
}
return formatter.format(Number(params.value));
},
},
]);
}
Exercise
The goal of this exercise is to learn how to use the valueGetter
function.
- Open the exercise on Stackblitz.
- Add a
valueFormatter
to the Total column to format the value using theIntl.NumberFormat
class
Solution
export default function Grid() {
const [columnDefs] = useState<ColDef<RowData>[]>([
{
headerName: 'Total',
field: 'total',
filter: 'agNumberColumnFilter',
valueFormatter: (params) => {
if (!params.data) {
return '0';
}
return new Intl.NumberFormat('en-US', {
style: 'currency',
currency: 'USD',
}).format(params.value);
},
},
]);
}
Reusable Value Formatters
Similar to how we learned to use a higher-order function for reusable value getters, let's look at an example of a reusable value formatter:
export const decimalValueFormatter =
<TData, TValue>(digits = 0) =>
(params: ValueFormatterParams<TData, TValue>): string => {
const formatter = new Intl.NumberFormat('en-US', {
minimumFractionDigits: digits,
maximumFractionDigits: digits,
});
if (params.value === undefined) {
return formatter.format(0);
}
return formatter.format(Number(params.value));
};
Let's review the code:
- We have declared a
decimalValueFormatter()
higher-order function. This enables the implementation of this value formatter to specify two generic types:TData
andTValue
. The generic ofTData
represents the type for thedata
parameter, and the generic ofTValue
represents the type for thevalue
parameter. Our higher-order function has an optionaldigits
parameter that specifies the min and maximum number of digits for the decimal formatting. The higher-order function returns a function that is the value getter that is invoked by AG Grid with theValueGetterParams<TData, TValue>
object. - In this value formatter, we are using the
Intl.NumberFormat
class to create a new formatter instance, specifying the minimum and maximum number of fraction digits. - If the
data
is undefined, which can be the case when using infinite row model or row grouping in AG Grid, then we simply return 0. - Otherwise, we return the formatted value.
Here is an example implementation of our decimalValueFormatter()
higher-order function.
export default function Grid() {
const [columnDefs] = useState<ColDef<RowData>[]>([
{
headerName: 'price',
valueFormatter: decimalValueFormatter<RowData, Pick<RowData, 'price'>>(2),
},
]);
}