Mohamed Said
Mohamed Said

Reputation: 563

Loading Indicators in SwiftUI causing infinite renders

I have a loading indicator class that is utilized in all view models, what I'm trying to do is to track each API's loading state independently rather than having one loading flag for the entire VM.

I have a super class which is an observable object that has all the common properties needed for each VM, I also have an @Obervable (the new macro) which is a loading indicator, if I don't use combine the view is updated once and everything works as expected however the UI doesn't get notified of the changes since it's an observable object (super class) inside an observable object, and when I add combine it keeps looping. I've also tried migrating ObservableObject classes to Observable and the same loading indicator class caused infinite renders.

Here's the code below

Loading Indicator

class LoadingIndicatorVM<T: Hashable>: ObservableObject {
@Published var loadingStates: [T: Bool] = [:]
@Published var indicatorId: UUID = UUID()
// Method to update the loading state externally
internal func updateLoadingState(for apiDictionary: T, isLoading: Bool) {
    loadingStates[apiDictionary] = isLoading
}

// Method to retrieve the loading state for a specific API
func isLoading(for apiDictionary: T) -> Bool {
    let currentState = loadingStates[apiDictionary] ?? false
    if !currentState {
        indicatorId = UUID()
    }
    return currentState
}

func isLoading() -> Bool {
     loadingStates.values.contains(true)
}

}

And this is the super class

 class ViewModelObject<T: Hashable, DataType>: ObservableObject {
 // props
 var cancellable : AnyCancellable?
 @Published var loading = LoadingIndicatorVM<T>() <-- problem comes from this
 @Published var data: [DataType] = []
 let manager = NetworkManager()
 // rest

}

Any help or insight would greatly be appreciated! Thank you

Upvotes: 0

Views: 29

Answers (1)

Mohamed Said
Mohamed Said

Reputation: 563

The problem was not in the observable class, my custom scroll viewer used to generate Ids on each render causing infinite re-renders of the views.

Upvotes: 0

Related Questions