created many line chart stories

This commit is contained in:
Nate Kelley 2025-03-12 10:59:40 -06:00
parent b8a3c92cb9
commit ffdcabf48a
No known key found for this signature in database
GPG Key ID: FD90372AB8D98B4F
6 changed files with 559 additions and 191 deletions

View File

@ -0,0 +1,50 @@
import type { Meta, StoryObj } from '@storybook/react';
import { BusterChart } from './BusterChart';
import { ChartType } from '../../../api/asset_interfaces/metric/charts/enum';
import { IColumnLabelFormat } from '../../../api/asset_interfaces/metric/charts/columnLabelInterfaces';
import { generateBarChartData } from '../../../mocks/chart/chartMocks';
import { sharedMeta } from './BusterChart.shared';
type BarChartData = ReturnType<typeof generateBarChartData>[0];
const meta: Meta<typeof BusterChart> = {
...sharedMeta,
title: 'UI/Charts/BusterChart/Bar'
} as Meta<typeof BusterChart>;
export default meta;
type Story = StoryObj<typeof BusterChart>;
export const Default: Story = {
args: {
selectedChartType: ChartType.Bar,
data: generateBarChartData(),
barAndLineAxis: {
x: ['category'],
y: ['sales', 'units', 'returns'],
category: []
},
columnLabelFormats: {
category: {
columnType: 'text',
style: 'string'
} satisfies IColumnLabelFormat,
sales: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
units: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat,
returns: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
} satisfies Record<keyof BarChartData, IColumnLabelFormat>,
className: 'w-[800px] h-[400px]'
}
};

View File

