Bladeren bron

add viewmodel for MainActivity
add BaseMapper, Mapper
add simply logic for MainActivity

MrOzOn 5 jaren geleden
bovenliggende
commit
a23aa83efb

+ 32 - 0
app/src/main/java/com/mrozon/healthdiary/di/main/DaggerViewModelFactory.kt

@@ -0,0 +1,32 @@
+package com.mrozon.healthdiary.di.main
+
+import androidx.lifecycle.ViewModel
+import androidx.lifecycle.ViewModelProvider
+import javax.inject.Inject
+import javax.inject.Provider
+import javax.inject.Singleton
+
+class DaggerViewModelFactory @Inject constructor(
+    private val creators: @JvmSuppressWildcards Map<Class<out ViewModel>, Provider<ViewModel>>
+) : ViewModelProvider.Factory {
+    override fun <T : ViewModel> create(modelClass: Class<T>): T {
+        var creator: Provider<out ViewModel>? = creators[modelClass]
+        if (creator == null) {
+            for ((key, value) in creators) {
+                if (modelClass.isAssignableFrom(key)) {
+                    creator = value
+                    break
+                }
+            }
+        }
+        if (creator == null) {
+            throw IllegalArgumentException("Unknown model class: $modelClass")
+        }
+        try {
+            @Suppress("UNCHECKED_CAST")
+            return creator.get() as T
+        } catch (e: Exception) {
+            throw RuntimeException(e)
+        }
+    }
+}

+ 33 - 0
app/src/main/java/com/mrozon/healthdiary/di/main/MainActivityComponent.kt

@@ -0,0 +1,33 @@
+package com.mrozon.healthdiary.di.main
+
+import com.mrozon.core.CoreProvidersFactory
+import com.mrozon.core_api.db.DatabaseProvider
+import com.mrozon.core_api.navigation.SplashNavigator
+import com.mrozon.core_api.providers.ProvidersFacade
+import com.mrozon.core_api.viewmodel.ViewModelsFactoryProvider
+import com.mrozon.feature_splash.di.SplashFragmentModule
+import com.mrozon.healthdiary.di.FacadeComponent
+import com.mrozon.healthdiary.presentation.main.MainActivity
+import dagger.Component
+import javax.inject.Singleton
+
+@Singleton
+@Component(
+    modules = [MainActivityModule::class],
+    dependencies = [ProvidersFacade::class]
+)
+interface MainActivityComponent : ViewModelsFactoryProvider {
+
+    companion object {
+
+        fun create(providersFacade: ProvidersFacade): MainActivityComponent {
+            return DaggerMainActivityComponent
+                .builder()
+//                .viewModelsProvider(CoreProvidersFactory.createViewModelBuilder())
+                .providersFacade(providersFacade)
+                .build()
+        }
+    }
+
+    fun inject(activity: MainActivity)
+}

+ 42 - 0
app/src/main/java/com/mrozon/healthdiary/di/main/MainActivityModule.kt

@@ -0,0 +1,42 @@
+package com.mrozon.healthdiary.di.main
+
+import androidx.lifecycle.ViewModel
+import androidx.lifecycle.ViewModelProvider
+import com.mrozon.core_api.db.DatabaseProvider
+import com.mrozon.core_api.db.HealthDiaryDao
+import com.mrozon.core_api.mapper.UserToUserDbMapper
+import com.mrozon.core_api.viewmodel.ViewModelKey
+import com.mrozon.feature_splash.di.DaggerViewModelFactory
+import com.mrozon.feature_splash.presentation.SplashFragmentViewModel
+import com.mrozon.healthdiary.presentation.main.MainActivityViewModel
+import com.mrozon.healthdiary.repository.LocalUser
+import com.mrozon.healthdiary.repository.LocalUserImp
+import dagger.Binds
+import dagger.Module
+import dagger.Provides
+import dagger.multibindings.IntoMap
+import javax.inject.Singleton
+
+@Module
+abstract class MainActivityModule {
+    @Binds
+    @IntoMap
+    @ViewModelKey(MainActivityViewModel::class)
+    abstract fun bindViewModel(viewmodel: MainActivityViewModel): ViewModel
+
+    @Binds
+    abstract fun viewModelFactory(factory: DaggerViewModelFactory): ViewModelProvider.Factory
+
+    @Module
+    companion object {
+
+        @Provides
+        @Singleton
+        @JvmStatic
+        fun provideLocalUser(
+            healthDiaryDao: HealthDiaryDao,
+            mapper: UserToUserDbMapper
+        ): LocalUser = LocalUserImp(healthDiaryDao, mapper)
+    }
+
+}

