Trying to move the initial state setup before `onAppear` to fix the watchOS switching url or any other state issue
This maybe a behavior changes, need testing
This commit is contained in:
parent
8b26cb7d0d
commit
5f8a8acf09
|
@ -7,7 +7,6 @@
|
||||||
objects = {
|
objects = {
|
||||||
|
|
||||||
/* Begin PBXBuildFile section */
|
/* Begin PBXBuildFile section */
|
||||||
3243AFE62AA37EFF0049A43B /* SwiftUICompatibility.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */; };
|
|
||||||
3243AFE72AA37EFF0049A43B /* WebImage.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32C43DDE22FD54C600BE87F5 /* WebImage.swift */; };
|
3243AFE72AA37EFF0049A43B /* WebImage.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32C43DDE22FD54C600BE87F5 /* WebImage.swift */; };
|
||||||
3243AFE82AA37EFF0049A43B /* ImagePlayer.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32CBA77E25E4D7D800C6A8DC /* ImagePlayer.swift */; };
|
3243AFE82AA37EFF0049A43B /* ImagePlayer.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32CBA77E25E4D7D800C6A8DC /* ImagePlayer.swift */; };
|
||||||
3243AFE92AA37EFF0049A43B /* ImageViewWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 326E480923431C0F00C633E9 /* ImageViewWrapper.swift */; };
|
3243AFE92AA37EFF0049A43B /* ImageViewWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 326E480923431C0F00C633E9 /* ImageViewWrapper.swift */; };
|
||||||
|
@ -26,10 +25,6 @@
|
||||||
326E480C23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 326E480923431C0F00C633E9 /* ImageViewWrapper.swift */; };
|
326E480C23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 326E480923431C0F00C633E9 /* ImageViewWrapper.swift */; };
|
||||||
326E480D23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 326E480923431C0F00C633E9 /* ImageViewWrapper.swift */; };
|
326E480D23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 326E480923431C0F00C633E9 /* ImageViewWrapper.swift */; };
|
||||||
329885EE2AA37FCB0071F2BA /* SDWebImage.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 329885ED2AA37FCB0071F2BA /* SDWebImage.framework */; };
|
329885EE2AA37FCB0071F2BA /* SDWebImage.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 329885ED2AA37FCB0071F2BA /* SDWebImage.framework */; };
|
||||||
32B79C9528DB40430088C432 /* SwiftUICompatibility.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */; };
|
|
||||||
32B79C9628DB40430088C432 /* SwiftUICompatibility.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */; };
|
|
||||||
32B79C9728DB40430088C432 /* SwiftUICompatibility.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */; };
|
|
||||||
32B79C9828DB40430088C432 /* SwiftUICompatibility.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */; };
|
|
||||||
32B933E523659A1900BB7CAD /* Transition.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B933E423659A1900BB7CAD /* Transition.swift */; };
|
32B933E523659A1900BB7CAD /* Transition.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B933E423659A1900BB7CAD /* Transition.swift */; };
|
||||||
32B933E623659A1900BB7CAD /* Transition.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B933E423659A1900BB7CAD /* Transition.swift */; };
|
32B933E623659A1900BB7CAD /* Transition.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B933E423659A1900BB7CAD /* Transition.swift */; };
|
||||||
32B933E723659A1900BB7CAD /* Transition.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B933E423659A1900BB7CAD /* Transition.swift */; };
|
32B933E723659A1900BB7CAD /* Transition.swift in Sources */ = {isa = PBXBuildFile; fileRef = 32B933E423659A1900BB7CAD /* Transition.swift */; };
|
||||||
|
@ -83,7 +78,6 @@
|
||||||
326B84812363350C0011BDFB /* Indicator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Indicator.swift; sourceTree = "<group>"; };
|
326B84812363350C0011BDFB /* Indicator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Indicator.swift; sourceTree = "<group>"; };
|
||||||
326E480923431C0F00C633E9 /* ImageViewWrapper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ImageViewWrapper.swift; sourceTree = "<group>"; };
|
326E480923431C0F00C633E9 /* ImageViewWrapper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ImageViewWrapper.swift; sourceTree = "<group>"; };
|
||||||
329885ED2AA37FCB0071F2BA /* SDWebImage.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = SDWebImage.framework; path = Carthage/Build/visionOS/SDWebImage.framework; sourceTree = "<group>"; };
|
329885ED2AA37FCB0071F2BA /* SDWebImage.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = SDWebImage.framework; path = Carthage/Build/visionOS/SDWebImage.framework; sourceTree = "<group>"; };
|
||||||
32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SwiftUICompatibility.swift; sourceTree = "<group>"; };
|
|
||||||
32B933E423659A1900BB7CAD /* Transition.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Transition.swift; sourceTree = "<group>"; };
|
32B933E423659A1900BB7CAD /* Transition.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Transition.swift; sourceTree = "<group>"; };
|
||||||
32C43DCC22FD540D00BE87F5 /* SDWebImageSwiftUI.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = SDWebImageSwiftUI.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
32C43DCC22FD540D00BE87F5 /* SDWebImageSwiftUI.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = SDWebImageSwiftUI.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||||
32C43DDC22FD54C600BE87F5 /* ImageManager.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ImageManager.swift; sourceTree = "<group>"; };
|
32C43DDC22FD54C600BE87F5 /* ImageManager.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ImageManager.swift; sourceTree = "<group>"; };
|
||||||
|
@ -221,7 +215,6 @@
|
||||||
32C43DDE22FD54C600BE87F5 /* WebImage.swift */,
|
32C43DDE22FD54C600BE87F5 /* WebImage.swift */,
|
||||||
32C43DDF22FD54C600BE87F5 /* AnimatedImage.swift */,
|
32C43DDF22FD54C600BE87F5 /* AnimatedImage.swift */,
|
||||||
32C43E3122FD5DE100BE87F5 /* SDWebImageSwiftUI.swift */,
|
32C43E3122FD5DE100BE87F5 /* SDWebImageSwiftUI.swift */,
|
||||||
32B79C9428DB40430088C432 /* SwiftUICompatibility.swift */,
|
|
||||||
326E480923431C0F00C633E9 /* ImageViewWrapper.swift */,
|
326E480923431C0F00C633E9 /* ImageViewWrapper.swift */,
|
||||||
32D26A012446B546005905DA /* Image.swift */,
|
32D26A012446B546005905DA /* Image.swift */,
|
||||||
);
|
);
|
||||||
|
@ -491,7 +484,6 @@
|
||||||
3243AFEB2AA37EFF0049A43B /* AnimatedImage.swift in Sources */,
|
3243AFEB2AA37EFF0049A43B /* AnimatedImage.swift in Sources */,
|
||||||
3243AFE82AA37EFF0049A43B /* ImagePlayer.swift in Sources */,
|
3243AFE82AA37EFF0049A43B /* ImagePlayer.swift in Sources */,
|
||||||
3243AFED2AA37EFF0049A43B /* SDWebImageSwiftUI.swift in Sources */,
|
3243AFED2AA37EFF0049A43B /* SDWebImageSwiftUI.swift in Sources */,
|
||||||
3243AFE62AA37EFF0049A43B /* SwiftUICompatibility.swift in Sources */,
|
|
||||||
3243AFEE2AA37F010049A43B /* Indicator.swift in Sources */,
|
3243AFEE2AA37F010049A43B /* Indicator.swift in Sources */,
|
||||||
3243AFEA2AA37EFF0049A43B /* Image.swift in Sources */,
|
3243AFEA2AA37EFF0049A43B /* Image.swift in Sources */,
|
||||||
);
|
);
|
||||||
|
@ -507,7 +499,6 @@
|
||||||
326B84822363350C0011BDFB /* Indicator.swift in Sources */,
|
326B84822363350C0011BDFB /* Indicator.swift in Sources */,
|
||||||
32C43E3222FD5DE100BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
32C43E3222FD5DE100BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
||||||
326E480A23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
326E480A23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
||||||
32B79C9528DB40430088C432 /* SwiftUICompatibility.swift in Sources */,
|
|
||||||
32C43E1622FD583700BE87F5 /* ImageManager.swift in Sources */,
|
32C43E1622FD583700BE87F5 /* ImageManager.swift in Sources */,
|
||||||
32C43E1822FD583700BE87F5 /* AnimatedImage.swift in Sources */,
|
32C43E1822FD583700BE87F5 /* AnimatedImage.swift in Sources */,
|
||||||
32D26A022446B546005905DA /* Image.swift in Sources */,
|
32D26A022446B546005905DA /* Image.swift in Sources */,
|
||||||
|
@ -524,7 +515,6 @@
|
||||||
326B84832363350C0011BDFB /* Indicator.swift in Sources */,
|
326B84832363350C0011BDFB /* Indicator.swift in Sources */,
|
||||||
32C43E3322FD5DF400BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
32C43E3322FD5DF400BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
||||||
326E480B23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
326E480B23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
||||||
32B79C9628DB40430088C432 /* SwiftUICompatibility.swift in Sources */,
|
|
||||||
32C43E1922FD583700BE87F5 /* ImageManager.swift in Sources */,
|
32C43E1922FD583700BE87F5 /* ImageManager.swift in Sources */,
|
||||||
32C43E1B22FD583700BE87F5 /* AnimatedImage.swift in Sources */,
|
32C43E1B22FD583700BE87F5 /* AnimatedImage.swift in Sources */,
|
||||||
32D26A032446B546005905DA /* Image.swift in Sources */,
|
32D26A032446B546005905DA /* Image.swift in Sources */,
|
||||||
|
@ -541,7 +531,6 @@
|
||||||
326B84842363350C0011BDFB /* Indicator.swift in Sources */,
|
326B84842363350C0011BDFB /* Indicator.swift in Sources */,
|
||||||
32C43E3422FD5DF400BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
32C43E3422FD5DF400BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
||||||
326E480C23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
326E480C23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
||||||
32B79C9728DB40430088C432 /* SwiftUICompatibility.swift in Sources */,
|
|
||||||
32C43E1C22FD583800BE87F5 /* ImageManager.swift in Sources */,
|
32C43E1C22FD583800BE87F5 /* ImageManager.swift in Sources */,
|
||||||
32C43E1E22FD583800BE87F5 /* AnimatedImage.swift in Sources */,
|
32C43E1E22FD583800BE87F5 /* AnimatedImage.swift in Sources */,
|
||||||
32D26A042446B546005905DA /* Image.swift in Sources */,
|
32D26A042446B546005905DA /* Image.swift in Sources */,
|
||||||
|
@ -558,7 +547,6 @@
|
||||||
326B84852363350C0011BDFB /* Indicator.swift in Sources */,
|
326B84852363350C0011BDFB /* Indicator.swift in Sources */,
|
||||||
32C43E3522FD5DF400BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
32C43E3522FD5DF400BE87F5 /* SDWebImageSwiftUI.swift in Sources */,
|
||||||
326E480D23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
326E480D23431C0F00C633E9 /* ImageViewWrapper.swift in Sources */,
|
||||||
32B79C9828DB40430088C432 /* SwiftUICompatibility.swift in Sources */,
|
|
||||||
32C43E1F22FD583800BE87F5 /* ImageManager.swift in Sources */,
|
32C43E1F22FD583800BE87F5 /* ImageManager.swift in Sources */,
|
||||||
32C43E2122FD583800BE87F5 /* AnimatedImage.swift in Sources */,
|
32C43E2122FD583800BE87F5 /* AnimatedImage.swift in Sources */,
|
||||||
32D26A052446B546005905DA /* Image.swift in Sources */,
|
32D26A052446B546005905DA /* Image.swift in Sources */,
|
||||||
|
|
|
@ -15,17 +15,47 @@ import SDWebImage
|
||||||
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
||||||
public final class ImageManager : ObservableObject {
|
public final class ImageManager : ObservableObject {
|
||||||
/// loaded image, note when progressive loading, this will published multiple times with different partial image
|
/// loaded image, note when progressive loading, this will published multiple times with different partial image
|
||||||
@Published public var image: PlatformImage?
|
public var image: PlatformImage? {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
/// loaded image data, may be nil if hit from memory cache. This will only published once even on incremental image loading
|
/// loaded image data, may be nil if hit from memory cache. This will only published once even on incremental image loading
|
||||||
@Published public var imageData: Data?
|
public var imageData: Data? {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
/// loaded image cache type, .none means from network
|
/// loaded image cache type, .none means from network
|
||||||
@Published public var cacheType: SDImageCacheType = .none
|
public var cacheType: SDImageCacheType = .none {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
/// loading error, you can grab the error code and reason listed in `SDWebImageErrorDomain`, to provide a user interface about the error reason
|
/// loading error, you can grab the error code and reason listed in `SDWebImageErrorDomain`, to provide a user interface about the error reason
|
||||||
@Published public var error: Error?
|
public var error: Error? {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
/// true means during incremental loading
|
/// true means during incremental loading
|
||||||
@Published public var isIncremental: Bool = false
|
public var isIncremental: Bool = false {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
/// A observed object to pass through the image manager loading status to indicator
|
/// A observed object to pass through the image manager loading status to indicator
|
||||||
@Published public var indicatorStatus = IndicatorStatus()
|
public var indicatorStatus = IndicatorStatus()
|
||||||
|
|
||||||
weak var currentOperation: SDWebImageOperation? = nil
|
weak var currentOperation: SDWebImageOperation? = nil
|
||||||
|
|
||||||
|
@ -51,8 +81,8 @@ public final class ImageManager : ObservableObject {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
currentURL = url
|
currentURL = url
|
||||||
indicatorStatus.isLoading = true
|
self.indicatorStatus.isLoading = true
|
||||||
indicatorStatus.progress = 0
|
self.indicatorStatus.progress = 0
|
||||||
currentOperation = manager.loadImage(with: url, options: options, context: context, progress: { [weak self] (receivedSize, expectedSize, _) in
|
currentOperation = manager.loadImage(with: url, options: options, context: context, progress: { [weak self] (receivedSize, expectedSize, _) in
|
||||||
guard let self = self else {
|
guard let self = self else {
|
||||||
return
|
return
|
||||||
|
@ -63,9 +93,7 @@ public final class ImageManager : ObservableObject {
|
||||||
} else {
|
} else {
|
||||||
progress = 0
|
progress = 0
|
||||||
}
|
}
|
||||||
DispatchQueue.main.async {
|
|
||||||
self.indicatorStatus.progress = progress
|
self.indicatorStatus.progress = progress
|
||||||
}
|
|
||||||
self.progressBlock?(receivedSize, expectedSize)
|
self.progressBlock?(receivedSize, expectedSize)
|
||||||
}) { [weak self] (image, data, error, cacheType, finished, _) in
|
}) { [weak self] (image, data, error, cacheType, finished, _) in
|
||||||
guard let self = self else {
|
guard let self = self else {
|
||||||
|
|
|
@ -28,9 +28,21 @@ public struct Indicator<T> where T : View {
|
||||||
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
||||||
public class IndicatorStatus : ObservableObject {
|
public class IndicatorStatus : ObservableObject {
|
||||||
/// whether indicator is loading or not
|
/// whether indicator is loading or not
|
||||||
@Published var isLoading: Bool = false
|
var isLoading: Bool = false {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
/// indicator progress, should only be used for indicator binding, value between [0.0, 1.0]
|
/// indicator progress, should only be used for indicator binding, value between [0.0, 1.0]
|
||||||
@Published var progress: Double = 0
|
var progress: Double = 0 {
|
||||||
|
didSet {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
self.objectWillChange.send()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A implementation detail View Modifier with indicator
|
/// A implementation detail View Modifier with indicator
|
||||||
|
|
|
@ -1,92 +0,0 @@
|
||||||
/*
|
|
||||||
* This file is part of the SDWebImage package.
|
|
||||||
* (c) DreamPiggy <lizhuoli1126@126.com>
|
|
||||||
*
|
|
||||||
* For the full copyright and license information, please view the LICENSE
|
|
||||||
* file that was distributed with this source code.
|
|
||||||
*/
|
|
||||||
|
|
||||||
import Foundation
|
|
||||||
import SwiftUI
|
|
||||||
|
|
||||||
#if !os(watchOS)
|
|
||||||
|
|
||||||
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
|
||||||
struct PlatformAppear: PlatformViewRepresentable {
|
|
||||||
let appearAction: () -> Void
|
|
||||||
let disappearAction: () -> Void
|
|
||||||
|
|
||||||
#if os(iOS) || os(tvOS) || os(visionOS)
|
|
||||||
func makeUIView(context: Context) -> some UIView {
|
|
||||||
let view = PlatformAppearView()
|
|
||||||
view.appearAction = appearAction
|
|
||||||
view.disappearAction = disappearAction
|
|
||||||
return view
|
|
||||||
}
|
|
||||||
|
|
||||||
func updateUIView(_ uiView: UIViewType, context: Context) {}
|
|
||||||
#endif
|
|
||||||
#if os(macOS)
|
|
||||||
func makeNSView(context: Context) -> some NSView {
|
|
||||||
let view = PlatformAppearView()
|
|
||||||
view.appearAction = appearAction
|
|
||||||
view.disappearAction = disappearAction
|
|
||||||
return view
|
|
||||||
}
|
|
||||||
|
|
||||||
func updateNSView(_ nsView: NSViewType, context: Context) {}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
|
||||||
class PlatformAppearView: PlatformView {
|
|
||||||
var appearAction: () -> Void = {}
|
|
||||||
var disappearAction: () -> Void = {}
|
|
||||||
|
|
||||||
#if os(iOS) || os(tvOS)
|
|
||||||
override func willMove(toWindow newWindow: UIWindow?) {
|
|
||||||
if newWindow != nil {
|
|
||||||
DispatchQueue.main.async {
|
|
||||||
self.appearAction()
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
DispatchQueue.main.async {
|
|
||||||
self.disappearAction()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if os(macOS)
|
|
||||||
override func viewWillMove(toWindow newWindow: NSWindow?) {
|
|
||||||
if newWindow != nil {
|
|
||||||
DispatchQueue.main.async {
|
|
||||||
self.appearAction()
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
DispatchQueue.main.async {
|
|
||||||
self.disappearAction()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
@available(iOS 14.0, OSX 11.0, tvOS 14.0, watchOS 7.0, *)
|
|
||||||
extension View {
|
|
||||||
/// Used UIKit/AppKit behavior to detect the SwiftUI view's visibility.
|
|
||||||
/// This hack is because of SwiftUI 1.0/2.0 buggy behavior. The built-in `onAppear` and `onDisappear` is so massive on some cases. Where UIKit/AppKit is solid.
|
|
||||||
/// - Parameters:
|
|
||||||
/// - appear: The action when view appears
|
|
||||||
/// - disappear: The action when view disappears
|
|
||||||
/// - Returns: Some view
|
|
||||||
func onPlatformAppear(appear: @escaping () -> Void = {}, disappear: @escaping () -> Void = {}) -> some View {
|
|
||||||
#if os(iOS) || os(tvOS) || os(macOS)
|
|
||||||
return self.background(PlatformAppear(appearAction: appear, disappearAction: disappear))
|
|
||||||
#else
|
|
||||||
return self.onAppear(perform: appear).onDisappear(perform: disappear)
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -163,26 +163,22 @@ public struct WebImage<Content> : View where Content: View {
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
content((imageManager.error != nil) ? .failure(imageManager.error!) : .empty)
|
content((imageManager.error != nil) ? .failure(imageManager.error!) : .empty)
|
||||||
setupPlaceholder()
|
setupInitialState()
|
||||||
// Load Logic
|
// Load Logic
|
||||||
.onPlatformAppear(appear: {
|
.onAppear {
|
||||||
self.setupManager()
|
|
||||||
if (self.imageManager.error == nil) {
|
|
||||||
// Load remote image when first appear
|
|
||||||
self.imageManager.load(url: imageModel.url, options: imageModel.options, context: imageModel.context)
|
|
||||||
}
|
|
||||||
guard self.imageConfiguration.retryOnAppear else { return }
|
guard self.imageConfiguration.retryOnAppear else { return }
|
||||||
// When using prorgessive loading, the new partial image will cause onAppear. Filter this case
|
// When using prorgessive loading, the new partial image will cause onAppear. Filter this case
|
||||||
if self.imageManager.error != nil && !self.imageManager.isIncremental {
|
if self.imageManager.error != nil && !self.imageManager.isIncremental {
|
||||||
self.imageManager.load(url: imageModel.url, options: imageModel.options, context: imageModel.context)
|
self.imageManager.load(url: imageModel.url, options: imageModel.options, context: imageModel.context)
|
||||||
}
|
}
|
||||||
}, disappear: {
|
}
|
||||||
|
.onDisappear {
|
||||||
guard self.imageConfiguration.cancelOnDisappear else { return }
|
guard self.imageConfiguration.cancelOnDisappear else { return }
|
||||||
// When using prorgessive loading, the previous partial image will cause onDisappear. Filter this case
|
// When using prorgessive loading, the previous partial image will cause onDisappear. Filter this case
|
||||||
if self.imageManager.error != nil && !self.imageManager.isIncremental {
|
if self.imageManager.error != nil && !self.imageManager.isIncremental {
|
||||||
self.imageManager.cancel()
|
self.imageManager.cancel()
|
||||||
}
|
}
|
||||||
})
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -328,6 +324,16 @@ public struct WebImage<Content> : View where Content: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Initial state management (update when imageModel.url changed)
|
||||||
|
func setupInitialState() -> some View {
|
||||||
|
self.setupManager()
|
||||||
|
if (self.imageManager.error == nil) {
|
||||||
|
// Load remote image when first appear
|
||||||
|
self.imageManager.load(url: imageModel.url, options: imageModel.options, context: imageModel.context)
|
||||||
|
}
|
||||||
|
return setupPlaceholder()
|
||||||
|
}
|
||||||
|
|
||||||
/// Placeholder View Support
|
/// Placeholder View Support
|
||||||
func setupPlaceholder() -> some View {
|
func setupPlaceholder() -> some View {
|
||||||
let result = content((imageManager.error != nil) ? .failure(imageManager.error!) : .empty)
|
let result = content((imageManager.error != nil) ? .failure(imageManager.error!) : .empty)
|
||||||
|
|
Loading…
Reference in New Issue