@ -0,0 +1,373 @@
import type { Meta, StoryObj } from '@storybook/react';
import { BusterChart } from './BusterChart';
import { ChartType } from '../../../api/asset_interfaces/metric/charts/enum';
import { IColumnLabelFormat } from '../../../api/asset_interfaces/metric/charts/columnLabelInterfaces';
import { generateLineChartData } from '../../../mocks/chart/chartMocks';
import { sharedMeta } from './BusterChart.shared';
type LineChartData = ReturnType<typeof generateLineChartData>[0];
const meta: Meta<typeof BusterChart> = {
...sharedMeta,
title: 'UI/Charts/BusterChart/Line'
} as Meta<typeof BusterChart>;
export default meta;
type Story = StoryObj<typeof BusterChart>;
export const Default: Story = {
args: {
selectedChartType: ChartType.Line,
data: generateLineChartData(),
barAndLineAxis: {
x: ['date'],
y: ['revenue', 'profit', 'customers'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
date: {
columnType: 'date',
style: 'date',
dateFormat: 'MMM DD'
} satisfies IColumnLabelFormat,
revenue: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
profit: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
customers: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
} satisfies Record<keyof LineChartData, IColumnLabelFormat>
}
};
// Simple X and Y axis with numeric values
export const NumericXY: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ score: 10, value: 100 },
{ score: 20, value: 200 },
{ score: 30, value: 150 },
{ score: 40, value: 300 },
{ score: 50, value: 250 }
],
barAndLineAxis: {
x: ['score'],
y: ['value'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
score: {
columnType: 'number',
style: 'number'
} satisfies IColumnLabelFormat,
value: {
columnType: 'number',
style: 'number'
} satisfies IColumnLabelFormat
}
}
};
// X axis with categorical data and Y axis with numeric values
export const CategoricalXNumericY: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ category: 'A', value: 100 },
{ category: 'B', value: 200 },
{ category: 'C', value: 150 },
{ category: 'D', value: 300 },
{ category: 'E', value: 250 }
],
barAndLineAxis: {
x: ['category'],
y: ['value'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
category: {
columnType: 'string',
style: 'string'
} satisfies IColumnLabelFormat,
value: {
columnType: 'number',
style: 'number'
} satisfies IColumnLabelFormat
}
}
};
// Multi-year date range
export const MultiYearDate: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ date: new Date('2020-01-01'), value: 100 },
{ date: new Date('2021-01-01'), value: 150 },
{ date: new Date('2022-01-01'), value: 200 },
{ date: new Date('2023-01-01'), value: 250 },
{ date: new Date('2024-01-01'), value: 300 }
],
barAndLineAxis: {
x: ['date'],
y: ['value'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
date: {
columnType: 'date',
style: 'date',
dateFormat: 'YYYY' // Show only year for multi-year view
} satisfies IColumnLabelFormat,
value: {
columnType: 'number',
style: 'number'
} satisfies IColumnLabelFormat
}
}
};
// Multiple Y axes with date X axis
export const MultipleYAxes: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{
date: new Date('2024-01-01'),
revenue: 1000,
units: 50,
satisfaction: 4.5
},
{
date: new Date('2024-02-01'),
revenue: 1200,
units: 60,
satisfaction: 4.7
},
{
date: new Date('2024-03-01'),
revenue: 1400,
units: 70,
satisfaction: 4.8
}
],
barAndLineAxis: {
x: ['date'],
y: ['revenue', 'units', 'satisfaction'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
date: {
columnType: 'date',
style: 'date',
dateFormat: 'MMM YYYY'
} satisfies IColumnLabelFormat,
revenue: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
units: {
columnType: 'number',
style: 'number'
} satisfies IColumnLabelFormat,
satisfaction: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 1,
maximumFractionDigits: 1
} satisfies IColumnLabelFormat
}
}
};
// Unevenly spaced dates
export const UnevenlySpacedDates: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ date: new Date('2024-01-05'), value: 120 },
{ date: new Date('2024-01-28'), value: 145 },
{ date: new Date('2024-02-15'), value: 160 },
{ date: new Date('2024-03-02'), value: 155 },
{ date: new Date('2024-04-18'), value: 180 },
{ date: new Date('2024-05-30'), value: 210 },
{ date: new Date('2024-07-12'), value: 195 },
{ date: new Date('2024-08-03'), value: 225 },
{ date: new Date('2024-09-22'), value: 240 },
{ date: new Date('2024-11-15'), value: 260 },
{ date: new Date('2024-12-28'), value: 280 },
{ date: new Date('2025-04-08'), value: 310 }
],
barAndLineAxis: {
x: ['date'],
y: ['value'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
date: {
columnType: 'date',
style: 'date',
dateFormat: 'll' // Full date format to show uneven spacing clearly
} satisfies IColumnLabelFormat,
value: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 0,
maximumFractionDigits: 0
} satisfies IColumnLabelFormat
}
}
};
// X, Y, and Category axes combined
export const WithCategory: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ month: new Date('2024-01-01'), sales: 1200, region: 'North' },
{ month: new Date('2024-02-01'), sales: 1400, region: 'North' },
{ month: new Date('2024-03-01'), sales: 1600, region: 'North' },
{ month: new Date('2024-01-01'), sales: 800, region: 'South' },
{ month: new Date('2024-02-01'), sales: 900, region: 'South' },
{ month: new Date('2024-03-01'), sales: 1100, region: 'South' },
{ month: new Date('2024-01-01'), sales: 1500, region: 'East' },
{ month: new Date('2024-02-01'), sales: 1700, region: 'East' },
{ month: new Date('2024-03-01'), sales: 1900, region: 'East' },
{ month: new Date('2024-01-01'), sales: 1000, region: 'West' },
{ month: new Date('2024-02-01'), sales: 1300, region: 'West' },
{ month: new Date('2024-03-01'), sales: 1500, region: 'West' }
],
barAndLineAxis: {
x: ['month'],
y: ['sales'],
category: ['region']
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
month: {
columnType: 'date',
style: 'date',
dateFormat: 'MMM YYYY'
} satisfies IColumnLabelFormat,
sales: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
region: {
columnType: 'string',
style: 'string'
} satisfies IColumnLabelFormat
}
}
};
// Multiple Y axes with Category
export const MultipleYAxesWithCategory: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ date: new Date('2024-01-01'), revenue: 1200, satisfaction: 4.2, product: 'Hardware' },
{ date: new Date('2024-02-01'), revenue: 1400, satisfaction: 4.3, product: 'Hardware' },
{ date: new Date('2024-03-01'), revenue: 1600, satisfaction: 4.4, product: 'Hardware' },
{ date: new Date('2024-01-01'), revenue: 800, satisfaction: 4.7, product: 'Software' },
{ date: new Date('2024-02-01'), revenue: 1000, satisfaction: 4.8, product: 'Software' },
{ date: new Date('2024-03-01'), revenue: 1200, satisfaction: 4.9, product: 'Software' },
{ date: new Date('2024-01-01'), revenue: 2000, satisfaction: 4.0, product: 'Services' },
{ date: new Date('2024-02-01'), revenue: 2200, satisfaction: 4.1, product: 'Services' },
{ date: new Date('2024-03-01'), revenue: 2400, satisfaction: 4.2, product: 'Services' }
],
barAndLineAxis: {
x: ['date'],
y: ['revenue', 'satisfaction'],
category: ['product']
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
date: {
columnType: 'date',
style: 'date',
dateFormat: 'MMM YYYY'
} satisfies IColumnLabelFormat,
revenue: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
satisfaction: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 1,
maximumFractionDigits: 1
} satisfies IColumnLabelFormat,
product: {
columnType: 'string',
style: 'string'
} satisfies IColumnLabelFormat
}
}
};
// Numeric month X axis
export const NumericMonthX: Story = {
args: {
selectedChartType: ChartType.Line,
data: [
{ month: 1, sales: 1000, customers: 150 },
{ month: 2, sales: 1200, customers: 180 },
{ month: 3, sales: 1100, customers: 165 },
{ month: 4, sales: 1400, customers: 200 },
{ month: 5, sales: 1600, customers: 220 },
{ month: 6, sales: 1800, customers: 240 },
{ month: 7, sales: 2000, customers: 260 },
{ month: 8, sales: 2200, customers: 280 },
{ month: 9, sales: 2100, customers: 270 },
{ month: 10, sales: 1900, customers: 250 },
{ month: 11, sales: 2300, customers: 290 },
{ month: 12, sales: 2500, customers: 300 }
],
barAndLineAxis: {
x: ['month'],
y: ['sales', 'customers'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
month: {
columnType: 'number',
style: 'date',
dateFormat: 'MMM',
minimumFractionDigits: 0,
maximumFractionDigits: 0
} satisfies IColumnLabelFormat,
sales: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
customers: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
}
}
};

View File

@ -0,0 +1,41 @@
import type { Meta, StoryObj } from '@storybook/react';
import { BusterChart } from './BusterChart';
import { ChartType } from '../../../api/asset_interfaces/metric/charts/enum';
import { IColumnLabelFormat } from '../../../api/asset_interfaces/metric/charts/columnLabelInterfaces';
import { generatePieChartData } from '../../../mocks/chart/chartMocks';
import { sharedMeta } from './BusterChart.shared';
type PieChartData = ReturnType<typeof generatePieChartData>[0];
const meta: Meta<typeof BusterChart> = {
...sharedMeta,
title: 'UI/Charts/BusterChart/Pie'
} as Meta<typeof BusterChart>;
export default meta;
type Story = StoryObj<typeof BusterChart>;
export const Default: Story = {
args: {
selectedChartType: ChartType.Pie,
data: generatePieChartData(),
pieChartAxis: {
x: ['segment'],
y: ['value']
},
columnLabelFormats: {
segment: {
columnType: 'text',
style: 'string'
} satisfies IColumnLabelFormat,
value: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
} satisfies Record<keyof PieChartData, IColumnLabelFormat>,
pieDisplayLabelAs: 'percent',
pieDonutWidth: 0,
className: 'w-[500px] h-[500px]'
}
};

View File

@ -0,0 +1,53 @@
import type { Meta, StoryObj } from '@storybook/react';
import { BusterChart } from './BusterChart';
import { ChartType } from '../../../api/asset_interfaces/metric/charts/enum';
import { IColumnLabelFormat } from '../../../api/asset_interfaces/metric/charts/columnLabelInterfaces';
import { generateScatterChartData } from '../../../mocks/chart/chartMocks';
import { sharedMeta } from './BusterChart.shared';
type ScatterChartData = ReturnType<typeof generateScatterChartData>[0];
const meta: Meta<typeof BusterChart> = {
...sharedMeta,
title: 'UI/Charts/BusterChart/Scatter'
} as Meta<typeof BusterChart>;
export default meta;
type Story = StoryObj<typeof BusterChart>;
export const Default: Story = {
args: {
selectedChartType: ChartType.Scatter,
data: generateScatterChartData(),
scatterAxis: {
x: ['x'],
y: ['y'],
size: ['size'],
category: ['category']
},
columnLabelFormats: {
x: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 1,
maximumFractionDigits: 1
} satisfies IColumnLabelFormat,
y: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 1,
maximumFractionDigits: 1
} satisfies IColumnLabelFormat,
size: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat,
category: {
columnType: 'text',
style: 'string'
} satisfies IColumnLabelFormat
} satisfies Record<keyof ScatterChartData, IColumnLabelFormat>,
className: 'w-[800px] h-[600px]'
}
};

