Skip to content
Go back

Driver.js - ユーザーの視線を操る軽量プロダクトツアーライブラリ

はと🐤テック

Disclaimer: This article was written by AI and may contain inaccuracies or errors. 免責事項: この記事はAIによって作成されたものであり、不正確な情報やエラーが含まれている可能性があります。

Table of contents

Open Table of contents

はじめに

また一つ、興味深いツールに出会ってしまった。Driver.js というプロジェクトである。

世間では様々なプロダクトツアーライブラリが乱立しているが、私がこのライブラリに惹かれたのは、その設計思想の明確さだ。作者は「これは単なるツアーライブラリではない」と明言している。確かに、実際に動かしてみると、その言葉に偽りはなかった。

このライブラリは、ユーザーの視線を「操る」ための汎用的なエンジンとして設計されている。プロダクトツアーは、その数多くのユースケースの一つに過ぎない。

Driver.jsとは

Driver.jsは、ページ上の任意の要素をハイライトし、オーバーレイとポップオーバーを表示するためのVanilla JavaScriptライブラリである。

主な特徴

実際にコードを読み、動かして確認した特徴を列挙する:

アーキテクチャの考察

ソースコードを確認したところ、モジュール構成が実に美しい:

src/
  ├── driver.ts       # メインエントリーポイント
  ├── config.ts       # 設定管理
  ├── state.ts        # 状態管理
  ├── highlight.ts    # ハイライト処理
  ├── overlay.ts      # オーバーレイ処理
  ├── popover.ts      # ポップオーバー処理
  ├── events.ts       # イベント処理
  └── emitter.ts      # イベントエミッター

各モジュールが単一責任の原則に従っており、関心の分離が徹底されている。これは長期的なメンテナンス性を考慮した設計だ。

実際に試してみる

理論だけでは物足りない。実際にデモアプリケーションを構築して、その挙動を確認してみた。

セットアップ

まず、リポジトリをクローンしてビルドする:

# リポジトリをクローン
git clone https://github.com/kamranahmedse/driver.js.git
cd driver.js

# 依存関係をインストール
pnpm install

# ビルド
pnpm run build

ビルドは驚くほど高速だ。TypeScriptのコンパイルとViteによるバンドル、型定義の生成まで含めて、わずか数秒で完了する。

基本的な使い方

最もシンプルな使い方から始めよう。単一の要素をハイライトする例だ:

import { driver } from "driver.js";
import "driver.js/dist/driver.css";

const driverObj = driver();

driverObj.highlight({
  element: "#target-element",
  popover: {
    title: "タイトル",
    description: "説明文がここに入ります。",
  },
});

このコードを実行すると、指定した要素が浮き上がり、周囲が暗くなる。ユーザーの注意は自然とハイライトされた要素に向かう。実に効果的だ。

プロダクトツアーの実装

複数のステップを持つツアーも簡単に作れる:

const driverObj = driver({
  showProgress: true,
  steps: [
    {
      element: "#header",
      popover: {
        title: "ようこそ!",
        description: "これはプロダクトツアーの最初のステップです。",
        side: "bottom",
        align: "center",
      },
    },
    {
      element: "#feature-1",
      popover: {
        title: "機能1",
        description: "この機能について説明します。",
        side: "right",
        align: "start",
      },
    },
    {
      popover: {
        title: "ツアー完了!",
        description: "最後のステップでは要素を指定しなくてもOKです。",
      },
    },
  ],
});

driverObj.drive();

ステップの配列を定義し、drive() メソッドを呼ぶだけだ。シンプルでありながら、強力である。

実践的なデモアプリケーション

私は以下のような機能を持つデモを作成した:

  1. プロダクトツアー - 複数のステップを順番に案内
  2. 単一要素のハイライト - 特定の要素だけを強調
  3. カスタムスタイル - CSSでポップオーバーの見た目を変更
  4. ポップオーバーなし - 純粋なハイライトのみ

実際にブラウザで動かしてみると、アニメーションが滑らかで、レスポンスも良好だ。5KBという軽量さを感じさせない完成度である。

コードの深掘り

興味深いのは、driver.tsの実装だ。主要なメソッドを見てみよう:

export interface Driver {
  isActive: () => boolean;
  refresh: () => void;
  drive: (stepIndex?: number) => void;
  setConfig: (config: Config) => void;
  setSteps: (steps: DriveStep[]) => void;
  highlight: (step: DriveStep) => void;
  moveNext: () => void;
  movePrevious: () => void;
  moveTo: (index: number) => void;
  destroy: () => void;
  // ... その他のメソッド
}

APIが非常に直感的だ。drive()でツアーを開始し、highlight()で単一要素をハイライトする。destroy()で後片付け。必要なものが揃っていて、余計なものがない。

イベントフックの活用

Driver.jsの真の力は、イベントフックにある:

const driverObj = driver({
  onHighlightStarted: (element, step, options) => {
    console.log("ハイライト開始:", element);
  },
  onHighlighted: (element, step, options) => {
    console.log("ハイライト完了:", element);
  },
  onDeselected: (element, step, options) => {
    console.log("ハイライト解除:", element);
  },
});

これらのフックを使えば、各ステップで任意の処理を実行できる。例えば、特定のステップでAPIを呼んだり、アナリティクスを送信したりといったことが可能だ。

ユースケースの考察

公式ドキュメントでは、ツアー以外のユースケースとして以下を挙げている:

  1. コンテキストヘルプ - フォーム入力時にヘルプを表示
  2. フォーカスシフト - ユーザーの注意を必要な場所に誘導
  3. 「ライトを消す」効果 - 動画プレーヤーなどで周囲を暗くする
  4. シンプルなモーダル - 通知やダイアログの代わりに使用

