Power Apps で投票ツールを作る

※ データや見た目は一部記事用に改変しています

## 作ったもの

こんな感じの投票ツールを Power Apps で作りました
👍 ボタンを押すと投票できて、投票数（青文字）を押すと投票したユーザーの一覧を見ることができるツールです
<img width="700" alt="投票ツールの画像" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/175234/04d3e2f7-c0a3-7a5e-8967-78e1a28b3af1.png">

## データの持ち方

SharePoint のリストを DB にしました
データの持ち方はこんな感じです

| カラム | タイプ | 説明 |
| :-- | :-- | :-- |
| 番号 | 1行テキスト | 項目の番号を格納します |
| 項目名 | 1行テキスト | 項目の名前を格納します |
| ユーザー | 複数行テキスト | 投票したユーザーのメールアドレスを`,`区切りで格納します |

投票数の持ち方は色々あると思うのですが、今回は投票したユーザーを一覧できるようにしたかったのでこんな風にしました
Office365 コネクタを使って、メールアドレスからユーザの名前と写真を引っ張ってきて表示します

## Power Apps 側

一覧部分は `挿入 ＞ ギャラリー` から「ギャラリー(Gallery」を挿入してアイテムをループで表示します
<img width="700" alt="投票ツールの画像" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/175234/6d38c36b-3112-347d-80f0-3bf51fbff02d.png">

### 投票数が多い ＞ 番号が早い 順で表示する

投票数（ユーザー）の持ち方のせいで、ここでけっこう苦戦しました...
SQL 慣れてる人はちょちょい！とできてしまうのかも😅

最終的なコードはこんな感じです

```:ギャラリー：Items
Sort(
    Sort(
        'リスト名',
        番号,
        Ascending
    ),
    If(
        IsBlank(
            Trim(
                Substitute(
                    Substitute(
                        PlainText(ユーザー),
                        Char(10),
                        ""
                    ),
                    Char(13),
                    ""
                )
            )
        ),
        0,
        CountRows(
            Split(
                Trim(
                    Substitute(
                        Substitute(
                            PlainText(ユーザー),
                            Char(10),
                            ""
                        ),
                        Char(13),
                        ""
                    )
                ),
                ","
            )
        )
    ),
    Descending
)
```

#### ポイント① 二重で Sort する
投票数が多い ＞ 番号が早い 順で表示したいので、二重で Sort します
優先度が高いもの（今回で言うと「投票数」）を外側にします

#### ポイント② 投票数「0」の出し方
はじめは `ユーザーカラムの中身を Split => Split したものを CountRows で個数数えて投票数を出す`
という風にしていたのですが、 Split だと空の場合も 1 件としてカウントされてしまいます

そこで、 `If`を使って「空白の場合は 0 件」という条件を追加しました

空白の判定には`IsBlank`を使う + ユーザーカラムは複数行テキストなので改行・空白を取り除く ようにしました
改行は `CR = Char(13)` `LF = Char(10)` です

投票数の算出ロジックは、投票数を表示している箇所・投票数によってテキストの色を変えている箇所も同様です

※ こちら参考にさせていただきました
https://qiita.com/yamad365/items/4f0bec10ae57368173d3


### 投票する

👍 ボタンを押して投票できるようにしています

`Office365ユーザー`コネクタの`MyProfileV2()`を使うと、アプリケーションの画面を見ているユーザーの情報を取得できます
`Office365ユーザー.MyProfileV2().mail` でメールアドレスを取得して、 SharePoint のリストのユーザーカラムに書き込みます

コードはこんな感じ

```:投票ボタン：OnSelect
Patch(
    [@'リスト名'],
    LookUp(
        [@'リスト名'],
        番号 = ThisItem.番号
    ),
    If(
        IsBlank(
            LookUp(
                [@'リスト名],
                番号 = ThisItem.番号
            ).ユーザー
        ),
        {ユーザー: Office365ユーザー.MyProfileV2().mail},
        {
            ユーザー: Concatenate(
                LookUp(
                    [@'リスト名'],
                    番号 = ThisItem.番号
                ).ユーザー,
                ",",
                Office365ユーザー.MyProfileV2().mail
            )
        }
    )
)

```

## 心残り

投票したときにリアルタイムで投票数・表示順が変わりますが、そのときに `Sort` が実行されるので表示がちらついてしまいます
不格好なのでなんとかしたかったのですが、Sortが完了するまで表示しないようにするやり方がなさそう（PowerAppsのタイミングに任されている）だったので諦めました
もしこうするといいよ！という方法ご存知の方いらっしゃいましたら、是非教えてほしいです〜〜