|
|
@@ -13,14 +13,21 @@ export function LineGraph({ element }: ComponentRenderProps) {
|
|
|
const customClass = getCustomClass(props);
|
|
|
const data = (props.data as DataPoint[]) || [];
|
|
|
const title = props.title as string | undefined;
|
|
|
- const maxValue = Math.max(...data.map((d) => d.value), 1);
|
|
|
- const minValue = Math.min(...data.map((d) => d.value), 0);
|
|
|
+ const maxValue = Math.max(...data.map((d) => d.value));
|
|
|
+ const minValue = Math.min(...data.map((d) => d.value));
|
|
|
const range = maxValue - minValue || 1;
|
|
|
|
|
|
+ // SVG dimensions with padding
|
|
|
+ const width = 300;
|
|
|
+ const height = 100;
|
|
|
+ const padding = { top: 10, right: 10, bottom: 10, left: 10 };
|
|
|
+ const chartWidth = width - padding.left - padding.right;
|
|
|
+ const chartHeight = height - padding.top - padding.bottom;
|
|
|
+
|
|
|
// Calculate points for the SVG path
|
|
|
const points = data.map((d, i) => {
|
|
|
- const x = data.length > 1 ? (i / (data.length - 1)) * 100 : 50;
|
|
|
- const y = 100 - ((d.value - minValue) / range) * 100;
|
|
|
+ const x = padding.left + (data.length > 1 ? (i / (data.length - 1)) * chartWidth : chartWidth / 2);
|
|
|
+ const y = padding.top + chartHeight - ((d.value - minValue) / range) * chartHeight;
|
|
|
return { x, y, ...d };
|
|
|
});
|
|
|
|
|
|
@@ -36,19 +43,36 @@ export function LineGraph({ element }: ComponentRenderProps) {
|
|
|
) : null}
|
|
|
<div className="relative h-24">
|
|
|
<svg
|
|
|
- viewBox="0 0 100 100"
|
|
|
- preserveAspectRatio="none"
|
|
|
+ viewBox={`0 0 ${width} ${height}`}
|
|
|
className="w-full h-full"
|
|
|
>
|
|
|
{/* Grid lines */}
|
|
|
<line
|
|
|
- x1="0"
|
|
|
- y1="50"
|
|
|
- x2="100"
|
|
|
- y2="50"
|
|
|
+ x1={padding.left}
|
|
|
+ y1={padding.top + chartHeight / 2}
|
|
|
+ x2={width - padding.right}
|
|
|
+ y2={padding.top + chartHeight / 2}
|
|
|
+ stroke="currentColor"
|
|
|
+ strokeOpacity="0.1"
|
|
|
+ strokeWidth="1"
|
|
|
+ />
|
|
|
+ <line
|
|
|
+ x1={padding.left}
|
|
|
+ y1={padding.top}
|
|
|
+ x2={width - padding.right}
|
|
|
+ y2={padding.top}
|
|
|
+ stroke="currentColor"
|
|
|
+ strokeOpacity="0.1"
|
|
|
+ strokeWidth="1"
|
|
|
+ />
|
|
|
+ <line
|
|
|
+ x1={padding.left}
|
|
|
+ y1={height - padding.bottom}
|
|
|
+ x2={width - padding.right}
|
|
|
+ y2={height - padding.bottom}
|
|
|
stroke="currentColor"
|
|
|
strokeOpacity="0.1"
|
|
|
- vectorEffect="non-scaling-stroke"
|
|
|
+ strokeWidth="1"
|
|
|
/>
|
|
|
{/* Line */}
|
|
|
{pathD && (
|
|
|
@@ -59,7 +83,6 @@ export function LineGraph({ element }: ComponentRenderProps) {
|
|
|
strokeWidth="2"
|
|
|
strokeLinecap="round"
|
|
|
strokeLinejoin="round"
|
|
|
- vectorEffect="non-scaling-stroke"
|
|
|
className="text-foreground/80"
|
|
|
/>
|
|
|
)}
|
|
|
@@ -69,9 +92,8 @@ export function LineGraph({ element }: ComponentRenderProps) {
|
|
|
key={i}
|
|
|
cx={p.x}
|
|
|
cy={p.y}
|
|
|
- r="3"
|
|
|
+ r="4"
|
|
|
className="fill-foreground"
|
|
|
- vectorEffect="non-scaling-stroke"
|
|
|
/>
|
|
|
))}
|
|
|
</svg>
|