mirror of
https://github.com/Unleash/unleash.git
synced 2025-02-23 00:22:19 +01:00
162 lines
5.1 KiB
TypeScript
162 lines
5.1 KiB
TypeScript
|
import type { Theme } from '@mui/material/styles/createTheme';
|
||
|
import type { ChartOptions } from 'chart.js';
|
||
|
import { formatTickValue } from '../common/Chart/formatTickValue';
|
||
|
import type { ILocationSettings } from '../../hooks/useLocationSettings';
|
||
|
import type { IPoint } from '../feature/FeatureView/FeatureMetrics/FeatureMetricsChart/createChartData';
|
||
|
import {
|
||
|
formatDateHM,
|
||
|
formatDateYMD,
|
||
|
formatDateYMDHM,
|
||
|
} from '../../utils/formatDate';
|
||
|
|
||
|
const formatVariantEntry = (
|
||
|
variant: [string, number],
|
||
|
totalExposure: number,
|
||
|
) => {
|
||
|
if (totalExposure === 0) return '';
|
||
|
const [key, value] = variant;
|
||
|
const percentage = Math.floor((Number(value) / totalExposure) * 100);
|
||
|
return `${value} (${percentage}%) - ${key}`;
|
||
|
};
|
||
|
|
||
|
export const createPlaceholderBarChartOptions = (
|
||
|
theme: Theme,
|
||
|
): ChartOptions<'bar'> => ({
|
||
|
plugins: {
|
||
|
legend: {
|
||
|
position: 'bottom',
|
||
|
labels: {
|
||
|
color: theme.palette.text.primary,
|
||
|
pointStyle: 'circle',
|
||
|
usePointStyle: true,
|
||
|
boxHeight: 6,
|
||
|
padding: 15,
|
||
|
boxPadding: 5,
|
||
|
},
|
||
|
},
|
||
|
tooltip: {
|
||
|
enabled: false,
|
||
|
},
|
||
|
},
|
||
|
responsive: true,
|
||
|
scales: {
|
||
|
x: {
|
||
|
stacked: true,
|
||
|
ticks: {
|
||
|
color: theme.palette.text.secondary,
|
||
|
},
|
||
|
grid: {
|
||
|
display: false,
|
||
|
},
|
||
|
},
|
||
|
y: {
|
||
|
stacked: true,
|
||
|
ticks: {
|
||
|
color: theme.palette.text.secondary,
|
||
|
maxTicksLimit: 5,
|
||
|
callback: formatTickValue,
|
||
|
},
|
||
|
grid: {
|
||
|
drawBorder: false,
|
||
|
},
|
||
|
},
|
||
|
},
|
||
|
elements: {
|
||
|
bar: {
|
||
|
borderRadius: 5,
|
||
|
},
|
||
|
},
|
||
|
interaction: {
|
||
|
mode: 'index',
|
||
|
intersect: false,
|
||
|
},
|
||
|
});
|
||
|
|
||
|
export const createBarChartOptions = (
|
||
|
theme: Theme,
|
||
|
hoursBack: number,
|
||
|
locationSettings: ILocationSettings,
|
||
|
): ChartOptions<'bar'> => {
|
||
|
const { plugins, responsive, elements, interaction, scales } =
|
||
|
createPlaceholderBarChartOptions(theme);
|
||
|
return {
|
||
|
plugins: {
|
||
|
legend: plugins?.legend,
|
||
|
tooltip: {
|
||
|
backgroundColor: theme.palette.background.paper,
|
||
|
titleColor: theme.palette.text.primary,
|
||
|
bodyColor: theme.palette.text.primary,
|
||
|
bodySpacing: 6,
|
||
|
padding: {
|
||
|
top: 20,
|
||
|
bottom: 20,
|
||
|
left: 30,
|
||
|
right: 30,
|
||
|
},
|
||
|
borderColor: 'rgba(0, 0, 0, 0.05)',
|
||
|
borderWidth: 3,
|
||
|
usePointStyle: true,
|
||
|
caretSize: 0,
|
||
|
boxPadding: 10,
|
||
|
callbacks: {
|
||
|
label: (item) => {
|
||
|
return `${item.formattedValue} - ${item.dataset.label}`;
|
||
|
},
|
||
|
afterLabel: (item) => {
|
||
|
const data = item.dataset.data[
|
||
|
item.dataIndex
|
||
|
] as unknown as IPoint;
|
||
|
|
||
|
if (
|
||
|
item.dataset.label !== 'Exposed' ||
|
||
|
data.variants === undefined
|
||
|
) {
|
||
|
return '';
|
||
|
}
|
||
|
const { disabled, ...actualVariants } = data.variants;
|
||
|
return Object.entries(actualVariants)
|
||
|
.map((entry) => formatVariantEntry(entry, data.y))
|
||
|
.join('\n');
|
||
|
},
|
||
|
title: (items) => {
|
||
|
return `Time: ${
|
||
|
hoursBack > 48
|
||
|
? formatDateYMDHM(
|
||
|
items[0].label,
|
||
|
locationSettings.locale,
|
||
|
'UTC',
|
||
|
)
|
||
|
: formatDateHM(
|
||
|
items[0].label,
|
||
|
locationSettings.locale,
|
||
|
)
|
||
|
}`;
|
||
|
},
|
||
|
},
|
||
|
},
|
||
|
},
|
||
|
responsive,
|
||
|
scales: {
|
||
|
x: {
|
||
|
...(scales ? scales.x : {}),
|
||
|
ticks: {
|
||
|
color: theme.palette.text.secondary,
|
||
|
callback(tickValue) {
|
||
|
const label = this.getLabelForValue(Number(tickValue));
|
||
|
return hoursBack > 48
|
||
|
? formatDateYMD(
|
||
|
label,
|
||
|
locationSettings.locale,
|
||
|
'UTC',
|
||
|
)
|
||
|
: formatDateHM(label, locationSettings.locale);
|
||
|
},
|
||
|
},
|
||
|
},
|
||
|
y: scales ? scales.y : {},
|
||
|
},
|
||
|
elements,
|
||
|
interaction,
|
||
|
};
|
||
|
};
|