Power Platformでノンコーディングで筋トレ成果を記録するアプリを作ってみた - 2.Power Apps編 -

# 1.やったこと
iPhoneのアクティビティアプリのスクショを画像認識して、筋トレ結果を抽出、データを格納してダッシュボードで表示する…までを、Power Platformの各種サービスを駆使してノンコーディングでやってみたことのうち、**Power Apps**でやったことのメモです。

1. [Power Platformでノンコーディングで筋トレ成果を記録するアプリを作ってみた - AI Builder編 -](https://qiita.com/miokawa/items/17d84d8811fe38ff4704)
2. [Power Platformでノンコーディングで筋トレ成果を記録するアプリを作ってみた - Power Apps編 -] (https://qiita.com/miokawa/items/0f3dc6ac6a1be01984d6)←コレ
3. [Power Platformでノンコーディングで筋トレ成果を記録するアプリを作ってみた - Common Data Service編 -](https://qiita.com/miokawa/items/da330e778afabf46579d)
4. [Power Platformでノンコーディングで筋トレ成果を記録するアプリを作ってみた - Power Automate編 -](https://qiita.com/miokawa/items/2ca2c75fdb52fcc90e78)
5. [Power Platformでノンコーディングで筋トレ成果を記録するアプリを作ってみた - Power BI編 -](https://qiita.com/miokawa/items/c7afe408e076cb9f7578)

人恋しさと運動不足解消のため、定期的にオンラインフィットネス（Teams繋ぎながらyoutubeのトレーニング動画を流してみんなでやる）を会社の人とやり始めたことがきっかけで作りました。

最終的な成果物はこんな感じ（細かいデザイン方法については触れません）。
<img width="250" alt="サンプルスクショ" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/5369c570-2e83-4f8e-c113-e0be8f557090.jpeg"> <img width="250" alt="サンプルスクショ" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/badb9fb8-1fea-ea0e-387b-f1a46ac248b9.jpeg"> <img width="250" alt="サンプルスクショ" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/ed233619-7794-1379-2ef0-c5e85ac2b356.jpeg">

※試行錯誤した結果、こうしたらできた！って感じなので、これが一番スマートなのかどうかは不明ですのでご注意ください。

# 2.本アプリでのPower Platformの各サービスの役割
- **Power Apps**：iPhoneのアクティビティアプリのスクショをアップロードする。Power BIで筋トレ記録見られる。
- **AI Builder**：アクティビティアプリのスクショに含まれる筋トレ時間、消費カロリー、日付などを画像認識する
- **Power Automate**：Power Appsのアップロードボタンをトリガーに、アップロードされたスクショをAI Builderに投げ、結果のデータをCommon Data Serviceに格納する
- **Common Data Service**：ひたすら筋トレ結果を格納する
- **Power BI**：Common Data Serviceに格納された筋トレ成果たちをそれっぽく表示する


図にすると以下のような感じです。
気づいたら割といろいろ使ってた。わお。

![筋トレアプリ図解.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/17447ad0-bd5a-0f5f-e48a-20bddeeb914e.png)


# 3.開発環境
今回はこちらの無料ライセンスを使いました。
[Power Apps Community Plan](https://powerapps.microsoft.com/ja-jp/communityplan/)


# 4.実現したいこと
デバイス内に格納されたアクティティアプリのスクショを選択し、アップロードボタンを押すと、Power Automateのフローをトリガーする。

# 5.作成過程
[Power Apps](https://make.powerapps.com/)にログインし**アプリ**から**新しいアプリを作成**、**キャンバス**を選択。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/0a21ee0e-6f69-f6f7-7a8b-c35ccd55107a.png)

今回はiPhoneからの画像アップロードを想定しているので、**空のアプリ**から**携帯電話レイアウト**を選択。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/0258d418-3021-2a33-dd2b-7ef340500c8d.png)

まっさらなキャンバスアプリの画面が出てくるので、**挿入**から**メディア**、**画像の追加**を選択。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/a46c87c4-23a8-b711-0aa3-964747bc6869.png)

**AddMediaWithImage**という部品がキャンバスに出現します。これを開くと、**AddMediaButton**、**UploadedImage**という2つの部品が入っていることがわかります。
簡単に説明すると、**AddMediaButton**は、その名の通りボタンになっていて、スマホのアルバムを開くことができるボタンです。**UploadedImage**は、アルバムで選択された画像を表示する部品です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/57584a79-bd6e-8f0a-54b1-add81a5f463a.png)

ここで**UploadedImage**を選択し、**詳細設定**タブから、**ImagePosition**を`ImagePosition.Fill`から`ImagePosition.Fit`にしておきます。
これにより、枠より画像が大きい場合でも、枠内に収まるようにうまく調整してくれるようになります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/ae8291a3-2b95-3239-1c23-a57ae05381c3.png)



続いて、選択した画像をアップロードするためのトリガーとなる、アップロードボタンを追加します。
**挿入**から**ボタン**を選択すると、キャンバスにボタンが出現しますので、適当に移動させておきます。
また、ボタンに表示されるテキストを`ボタン`から`アップロード`に変更しておきます。

次に、ゆくゆくは溜まった筋トレデータをPower BIで見られるようにしたいので、Power BIへリンクする用の画面を用意しておきます。**新しい画面**から**空の画面**を選びます。Screen2が追加されると思います。
<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/ea3a87c2-a5c3-340f-772e-d71dd523f999.png">

この時点では、Screen2に配置するPower BI側が何もできていないのですが、Power BIを呼び出す部品だけ配置したいと思います。
**挿入**タブから**グラフ**、**Power BIタイル**を選び、配置します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/34c89f4a-f5e8-5f07-ce18-c6ab09f62a28.png)

更に、Screen1とScreen2を行き来できるようにボタンを配置します。
**挿入**タブから**アイコン**、**次へ**（画面移動ができるとわかるアイコンならなんでもOKです）を選び、アイコンを適当な場所に配置します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/adbbb163-340a-f50e-9fc4-e08e5b33203d.png)

Icon1を選択した状態で、**アクション**タブから**移動**を選択し、移動先となるscreen2を選びます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/e995c317-5c48-05ad-b169-6b9fca9c8393.png)

