dmytro-anokhin / url-image

AsyncImage before iOS 15. Lightweight, pure SwiftUI Image view, that displays an image downloaded from URL, with auxiliary views and local cache.
MIT License
1.1k stars 96 forks source link

URLImage reloads whenever the view is refreshed even if URL stays the same #159

Closed TomShen1234 closed 3 years ago

TomShen1234 commented 3 years ago

Summary and/or background When the view is refreshed (for example, via a state change), the image is always reloaded. This can be seen in the following code:

import SwiftUI
import URLImage

struct ContentView: View {
    private let url = URL(string: "URL to image")!

    @State private var text = ""
    @State private var saved = ""

    var body: some View {
        VStack {
            TextField("Enter some Text", text: $text, onCommit: { saved = text })
                .textFieldStyle(.roundedBorder)

            Text("The text is: \(saved)")

            URLImage(url) { image in
                image.resizable()
            }
        }
        .padding()
    }
}

The URLImage will reload once the saved property is changed (aka when you press the return key on the text field).

OS and what device you are using iOS 14 and iOS 15 beta 6

Version of URLImage library 3.1.0

What you expected would happen The image should stays without reloading.

What actually happens See above

Sample code See above

Test data Any image works

Additional information

Misc

dmytro-anokhin commented 3 years ago

Hello,

thank you for the sample code.

When the view updates, the image reloads because accessing URLCache is asynchronous operation. The way to "fix" this is to use provided in-memory cache.

import SwiftUI
import URLImage
import URLImageStore

@main
struct URLImage_Issue159App: App {
    var body: some Scene {
        let urlImageService = URLImageService(fileStore: nil, inMemoryStore: URLImageInMemoryStore())

        return WindowGroup {
            ContentView()
                .environment(\.urlImageService, urlImageService)
        }
    }
}

I will review implementation to see if there is some new tool in SwiftUI that can help with this particular case.