Skip to content

Commit

Permalink
Added a ViewModel sample
Browse files Browse the repository at this point in the history
  • Loading branch information
Gabriel Peal committed May 22, 2022
1 parent 77ac8c0 commit 229855f
Show file tree
Hide file tree
Showing 8 changed files with 52 additions and 13 deletions.
Original file line number Diff line number Diff line change
@@ -1,15 +1,18 @@
package com.gpeal.droidconanvilsample.feature.weatherui
package com.gpeal.droidconanvilsample.app

import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import com.gpeal.droidconanvilsample.feature.weatherui.R
import com.gpeal.droidconanvilsample.feature.weatherui.WeatherFragmentSimple
import com.gpeal.droidconanvilsample.feature.weatherui.WeatherFragmentWithViewModel

class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
if (savedInstanceState == null) {
supportFragmentManager.beginTransaction()
.replace(R.id.container, WeatherFragment())
.replace(R.id.container, WeatherFragmentWithViewModel())
.commitNow()
}
}
Expand Down
2 changes: 1 addition & 1 deletion feature.weatherui/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ dependencies {
implementation project(':lib.weatherdata')
implementation project(':lib.userprefs')
implementation 'androidx.core:core-ktx:1.7.0'
implementation 'androidx.appcompat:appcompat:1.4.1'
implementation 'androidx.fragment:fragment-ktx:1.4.1'
implementation 'androidx.lifecycle:lifecycle-viewmodel-ktx:2.4.1'
implementation 'com.google.dagger:dagger:2.42'
}
2 changes: 1 addition & 1 deletion feature.weatherui/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<application>
<activity
android:name=".MainActivity"
android:name="com.gpeal.droidconanvilsample.app.MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
package com.gpeal.droidconanvilsample.feature.weatherui

import com.gpeal.droidconanvilsample.lib.daggerscopes.WeatherScope
import com.squareup.anvil.annotations.ContributesTo

@ContributesTo(WeatherScope::class)
interface WeatherBindings {
fun inject(fragment: WeatherFragmentSimple)
fun inject(vm: WeatherViewModel)
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,20 +2,13 @@ package com.gpeal.droidconanvilsample.feature.weatherui

import android.content.Context
import androidx.fragment.app.Fragment
import com.gpeal.droidconanvilsample.lib.daggerscopes.WeatherScope
import com.gpeal.droidconanvilsample.lib.weatherdata.WeatherRepository
import com.gpeal.droidconanvilsample.lib.daggerscopes.utils.DaggerComponentOwner
import com.gpeal.droidconanvilsample.lib.daggerscopes.utils.bindings
import com.gpeal.droidconanvilsample.lib.daggerscopes.utils.fragmentComponent
import com.squareup.anvil.annotations.ContributesTo
import javax.inject.Inject

@ContributesTo(WeatherScope::class)
interface WeatherBindings {
fun inject(fragment: WeatherFragment)
}

class WeatherFragment : Fragment(R.layout.main_fragment), DaggerComponentOwner {
class WeatherFragmentSimple : Fragment(R.layout.weather_fragment), DaggerComponentOwner {
override val daggerComponent: WeatherComponent by fragmentComponent { _, app ->
// If you want a ViewModel scoped component, just instantiate this component inside of your ViewModel.
// You instantiate this component anywhere, really.
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package com.gpeal.droidconanvilsample.feature.weatherui

import android.app.Application
import android.content.Context
import androidx.fragment.app.Fragment
import androidx.fragment.app.viewModels
import androidx.lifecycle.AndroidViewModel
import androidx.lifecycle.ViewModel
import com.gpeal.droidconanvilsample.lib.daggerscopes.utils.DaggerComponentOwner
import com.gpeal.droidconanvilsample.lib.daggerscopes.utils.bindings
import com.gpeal.droidconanvilsample.lib.weatherdata.WeatherRepository
import javax.inject.Inject

class WeatherViewModel(application: Application) : AndroidViewModel(application), DaggerComponentOwner {

override val daggerComponent = application.bindings<WeatherComponent.ParentBindings>().weatherComponentBuilder().create()

@Inject
lateinit var weatherRepository: WeatherRepository

init {
bindings<WeatherBindings>().inject(this)
}
}

class WeatherFragmentWithViewModel : Fragment(R.layout.weather_fragment) {
private val viewModel: WeatherViewModel by viewModels()
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
android:id="@+id/main"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".WeatherFragment">
tools:context=".WeatherFragmentSimple">

<TextView
android:id="@+id/message"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
package com.gpeal.droidconanvilsample.lib.daggerscopes.utils

import android.app.Application
import android.content.Context
import android.content.ContextWrapper
import androidx.fragment.app.Fragment
import androidx.lifecycle.AndroidViewModel

/**
* Use this to get the dagger "Bindings" for your module. Bindings are used if you need to directly interact with a dagger component such as:
Expand All @@ -24,6 +26,9 @@ inline fun <reified T : Any> Context.bindings() = _bindings(T::class.java)
*/
inline fun <reified T : Any> Fragment.bindings() = _bindings(T::class.java)

inline fun <reified T : Any> AndroidViewModel.bindings() = ((this as? DaggerComponentOwner)?.daggerComponent as? T) ?: getApplication<Application>()._bindings(T::class.java)


/** Use no-arg extension function instead: [Context._bindings] */
@Suppress("FunctionName")
fun <T : Any> Context._bindings(klass: Class<T>): T {
Expand Down

0 comments on commit 229855f

Please sign in to comment.