How to create a stepper dot progress ドットステップナビの作り方
A multi-step progress component using dots and a connecting line that animates to the active step. 複数ステップの進捗をドットとラインで可視化し、アクティブインジケーターが滑らかに切り替わるステッパーUI。
ライブデモ Live Demo
概要・用途・特徴Overview, Usage & Features
何ができるかWhat it does
A multi-step progress component using dots and a connecting line that animates to the active step.
複数ステップの進捗をドットとラインで可視化し、アクティブインジケーターが滑らかに切り替わるステッパーUI。
どこで使うかWhere to use
website header, dashboard sidebar, mobile menu, admin panel
チェックアウトフロー、オンボーディング、フォームウィザード、プロセス表示
特徴Key features
Visual step progress indicator using dot or circle markers. Active, completed, and upcoming states with distinct styling. CSS-only progress line fill between steps. Responsive horizontal or vertical orientation.
ドットまたは丸マーカーを使用した視覚的なステップ進行インジケーター。アクティブ・完了・未完了の各状態に異なるスタイル。ステップ間のCSSオンリーの進行ラインフィル。水平または垂直方向のレスポンシブ表示。
調整可能パラメータ Adjustable Parameters
| Parameter | Default | Description |
|---|---|---|
step count | — | adjust step count for different workflows |
transition duration | — | adjust `transition-duration` for faster/slower fills |
labels | — | attach step titles or tooltips |
reduced motion | — | switch to instant changes under reduced motion |
実装コード Implementation Code
// react/N-002.jsx
import { useState, useRef, useEffect } from "react";
import "./N-002.css";
export default function StepperDotProgress({ steps = 4 }) {
const [active, setActive] = useState(0);
const stepperRef = useRef(null);
const [progressWidth, setProgressWidth] = useState(0);
useEffect(() => {
const dots = stepperRef.current?.querySelectorAll(".stepper__dot");
if (!dots?.length) return;
const first = dots[0], current = dots[active];
setProgressWidth(
current.offsetLeft + current.offsetWidth / 2 -
(first.offsetLeft + first.offsetWidth / 2)
);
}, [active]);
return (
<div className="stepper" ref={stepperRef}>
<div className="stepper__track" />
<div className="stepper__progress" style={{ width: progressWidth }} />
{Array.from({ length: steps }).map((_, i) => (
<button
key={i}
className={`stepper__dot ${i < active ? "is-complete" : ""} ${i === active ? "is-active" : ""}`}
onClick={() => setActive(i)}
>
{i + 1}
</button>
))}
</div>
);
}
.stepper {
display: flex;
align-items: center;
justify-content: space-between;
position: relative;
}
.stepper__track {
position: absolute;
top: 50%;
left: 32px;
right: 32px;
height: 2px;
background: rgba(255, 255, 255, 0.2);
transform: translateY(-50%);
}
.stepper__progress {
position: absolute;
top: 50%;
left: 32px;
height: 2px;
background: linear-gradient(90deg, #5c6ac4, #22d3ee);
transform: translateY(-50%);
transition: width 0.35s ease;
}
.stepper__dot {
width: 48px;
height: 48px;
border-radius: 50%;
border: 2px solid rgba(255, 255, 255, 0.35);
position: relative;
cursor: pointer;
}
.stepper__dot.is-active { border-color: #22d3ee; color: #22d3ee; }
.stepper__dot.is-complete::after {
content: "";
position: absolute;
inset: 6px;
border-radius: 50%;
background: linear-gradient(135deg, #5c6ac4, #22d3ee);
opacity: 1;
}
import { useState } from "react";
import "./N-002.css";
const steps = ["Plan", "Design", "Build", "Launch"];
export default function StepperDotProgress() {
const [current, setCurrent] = useState(1);
const percentage = (current - 1) / (steps.length - 1);
return (
<div className="stepper">
<div className="stepper__track" />
<div className="stepper__progress" style={{ width: `${percentage * 100}%` }} />
{steps.map((label, index) => {
const stepNumber = index + 1;
const isActive = stepNumber === current;
const isComplete = stepNumber < current;
return (
<button
key={label}
className={`stepper__dot${isActive ? " is-active" : ""}${isComplete ? " is-complete" : ""}`}
onClick={() => setCurrent(stepNumber)}
>
{stepNumber}
</button>
);
})}
</div>
);
}
.stepper {
position: relative;
display: flex;
justify-content: space-between;
align-items: center;
gap: 20px;
}
.stepper__track,
.stepper__progress {
position: absolute;
left: 32px;
right: 32px;
top: 50%;
height: 2px;
transform: translateY(-50%);
}
.stepper__track {
background: rgba(255, 255, 255, 0.2);
}
.stepper__progress {
background: linear-gradient(90deg, #5c6ac4, #22d3ee);
height: 2px;
transition: width 0.35s ease;
}
.stepper__dot {
width: 48px;
height: 48px;
border-radius: 50%;
border: 2px solid rgba(255, 255, 255, 0.35);
background: rgba(255, 255, 255, 0.05);
color: #fff;
font-weight: 600;
position: relative;
cursor: pointer;
}
.stepper__dot.is-active {
border-color: #22d3ee;
color: #22d3ee;
}
.stepper__dot.is-complete::after {
content: "";
position: absolute;
inset: 6px;
border-radius: 50%;
background: linear-gradient(135deg, #5c6ac4, #22d3ee);
}
仕組みとカスタマイズHow It Works & Customization
仕組みHow it works
Steps are flex items connected by a pseudo-element line. Completed steps get a filled background and a checkmark; the active step gets an accent border and pulse; upcoming steps are muted. The connector line uses a width or scaleX transition to animate fill as steps are completed.
ステップは疑似要素ラインで接続されたflexアイテム。完了済みステップはチェックマーク付きの塗りつぶし背景、アクティブステップはアクセントボーダーとパルス、未完了ステップはミュートされます。コネクターラインはステップ完了に伴ってwidthまたはscaleXトランジションでフィルをアニメーション。
カスタマイズ方法Customization
Replace dot markers with numbered circles for instructional flows. Add step labels below each marker. Switch to a vertical layout by changing flex-direction to column. Animate the connector fill on step advance.
説明フロー用にドットマーカーを番号付き丸に置き換え。各マーカーの下にステップラベルを追加。flex-directionをcolumnに変えて縦レイアウトに切り替え。ステップ進行時にコネクターフィルをアニメーション。
注意点Caveats
Provide aria-current="step" on the active step and aria-label on each step marker describing its position (e.g., "Step 2 of 4: Shipping"). Use a visually hidden live region to announce step changes to screen reader users.
アクティブステップにaria-current="step"を設定し、各ステップマーカーに位置を説明するaria-label(例:"4ステップ中ステップ2:配送")を追加してください。スクリーンリーダーユーザーへのステップ変更アナウンスには視覚的に非表示のlive regionを使用してください。
よくある質問 Frequently Asked Questions
How to customize the stepper dot progress? Stepper Dot Progressをカスタマイズするには?
Modify the CSS custom properties and class styles defined in the code section. Key adjustable values include colors, sizes, durations, and spacing. See the Adjustable Parameters section for specific variables.
コードセクションで定義されているCSSカスタムプロパティとクラススタイルを変更してください。色、サイズ、時間、間隔が主な調整可能値です。具体的な変数は調整可能パラメータセクションを参照してください。
How to use the stepper dot progress in React? ReactでStepper Dot Progressを使うには?
Import the provided React component and its CSS file. The component accepts props for customization. Check the React code section for the full implementation and available props.
提供されているReactコンポーネントとCSSファイルをインポートしてください。コンポーネントのpropsでカスタマイズできます。完全な実装と利用可能なpropsはReactコードセクションを参照してください。
What are the performance implications of stepper dot progress? Stepper Dot Progressのパフォーマンスへの影響は?
This implementation uses CSS transforms and opacity for animations, which are GPU-accelerated. It's lightweight and doesn't cause layout thrashing. Consider using prefers-reduced-motion for accessibility.
この実装はCSSのtransformとopacityを使用しており、GPUアクセラレーションされます。軽量でレイアウトスラッシングを引き起こしません。アクセシビリティのためにprefers-reduced-motionの使用を検討してください。
AIへの指示テンプレート AI Prompt Template
以下をAIに貼り付けると実装を依頼できます。 Paste the following into your AI assistant to request implementation.