@chakra-ui/charts
Version:
Data visualization components for Chakra UI
147 lines (141 loc) • 4.34 kB
JavaScript
"use client";
;
var react = require('@chakra-ui/react');
var React = require('react');
function _interopNamespaceDefault(e) {
var n = Object.create(null);
if (e) {
Object.keys(e).forEach(function (k) {
if (k !== 'default') {
var d = Object.getOwnPropertyDescriptor(e, k);
Object.defineProperty(n, k, d.get ? d : {
enumerable: true,
get: function () { return e[k]; }
});
}
});
}
n.default = e;
return Object.freeze(n);
}
var React__namespace = /*#__PURE__*/_interopNamespaceDefault(React);
function useChart(props) {
const { data, series = [], sort } = props;
const id = React__namespace.useId();
const [highlightedSeries, setHighlightedSeries] = React__namespace.useState(null);
const isHighlightedSeries = (name) => highlightedSeries === name;
const env = react.useLocaleContext();
const sys = react.useChakraContext();
const color = (key2) => sys.token(`colors.${key2}`, key2);
const size = (key2) => sys.token(`sizes.${key2}`, key2);
const spacing = (key2) => sys.token(`spacing.${key2}`, key2);
const key = (prop) => prop ?? "value";
const formatNumber = React__namespace.useCallback(
(options) => {
const formatter = new Intl.NumberFormat(env.locale, options);
return (value) => formatter.format(value);
},
[env.locale]
);
const formatDate = React__namespace.useCallback(
(options) => {
return (value) => new Date(value).toLocaleDateString(env.locale, options);
},
[env.locale]
);
const getSeries = (item) => {
if (!isObject(item)) return;
const result = series.find((s) => {
return s.name === item.name || s.name === getProp(item.payload, "name") || s.name === item.dataKey || s.name === getProp(item.payload, "dataKey");
}) || { color: void 0 };
result.color || (result.color = getProp(item.payload, "color"));
result.label || (result.label = result.name?.toLocaleString() || getProp(item.payload, "name"));
return result;
};
const getTotal = (key2) => {
return data.reduce((acc, d) => acc + Number(d[key2]), 0);
};
function getPayloadTotal(payload) {
return payload?.reduce((acc, item) => {
if (!item.value) return acc;
const num = Number(item.value);
const value = Number.isNaN(num) ? 0 : num;
return acc + value;
}, 0);
}
function getMin(key2) {
return Math.min(...data.map((d) => Number(d[key2])));
}
function getMax(key2) {
return Math.max(...data.map((d) => Number(d[key2])));
}
function getValuePercent(key2, value, domain) {
const min = getMin(key2);
const max = getMax(key2);
if (domain) {
const d = typeof domain === "function" ? domain({ min, max }) : domain;
return (value - d[0]) / (d[1] - d[0]) * 100;
}
return value / getTotal(key2) * 100;
}
const sortedData = React__namespace.useMemo(() => {
if (!sort) return data;
return data.sort((a, b) => {
const aValue = Number(a[sort.by]);
const bValue = Number(b[sort.by]);
return sort.direction === "desc" ? bValue - aValue : aValue - bValue;
});
}, [data, sort]);
const getSeriesOpacity = (name, fallback = 0.2) => {
if (name && highlightedSeries)
return isHighlightedSeries(name) ? 1 : fallback;
};
const groupByImpl = (key2) => {
return groupBy(data, key2);
};
return {
id,
key,
// series
data: sortedData,
groupBy: groupByImpl,
series,
getSeries,
// token functions
color,
size,
spacing,
// formatters
formatNumber,
formatDate,
// state
highlightedSeries,
setHighlightedSeries,
isHighlightedSeries,
getSeriesOpacity,
// value functions
getTotal,
getMin,
getMax,
getPayloadTotal,
getValuePercent
};
}
const isObject = (value) => typeof value === "object" && value !== null;
function getProp(item, key) {
if (!key || !isObject(item)) return;
return Reflect.get(item, key);
}
function groupBy(data, key) {
const groups = /* @__PURE__ */ new Map();
for (const item of data) {
const value = item[key];
const group = groups.get(value) || [];
group.push(item);
groups.set(value, group);
}
return Array.from(groups.values());
}
exports.getProp = getProp;
exports.useChart = useChart;
;