Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow dataset specific ChartMeta type extensions #9432

Merged
merged 1 commit into from Jul 19, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
35 changes: 29 additions & 6 deletions types/index.esm.d.ts
Expand Up @@ -327,11 +327,16 @@ export const DoughnutController: ChartComponent & {
new (chart: Chart, datasetIndex: number): DoughnutController;
};

export interface DoughnutMetaExtensions {
total: number;
}

export type PieControllerDatasetOptions = DoughnutControllerDatasetOptions;
export type PieControllerChartOptions = DoughnutControllerChartOptions;
export type PieAnimationOptions = DoughnutAnimationOptions;

export type PieDataPoint = DoughnutDataPoint;
export type PieMetaExtensions = DoughnutMetaExtensions;

export type PieController = DoughnutController
export const PieController: ChartComponent & {
Expand Down Expand Up @@ -401,7 +406,7 @@ export const RadarController: ChartComponent & {
prototype: RadarController;
new (chart: Chart, datasetIndex: number): RadarController;
};
export interface ChartMeta<TElement extends Element = Element, TDatasetElement extends Element = Element> {
interface ChartMetaCommon<TElement extends Element = Element, TDatasetElement extends Element = Element> {
type: string;
controller: DatasetController;
order: number;
Expand Down Expand Up @@ -436,6 +441,16 @@ export interface ChartMeta<TElement extends Element = Element, TDatasetElement e
_parsed: unknown[];
}

export type ChartMeta<
TElement extends Element = Element,
TDatasetElement extends Element = Element,
// TODO - V4, move this to the first parameter.
// When this was introduced, doing so was a breaking change
TType extends ChartType = ChartType,
> = DeepPartial<
{ [key in ChartType]: ChartTypeRegistry[key]['metaExtensions'] }[TType]
> & ChartMetaCommon<TElement, TDatasetElement>;

export interface ActiveDataPoint {
datasetIndex: number;
index: number;
Expand Down Expand Up @@ -547,7 +562,7 @@ export class DatasetController<

readonly chart: Chart;
readonly index: number;
readonly _cachedMeta: ChartMeta<TElement, TDatasetElement>;
readonly _cachedMeta: ChartMeta<TElement, TDatasetElement, TType>;
enableOptionSharing: boolean;

linkScales(): void;
Expand All @@ -560,7 +575,7 @@ export class DatasetController<
draw(): void;
reset(): void;
getDataset(): ChartDataset;
getMeta(): ChartMeta<TElement, TDatasetElement>;
getMeta(): ChartMeta<TElement, TDatasetElement, TType>;
getScaleForId(scaleID: string): Scale | undefined;
configure(): void;
initialize(): void;
Expand Down Expand Up @@ -596,9 +611,9 @@ export class DatasetController<
setHoverStyle(element: TElement, datasetIndex: number, index: number): void;

parse(start: number, count: number): void;
protected parsePrimitiveData(meta: ChartMeta<TElement, TDatasetElement>, data: AnyObject[], start: number, count: number): AnyObject[];
protected parseArrayData(meta: ChartMeta<TElement, TDatasetElement>, data: AnyObject[], start: number, count: number): AnyObject[];
protected parseObjectData(meta: ChartMeta<TElement, TDatasetElement>, data: AnyObject[], start: number, count: number): AnyObject[];
protected parsePrimitiveData(meta: ChartMeta<TElement, TDatasetElement, TType>, data: AnyObject[], start: number, count: number): AnyObject[];
protected parseArrayData(meta: ChartMeta<TElement, TDatasetElement, TType>, data: AnyObject[], start: number, count: number): AnyObject[];
protected parseObjectData(meta: ChartMeta<TElement, TDatasetElement, TType>, data: AnyObject[], start: number, count: number): AnyObject[];
protected getParsed(index: number): TParsedData;
protected applyStack(scale: Scale, parsed: unknown[]): number;
protected updateRangeFromParsed(
Expand Down Expand Up @@ -3335,55 +3350,63 @@ export interface ChartTypeRegistry {
chartOptions: BarControllerChartOptions;
datasetOptions: BarControllerDatasetOptions;
defaultDataPoint: number;
metaExtensions: {};
parsedDataType: BarParsedData,
scales: keyof CartesianScaleTypeRegistry;
};
line: {
chartOptions: LineControllerChartOptions;
datasetOptions: LineControllerDatasetOptions & FillerControllerDatasetOptions;
defaultDataPoint: ScatterDataPoint | number | null;
metaExtensions: {};
parsedDataType: CartesianParsedData;
scales: keyof CartesianScaleTypeRegistry;
};
scatter: {
chartOptions: ScatterControllerChartOptions;
datasetOptions: ScatterControllerDatasetOptions;
defaultDataPoint: ScatterDataPoint | number | null;
metaExtensions: {};
parsedDataType: CartesianParsedData;
scales: keyof CartesianScaleTypeRegistry;
};
bubble: {
chartOptions: unknown;
datasetOptions: BubbleControllerDatasetOptions;
defaultDataPoint: BubbleDataPoint;
metaExtensions: {};
parsedDataType: BubbleParsedData;
scales: keyof CartesianScaleTypeRegistry;
};
pie: {
chartOptions: PieControllerChartOptions;
datasetOptions: PieControllerDatasetOptions;
defaultDataPoint: PieDataPoint;
metaExtensions: PieMetaExtensions;
parsedDataType: number;
scales: keyof CartesianScaleTypeRegistry;
};
doughnut: {
chartOptions: DoughnutControllerChartOptions;
datasetOptions: DoughnutControllerDatasetOptions;
defaultDataPoint: DoughnutDataPoint;
metaExtensions: DoughnutMetaExtensions;
parsedDataType: number;
scales: keyof CartesianScaleTypeRegistry;
};
polarArea: {
chartOptions: PolarAreaControllerChartOptions;
datasetOptions: PolarAreaControllerDatasetOptions;
defaultDataPoint: number;
metaExtensions: {};
parsedDataType: RadialParsedData;
scales: keyof RadialScaleTypeRegistry;
};
radar: {
chartOptions: RadarControllerChartOptions;
datasetOptions: RadarControllerDatasetOptions & FillerControllerDatasetOptions;
defaultDataPoint: number | null;
metaExtensions: {};
parsedDataType: RadialParsedData;
scales: keyof RadialScaleTypeRegistry;
};
Expand Down
16 changes: 16 additions & 0 deletions types/tests/controllers/doughnut_meta_total.ts
@@ -0,0 +1,16 @@
import { Chart, ChartMeta, Element } from '../../index.esm';

const chart = new Chart('id', {
type: 'doughnut',
data: {
labels: [],
datasets: [{
data: [],
}]
},
});

// A cast is required because the exact type of ChartMeta will vary with
// mixed charts
const meta = <ChartMeta<Element, Element, 'doughnut'>>chart.getDatasetMeta(0);
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure if the casting is acceptable here. It would be a lot simpler to cast if TType was the first parameter, but I wasn't sure that would be considered a breaking change or not

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ideally it should not need to be casted, because its not a mixed chart. I don't know if there is a way to type it so it would return the correct meta for the given dataset index.

const total = meta.total;