+ 42 - 2
app/src/main/java/com/mrozon/healthdiary/presentation/main/MainActivity.kt

@@ -2,22 +2,34 @@ package com.mrozon.healthdiary.presentation.main
 
 import android.os.Bundle
 import android.view.View
+import androidx.activity.viewModels
 import androidx.core.view.GravityCompat
 import androidx.drawerlayout.widget.DrawerLayout
+import androidx.fragment.app.viewModels
+import androidx.lifecycle.Observer
+import androidx.lifecycle.ViewModelProvider
 import androidx.navigation.NavController
 import androidx.navigation.findNavController
 import androidx.navigation.ui.AppBarConfiguration
 import androidx.navigation.ui.navigateUp
 import androidx.navigation.ui.setupActionBarWithNavController
+import com.mrozon.core_api.providers.AppWithFacade
+import com.mrozon.feature_splash.di.SplashFragmentComponent
+import com.mrozon.feature_splash.presentation.SplashFragmentViewModel
 import com.mrozon.healthdiary.R
 import com.mrozon.healthdiary.databinding.ActivityMainBinding
+import com.mrozon.healthdiary.di.main.DaggerMainActivityComponent
+import com.mrozon.healthdiary.di.main.MainActivityComponent
 import com.mrozon.utils.base.BaseActivity