すると、Icon1のOnselect（クリック時の動作）にScreen2への移動が設定されます。
同じことをScreen2→Screen1でもやり、行き来ができるようにします。
<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/bc2699e3-aa60-d1d1-af47-08ba5d4912c2.png">

これで一通り必要な部品は揃いましたので、試しに動かしてみたいと思います。右上の▷ボタンでプレビューができます。
<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/38f1ca56-ac88-b8aa-c231-804cafb23fe2.png">


**タップまたはクリックして画像を追加**となっていた部分をクリックすると、ファイルダイアログが出てきます。
ここでローカルの画像を選択すると、枠内に収まる形で画像が表示されます。
<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/eda5231b-02ce-c199-36f0-6a688e54311d.png">

画面移動用のアイコンをクリックすると、Power BIを確認する画面に移動できます。
<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/12a83bd9-c48c-36e2-d4e7-011e2360e737.png">

なお、アップロードボタンにはクリック時の動きを何も設定していないので、まだ押しても何も起きませんので、この部分の処理を追加していきます。
アップロードボタンを選択した状態で**アクション**から**Power Automate**を選択し、**新しいフローを作成**を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/0e2ddd05-f671-d825-0f88-1ec4c4932573.png)![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/a009be8e-2ded-7e0e-4ffb-c1380ee97e68.png)

Power Automateのテンプレートのうち、Power Appsのボタンをトリガーとしたものがずらっと出てきます。
今回は**Power Appsボタン**を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/551cb1c5-5fd5-7dd6-601c-3a0d9dd33d83.png)

こんな感じの画面が出てきたら、**新しいステップ**から**AI Builder**を選択し、**フォームの情報を処理して保存する**というアクションを設定しておきます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/e047a64f-a5b6-02e5-a322-19310520e5b2.png)

