【Unity】DoozyUIのUIPopupの使い方

##初めに
こちらはUnityのAssetの[DoozyUI](https://assetstore.unity.com/packages/tools/gui/doozyui-complete-ui-management-system-138361)のUIPopupについての記事です。
DoozyUIのチュートリアル動画はだいたい理解できる内容だったのですが、[UIPopupの動画](https://www.youtube.com/watch?v=TQXgouPw5rY)だけは少しわかりにくかったので記事にしました。
DoozyUIの他の機能と共通なところはあまり説明していません。ご容赦ください。
この記事ではDoozyUIのversion3.0.c4を使用しています。

##UIPopupとは
- UIPopupはuGUIのプレハブをアニメーションさせて表示する機能です。
- キューに登録して順番に１個づつ表示することもできます。
- UIViewと似たようなところがありますが単体で使う時に向いてそうです。

##UIPopupの使用方法
まずは最小構成で動作させてみます。

1. UIPopupを持つuGUIのプレハブを作ります。
Hierarchyで右クリックからDoozy＞UI＞UiPopupで作ります。
UIPopupのShowとHideにアニメーションを設定をしておきます。
![UIPopupShowHide2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/316385/27ab4a5f-c07f-cba6-9698-adbe3150d2d0.png)

2. メニューのTool＞Control PanelからDoozyUIのウィンドウを開いて、Popupsデータベースに名前を入力してプレハブを登録します。
![UIPopupPopups.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/316385/9ac900be-dca5-fedd-79d1-c9b97e8bd40e.png)

3. 下記スクリプトを実行するとプレハブからインスタンスを作成して表示します。
ボタン等のイベントに設定して実行してください。

####最小構成のスクリプト
```
using UnityEngine;
using Doozy.Engine.UI;

public class DoozyPopupShowExample : MonoBehaviour
{
    [SerializeField]
    string PopupName;

    public void PopupShow()
    {
        UIPopup popup = UIPopupManager.GetPopup(PopupName);
        UIPopupManager.ShowPopup(popup, popup.AddToPopupQueue, false);
    }
}
```

##表示内容の変更方法
UIPopupの例を見るとテキスト、スプライト、ボタン等の内容を変更していました。
UIPopupには変更対象を管理しやすくする仕組みが用意されていて対象のオブジェクトをリストに設定しておきます。
![Popups_003.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/316385/237f3065-9002-d4d6-baf1-2fa78bfe4a99.png)

それぞれの設定数とスクリプトの関数の引数の数は合わせます。
スクリプトの関数の引数が多い場合はエラーになります。
####表示内容の変更のスクリプト例
```
UIPopup popup = UIPopupManager.GetPopup(PopupName);

popup.Data.SetLabelsTexts(Title, Message);          //←追加 テキストの文字を変更
popup.Data.SetImagesSprites(sprite);                //←追加 画像の変更
popup.Data.SetButtonsLabels(LabelButtonOne);        //←追加 ボタンの文字を変更
popup.Data.SetButtonsCallbacks(ClickButtonOne);     //←追加 ボタンで実行したい関数を登録

UIPopupManager.ShowPopup(popup, popup.AddToPopupQueue, false);
```

公式の参考例E11のスクリプトでは登録したリストを取得して直接色を変更していたりする例もありました。
ここまでの流れがわかれば、あとは公式資料も参考にしていけば良いかと思います。

##気になったところ
1. DoozyUIでTextMeshProを使用する設定にしているとSetLabelsTextsで通常のTextは変更できないようです。
2. 公式のE11のスクリプトでm_popup.Show()になっていました。
UIPopupManager.ShowPopupを使わないとAftar to Popup Quaueの設定が無視されます。
3. GetPopup関数の処理が少し遅い気がしました。
私の環境で測定したらほぼ0.9ms程度かかっていました。
関数内の処理を見るとデータベースからプレハブを探す際にList\<UIPopupLink\>をforeachで2回ループしていたことと、そもそものInstantrateが遅いのが原因と思います。

※UIPopupLinkはDoozyUIデータベースが管理している名前とプレハブを持つScriptableObjectです。
※UIPopupLinkはAssets\Doozy\Engine\Resources\Data\UIPopupEngineフォルダに作成されてました。

##今回考えた遅延対策
使い方次第なのでここからは蛇足かもしれませんが、下記の2点をやってみました。
1. UIPopupLinkからプレハブを取得する。
2. オブジェクトプールを使用する。
####参考スクリプト例

```
using System.Collections.Generic;
using UnityEngine;
using Doozy.Engine.UI;
using A_rosuko.ObjectPool;

public class DoozyUIPopupInstantiate : MonoBehaviour
{
    [SerializeField]
    UIPopupLink uiPopupLink;

    public void AddMessage(string Message)
    {
        //オブジェクトプールからプレハブのインスタンスを取得
        GameObject clone = ObjectPool.Instance.GetGameObject(uiPopupLink.Prefab);
        UIPopup popup = clone.GetComponent<UIPopup>();
        
        //UIPopupの設定を変更する
        popup.Data.SetLabelsTexts(Message);

        UIPopupManager.ShowPopup(popup, popup.AddToPopupQueue, false);
    }
}
```

オブジェクトをプールに戻す処理はUIPopup側でDestroyしない設定にして、HidePopupのFinishのUnityEventsにプールする処理を登録して実行してます。
1の方は効果が少なかったですが、2の効果が大きかったので約0.08ms程度に改善しました。

最後まで読んでいただきありがとうございました。