わかれば簡単！ #PowerApps のTemplateSize=0の手法

# はじめに
日本のPowerApps makerたちの一部では『TemplateSize:0』という手法が使われているのですが、まだまだあまり知られていないと感じたので、今回簡単にご紹介します。
Power Appsのキャンバスアプリの中でも、ギャラリーコントロールを利用する際のテクニックです。

一番すぐに思いつくのは、NxMのグリッドを作成するようなパターンで、かつ列方向が10を超える場合です。
Power Appsのギャラリーには、WrapCountというプロパティがあり、縦型のギャラリーであれば、横方向に何列カードを配置するかを記述しています。
しかし、この上限が10であるために、表示上の制限が出てくる場合があります。
この制限を緩和する手段として、GalleryのTemplateSizeを0にするというものがありますので、今回紹介します。

# PowerApps のスクリーンにおける座標
Power Appsのキャンバスアプリでは、スクリーンの左上にXY座標の原点、(X=0, Y=0)が存在します。
スクリーン上のコントロールやアイコンは、この原点から見て、どの位置にあるのかを、それぞれのXYプロパティによって表現しています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/202779/67dd633a-3c13-6a82-9aa2-528914d51dea.png)

# ギャラリーコントロールにおける座標
ギャラリーコントロール(以後縦型に限定します)では、ギャラリー内に適当なコントロールを追加すると、横方向に同じ位置に、各行でコントロールが表示されることがわかるかと思います。
また各行にセパレータを入れると何となくわかりますが、各行の天井からの位置もそろっているのが見て取れます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/202779/ab99a47c-0eeb-2d31-3c5a-90c2755ae934.png)
このようにキレイに表示されるのは、各行の中で座標の原点を持っていて、それが左上にあるからなんです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/202779/67e429b9-7254-a8f6-4b37-498a596fc52e.png)
また、スクリーン側から見ると、各行のコントロールの間は、TemplateHeightのぶんだけ、離れていることもわかります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/202779/8ddec353-286d-0dba-4522-a76e5c2f0071.png)

ではTemplateHeightが0になるとどうなるでしょう？
ナイーブには、各行のコントロールが、縦方向に接近していって、最終的に重なるだろうと予想できます。
これがまさにTemplateSize:0のポイントです。

# TemplateSizeを0にすると何がおこるか
TemplateHeightをスライダーで調整したデモがこちらです。
<blockquote class="twitter-tweet"><p lang="en" dir="ltr">Quick demo: Gallery.TemplateHeight=0 in <a href="https://twitter.com/hashtag/PowerApps?src=hash&amp;ref_src=twsrc%5Etfw">#PowerApps</a> canvas app <a href="https://t.co/e3LsrKCFVA">pic.twitter.com/e3LsrKCFVA</a></p>&mdash; Hiro (@mofumofu_dance) <a href="https://twitter.com/mofumofu_dance/status/1209473973563428866?ref_src=twsrc%5Etfw">December 24, 2019</a></blockquote> <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

予想通り、各行のコントロールが接近していって、同じ高さにそろいました。
ただし、気を付けなければならないのは、Y方向に少しの補正が必要だということです。
各コントロールのYプロパティには、たとえTemplateHEight=0であったとしても以下の補正が必要です。

```someControl.Y
配置したいYの値-ThisItem.RowNumber
```
RowNumberはギャラリーの各アイテムの順番で、1から始まる連番の数字がふられていることを想定しています。
この補正のもとで、各行の原点は一致し、ギャラリーの中がすべてのアイテムに対して同じ座標になります。

これを利用することで、これまでよりも自由なレイアウトができます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/202779/2e776da6-4641-9191-9ef1-4fe48743af72.png)

# WrapCount>10
TemplateSize:0を利用すると、WrapCountを10以上に引き上げることができます。
<blockquote class="twitter-tweet"><p lang="en" dir="ltr">and generalized &quot;WrapCount&quot; <a href="https://t.co/ZGPmrnwIxX">pic.twitter.com/ZGPmrnwIxX</a></p>&mdash; Hiro (@mofumofu_dance) <a href="https://twitter.com/mofumofu_dance/status/1209480894831943686?ref_src=twsrc%5Etfw">December 24, 2019</a></blockquote> <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>
ここでは、スライダーで横方向に配置したいアイテムの数を設定しています。

きっちりとNxMで並べたいような場合には、一般性を失うことなく、各コントロール（RectangleやButton,Labelなど)のX,Yプロパティは以下の式で決定することができます。

```control.X
Button2.Width*((ThisItem.RowNumber)-wrapNum*(RoundDown((ThisItem.RowNumber-1)/wrapNum,0))-1)
```
```control.Y
0-ThisItem.RowNumber+control.Height*RoundDown((ThisItem.RowNumber-1)/wrapNum,0)
```

ここでwrapNumは横方向に配置したいアイテム数です。

このようにして、WrapCount10の制限は緩和可能です。

# 参考
RowNumberを付与する際には、下記ブログが参考になります。

http://powerappsguide.com/blog/post/generating-row-numbers