【SwiftUI】Circleくん、君は丸の形をした何者なんだい?
SwiftUIでVStack
を使用してCircle()
を上寄せにしたかったのに思ったような挙動にならなかったので原因を調べてみました。
環境
- Xcode 13.3
事象
コード
VStack
とSpacer()
を組み合わせることでCircle()
を上詰したいと思っています。
struct ContentView: View { var body: some View { VStack { Circle() .frame(width: 30) Spacer() } } }
結果
上詰されませんでした。
調査
コード
backgroundに色を付けてみました。
struct ContentView: View { var body: some View { VStack { Circle() .frame(width: 30) .background(.red) Spacer() } } }
結果
backgroundに色を付けてみると、Circle
は30 × 30
の円の形のように振る舞うも実際のViewとしてはframe
が設定されていない高さの方向には画面いっぱいに広がっていました。
Rectangleの場合
Rectangle
で試してみると縦方向はしっかり画面いっぱいに表示されました。
コード
var body: some View { VStack { Rectangle() .frame(width: 30) Spacer() } }
結果
Circle
もこんな感じに縦方向に広がってくれたらよかったのですが、、
原因
Circle
が見た目上は30 × 30の円の形のように振る舞うも、実際のViewとしてはwidth
は30
だが、height
は画面いっぱいに広がっていたのが原因だった。
Circle
がViewとしては縦方向画面いっぱいに広がっている為、VStack
とSpacer()
を併用して上詰にしようとしても出来なかった。
解決法
frame
で幅も高さも指定してあげると意図した挙動になりました。
Circle
はRectangle
とは違って指定していない高さ(または幅)方向にViewとしては広がっているけど、見た目上は広がっていないように見せてくるので幅と高さを指定していないとふとした時にハマりそうですね。
コード
var body: some View { VStack { Circle() .frame(width: 30, height: 30) Spacer() } }
結果
まとめ
Circle
も、VStack
やSpacer
と同じように可能な限り広がろうとするViewであることが分りました。今回Circleくんに出会えたことでまた少しSwiftUIのレイアウトシステムについて理解出来たような気がします。
SwiftUIをしているとPaddingが意図したように表示されてないや、今回のようにStackやSpacerがうまく機能していないと思う時は、.background
モディファイアを使用してViewに色付けすることで実際どうなっているのか可視化すると問題解決の糸口を見つけやすくなりそうだなと感じたので、今後試していきたいと思います!
Circleくん、君に会えてよかった。