Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add viewmodel get key to koin, and add KoinViewModelLazy class #1373

Closed
wants to merge 1 commit into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@
package org.koin.android.compat

import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelLazy
import androidx.lifecycle.ViewModelStoreOwner
import org.koin.androidx.viewmodel.KoinViewModelLazy
import org.koin.androidx.viewmodel.ViewModelParameter
import org.koin.androidx.viewmodel.pickFactory
import org.koin.core.annotation.KoinInternalApi
Expand Down Expand Up @@ -49,11 +49,12 @@ object ScopeCompat {
scope: Scope,
owner: ViewModelStoreOwner,
clazz: Class<T>,
key: String? = null,
qualifier: Qualifier? = null,
parameters: ParametersDefinition? = null
): ViewModelLazy<T> {
): KoinViewModelLazy<T> {
val viewModelClass = clazz.kotlin
return ViewModelLazy(viewModelClass, { owner.viewModelStore }){
return KoinViewModelLazy(viewModelClass, key, { owner.viewModelStore }){
val viewModelParameters = ViewModelParameter(
clazz = viewModelClass,
qualifier = qualifier,
Expand All @@ -78,9 +79,10 @@ object ScopeCompat {
scope: Scope,
owner: ViewModelStoreOwner,
clazz: Class<T>,
key: String? = null,
qualifier: Qualifier? = null,
parameters: ParametersDefinition? = null
): T {
return viewModel(scope, owner, clazz, qualifier,parameters).value
return viewModel(scope, owner, clazz, key, qualifier,parameters).value
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,11 @@ object SharedViewModelCompat {
fun <T : ViewModel> sharedViewModel(
fragment: Fragment,
clazz: Class<T>,
key: String? = null,
qualifier: Qualifier? = null,
parameters: ParametersDefinition? = null,
): Lazy<T> =
ViewModelCompat.viewModel(lazy(LazyThreadSafetyMode.NONE) { fragment.requireActivity() }, clazz, qualifier, parameters)
ViewModelCompat.viewModel(lazy(LazyThreadSafetyMode.NONE) { fragment.requireActivity() }, clazz, key, qualifier, parameters)

/**
* Get a shared viewModel instance from underlying Activity
Expand All @@ -62,9 +63,10 @@ object SharedViewModelCompat {
fun <T : ViewModel> getSharedViewModel(
fragment: Fragment,
clazz: Class<T>,
key: String? = null,
qualifier: Qualifier? = null,
parameters: ParametersDefinition? = null,
): T {
return sharedViewModel(fragment, clazz, qualifier, parameters).value
return sharedViewModel(fragment, clazz, key, qualifier, parameters).value
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@
package org.koin.android.compat

import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelLazy
import androidx.lifecycle.ViewModelStoreOwner
import org.koin.androidx.viewmodel.KoinViewModelLazy
import org.koin.androidx.viewmodel.ViewModelParameter
import org.koin.androidx.viewmodel.pickFactory
import org.koin.core.annotation.KoinInternalApi
Expand Down Expand Up @@ -48,12 +48,14 @@ object ViewModelCompat {
fun <T : ViewModel> viewModel(
owner: Lazy<ViewModelStoreOwner>,
clazz: Class<T>,
key: String? = null,
qualifier: Qualifier? = null,
parameters: ParametersDefinition? = null
): Lazy<T>{
val scope = GlobalContext.get().scopeRegistry.rootScope
val viewModelClass = clazz.kotlin
return ViewModelLazy(viewModelClass, { owner.value.viewModelStore }){

return KoinViewModelLazy(viewModelClass, key, { owner.value.viewModelStore }){
val viewModelParameters = ViewModelParameter(
clazz = viewModelClass,
qualifier = qualifier,
Expand All @@ -78,7 +80,8 @@ object ViewModelCompat {
fun <T : ViewModel> getViewModel(
owner: Lazy<ViewModelStoreOwner>,
clazz: Class<T>,
key: String? = null,
qualifier: Qualifier? = null,
parameters: ParametersDefinition? = null
): T = viewModel(owner, clazz, qualifier, parameters).value
): T = viewModel(owner, clazz, key, qualifier, parameters).value
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
package org.koin.androidx.viewmodel

import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelProvider
import androidx.lifecycle.ViewModelStore
import kotlin.reflect.KClass

class KoinViewModelLazy<VM : ViewModel> (
private val viewModelClass: KClass<VM>,
private val viewModelKey: String? = null,
private val storeProducer: () -> ViewModelStore,
private val factoryProducer: () -> ViewModelProvider.Factory,
) : Lazy<VM> {
private var cached: VM? = null

override val value: VM
get() {
val viewModel = cached
return if (viewModel == null) {
val factory = factoryProducer()
val store = storeProducer()
if (viewModelKey != null) {
ViewModelProvider(store, factory)[viewModelKey, viewModelClass.java].also {
cached = it
}
} else {
ViewModelProvider(store, factory)[viewModelClass.java].also {
cached = it
}
}
} else {
viewModel
}
}

override fun isInitialized(): Boolean = cached != null
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,9 @@
package org.koin.androidx.viewmodel.ext.android

import androidx.activity.ComponentActivity
import androidx.activity.viewModels
import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelLazy
import org.koin.android.ext.android.getKoinScope
import org.koin.androidx.viewmodel.KoinViewModelLazy
import org.koin.androidx.viewmodel.scope.BundleDefinition
import org.koin.androidx.viewmodel.scope.emptyState
import org.koin.core.annotation.KoinInternalApi
Expand All @@ -35,42 +34,46 @@ import kotlin.reflect.KClass
@OptIn(KoinInternalApi::class)
inline fun <reified T : ViewModel> ComponentActivity.stateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
noinline state: BundleDefinition = emptyState(),
noinline parameters: ParametersDefinition? = null,
): Lazy<T> {
val scope = getKoinScope()
return viewModels {
return KoinViewModelLazy(T::class, key, { viewModelStore }){
getViewModelFactory<T>(this, qualifier, parameters, state = state, scope = scope)
}
}

@OptIn(KoinInternalApi::class)
fun <T : ViewModel> ComponentActivity.stateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
state: BundleDefinition = emptyState(),
clazz: KClass<T>,
parameters: ParametersDefinition? = null,
): Lazy<T> {
val scope = getKoinScope()
return ViewModelLazy(clazz, { viewModelStore }){
return KoinViewModelLazy(clazz, key, { viewModelStore }){
getViewModelFactory(this, clazz, qualifier, parameters, state = state, scope = scope)
}
}

inline fun <reified T : ViewModel> ComponentActivity.getStateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
noinline state: BundleDefinition = emptyState(),
noinline parameters: ParametersDefinition? = null,
): T {
return stateViewModel<T>(qualifier, state, parameters).value
return stateViewModel<T>(qualifier, key, state, parameters).value
}

@OptIn(KoinInternalApi::class)
fun <T : ViewModel> ComponentActivity.getStateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
state: BundleDefinition = emptyState(),
clazz: KClass<T>,
parameters: ParametersDefinition? = null,
): T {
return stateViewModel(qualifier, state,clazz, parameters).value
return stateViewModel(qualifier, key, state, clazz, parameters).value
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,10 @@
package org.koin.androidx.viewmodel.ext.android

import androidx.activity.ComponentActivity
import androidx.activity.viewModels
import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelStoreOwner
import org.koin.android.ext.android.getKoinScope
import org.koin.androidx.viewmodel.KoinViewModelLazy
import org.koin.core.annotation.KoinInternalApi
import org.koin.core.parameter.ParametersDefinition
import org.koin.core.qualifier.Qualifier
Expand All @@ -35,19 +35,21 @@ import org.koin.core.qualifier.Qualifier
@OptIn(KoinInternalApi::class)
inline fun <reified T : ViewModel> ComponentActivity.viewModel(
qualifier: Qualifier? = null,
owner : ViewModelStoreOwner = this,
key: String? = null,
owner: ViewModelStoreOwner = this,
noinline parameters: ParametersDefinition? = null
): Lazy<T> {
val scope = getKoinScope()
return viewModels {
return KoinViewModelLazy(T::class, key, { viewModelStore }) {
getViewModelFactory<T>(owner, qualifier, parameters, scope = scope)
}
}

inline fun <reified T : ViewModel> ComponentActivity.getViewModel(
qualifier: Qualifier? = null,
owner : ViewModelStoreOwner = this,
key: String? = null,
owner: ViewModelStoreOwner = this,
noinline parameters: ParametersDefinition? = null,
): T {
return viewModel<T>(qualifier, owner, parameters).value
return viewModel<T>(qualifier, key, owner, parameters).value
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,9 @@
package org.koin.androidx.viewmodel.ext.android

import androidx.fragment.app.Fragment
import androidx.fragment.app.viewModels
import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelLazy
import org.koin.android.ext.android.getKoinScope
import org.koin.androidx.viewmodel.KoinViewModelLazy
import org.koin.androidx.viewmodel.ViewModelStoreOwnerProducer
import org.koin.androidx.viewmodel.scope.BundleDefinition
import org.koin.androidx.viewmodel.scope.emptyState
Expand All @@ -36,47 +35,51 @@ import kotlin.reflect.KClass
@OptIn(KoinInternalApi::class)
inline fun <reified T : ViewModel> Fragment.sharedStateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
noinline state: BundleDefinition = emptyState(),
noinline owner: ViewModelStoreOwnerProducer = { requireActivity() },
noinline parameters: ParametersDefinition? = null,
): Lazy<T> {
val scope = getKoinScope()
return viewModels(ownerProducer = owner) {
return KoinViewModelLazy(T::class, key, { owner().viewModelStore }) {
getViewModelFactory<T>(owner(), qualifier, parameters, state = state, scope = scope)
}
}

@OptIn(KoinInternalApi::class)
fun <T : ViewModel> Fragment.sharedStateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
state: BundleDefinition = emptyState(),
//TODO Clean up
owner: ViewModelStoreOwnerProducer = { requireActivity() },
clazz: KClass<T>,
parameters: ParametersDefinition? = null,
): Lazy<T> {
val scope = getKoinScope()
return ViewModelLazy(clazz, { viewModelStore }) {
return KoinViewModelLazy(clazz, key, { viewModelStore }) {
getViewModelFactory(owner(), clazz, qualifier, parameters, state = state, scope = scope)
}
}

inline fun <reified T : ViewModel> Fragment.getSharedStateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
noinline state: BundleDefinition = emptyState(),
noinline owner: ViewModelStoreOwnerProducer = { requireActivity() },
noinline parameters: ParametersDefinition? = null,
): T {
return sharedStateViewModel<T>(qualifier, state, owner, parameters).value
return sharedStateViewModel<T>(qualifier, key, state, owner, parameters).value
}

@OptIn(KoinInternalApi::class)
fun <T : ViewModel> Fragment.getSharedStateViewModel(
qualifier: Qualifier? = null,
key: String? = null,
state: BundleDefinition = emptyState(),
owner: ViewModelStoreOwnerProducer = { requireActivity() },
clazz: KClass<T>,
parameters: ParametersDefinition? = null,
): T {
return sharedStateViewModel(qualifier, state, owner, clazz, parameters).value
return sharedStateViewModel(qualifier, key, state, owner, clazz, parameters).value
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,16 +28,18 @@ import org.koin.core.qualifier.Qualifier
*/
inline fun <reified T : ViewModel> Fragment.sharedViewModel(
qualifier: Qualifier? = null,
key: String? = null,
noinline owner: ViewModelStoreOwnerProducer = { requireActivity() },
noinline parameters: ParametersDefinition? = null,
): Lazy<T> {
return viewModel(qualifier, owner, parameters)
return viewModel(qualifier, key, owner, parameters)
}

inline fun <reified T : ViewModel> Fragment.getSharedViewModel(
qualifier: Qualifier? = null,
key: String? = null,
noinline owner: ViewModelStoreOwnerProducer = { requireActivity() },
noinline parameters: ParametersDefinition? = null,
): T {
return sharedViewModel<T>(qualifier, owner, parameters).value
return sharedViewModel<T>(qualifier, key, owner, parameters).value
}