View File

@ -0,0 +1,42 @@
import type { Meta } from '@storybook/react';
import { BusterChart } from './BusterChart';
import { ChartType } from '../../../api/asset_interfaces/metric/charts/enum';
import { DEFAULT_CHART_CONFIG } from '../../../api/asset_interfaces/metric/defaults';
export const sharedMeta: Partial<Meta<typeof BusterChart>> = {
component: BusterChart,
parameters: {
layout: 'centered'
},
argTypes: {
colors: {
description:
'Array of colors to be used for the chart series. If not provided, defaults to the theme colors.',
control: { type: 'object' },
table: {
type: { summary: 'string[]' },
defaultValue: { summary: 'DEFAULT_CHART_THEME' }
}
},
selectedChartType: {
control: 'select',
description: 'The type of chart to display.',
defaultValue: ChartType.Table,
options: Object.values(ChartType)
},
xAxisTimeInterval: {
control: 'select',
description:
'Time interval for x-axis when displaying time series data. Only applies to combo and line charts.',
options: ['day', 'week', 'month', 'quarter', 'year', null],
table: {
type: { summary: "'day' | 'week' | 'month' | 'quarter' | 'year' | null" },
defaultValue: { summary: 'null' }
}
}
},
args: {
...DEFAULT_CHART_CONFIG,
className: 'w-[800px] h-[400px]'
}
};

