---
title: "Range Chart"
enterprise: true
framework: angular
version: "36.1.0"
---

# Range Chart

This section covers how charts can be created directly from a range of selected cells.

Range charts provide a quick and easy way for users to create charts from inside the grid.

## Creating Chart Ranges

When a chart is created from a selected range of cells in the grid, or via the charting API, the underlying cell range is replaced by a chart range.

To see how chart ranges are created from a cell range, using our [demo page](https://www.ag-grid.com/example/) do the following:

- Select a [Cell Range](https://www.ag-grid.com/angular-data-grid/cell-selection/) of numeric values in the grid by dragging the mouse over a range of cells.
- Bring up the [Context Menu](https://www.ag-grid.com/angular-data-grid/context-menu/) and select the desired chart type from the 'Chart Range' sub menu.

![Charting Ranges](https://www.ag-grid.com/_astro/range-chart.Dd6NhdsT.gif)

As illustrated above, the resulting chart range can subsequently be modified by dragging on the chart range handle, located in the bottom right corner of the chart range.

## Category and Series Ranges

There are two types of charting ranges: a category range that is highlighted in green and a series range that is highlighted in blue.

A category range can only contain cells from a single column, whereas a series range can contain values from many columns.

Chart ranges can be adjusted from within the grid by dragging on the chart range handle located at the bottom right of the series range. Both the category and series ranges are connected so when the chart range is dragged in an up or down direction they will be updated together.

> **Note**
>
> The chart range handle will only appear when all series columns are contiguous. However, it is possible to move columns around in the grid to connect the series range.

## Defining Categories and Series

There are several ways for columns to be classified as chart categories or series. Columns can be explicitly configured or left for the grid to infer the type based on the data contained in the cells.

### ColDef.chartDataType

When defining column definitions the `ColDef.chartDataType` property can be used to define how the column should be considered within the context of charting.

| Property | Type | Required | Default | Description |
| --- | --- | --- | --- | --- |
| `chartDataType` | `'category' \| 'series' \| 'time' \| 'excluded'` |  |  | Defines the chart data type that should be used for a column. Module: [`IntegratedChartsModule`](https://www.ag-grid.com/angular-data-grid/modules/). |

Columns defined as `excluded` will not be included in charts or charting ranges.

> **Warning**
>
> It is recommended that `ColDef.chartDataType` or `ColDef.cellDataType` is specified rather than relying on the grid to infer the chart data type as `null` and `undefined` values can yield unexpected results or missing chart data series. Please also see [Cell Data Types](https://www.ag-grid.com/angular-data-grid/cell-data-types/) for more information.

The following column definitions show how the different `ColDef.chartDataType` values are applied:

```ts
<ag-grid-angular
    [columnDefs]="columnDefs"
    /* other grid options ... */ />

this.columnDefs = [
    // 'category' columns
    { field: 'athlete', chartDataType: 'category' },
    { field: 'age', chartDataType: 'category' },
    { field: 'country' },

    // 'excluded' from charts
    { field: 'date', chartDataType: 'excluded' },

    // 'series' columns
    { field: 'gold', chartDataType: 'series' },
    { field: 'silver' }
];
```

Note from the snippet above that the `age` column contains numbers but explicitly defined as a category, however as the `country` column contains strings it can be inferred correctly as a category column without needing to specify the `chartDataType`.

See the [Time Series](https://www.ag-grid.com/angular-data-grid/integrated-charts-time-series/) section for details on the `'time'` chart data type.

### Inferred by the Grid

If none of the above `ColDef` properties are present then the grid will infer the charting column type based on the data contained in the cells of the first row. Columns containing `number` values will map to `'series'` charting columns, and columns containing anything else will map to `'category'`.

### Example: Defining Categories and Series

The example below demonstrates the different ways columns can be defined for charting:

- **Athlete**: defined as a 'category' as `chartType='category'`.
- **Age**: defined as a 'category' as `chartType='category'`.
- **Sport**: considered a 'category' as data is a `string`.
- **Year**: defined 'excluded' from charting as data is of type `chartType='excluded'`.
- **Gold**: defined as 'series' as `chartType='series'`.
- **Silver**: defined as 'series' as `chartType='series'`.
- **Bronze**: considered a 'series' as data is a `number`.

#### Defining Categories and Series

```ts
import { Component, ViewChild } from "@angular/core";
import { HttpClient } from "@angular/common/http";
import { AgGridAngular } from "ag-grid-angular";
import "./style.css";
import { AgChartsEnterpriseModule } from "ag-charts-enterprise";
import {
  AgChartThemeOverrides,
  CellSelectionOptions,
  ClientSideRowModelModule,
  ColDef,
  ColGroupDef,
  FirstDataRenderedEvent,
  GridApi,
  GridOptions,
  GridReadyEvent,
  ModuleRegistry,
  enableDevValidations,
} from "ag-grid-community";
import {
  ColumnMenuModule,
  ContextMenuModule,
  IntegratedChartsModule,
  RowGroupingModule,
} from "ag-grid-enterprise";
if (process.env.NODE_ENV !== "production") {
  enableDevValidations();
}

ModuleRegistry.registerModules([
  ClientSideRowModelModule,
  IntegratedChartsModule.with(AgChartsEnterpriseModule),
  ColumnMenuModule,
  ContextMenuModule,
  RowGroupingModule,
]);

@Component({
  selector: "my-app",
  standalone: true,
  imports: [AgGridAngular],
  template: `<div class="wrapper">
    <ag-grid-angular
      style="width: 100%; height: 100%;"
      class="my-grid"
      [columnDefs]="columnDefs"
      [defaultColDef]="defaultColDef"
      [cellSelection]="true"
      [popupParent]="popupParent"
      [enableCharts]="true"
      [chartThemeOverrides]="chartThemeOverrides"
      [rowData]="rowData"
      (firstDataRendered)="onFirstDataRendered($event)"
      (gridReady)="onGridReady($event)"
    />
    <div id="myChart" class="my-chart"></div>
  </div> `,
})
export class AppComponent {
  columnDefs: ColDef[] = [
    // different ways to define 'categories'
    { field: "athlete", width: 150, chartDataType: "category" },
    { field: "age", chartDataType: "category", sort: "asc" },
    { field: "sport" }, // inferred as category by grid
    // excludes year from charts
    { field: "year", chartDataType: "excluded" },
    // different ways to define 'series'
    { field: "gold", chartDataType: "series" },
    { field: "silver", chartDataType: "series" },
    { field: "bronze" }, // inferred as series by grid
  ];
  defaultColDef: ColDef = {
    flex: 1,
  };
  popupParent: HTMLElement | null = document.body;
  chartThemeOverrides: AgChartThemeOverrides = {
    common: {
      title: {
        enabled: true,
        text: "Medals by Age",
      },
    },
    bar: {
      axes: {
        category: {
          label: {
            rotation: 0,
          },
        },
      },
    },
  };
  rowData!: any[];

  constructor(private http: HttpClient) {}

  onFirstDataRendered(params: FirstDataRenderedEvent) {
    params.api.createRangeChart({
      chartContainer: document.querySelector("#myChart") as HTMLElement,
      cellRange: {
        rowStartIndex: 0,
        rowEndIndex: 79,
        columns: ["age", "gold", "silver", "bronze"],
      },
      chartType: "groupedColumn",
      aggFunc: "sum",
    });
  }

  onGridReady(params: GridReadyEvent) {
    this.http
      .get<
        any[]
      >("https://www.ag-grid.com/example-assets/wide-spread-of-sports.json")
      .subscribe((data) => {
        this.rowData = data;
      });
  }
}
```

[Live example: Defining Categories and Series](https://www.ag-grid.com/examples/integrated-charts-range-chart/defining-categories-and-series/angular)

Cell ranges from which categories and data are taken will be highlighted on the grid. The highlight colours can be customised using the `--ag-range-selection-chart-category-background-color` and `--ag-range-selection-chart-background-color` CSS variables. See `style.css` in the example above.

### Switching Categories and Series

It's possible to switch categories and series. This can be done either via the [Set Up Tool Panel](https://www.ag-grid.com/angular-data-grid/integrated-charts-chart-tool-panels/#set-up-tool-panel) or the [Range Chart API](https://www.ag-grid.com/angular-data-grid/integrated-charts-api-range-chart/). When this is done, the values in the category column will become series, and the series columns will become values in the category.

The example below demonstrates switching categories and series:

#### Switching Categories and Series

```ts
import { Component, ViewChild } from "@angular/core";
import { AgGridAngular } from "ag-grid-angular";
import "./style.css";
import { AgChartsEnterpriseModule } from "ag-charts-enterprise";
import {
  CellSelectionOptions,
  ClientSideRowModelModule,
  ColDef,
  ColGroupDef,
  FirstDataRenderedEvent,
  GridApi,
  GridOptions,
  GridReadyEvent,
  ModuleRegistry,
  enableDevValidations,
} from "ag-grid-community";
import {
  ColumnMenuModule,
  ContextMenuModule,
  IntegratedChartsModule,
  RowGroupingModule,
} from "ag-grid-enterprise";
import { generateData } from "./data";
if (process.env.NODE_ENV !== "production") {
  enableDevValidations();
}

ModuleRegistry.registerModules([
  ClientSideRowModelModule,
  IntegratedChartsModule.with(AgChartsEnterpriseModule),
  ColumnMenuModule,
  ContextMenuModule,
  RowGroupingModule,
]);

@Component({
  selector: "my-app",
  standalone: true,
  imports: [AgGridAngular],
  template: `<div class="wrapper">
    <ag-grid-angular
      style="width: 100%; height: 100%;"
      class="my-grid"
      [columnDefs]="columnDefs"
      [defaultColDef]="defaultColDef"
      [rowData]="rowData"
      [cellSelection]="true"
      [popupParent]="popupParent"
      [enableCharts]="true"
      (firstDataRendered)="onFirstDataRendered($event)"
    />
    <div id="myChart" class="my-chart"></div>
  </div> `,
})
export class AppComponent {
  columnDefs: ColDef[] = [
    { field: "year", chartDataType: "category" },
    { field: "jan" },
    { field: "feb" },
    { field: "mar" },
    { field: "apr" },
    { field: "may" },
    { field: "jun" },
    { field: "jul" },
    { field: "aug" },
    { field: "sep" },
    { field: "oct" },
    { field: "nov" },
    { field: "dec" },
  ];
  defaultColDef: ColDef = {
    flex: 1,
    minWidth: 100,
  };
  rowData: any[] | null = generateData();
  popupParent: HTMLElement | null = document.body;

  onFirstDataRendered(params: FirstDataRenderedEvent) {
    params.api.createRangeChart({
      chartContainer: document.querySelector("#myChart") as HTMLElement,
      cellRange: {
        rowStartIndex: 0,
        rowEndIndex: 79,
        columns: [
          "year",
          "jan",
          "feb",
          "mar",
          "apr",
          "may",
          "jun",
          "jul",
          "aug",
          "sep",
          "oct",
          "nov",
          "dec",
        ],
      },
      chartType: "line",
      aggFunc: "sum",
      switchCategorySeries: true,
    });
  }
}
```

[Live example: Switching Categories and Series](https://www.ag-grid.com/examples/integrated-charts-range-chart/switching-categories-and-series/angular)

## Row Grouping

The best way to display grouped data in a chart is using [Pivot Charts](https://www.ag-grid.com/angular-data-grid/integrated-charts-pivot-chart/). However, it is also possible to use Range Charts with [Row Grouping](https://www.ag-grid.com/angular-data-grid/grouping/).

When Row Grouping is enabled, the chart can display in one of three ways:

- Without the group column
- As a grouped category
- With aggregated values

### Without Group Column

If the group column is not included in the cell range, the chart will be displayed flat as if grouping was disabled.

If the chart range spreads across groups and there are no values at the group level, the chart will have blank values.

### Grouped Category

If the group column is included in the cell range, by default a grouped category will be displayed. For the group category to be displayed correctly, it is necessary to [Add Values to Leaf Nodes](https://www.ag-grid.com/angular-data-grid/grouping-single-group-column/#configuration) in the grid.

The following example demonstrates this via defining the `field` **Resource** on the [Group Column Configuration](https://www.ag-grid.com/angular-data-grid/grouping-single-group-column/#configuration):

#### Grouped Category

```ts
import { Component, ViewChild } from "@angular/core";
import { AgGridAngular } from "ag-grid-angular";
import "./style.css";
import { AgChartsEnterpriseModule } from "ag-charts-enterprise";
import {
  AgChartThemeOverrides,
  AutoGroupColumnDef,
  CellSelectionOptions,
  ClientSideRowModelModule,
  ColDef,
  ColGroupDef,
  FirstDataRenderedEvent,
  GridApi,
  GridOptions,
  GridReadyEvent,
  ModuleRegistry,
  enableDevValidations,
} from "ag-grid-community";
import {
  ColumnMenuModule,
  ContextMenuModule,
  IntegratedChartsModule,
  RowGroupingModule,
} from "ag-grid-enterprise";
import { generateData } from "./data";
if (process.env.NODE_ENV !== "production") {
  enableDevValidations();
}

ModuleRegistry.registerModules([
  ClientSideRowModelModule,
  IntegratedChartsModule.with(AgChartsEnterpriseModule),
  ColumnMenuModule,
  ContextMenuModule,
  RowGroupingModule,
]);

@Component({
  selector: "my-app",
  standalone: true,
  imports: [AgGridAngular],
  template: `<div class="wrapper">
    <ag-grid-angular
      style="width: 100%; height: 100%;"
      class="my-grid"
      [columnDefs]="columnDefs"
      [defaultColDef]="defaultColDef"
      [autoGroupColumnDef]="autoGroupColumnDef"
      [rowData]="rowData"
      [cellSelection]="true"
      [popupParent]="popupParent"
      [enableCharts]="true"
      [groupDefaultExpanded]="groupDefaultExpanded"
      [chartThemeOverrides]="chartThemeOverrides"
      (firstDataRendered)="onFirstDataRendered($event)"
    />
    <div id="myChart" class="my-chart"></div>
  </div> `,
})
export class AppComponent {
  columnDefs: ColDef[] = [
    { field: "division", width: 150, rowGroup: true, hide: true },
    { field: "resource", width: 150, hide: true },
    { field: "revenue" },
    { field: "expenses" },
    { field: "headcount" },
  ];
  defaultColDef: ColDef = {
    flex: 1,
  };
  autoGroupColumnDef: AutoGroupColumnDef = {
    field: "resource",
  };
  rowData: any[] | null = generateData();
  popupParent: HTMLElement | null = document.body;
  groupDefaultExpanded = 1;
  chartThemeOverrides: AgChartThemeOverrides = {
    bar: {
      axes: {
        "grouped-category": {
          label: {
            fontSize: 8,
          },
        },
      },
    },
  };

  onFirstDataRendered(params: FirstDataRenderedEvent) {
    params.api.createRangeChart({
      chartContainer: document.querySelector("#myChart") as HTMLElement,
      cellRange: {
        rowStartIndex: 0,
        rowEndIndex: 16,
        columns: ["expenses"],
      },
      chartType: "groupedColumn",
      useGroupColumnAsCategory: true,
    });
  }
}
```

[Live example: Grouped Category](https://www.ag-grid.com/examples/integrated-charts-range-chart/grouped-category/angular)

### Aggregated Values

Group values can also be displayed aggregated. This is done by enabling aggregation in the [Set Up Tool Panel](https://www.ag-grid.com/angular-data-grid/integrated-charts-chart-tool-panels/#set-up-tool-panel) or by providing an aggregation function to the [Range Chart API](https://www.ag-grid.com/angular-data-grid/integrated-charts-api-range-chart/).

This is demonstrated in the following example:

#### Aggregated Values

```ts
import { Component, ViewChild } from "@angular/core";
import { AgGridAngular } from "ag-grid-angular";
import "./style.css";
import { AgChartsEnterpriseModule } from "ag-charts-enterprise";
import {
  AgChartThemeOverrides,
  CellSelectionOptions,
  ClientSideRowModelModule,
  ColDef,
  ColGroupDef,
  FirstDataRenderedEvent,
  GridApi,
  GridOptions,
  GridReadyEvent,
  ModuleRegistry,
  enableDevValidations,
} from "ag-grid-community";
import {
  ColumnMenuModule,
  ContextMenuModule,
  IntegratedChartsModule,
  RowGroupingModule,
} from "ag-grid-enterprise";
import { generateData } from "./data";
if (process.env.NODE_ENV !== "production") {
  enableDevValidations();
}

ModuleRegistry.registerModules([
  ClientSideRowModelModule,
  IntegratedChartsModule.with(AgChartsEnterpriseModule),
  ColumnMenuModule,
  ContextMenuModule,
  RowGroupingModule,
]);

@Component({
  selector: "my-app",
  standalone: true,
  imports: [AgGridAngular],
  template: `<div class="wrapper">
    <ag-grid-angular
      style="width: 100%; height: 100%;"
      class="my-grid"
      [columnDefs]="columnDefs"
      [defaultColDef]="defaultColDef"
      [rowData]="rowData"
      [cellSelection]="true"
      [popupParent]="popupParent"
      [enableCharts]="true"
      [groupDefaultExpanded]="groupDefaultExpanded"
      [chartThemeOverrides]="chartThemeOverrides"
      (firstDataRendered)="onFirstDataRendered($event)"
    />
    <div id="myChart" class="my-chart"></div>
  </div> `,
})
export class AppComponent {
  columnDefs: ColDef[] = [
    { field: "division", width: 150, rowGroup: true, hide: true },
    { field: "resource", width: 150, hide: true },
    { field: "revenue" },
    { field: "expenses" },
    { field: "headcount" },
  ];
  defaultColDef: ColDef = {
    flex: 1,
  };
  rowData: any[] | null = generateData();
  popupParent: HTMLElement | null = document.body;
  groupDefaultExpanded = 1;
  chartThemeOverrides: AgChartThemeOverrides = {
    bar: {
      axes: {
        category: {
          label: {
            fontSize: 8,
          },
        },
      },
    },
  };

  onFirstDataRendered(params: FirstDataRenderedEvent) {
    params.api.createRangeChart({
      chartContainer: document.querySelector("#myChart") as HTMLElement,
      cellRange: {
        rowStartIndex: 0,
        rowEndIndex: 16,
        columns: ["expenses"],
      },
      chartType: "groupedColumn",
      aggFunc: "sum",
      useGroupColumnAsCategory: true,
    });
  }
}
```

[Live example: Aggregated Values](https://www.ag-grid.com/examples/integrated-charts-range-chart/aggregated-values/angular)
