Open3

SwiftUIでLazyVStackを使う場合に画像カラムを正方形にする方法

yimajoyimajo

LazyVStackとかでカラムの横をフレキシブルにする時の方法

How do you clip an image to a square inside a lazy grid? (SwiftUI)
https://stackoverflow.com/q/62791912/5322090

回答があるのに解決してない。

これで解決しないということはおそらく根本原因はPHAsset自体のリクエスト方法な気がするけど、やりとりが勉強になったのでスクラップしておく。

yimajoyimajo

まず、正方形にするだけなら aspectRatio(1, contentMode: .fill)

次のStackOverflowのコード

  • 3列にしているのでGridの配列要素3つ
  • 縦もそれに追随させたいから.aspectRatio(1)
private let threeColumnGrid = [
    GridItem(.flexible(minimum: 40)), // 横幅が最低40
    GridItem(.flexible(minimum: 40)),
    GridItem(.flexible(minimum: 40)),
]

// In my body...

LazyVGrid(columns: threeColumnGrid, alignment: .center) {
    ForEach(model.imageNames, id: \.self) { imageName in
        Rectangle()
            .foregroundColor(.red)
            .aspectRatio(1, contentMode: .fill) 横幅に合わせて高さも変わってくれる
    }
}

質問者はここまでやっているが、画像のもとが歪んでいるという質問になっている。

まあおそらく画像のもと自体がPHAssetでそれを取得しているときにサイズを指定してるのかとかcontentModeがどうなってるのかっていうのが原因と思う。

yimajoyimajo

GeometryReader使って親から縦も同じ値にすれば?という回答
https://stackoverflow.com/a/62801262/5322090

LazyVGrid(columns: threeColumnGrid, alignment: .center) {
    ForEach(model.imageNames, id: \.self) { item in
        GeometryReader { gr in
            Image(item)
                .resizable()
                .scaledToFill()
                .frame(height: gr.size.width)
        }
        .clipped()
        .aspectRatio(1, contentMode: .fit)
    }
}

aspectRatio(1)してるんだからframe指定しなくてもいいと思うけど...。まあこの方法は面白いと思う。