Mobile Dev.
07/16/2022, 11:50 PMfun appModule() = listOf(AppModule().module)
@Module
@ComponentScan("com.makswin.bifrost")
class AppModule
class DependencyInjection : KoinComponent {
val listTrainingsViewModel: ListTrainingsViewModel by inject()
val getLastTrainingViewModel: GetLastTrainingViewModel by inject()
val addFeedbackViewModel: AddFeedbackViewModel by inject()
val insuranceViewModel: InsuranceViewModel by inject()
val authViewModel: AuthViewModel by inject()
}
fun initKoin() {
startKoin {
modules(appModule())
}
}
My App Delegate on ios
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
AppModuleKt.doInitKoin()
return true
}
Here is my observable view model object
class ObservableListTrainingViewModel : ObservableObject {
@Published var state: ListTrainingsState?
var viewModel: ListTrainingsViewModel?
init(viewModel: ListTrainingsViewModel) {
self.viewModel = viewModel
asPublisher(viewModel.state)
.compactMap { $0 }
.receive(on: DispatchQueue.main)
.assign(to: &state)
}
}
Here is my sample swift ui view
struct ContentView : View {
@Environment(\.presentationMode) var presentationMode
@ObservedObject var viewModel: ObservableListTrainingViewModel
init() {
viewModel = ObservableListTrainingViewModel(viewModel: DependencyInjection().listTrainingsViewModel)
}
var body: some View {
VStack {
if let state = viewModel.state {
Button("Button") {
if state.trainings.isEmpty {
self.viewModel.viewModel?.getTrainings(type: .next) // api call
} else {
presentationMode.wrappedValue.dismiss() // close the page
}
}
if state.isLoading {
Text("LOADING")
}
if !state.trainings.isEmpty {
Text("\(state.trainings.first?.title ?? "NONE")")
}
}
}
}
}
and my Common View Model Class
@Single
class ListTrainingsViewModel(val listTrainingsUseCase: ListTrainingsUseCase) : ViewModel() {
private val _state: MutableStateFlow<ListTrainingsState> = MutableStateFlow(ListTrainingsState())
val state: CommonFlow<ListTrainingsState> = _state.asCommonFlow()
fun getTrainings(type: TrainingListTimeType) {
listTrainingsUseCase(type).collectCommon { result ->
when (result) {
is Resource.Error -> {
_state.value = ListTrainingsState(error = result.message ?: "")
}
is Resource.Loading -> {
_state.value = ListTrainingsState(isLoading = true)
}
is Resource.Success -> {
_state.value = ListTrainingsState(
trainings = result.data ?: emptyList(),
isLoading = false
)
}
}
}
}
}
fun <T> Flow<T>.collectCommon(
coroutineScope: CoroutineScope? = null,
callback: (T) -> Unit,
): Job {
return onEach {
callback(it)
}.launchIn(coroutineScope ?: CoroutineScope(Dispatchers.Main))
}
How can i solve this issue ?