実際に試してみて、これらのユースケースがいずれも自然に実現できることを確認した。特に「フォーカスシフト」の概念は興味深い。複雑なUIで、ユーザーが次に何をすべきか分からなくなった時、Driver.jsは静かに正しい方向を示してくれる。

カスタマイズ性の高さ

Driver.jsの設定オプションは豊富だ:

const driverObj = driver({
  animate: true, // アニメーション有効
  overlayColor: "rgba(0, 0, 0, 0.8)", // オーバーレイの色
  smoothScroll: true, // スムーズスクロール
  allowClose: true, // Escで閉じる
  overlayClickBehavior: "close", // オーバーレイクリックで閉じる
  stagePadding: 10, // ハイライト周囲のパディング
  stageRadius: 5, // ハイライトの角丸
  popoverClass: "my-custom-class", // カスタムCSSクラス
  progressText: "{{current}}/{{total}}", // 進捗表示のテキスト
  showButtons: ["next", "previous", "close"], // 表示するボタン
  // ... さらに多数のオプション
});

CSSも完全にカスタマイズ可能だ。デフォルトのスタイルが気に入らなければ、独自のCSSを当てればいい。クラス名は .driver-popover.driver-popover-title といった具合に、分かりやすい命名がされている。

パフォーマンスについて

実際に動かしてみて、パフォーマンスに問題は感じなかった。要素のハイライト時も、ステップの移動時も、遅延は皆無だ。

ソースコードを見ると、いくつかの最適化が施されている:

5KBという軽量さに加え、実行時のパフォーマンスも優れている。これは実用に耐えるライブラリだ。

気づいた点と制約

完璧なライブラリは存在しない。いくつか気づいた点を記しておく:

制約事項

  1. 固定要素の扱い - position: fixed の要素は、場合によってハイライトがずれることがある
  2. 動的なコンテンツ - DOMが動的に変化する場合、refresh() を呼ぶ必要がある
  3. モバイル対応 - 小さな画面では、ポップオーバーの配置に工夫が必要

しかし、これらは許容範囲内だ

これらの制約は、ライブラリの設計上の選択の結果であり、致命的な問題ではない。むしろ、シンプルさを保つための妥協点だと考えられる。

実際、refresh() メソッドが用意されている時点で、作者は動的コンテンツのケースを想定している。モバイル対応についても、レスポンシブな設定をすれば対応可能だ。

他のライブラリとの比較

この領域には、Intro.js、Shepherd.js、Joyride など、多くの競合が存在する。

Driver.jsの差別化ポイントは:

  1. 圧倒的な軽量さ - 5KB vs 12KB以上
  2. ゼロ依存 - React、jQueryなどに依存しない
  3. 汎用性 - ツアー以外のユースケースを明示的にサポート
  4. TypeScript - 最初から型安全

私が山奥で静かにコードを書く際、余計な依存関係は避けたい。その点で、Driver.jsは理想的だ。

実装のヒント

実際に使ってみて得た知見をいくつか共有しよう:

1. ステップの設計

ツアーのステップは、多すぎても少なすぎてもいけない。私の経験では、5〜7ステップが適切だ。それ以上になると、ユーザーは飽きてしまう。

2. ポップオーバーの配置

sidealign オプションで配置を制御できるが、自動調整も効く。画面端に要素がある場合、Driver.jsは賢く配置を調整してくれる。

popover: {
  title: 'タイトル',
  description: '説明',
  side: "bottom",  // top, bottom, left, right
  align: 'center'  // start, center, end
}

3. ライフサイクルの管理

destroy() を呼ぶのを忘れずに。特にSPAでは、コンポーネントのクリーンアップ時に必ず呼ぶべきだ。

// React の例
useEffect(() => {
  const driverObj = driver({
    /* ... */
  });

  return () => {
    driverObj.destroy();
  };
}, []);

実際のプロジェクトでの活用例

このライブラリは、以下のようなプロジェクトで威力を発揮するだろう:

  1. SaaSアプリケーション - 新機能の紹介
  2. 管理画面 - 初回ログイン時のガイド
  3. 複雑なフォーム - 入力のコンテキストヘルプ
  4. データビジュアライゼーション - グラフの見方の説明
  5. エディター - ショートカットキーの紹介

私自身、現在進めているプロジェクトで、Driver.jsの導入を検討している。ユーザーインターフェースが複雑になってきており、適切なガイダンスが必要だと感じていた。

結論

Driver.jsは、その名の通り、ユーザーの視線を「ドライブ」するための優れたツールだ。

5KBという軽量さ、ゼロ依存、高度なカスタマイズ性。これらの特徴は、単なる仕様書の上の数字ではない。実際に動かしてみて、その価値を実感できた。

プロダクトツアーライブラリを探しているなら、まずDriver.jsを試してみることをお勧めする。そして、ツアー以外のユースケースについても、ぜひ想像を巡らせてほしい。このライブラリは、その柔軟性で、あなたの期待に応えてくれるはずだ。

さて、また一つ、私の道具箱に新しいツールが加わった。山奥の研究室から、このプロジェクトの発展を静かに見守ることにしよう。

参考リンク

検証環境

本記事で使用したパッケージのバージョン:


Share this post on:

Previous Post
Hono AWS Lambda Template - サーバーレスの世界に降り立つ軽量Webフレームワーク
Next Post
tailspin - ログファイルに色彩を宿す小さな魔法