# Line Step

> A step line chart displaying infrastructure capacity and active server counts built with TanStack Charts.

A shadcn/ui block from the [@pacekit](https://ui.pacekit.dev/?utm_source=shadcn.exchange) registry, listed on [shadcn.exchange](https://shadcn.exchange/r/pacekit/tanstack-charts-line-step).

- Page, with a live preview: https://shadcn.exchange/r/pacekit/tanstack-charts-line-step
- Screenshot: https://abzjhwgwpdpz7ua5.public.blob.vercel-storage.com/shots/pacekit/tanstack-charts-line-step-light-5705ce5e189bb4f1.png
- Registry item: https://ui.pacekit.dev/r/tanstack-charts-line-step.json
- Listed: 2026-10-21, source last changed 2026-10-21

## Install

```bash
npx shadcn@latest add https://shadcn.exchange/r/pacekit/tanstack-charts-line-step.json
```

Run it in a project that has shadcn/ui set up. It adds the files below and installs what they depend on.

## Dependencies

- npm packages: `@tanstack/charts`, `@tanstack/react-charts`, `d3-array`, `d3-scale`, `d3-shape`
- Registry items: `card`

## Files

### `components/tanstack-charts/line/line-step.tsx`

```tsx
import { defineChart, lineY } from "@tanstack/charts";
import { d3Curve } from "@tanstack/charts/d3/shape";
import { motion } from "@tanstack/charts/motion";
import { tooltip } from "@tanstack/charts/tooltip";
import { Chart } from "@tanstack/react-charts/core";
import { useMemo } from "react";

import { max } from "d3-array";
import { scaleLinear, scalePoint } from "d3-scale";
import { curveStep } from "d3-shape";

import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card";

const motionRenderer = motion({
    initial: "always",
    transition: { type: "spring", stiffness: 170, damping: 18, mass: 1 },
});

const chartData = [
    { month: "January", activeServers: 42 },
    { month: "February", activeServers: 58 },
    { month: "March", activeServers: 65 },
    { month: "April", activeServers: 80 },
    { month: "May", activeServers: 70 },
    { month: "June", activeServers: 50 },
    { month: "July", activeServers: 60 },
    { month: "August", activeServers: 80 },
    { month: "September", activeServers: 100 },
];

export function LineStep() {
    const definition = useMemo(() => {
        const yMax = max(chartData, (d) => d.activeServers) ?? 0;

        return defineChart({
            renderer: motionRenderer,
            motion: {
                transition: { type: "spring", stiffness: 170, damping: 18, mass: 1 },
            },
            focus: "group-x",
            tooltip: {
                use: tooltip,
                motion: { type: "spring", stiffness: 170, damping: 18 },
                className: "font-sans! shadow-none! capitalize!",
                content: (points) => {
                    const datum = points[0]?.datum as (typeof chartData)[number];
                    if (!datum) return { rows: [] };
                    return {
                        title: String(points[0].xValue),
                        rows: [
                            {
                                label: "Active Servers",
                                value: String(datum.activeServers),
                                color: "var(--chart-1)",
                            },
                        ],
                    };
                },
            },
            marks: [
                lineY(chartData, {
                    id: "activeServers",
                    x: (d) => d.month.slice(0, 3),
                    y: (d) => d.activeServers,
                    stroke: "var(--chart-1)",
                    strokeWidth: 2,
                    curve: d3Curve(curveStep),
                    points: false,
                }),
            ],
            scales: {
                x: {
                    scale: scalePoint().domain(chartData.map((d) => d.month.slice(0, 3))),
                },
                y: {
                    scale: scaleLinear().domain([0, yMax]).nice(),
                    grid: true,
                },
            },
        });
    }, []);

    return (
        <Card className="gap-4">
            <CardHeader>
                <CardTitle className="text-lg">Infrastructure Capacity</CardTitle>
                <CardDescription>Active Instances (Q1–Q3 2024)</CardDescription>
            </CardHeader>
            <CardContent>
                <Chart
                    definition={definition}
                    renderer={motionRenderer}
                    height={250}
                    ariaLabel="Step line chart showing active server count over time"
                />
            </CardContent>
        </Card>
    );
}
```
