Async Images
1. AsyncImage (iOS 15+)
Phần tiêu đề “1. AsyncImage (iOS 15+)”AsyncImage(url: URL(string: "https://example.com/image.jpg"))2. Với Placeholder
Phần tiêu đề “2. Với Placeholder”AsyncImage(url: URL(string: urlString)) { image in image .resizable() .aspectRatio(contentMode: .fill)} placeholder: { ProgressView()}.frame(width: 100, height: 100)3. Phase Handler
Phần tiêu đề “3. Phase Handler”AsyncImage(url: URL(string: urlString)) { phase in switch phase { case .empty: ProgressView() case .success(let image): image .resizable() .aspectRatio(contentMode: .fill) case .failure: Image(systemName: "photo") .foregroundColor(.gray) @unknown default: EmptyView() }}4. Với Scale
Phần tiêu đề “4. Với Scale”AsyncImage(url: url, scale: 2.0) // For @2x images5. Caching
Phần tiêu đề “5. Caching”AsyncImage không cache mặc định. Dùng thư viện như Kingfisher hoặc custom:
// Custom cached image viewstruct CachedAsyncImage: View { let url: URL @State private var image: UIImage?
var body: some View { Group { if let image = image { Image(uiImage: image) .resizable() } else { ProgressView() .task { image = await loadImage() } } } }
func loadImage() async -> UIImage? { // Check cache, then load }}📝 Tips
Phần tiêu đề “📝 Tips”- Luôn handle failure state
- Specify frame cho consistent layout
- Consider caching cho performance