【ポートフォリオに是非！】Intro.jsとjquery.cookie.jsを利用してチュートリアル機能を作成

# はじめに
WEB業界への転職活動中の3isawaと申します。
転職活動の際、自分の実力を示すために、稚拙ながらポートフォリオを作成しました。
お忙しい採用担当の方に短い時間でポートフォリオの機能を把握して頂くために、
「チュートリアル」を作成したら、カジュアル面談などの場で「使い方がわかりやすかった！」や
「チュートリアルいいね！」とポジティブなフィードバックを頂くことができました:smiley:
ポートフォリオ作成や個人開発をしている方の参考になればと思い、本記事を作成しました。

# 完成イメージ
以下の様な、各画面の部品を示しながら説明を表示するチュートリアルを作成します。
![完成イメージ](https://media.giphy.com/media/kc0pC1mgJGOvacGVMQ/giphy.gif)

# 前提事項
本記事ではチュートリアルを呼び出すタイミングを2つに絞ります。
1. ユーザーが「チュートリアル開始ボタン(ヘルプボタン)」を押した時
2. ユーザーが初回アクセスした時(Cookieにアクセスした形跡が無い時)

チュートリアルを表示するために、Intro.jsというライブラリを使用します。
また、上記2のタイミングでチュートリアルを実行するために、jquery.cookie.jsを使用します。
なお、チュートリアルを表示するアプリケーションはRuby on Rails5系で作製しています。

# Intro.jsを入手
[Intro.jsのリポジトリ](https://github.com/usablica/intro.js)から`git clone〜`などの方法でライブラリを入手します。

その後、入手したフォルダの中から`intro.js`と`introjs.css`をアプリケーションフォルダの適切な箇所に格納します。
私はRailsアプリにIntro.jsを適用したかったため、`アプリディレクトリ/vendor`配下に格納しました。
(vendor配下に配置したファイルがRailsアプリ起動時に読み込まれるように設定して下さい)

# いざチュートリアルを作成
自分の望むチュートリアルの動作に近い物を[DEMOページ](https://introjs.com/)から探して下さい。
動作は各項目のDEMOボタンを押すことで確認が可能です。
その後、DEMOボタン横のSOURCEボタンを押すことで、そのDEMOを実現するコードが乗っているので真似しながら実装してみて下さい。
詳細な仕様については[ドキュメント](https://introjs.com/docs/)をご参照下さい。

前述した完成イメージの様な動作は以下のコードで実現しました。

```javascript:sample.js

introJs().setOptions({
    // setOptionsAPIでオプションの設定は可能です。設定可能な項目は以下のリンクをご確認下さい。
    // https://introjs.com/docs/intro/options/
    'nextLabel': '次 →',
    'prevLabel': '← 前',
    'skipLabel': 'スキップ',
    'doneLabel': '終了',
    'exitOnOverlayClick': false,
    'showStepNumbers': false,
    // stepsの項目に、具体的にチュートリアルで表示する内容を記述します。
    // intro: 表示するテキスト。HTMLタグが使用可能です。
    // element: elementで指定したオブジェクト周辺にintroの内容を表示する。
    //          CSSのセレクタの様に記述します。
    //          対象のオブジェクトにelementの中身と同じidが指定されている必要があります。
    steps: [
      {
        intro: "<b>Libnodeへようこそ！</b><br>簡単にLibnodeの機能をご紹介します！"
      },
      {
        element: '#introjs-step1',
        intro: "Libnodeに登録されている全ての書籍を確認できます！"
      },
      {
        element: '#introjs-step2',
        intro: "タイトルやカテゴリから書籍を効率的に検索することができます！"
      },
      {
        element: '#introjs-step3',
        intro: "各書籍の画像をクリックすると、<br>こちらに書籍の詳細情報が表示されます！"
      },
　　　//#################省略#################
    ]
  // 最終的にstart()を呼び出すことでチュートリアルが開始されます。
  }).start()
```
## 特定のボタンを押した時にチュートリアルを開始する
以上のコードを適当な関数でラップし、 チュートリアル開始ボタン(ヘルプボタン)を押した時に
実行するようにすれば、ひとまず完成です。

## ユーザーが初回アクセスした時(Cookieにアクセスした形跡が無い時)に自動的にチュートリアルを開始する

ユーザーが初回アクセスしたかどうかは、「Cookie」という各ユーザーのブラウザに備わる一時的に情報を保存するエリアを活用して判定します。

方針としては、ページに訪れた際、チュートリアルを実行するか確認する関数を呼び出し、

- Cookieに自分のサイトに訪れた形跡が有る → チュートリアルを開始しない
- Cookieに自分のサイトを訪れた形式が無い → チュートリアルを開始  
という様に条件分岐します。

### ページに訪れた際、チュートリアルを実行するか確認する関数を用意する
上述したチュートリアルを構成するコードを`tutorial()`で呼び出せるようにした場合、
以下のように実装します(jQueryを使用しています)

```javascript:sample.js
// $(function(){ ~ });内に記述したコードは自動的に実行されます
$(function(){
  // $.cookieでCookieを読み込む
  // `SampleFlg`というデータがonであれば、チュートリアルを呼び出す
  if ($.cookie('SampleFlg') != 'on') {
    tutorial();
  }
});
```

### Cookieにデータを書き込む
ユーザーがサイトにアクセスした際に、CookieにSampleFlgという値を書き込みます。
書き込むには`jquery.cookie.js`というjQueryライブラリを使用します。
当該ライブラリを使用すると簡単に値を書き込むことができます。

値はチュートリアルが終了したタイミングに書き込みます。
チュートリアルが終了したタイミングはIntro.jsのonExitというCallbackで取得することが
できます。

```javascript:onExit-sample.js
  introJs().setOptions({
    // 〜〜〜〜〜〜省略〜〜〜〜〜〜
    steps: [
    // 〜〜〜〜〜〜省略〜〜〜〜〜〜
    ]
  // onexit(function(){})がチュートリアルが終了したタイミングで呼び出されます
  // そのタイミングでCookieに値を書き込みます。
  }).start().onexit(function() {
    // $.cookieの中の第一引数で書き込むデータのKEY、第二引数でValue
    // expiresでCookieに書き込んだ値の有効期限を設定し、
    // pathで値が有効となるパスを指定します。
    $.cookie('SampleFlg', 'on', { expires: 30,path: '/' });
  });
```

## デザインに納得がいかなかったら
introjs.cssを編集することでデザインの編集が可能です。
私は`.introjs-helperLayer`内の`background-color`や、
`.introjs-tooltip`の`max-widthやmin-width`などを変更しました。

試してはいませんが、[テーマ一覧ページ](https://introjs.com/docs/themes/list#themes)のように、見た目を大きく変えるcssファイルも提供されています。

# おわりに
以上でチュートリアルの作成手順は終了です。
始めて使用したライブラリでしたが、驚くほど簡単に分かりやすいチュートリアルを作成する事ができて感動しました。

記事の内容に誤りや不明点があればコメントを頂けると幸いです。