この記事はAdvent Calendar 2018の18日目の記事です。
こんにちは!新規ゲーム開発プロジェクトでUnityエンジニアをしている米倉です。
今回は、UnityのUIを組む上で意外と難しい「文字サイズによって可変するUI」の一例を紹介したいと思います!
※この記事はGRIPHONE Advent Calendar 2018 18日目の記事です。
https://adventar.org/calendars/3147
https://qiita.com/advent-calendar/2018/griphone
今回作るものはこちら
こちらは「文字-間を埋める線-文字」という、2つのTextのサイズに依存するUIです。
左右の文字はそれぞれ、左寄せと右寄せです。
これ、適当なLayout系コンポーネントを組み合わせれば行けそうというところまではすぐ分かるのですが、ハマると時間が溶けてしまう代物です。
作ってみる
今回のUIはスクリプト不要でコンポーネントの組み合わせで実現できます。
実際に配置の様子を見ながら作ってみてください。
1.まずはオブジェクトを置く
「root(白い板)」、「a_text(左のText要素)」、「line(真ん中のImage要素)」、「b_text(右のText要素)」の順に、特にコンポーネントなどをつけずに配置しています。
ここでTextはそれぞれ左寄せ、右寄せに設定しておきます。
2.rootオブジェクトにHorizontalLayoutGroupをつける
一旦付けただけの状態だとめちゃくちゃになります(子が引き伸ばされている)。
ここではHorizontalLayoutGroupの値を調整し、左から並べ、子を引き伸ばさない設定にしておきます。
3.HorizontalLayoutGroupの設定を変更する
ここで、以下の設定の正しい理解が必要になります。
- Child Controls Size : 子のLayout要素によって算出された幅によって、子自身の幅を変える設定。
- Child Force Expand : 親の幅に対して子に余白がある場合、子を引き伸ばす設定。
今回は、「子の幅は自身のテキスト幅で敷き詰め、線は可能な限り敷き詰めたい」ので、Child Controls Size のXだけONにします。
これで、子のテキストたちはTextコンポーネントの文字列を元にサイズが決まります。
そうすると、HorizontalLayoutGroupとTextのサイズのみの関係で以下のようになります。
線(Image)が見えなくなっていますが、今の段階ではLayout要素が無いため幅が0になって、aとbの間に存在しています。
4.線のLayout要素を設定する
線にもLayout要素として幅を設定できるよう、Layout Elementコンポーネントをアタッチします。
Layout Elementは以下のような設定値を持っています。
- Min ~~ : 最低でもこのサイズは確保してほしい、という値。これ以上小さくならない。
- Preffered ~~ : 余っているサイズがあればこのサイズまで描画する。
- Flexible ~~ : 余っているサイズの中で、全てのFlexible間で占める割合
線はHorizontalLayoutGroupの子たちの中で可能な限り最大まで敷き詰めたいので、ここではFlexible Widthを選択し、1を設定します。
すると、以下のようにいい感じに線が伸ばされます。
Flexible Width :1を設定すると、子にいるFlexible要素全ての割合からサイズが求められます。(ここでは、Flexibleが他の子に設定されていないため、どんな値を設定しても最大まで伸びます)
5.余白を調整する
HorizontalLayoutGroupの設定項目に戻り、PaddingやSpacingを設定してあげると完成形となります。
値を設定すると、
きれいに整いました!
これで完成です!
aとbのテキスト内容を変えても、緑の線が間をきれいに埋めてくれるはずです。
終わりに
ちょっと難しいUI、いかかでしたでしょうか。
正しくLayout系コンポーネントを理解し、無駄なく設定してあげるのは意外と難しいですね。
私自身もこのあたりはよく調べたりするのですが、今回記事にまとめるにあたりしっかり振り返る良い機会となりました。
皆さんのUI開発の参考になれば幸いです。