+import timber.log.Timber
 import javax.inject.Inject
 
 class MainActivity : BaseActivity<ActivityMainBinding>() {
 
-    //TODO inject
-    lateinit var viewModel: MainActivityViewModel
+    @Inject
+    lateinit var viewModelFactory: ViewModelProvider.Factory
+
+    private val viewModel by viewModels<MainActivityViewModel> { viewModelFactory }
 
     override fun getLayoutId(): Int = R.layout.activity_main
 
@@ -27,10 +39,26 @@ class MainActivity : BaseActivity<ActivityMainBinding>() {
 
 
     override fun onCreate(savedInstanceState: Bundle?) {
+        initDI()
         super.onCreate(savedInstanceState)
         initNavigation()
     }
 
+    private fun initDI() {
+//        val component = SplashFragmentComponent.create(
+//            (fragment.activity?.application
+//                    as AppWithFacade).getFacade()
+//        )
+//        component.inject(fragment)
+//        return component
+//        DaggerMainActivityComponent.builder()
+//            .databaseProvider((application as AppWithFacade).getFacade().provideDatabase())
+//            .build()
+//            .inject(this)
+        MainActivityComponent.create((application as AppWithFacade).getFacade())
+            .inject(this)
+    }
+
     private fun initNavigation() {
         setSupportActionBar(binding.toolbar)
         drawerLayout = binding.drawerLayout
@@ -51,4 +79,16 @@ class MainActivity : BaseActivity<ActivityMainBinding>() {
             super.onBackPressed()
         }
     }
+
+    override fun subscribeUi() {
+        viewModel.currentUser.observe(this, Observer {
+            if(it==null){
+                Timber.d("user is null")
+            }
+            else
+            {
+                Timber.d("user not null")
+            }
+        })
+    }
 }

+ 10 - 1
app/src/main/java/com/mrozon/healthdiary/presentation/main/MainActivityViewModel.kt

@@ -1,7 +1,16 @@
 package com.mrozon.healthdiary.presentation.main
 
+import androidx.lifecycle.LiveData
+import androidx.lifecycle.MutableLiveData
 import androidx.lifecycle.ViewModel
+import com.mrozon.healthdiary.repository.LocalUser
 import com.mrozon.utils.base.BaseViewModel
 import javax.inject.Inject
 
-class MainActivityViewModel @Inject constructor(): ViewModel()
+class MainActivityViewModel @Inject constructor(
+    private val localUser: LocalUser
+): ViewModel() {
+
+    val currentUser = localUser.getLocalUser()
+
+}

+ 9 - 0
app/src/main/java/com/mrozon/healthdiary/repository/LocalUser.kt

@@ -0,0 +1,9 @@
+package com.mrozon.healthdiary.repository
+
+import androidx.lifecycle.LiveData
+import com.mrozon.core_api.entity.User
+
+interface LocalUser {
+
+    fun getLocalUser(): LiveData<User>
+}

+ 23 - 0
app/src/main/java/com/mrozon/healthdiary/repository/LocalUserImp.kt

@@ -0,0 +1,23 @@
+package com.mrozon.healthdiary.repository
+
+import androidx.lifecycle.LiveData
+import androidx.lifecycle.Transformations
+import com.mrozon.core_api.db.DatabaseProvider
+import com.mrozon.core_api.db.HealthDiaryDao
+import com.mrozon.core_api.entity.User
+import com.mrozon.core_api.mapper.UserToUserDbMapper
+import javax.inject.Inject
+
+class LocalUserImp @Inject constructor(
+    private val healthDiaryDao: HealthDiaryDao,
+    private val mapper: UserToUserDbMapper
+): LocalUser {
+
+    override fun getLocalUser(): LiveData<User> {
+        val userDb = healthDiaryDao.getUser()
+        return Transformations.map(userDb) {
+            mapper.reverseMap(it)
+        }
+    }
+
+}

+ 8 - 1
core_api/src/main/java/com/mrozon/core_api/db/HealthDiaryDao.kt

@@ -1,6 +1,13 @@
 package com.mrozon.core_api.db
 
+import androidx.lifecycle.LiveData
 import androidx.room.Dao
+import androidx.room.Query
+import com.mrozon.core_api.db.model.UserDb
 
 @Dao
-interface HealthDiaryDao
+interface HealthDiaryDao {
+
+    @Query("SELECT * FROM user_table LIMIT 1")
+    fun getUser(): LiveData<UserDb>
+}

+ 3 - 0
core_api/src/main/java/com/mrozon/core_api/db/model/UserDb.kt

@@ -16,6 +16,9 @@ data class UserDb(
     @ColumnInfo(name = "user_firstname")
     var firstname: String = "",
 
+    @ColumnInfo(name = "user_token")
+    var token: String = "",
+
     @ColumnInfo(name = "user_lastname")
     var lastname: String = ""
 )

+ 9 - 0
core_api/src/main/java/com/mrozon/core_api/entity/User.kt

@@ -0,0 +1,9 @@
+package com.mrozon.core_api.entity
+
+data class User (
+    var id: Long = 0L,
+    val email: String = "",
+    var firstname: String = "",
+    var token: String = "",
+    var lastname: String = ""
+)

+ 36 - 0
core_api/src/main/java/com/mrozon/core_api/mapper/UserToUserDbMapper.kt

@@ -0,0 +1,36 @@
+package com.mrozon.core_api.mapper
+
+import com.mrozon.core_api.db.model.UserDb
+import com.mrozon.core_api.entity.User
+import com.mrozon.utils.base.BaseMapper
+import javax.inject.Inject
+import javax.inject.Singleton
+
+@Singleton
+class UserToUserDbMapper @Inject constructor() : BaseMapper<User, UserDb>() {
+
+    override fun map(entity: User?): UserDb? {
+        entity?.let {
+            return UserDb(id = it.id,
+                    email = it.email,
+                    firstname = it.firstname,
+                    lastname = it.lastname,
+                    token = it.token
+                )
+        }
+        return null
+    }
+
+    override fun reverseMap(model: UserDb?): User? {
+        model?.let {
+            return User(id = it.id,
+                email = it.email,
+                firstname = it.firstname,
+                lastname = it.lastname,
+                token = it.token
+            )
+        }
+        return null
+    }
+
+}

+ 1 - 0
core_impl/build.gradle

@@ -34,6 +34,7 @@ dependencies {
     implementation dagger
     kapt daggerCompiler
     implementation room
+    kapt roomCompiler
     implementation okhttp
     implementation loggingInterceptor
     implementation gson

+ 3 - 3
core_impl/src/main/java/com/mrozon/core_impl/db/DatabaseModule.kt

@@ -16,16 +16,16 @@ class DatabaseModule {
 
     @Provides
     @Reusable
-    fun provideHabitsDao(healthDiaryDatabaseContract: HealthDiaryDatabaseContract): HealthDiaryDao {
+    fun provideHealthDiaryDao(healthDiaryDatabaseContract: HealthDiaryDatabaseContract): HealthDiaryDao {
         return healthDiaryDatabaseContract.healthDiaryDao()
     }
 
     @Provides
     @Singleton
-    fun provideHabitsDatabase(context: Context): HealthDiaryDatabaseContract {
+    fun provideHealthDiaryDatabase(context: Context): HealthDiaryDatabaseContract {
         return Room.databaseBuilder(
             context,
-            HabitsDatabase::class.java, DATABASE_NAME
+            HealthDiaryDb::class.java, DATABASE_NAME
         ).build()
     }
 }

+ 1 - 1
core_impl/src/main/java/com/mrozon/core_impl/db/HealthDiaryDb.kt

@@ -6,4 +6,4 @@ import com.mrozon.core_api.db.HealthDiaryDatabaseContract
 import com.mrozon.core_api.db.model.UserDb
 
 @Database(entities = [UserDb::class], version = 1)
-abstract class HabitsDatabase : RoomDatabase(), HealthDiaryDatabaseContract
+abstract class HealthDiaryDb : RoomDatabase(), HealthDiaryDatabaseContract

+ 2 - 0
feature_splash/src/main/java/com/mrozon/feature_splash/presentation/SplashFragment.kt

@@ -51,7 +51,9 @@ class SplashFragment : BaseFragment<FragmentSplashBinding>() {
         SplashFragmentComponent.injectFragment(this)
     }
 
+    override fun subscribeUi() {
 
+    }
 
 
 }

+ 3 - 0
utils/src/main/java/com/mrozon/utils/base/BaseActivity.kt

@@ -13,10 +13,13 @@ abstract class BaseActivity<T : ViewDataBinding>: AppCompatActivity(){
     @LayoutRes
     protected abstract fun getLayoutId(): Int
 
+    abstract fun subscribeUi()
+
 
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         performDataBinding()
+        subscribeUi()
     }
 
     private fun performDataBinding() {

+ 3 - 0
utils/src/main/java/com/mrozon/utils/base/BaseFragment.kt

@@ -22,6 +22,8 @@ abstract class BaseFragment<T : ViewDataBinding>: Fragment(),
     @LayoutRes
     abstract fun getLayoutId(): Int
 
+    abstract fun subscribeUi()
+
     override fun onGlobalLayout() {
         rootView!!.viewTreeObserver.removeOnGlobalLayoutListener(this)
     }
@@ -46,6 +48,7 @@ abstract class BaseFragment<T : ViewDataBinding>: Fragment(),
                 e.printStackTrace()
             }
         }
+        subscribeUi()
         return rootView
     }
 }

+ 28 - 0
utils/src/main/java/com/mrozon/utils/base/BaseMapper.kt

@@ -0,0 +1,28 @@
+package com.mrozon.utils.base
+
+abstract class BaseMapper<Entity, Model> {
+
+    abstract fun map(entity: Entity?) : Model?
+
+    abstract fun reverseMap(model: Model?) : Entity?
+
+    fun map(entityList: List<Entity>) : List<Model> {
+        val modelList = arrayListOf<Model>()
+        entityList.forEach {
+            map(it)?.let {
+                modelList.add(it)
+            }
+        }
+        return modelList
+    }
+
+    fun reverseMap(modelList: List<Model>) : List<Entity> {
+        val entityList = arrayListOf<Entity>()
+        modelList.forEach {
+            reverseMap(it)?.let {
+                entityList.add(it)
+            }
+        }
+        return entityList
+    }
+}