DiscordのRich PresenceをUnityで使ってみた

:::note alert
この記事は古く、ここで紹介している方法は非推奨となっています。今からRich Presenceを実装する場合はGameSDKを使用してください。
https://discord.com/developers/docs/game-sdk/sdk-starter-guide
:::

DiscordにRich Presenceという、プレイ中のゲームの詳細情報を表示するという機能が追加されたらしく、Unityもサポートしているとのことなので使ってみました。

# Rich Presenceとはどういう機能か
## ゲームの詳細情報を表示する

![2017-11-10_18h32_41.png](https://qiita-image-store.s3.amazonaws.com/0/213093/1accb738-6c3f-d182-b868-35b928ff9356.png)

ゲームをプレイ中のとき、普通はプレイ中のタイトルが表示されるだけですよね。

![2017-11-10_18h11_52.png](https://qiita-image-store.s3.amazonaws.com/0/213093/f90a1aee-2044-dc57-2094-466fb89c899e.png)

Rich Presenceを使うと、任意の文字列やサムネイルをここに追加することができるので、他のユーザーにリアルタイムに情報が伝わるようになります。

## ゲームへの参加・観戦を受け付ける

他にも、ゲームへの参加や観戦ができるボタンを設置する機能などもあります。……が、ゲームをDiscordの運営に承認してもらう必要があるらしく、今回は別にそこまでは必要ではなかったので試してません。ボタンを押したことがゲーム側に通知されるような感じだと思います。

詳細：https://discordapp.com/developers/docs/rich-presence/how-to


# 導入する

## Appを作成する

Rich Presenceを動かすにはDiscord App（botとか作るときに使うやつと同じ）のClient IDが必要なので、適当なものを持っていなければ[こちら](https://discordapp.com/developers/applications/me)から作成します。

![2017-11-10_20h05_54.png](https://qiita-image-store.s3.amazonaws.com/0/213093/9d48b1ec-76f7-ddd5-5108-6103eed7b17b.png)

この「APP NAME」ですが、**ここに設定したものが表示されるゲームの名前になる**ので、そのようにしてください。アイコンや説明などは今回は必要ありません。

「Create App」をクリックして作成したら、

+ Client IDが表示されるのでメモしておく
+ ページ下のほうにある「Enable Rich Presence」をクリックする

これで、このAppをRich Presenceの設定をするために使用できるようになりました。あとはゲーム側にいくつか導入していきます。

## DLLのダウンロード

1. https://github.com/discordapp/discord-rpc/releases から「discord-rpc-2.0.1.zip」をダウンロード
1. 解凍して中の「win64-dynamic」（または「win32-dynamic」？）＞「bin」＞「discord-rpc.dll」を
1. UnityのAssetsフォルダの中のPluginsフォルダに入れる（なければ作成）


## DLLをインポートするスクリプトとサンプルを入手

1. https://github.com/discordapp/discord-rpc/tree/master/examples/button-clicker/Assets から「DiscordController.cs」「DiscordRpc.cs」をコピーしてUnityのScriptsフォルダに入れる
2. DiscordController.csを適当なオブジェクトにアタッチ
3. アタッチしたら「Application Id」の項目があるので、先ほどメモったClient IDを入力

# 動作確認


ここまでで導入は完了で、あとはDiscordController.csの`OnClick()`を呼び出せば、サンプルが動作するようになってます。

```C#:DiscordTest.cs
using UnityEngine;

public class DiscordTest : MonoBehaviour {

    DiscordController controller;
    
	void Start () {
        controller = GetComponent<DiscordController>();
	}
	
	void Update () {
        if (Input.GetMouseButtonDown(0)) controller.OnClick(); //左クリックで呼び出す
	}

}
```

というわけで、やっつけ感満載のこれを`DiscordController.cs`をアタッチしたのと同じオブジェクトにくっつけて実行。

![2017-11-10_19h54_39.png](https://qiita-image-store.s3.amazonaws.com/0/213093/93ac8d70-c7c0-9d0b-3528-3df446d95d23.png)


Unityで左クリックした回数がDiscordのほうで出れば成功です。

実際には短時間に何度も変更することはできないらしく、15秒に1回程度表示を更新するようですが、実用上は（遊んでいるステージとかを表示する用なので）たぶん問題ないかと思います。

あと、ゲーム名もAppで設定した名前になってるのを確認してください。Discordでは今まで、認識できないゲームをプレイ中として表示するにはユーザーがいちいち設定しなければならなかったのですが、Rich Presenceはそれも解消したことになります。やったぜ。



# その他の情報を設定する

`DiscordController.cs`の`OnClick()`を今一度見てください。

```C#:DiscordConrtoller.cs
public void OnClick(){

    Debug.Log("Discord: on click!");
    clickCounter++;

    presence.details = string.Format("Button clicked {0} times", clickCounter);

    DiscordRpc.UpdatePresence(ref presence);

}
```

`presence`（`DiscordRpc.RichPresence`型です）を渡してますが、これが実際にRich Presenceで表示されるデータです。

今回は`details`に入れた文字列が表示されていたのが分かると思いますが、他のパラメータを変更することにより、他にもいろいろなデータを表示させることができます。

```C#:DiscordConrtoller.cs
public void OnClick(){

    Debug.Log("Discord: on click!");
    clickCounter++;

    presence.details = "鬼ごっこ：ランクマッチ";
    presence.state = "残り 04:53";
    presence.largeImageKey = "stage_mountain";
    presence.largeImageText = "Stage : 群馬県";

    DiscordRpc.UpdatePresence(ref presence);

}
```

このようにすると、

![2017-11-10_22h03_25.png](https://qiita-image-store.s3.amazonaws.com/0/213093/849fc9fb-4cf2-b31e-52c6-6f152ba90db2.png)

こうなります（頭が回らなかったのでよくわからん例でごめんなさい）。画像はどこから来たのかというと、先ほどのAppを作成したページの下のほうに、

![2017-11-10_20h46_50.png](https://qiita-image-store.s3.amazonaws.com/0/213093/534c7f37-bb42-e849-360c-d32b1f7b69bd.png)

「RICH PRESENCE ASSETS」という項目があり、ここで画像と名前を設定しておくと使えます。TYPEはSmallとLargeがあり、Smallのほうを選んでも`presence.smallImageKey`に指定すれば使えるはず。

その他にも設定できるものは色々あるようで、[こちら](https://discordapp.com/developers/docs/rich-presence/how-to#updating-presence-update-presence-payload-fields)の表で確認できます。

# 終わりに

あとは、ゲーム内の任意のタイミングで情報を書き換えていけばいいです。

私は今自作しているゲームではDiscordサーバーを活用してコミュニティを盛り上げようと考えているので、このように他のユーザーの現在のプレイ状況が分かるようにできるというのは嬉しい機能でした。