進捗がなかったらメンターが現れるATOM

# はじめに

進捗がなかったらメンターが現れて、僕たちを鼓舞してくれるATOMパッケージを作りました。

![english_completely.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/48fa0c03-361b-45d5-8212-3f1bf214ff90.gif)

https://atom.io/packages/atom-mentor
https://github.com/iwamatsu0430/atom-mentor

# インスパイア元

<blockquote class="twitter-tweet" data-lang="ja"><p lang="ja" dir="ltr">進捗がなかったらメンターが現れるエディター<a href="https://twitter.com/hashtag/%E9%A7%86%E3%81%91%E5%87%BA%E3%81%97%E3%82%A8%E3%83%B3%E3%82%B8%E3%83%8B%E3%82%A2%E3%81%A8%E7%B9%8B%E3%81%8C%E3%82%8A%E3%81%9F%E3%81%84?src=hash&amp;ref_src=twsrc%5Etfw">#駆け出しエンジニアと繋がりたい</a> <a href="https://t.co/QGkOMIuTgp">pic.twitter.com/QGkOMIuTgp</a></p>&mdash; Nino (@d151005) <a href="https://twitter.com/d151005/status/1144530641599356929?ref_src=twsrc%5Etfw">2019年6月28日</a></blockquote>
<script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

https://www.youtube.com/watch?v=ZXsQAXx_ao0 (※音量注意)

# 何ができるのか

コードを書かずに一定時間経過すると、大音量で「Just Do It!!!」と叫ぶおじさんの動画を表示します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/10164b34-2094-06c7-dcad-8dd26cd0dbe3.png)


動画の外側をクリックすれば消えますが、コードを書かずに一定時間経過するとまた表示します。
以下の設定を任意に変更する事もできます。

- メンターが出てくるまでの時間(デフォルト:60秒)
- 表示動画(デフォルト:[インスパイア元](https://www.youtube.com/watch?v=ZXsQAXx_ao0))

## 字幕表示 (2019/07/21 追記)

字幕が出せるようになりました。

![screenshot.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/f4fd201b-99e2-8afd-7edd-b8e257bc7e8d.gif)

セリフを変える事ができるので元ネタの再現も可能です。

![japanese.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/2681e9f7-b86f-ca55-2610-fdf486bbfe7d.gif)

## クロマキー (2019/07/22 追記)

メンターがATOMと和解しました。

![english_completely.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/48fa0c03-361b-45d5-8212-3f1bf214ff90.gif)

クロマキーを有効にするとPCがうなりだすので、有効/無効を切り替えられるようにしています。
また背景色やしきい値も設定できるので、任意の動画を透過させられるはずです。

# 技術解説

## ATOMパッケージの作り方

パッと雛形を作れるコマンドがあります。(`Generate Package`)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/4f129f61-75fc-571b-99ac-87330ffeec18.png)

作り方自体は[公式ブログ](https://github.blog/2016-08-19-building-your-first-atom-plugin/)が詳しいです。

## 起動時に自動的に読み込まれるようにする

雛形のままだと`my-package:toggle`といったコマンドを実行しないとパッケージが初期化されません。
メンターを呼び出すための操作が必要だとサボってしまう事があるかもしれません。それではせっかくのメンターも効果半減でしょう。
なのでATOM起動時にメンターが自動でスタンバイしてくれるようにします。

`my-package:toggle`を実行すると`package.json`の`main`で指定されたスクリプトから`activate`メソッドが実行されます。
`package.json`には`activationCommands`という項目があるのですが、これを削除する事で`activate`メソッドが起動時に自動で実行されるようになります。

## エディターイベント監視

ATOMにおける**進捗**とはなにか？今回はこれを「コードを書いているか」としました。
なのでエディタで何かしら編集したときのイベントをキャッチする必要があります。

今回は[Workspace APIのobserveTextEditorsメソッド](https://atom.io/docs/api/v1.0.7/Workspace#instance-observeTextEditors)を利用します。
ここで得られる[TextEditor](https://atom.io/docs/api/v1.0.19/TextEditor)クラスの[onDidChange](https://atom.io/docs/api/v1.0.19/TextEditor#instance-onDidChange)を使う事で「コードを書いているか」を検知できます。

```javascript
atom.workspace.observeTextEditors(editor => {
  editor.getBuffer().onDidChange(() => {
    // コードを書いたと判定
  });
});
```

## YouTubeの呼び出し

メンターにどのように現れてもらうかについては悩みどころでしたが、手っ取り早くYouTubeから来てもらう事としました。
YouTubeでは「共有」ボタンから埋め込み用のiframeコードを得ることができます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16913/040893a5-01b9-e901-a0c9-3c1a398f6e02.png)

これをちょっといじって自動再生できるようにします。[この記事](http://takuyakobayashi.id/blog/2018/08/25/2319)を参考にしました。

```html
<iframe src="https://www.youtube.com/embed/ZXsQAXx_ao0?controls=0&autoplay=1&loop=1&playlist=ZXsQAXx_ao0&muted=1" frameborder="0" allow="accelerometer; encrypted-media; gyroscope; picture-in-picture"></iframe>
```

## 設定を自由に変更できるようにする

メンターは60秒進捗がないと現れるようにしてみましたが、人によっては「もっと厳しくしてほしい！」と思われるかもしれません。また、字幕付きの動画じゃないと「何言ってるかわからない！」という事があるかもしれません。
なのでユーザがパラメータを自由に設定できるようにします。

ATOMパッケージでは`package.json`で`main`に指定されているスクリプトが`config`という項目をエクスポートする事でユーザーが編集可能な設定を定義できます。(詳しくは[ドキュメント参照](https://atom.io/docs/api/v1.0.7/Config))

```javascript
config: {
  video: {
    title: "Video ID",
    description: "Set YouTube ID",
    type: "string",
    default: "ZXsQAXx_ao0",
    order: 1,
  },
  showSeconds: {
    title: "Show Seconds",
    description: "Waiting time for your mentoring",
    type: "integer",
    default: 60,
    order: 2,
  },
},
```

設定の値を使いたいときは以下のように呼び出せば大丈夫です。

```javascript
atom.config.get('my-package.showSeconds')
```

# 今後について

~~今回は楽をするためにYouTubeを利用しましたが、インスパイア元のようにメンターとエディターが調和する姿を目指したいと考えています。なので以下の2機能は開発したい気持ちはあります。~~ (I did it!)

- ~~透過(クロマキー)~~ (I did it!)
    - [この記事](https://qiita.com/keiskimu/items/a4fc9ebb338906b9813e)が参考になりそう
- ~~字幕表示~~ (I did it!)
    - 字幕がないとインパクトがあまりない事に気づいた
    - 嘘字幕で遊べそう

# おわりに

思ったより邪魔なので作ってて楽しかったです。
メンターはアメとムチの使い分けが重要であると学びました。

# ちなみに

VSCode版もあるそうです
https://marketplace.visualstudio.com/items?itemName=dyuji.justdoitextension