View File

@ -1,191 +0,0 @@
import type { Meta, StoryObj } from '@storybook/react';
import { BusterChart } from './BusterChart';
import { ChartType } from '../../../api/asset_interfaces/metric/charts/enum';
import { IColumnLabelFormat } from '../../../api/asset_interfaces/metric/charts/columnLabelInterfaces';
import { DEFAULT_CHART_CONFIG } from '../../../api/asset_interfaces/metric/defaults';
import {
generateBarChartData,
generateLineChartData,
generatePieChartData,
generateScatterChartData
} from '../../../mocks/chart/chartMocks';
// Type-safe column label formats for each chart type
type LineChartData = ReturnType<typeof generateLineChartData>[0];
type BarChartData = ReturnType<typeof generateBarChartData>[0];
type PieChartData = ReturnType<typeof generatePieChartData>[0];
type ScatterChartData = ReturnType<typeof generateScatterChartData>[0];
const meta: Meta<typeof BusterChart> = {
title: 'UI/Charts/BusterChart',
component: BusterChart,
parameters: {
layout: 'centered'
},
argTypes: {
colors: {
description:
'Array of colors to be used for the chart series. If not provided, defaults to the theme colors.',
control: 'array',
table: {
type: { summary: 'string[]' },
defaultValue: { summary: 'DEFAULT_CHART_THEME' }
}
},
selectedChartType: {
control: 'select',
description: 'The type of chart to display.',
defaultValue: ChartType.Table,
options: Object.values(ChartType)
},
xAxisTimeInterval: {
control: 'select',
description:
'Time interval for x-axis when displaying time series data. Only applies to combo and line charts.',
options: ['day', 'week', 'month', 'quarter', 'year', null],
table: {
type: { summary: "'day' | 'week' | 'month' | 'quarter' | 'year' | null" },
defaultValue: { summary: 'null' }
}
}
},
args: {
...DEFAULT_CHART_CONFIG,
className: 'w-[800px] h-[400px]'
}
};
export default meta;
type Story = StoryObj<typeof BusterChart>;
export const LineChart: Story = {
argTypes: meta.argTypes,
args: {
selectedChartType: ChartType.Line,
data: generateLineChartData(),
barAndLineAxis: {
x: ['date'],
y: ['revenue', 'profit', 'customers'],
category: []
},
className: 'w-[800px] h-[400px]',
columnLabelFormats: {
date: {
columnType: 'date',
style: 'date',
dateFormat: 'MMM DD'
} satisfies IColumnLabelFormat,
revenue: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
profit: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
customers: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
} satisfies Record<keyof LineChartData, IColumnLabelFormat>
}
};
export const BarChart: Story = {
args: {
selectedChartType: ChartType.Bar,
data: generateBarChartData(),
barAndLineAxis: {
x: ['category'],
y: ['sales', 'units', 'returns'],
category: []
},
columnLabelFormats: {
category: {
columnType: 'text',
style: 'string'
} satisfies IColumnLabelFormat,
sales: {
columnType: 'number',
style: 'currency',
currency: 'USD'
} satisfies IColumnLabelFormat,
units: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat,
returns: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
} satisfies Record<keyof BarChartData, IColumnLabelFormat>,
className: 'w-[800px] h-[400px]'
}
};
export const PieChart: Story = {
args: {
selectedChartType: ChartType.Pie,
data: generatePieChartData(),
pieChartAxis: {
x: ['segment'],
y: ['value']
},
columnLabelFormats: {
segment: {
columnType: 'text',
style: 'string'
} satisfies IColumnLabelFormat,
value: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat
} satisfies Record<keyof PieChartData, IColumnLabelFormat>,
pieDisplayLabelAs: 'percent',
pieDonutWidth: 0,
className: 'w-[500px] h-[500px]'
}
};
export const ScatterChart: Story = {
args: {
selectedChartType: ChartType.Scatter,
data: generateScatterChartData(),
scatterAxis: {
x: ['x'],
y: ['y'],
size: ['size'],
category: ['category']
},
columnLabelFormats: {
x: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 1,
maximumFractionDigits: 1
} satisfies IColumnLabelFormat,
y: {
columnType: 'number',
style: 'number',
minimumFractionDigits: 1,
maximumFractionDigits: 1
} satisfies IColumnLabelFormat,
size: {
columnType: 'number',
style: 'number',
numberSeparatorStyle: ','
} satisfies IColumnLabelFormat,
category: {
columnType: 'text',
style: 'string'
} satisfies IColumnLabelFormat
} satisfies Record<keyof ScatterChartData, IColumnLabelFormat>,
className: 'w-[800px] h-[600px]'
}
};