ここで、[AI Builder編](https://qiita.com/miokawa/items/17d84d8811fe38ff4704)で作成したAIモデルを選択し、フォームの種類を**JPEG画像**（スクショがJPEGなので）にし、フォームは動的なコンテンツから**PowerAppsで確認**を選択します。
これは、PowerAppsからの入力を利用しますという意味です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/b2f86dfc-34c0-5796-a523-6111a582afba.png)

こんな感じの状態になったらOKです。
<img width="500" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/fd58907a-91b6-f211-de92-a0beefa80d5b.png">

わかりやすく、このフローに名前を付けます。今回は`筋トレアプリ`としました。
左上の名前の部分をクリックして、変更し、保存をクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/4eaac6d7-3aa5-adcc-23e0-f47597e7d0a8.png)

ここでPower Appsに戻ってみると、先ほど作成したPower Automateのフローが出てきていると思いますので、そちらを選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/896888d3-8760-9df1-adeb-b917a8595422.png)

アップロードボタンにPower Automateのフローが紐づけられると、アップロードボタンの**詳細設定**、**OnSelect**に`Power Automateのフロー名.Run(`と自動入力されます。OnSelectはその部品がクリックされたときの動作を入れるところになり、`Power Automate名.Run()`という関数でPower Automateが呼び出せるということを教えてくれています。
また、上の方に`Run（フォームの情報を処理して保存する_フォーム）`とあるのは、Power Automate側で待ち構えている値（引数）を教えてくれています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/8abb87d5-c720-83d5-1d92-ab8755841f89.png)

Power Automate側を見ると、確かに待ち構えているのがわかります。
<img width="500" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/c45238c9-4df7-2314-4f86-b2f62cd5f1c5.png">

ここに入れるべきは、Power Appsでアップロードしようと選ばれた画像です。以下の通り入力します。

```
<Power Automateフロー名>.Run(Substitute(JSON(UploadedImage1.Image, IncludeBinaryData),"""", ""))
```
画像の受け渡しがちょっと厄介なのですが、`UploadedImage1.Image`で、UploadedImageの部品に表示されている画像を表しています。しかし、画像をそのままPower Automateに渡すことができないので、一度[JSON関数](https://docs.microsoft.com/ja-jp/powerapps/maker/canvas-apps/functions/function-json)で受け渡しができる形に変換します。
また更に、JSON関数で変換したままだと、最初と最後に`"`がついてしまうので、それを排除するために[Substitute関数](https://docs.microsoft.com/ja-jp/powerapps/maker/canvas-apps/functions/function-replace-substitute)を使っています。
結果、以下のような形になります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/faf3f9b1-32b8-0934-883d-5f332efd594e.png)

ここまできたらPower Apps→Power Automateの動作が試せますので、右上の▷アプリのプレビューボタンから、画像を選んで、アップロードボタンクリックを試してみます。
ちなみに、アプリのデザイン画面のままでも、Altを押しながらクリックすることで同様に試すことが可能です。

Power Automateの画面に戻り、左上の←ボタンから筋トレアプリの概要ページに移ります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/42dce654-5ca7-60a1-67d2-ed44f039b96e.png)

実行履歴より、このフローの呼び出された履歴が確認できます。
実行日時をクリックすると詳細が見られますのでクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/8926ad9d-eb48-e70c-aeb4-fe31ea717afb.png)

**フォームの情報を処理して保存する**アクションを展開すると、必要な情報がきちんと画像から抽出できていることが確認できます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/596292/638026af-52af-22b6-0ebd-64aa0d7cf1db.png)

ここまで確認ができたら、Power Appsの画面に戻り、**ファイル**から保存か、**Ctrl+S**でアプリに名前を付けて保存します。

# 6.次のステップ
ここまでで、今回作ったPower AppsのボタンをトリガーにPower Automateを起動し、[AI Builder編](https://qiita.com/miokawa/items/17d84d8811fe38ff4704)で作ったAIモデルを使って画像から情報を抽出することができました。
次は[Common Data Service編](https://qiita.com/miokawa/items/da330e778afabf46579d)で、抽出したデータを格納する場所を用意していきたいと思います。