<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Android &#43; Dagger2 on Guowei Lv</title>
    <link>https://www.lvguowei.me/categories/android-&#43;-dagger2/</link>
    <description>Recent content in Android &#43; Dagger2 on Guowei Lv</description>
    <generator>Hugo -- gohugo.io</generator>
    <language>en-us</language>
    <lastBuildDate>Sun, 16 May 2021 08:59:40 +0300</lastBuildDate><atom:link href="https://www.lvguowei.me/categories/android-+-dagger2/index.xml" rel="self" type="application/rss+xml" />
    <item>
      <title>Dependency Injection in Android With Dagger2 (14)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-14/</link>
      <pubDate>Sun, 16 May 2021 08:59:40 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-14/</guid>
      <description>Here is one clean solution of how to combine Dagger + ViewModel + SavedStateHandle.
The only difference now is that inside our ViewModel has access to SavedStateHandle. We capture this through a abstract class:
abstract class SavedStateViewModel: ViewModel() { abstract fun init(savedStateHandle: SavedStateHandle) } And the ViewModel now looks like this:
class MyViewModel @Inject constructor( private val fetchQuestionsUseCase: FetchQuestionsUseCase ) : SavedStateViewModel() { private lateinit var _questions: MutableLiveData&amp;lt;List&amp;lt;Question&amp;gt;&amp;gt; val questions: LiveData&amp;lt;List&amp;lt;Question&amp;gt;&amp;gt; get() = _questions override fun init(savedStateHandle: SavedStateHandle) { _questions = savedStateHandle.</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (13)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-13/</link>
      <pubDate>Sun, 16 May 2021 07:53:38 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-13/</guid>
      <description>Previously, we created a centralized ViewModelFactory which can create all ViewModels in the app:
class ViewModelFactory @Inject constructor( private val myViewModelProvider: Provider&amp;lt;MyViewModel&amp;gt;, private val myViewModel2Provider: Provider&amp;lt;MyViewModel2&amp;gt; ): ViewModelProvider.Factory { override fun &amp;lt;T : ViewModel?&amp;gt; create(modelClass: Class&amp;lt;T&amp;gt;): T { return when(modelClass) { MyViewModel::class.java -&amp;gt; myViewModelProvider.get() as T MyViewModel2::class.java -&amp;gt; myViewModel2Provider.get() as T else -&amp;gt; throw RuntimeException(&amp;#34;unsupported ViewModel type: $modelClass&amp;#34;) } } } But with more and more ViewModels being added to our app, this class will grow quickly, is there a way to mitigate this?</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (12)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-12/</link>
      <pubDate>Sat, 15 May 2021 18:45:09 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-12/</guid>
      <description>It is a bit cumbersome to create a Factory for each ViewModel we have. Actually, we can just create one Factory that is responsible for creating all ViewModels in the app.
The Factory is very straightforward:
class ViewModelFactory @Inject constructor( private val myViewModelProvider: Provider&amp;lt;MyViewModel&amp;gt;, private val myViewModel2Provider: Provider&amp;lt;MyViewModel2&amp;gt; ): ViewModelProvider.Factory { override fun &amp;lt;T : ViewModel?&amp;gt; create(modelClass: Class&amp;lt;T&amp;gt;): T { return when(modelClass) { MyViewModel::class.java -&amp;gt; myViewModelProvider.get() as T MyViewModel2::class.java -&amp;gt; myViewModel2Provider.</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (11)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-11/</link>
      <pubDate>Sat, 15 May 2021 08:56:32 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-11/</guid>
      <description>The main advantage of using ViewModel is: it can survive configuration change. That means if you associate a ViewModel with an Activity, then after configuration change, the activity will get the same instance of that ViewModel.
Of course that comes with some setup work to do on developers side. But it is not that bad, basically the activity gets its ViewModel through ViewModelProvider.
If your ViewModel has empty constructor, then you can simply use:</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (10)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-10/</link>
      <pubDate>Sun, 09 May 2021 22:53:22 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-10/</guid>
      <description>Let&amp;rsquo;s take a look at the ViewMvcFactory:
class ViewMvcFactory @Inject constructor( private val layoutInflaterProvider: LayoutInflater, private val imageLoaderProvider: ImageLoader ) One thing worth paying attention is that this is a factory. Factory is used to create objects. So this means that its dependencies: LayoutInflater and ImageLoader will be reused to create objects everytime.
We know that ImageLoader has no state so that it can be reused, but what if it can&amp;rsquo;t?</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (9)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-9/</link>
      <pubDate>Sun, 09 May 2021 22:06:54 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-9/</guid>
      <description>This is a simple one. No more explanation, just paste the code here.
@UiThread @Module class AppModule { @Provides @AppScope @Retrofit1 fun retrofit1(urlProvider: UrlProvider): Retrofit { return Retrofit.Builder() .baseUrl(urlProvider.baseUrl1()) .addConverterFactory(GsonConverterFactory.create()) .build() } @Provides @AppScope @Retrofit2 fun retrofit2(): Retrofit { return Retrofit.Builder() .baseUrl(urlProvider().baseUrl2()) .addConverterFactory(GsonConverterFactory.create()) .build() } @Provides @AppScope fun stackOverflowApi(@Retrofit1 retrofit: Retrofit): StackoverflowApi = retrofit.create(StackoverflowApi::class.java) @Provides @AppScope fun urlProvider(): UrlProvider = UrlProvider() } @Qualifier annotation class Retrofit1() @Qualifier annotation class Retrofit2() </description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (8)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-8/</link>
      <pubDate>Sun, 09 May 2021 14:56:26 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-8/</guid>
      <description>Let&amp;rsquo;s create a ScreensNavigator interface:
interface ScreensNavigator { fun navigateBack() fun toQuestionDetails(questionId: String) } And ScreensNavigatorImpl implements it:
class ScreensNavigatorImpl @Inject constructor(private val activity: AppCompatActivity) : ScreensNavigator { override fun navigateBack() { activity.onBackPressed() } override fun toQuestionDetails(questionId: String) { QuestionDetailsActivity.start(activity, questionId) } } Now we have a problem that in activities and fragments we want to inject the interface type:
@Inject lateinit var screensNavigator: ScreensNavigator But Dagger only knows how to create ScreensNavigatorImpl.</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (7)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-7/</link>
      <pubDate>Fri, 07 May 2021 23:31:25 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-7/</guid>
      <description>One fact: it is more performant to make the all provider methods inside Modules static.
But for Modules that have bootstrap dependencies, this is impossible. Let&amp;rsquo;s take ActivityModule as example.
@Module class ActivityModule(private val activity: AppCompatActivity) { @Provides fun activity(): AppCompatActivity = activity @Provides fun layoutInflater(activity: AppCompatActivity): LayoutInflater = LayoutInflater.from(activity) @Provides fun fragmentManager(activity: AppCompatActivity) = activity.supportFragmentManager @Provides @ActivityScope fun screensNavigator(activity: AppCompatActivity) = ScreensNavigator(activity) } We can easily make fun layoutInflater(), fragmentManager() and screensNavigator static methods.</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (6)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-6/</link>
      <pubDate>Mon, 03 May 2021 13:20:50 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-6/</guid>
      <description>Components can have multiple Modules. So if you have huge Modules that provide tons of services, it is good to split it up.
Let&amp;rsquo;s create a UseCaseModule to hanle all the UseCases.
@Module class UseCasesModule { @Provides fun fetchQuestionsUseCase(stackOverflowApi: StackoverflowApi) = FetchQuestionsUseCase(stackOverflowApi) @Provides fun fetchQuestionDetailsUseCase(stackOverflowApi: StackoverflowApi) = FetchQuestionDetailsUseCase(stackOverflowApi) }  Some dagger conventions:
 Components can use more than 1 module. Modules of the same Component share the same object-graph. Dagger automatically instantiate modules with no argument constructor.</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (5)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-5/</link>
      <pubDate>Mon, 03 May 2021 06:54:09 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-5/</guid>
      <description>In previous post, we introduced the component dependencies. But there is one interesting subtlety: If Component B depends on Component A, B has access to all A&amp;rsquo;s exposed objects. Note that there is a difference between what a component exposes and what it provides.
Let&amp;rsquo;s look at PresentationComponent and ActivityComponent.
@PresentationScope @Component(dependencies = [ActivityComponent::class], modules = [PresentationModule::class]) interface PresentationComponent { fun inject(fragment: QuestionsListFragment) fun inject(questionDetailsActivity: QuestionDetailsActivity) } Here in PresentationComponent, even though it provides all the objects that QuestionsListFragment and QuestionDetailsActivity need, it exposes nothing.</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (4)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-4/</link>
      <pubDate>Sun, 02 May 2021 22:53:45 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-4/</guid>
      <description>Let&amp;rsquo;s look at the PresentationComponent more closely.
 One strange thing is that PresentationModule has ActivityComponent as its dependency, and it @Provide all the objects provided by ActivityComponent already.
This is rather ugly, can we do something about it?
The answer is Component Dependencies.
The idea is that we can make PresentationComponent depends on ActivityComponent. That way, PresentationComponent automatically gets access to all the objects exposed by ActivityComponent.
After this change, it looks like this:</description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (3)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-3/</link>
      <pubDate>Sun, 02 May 2021 14:56:51 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-3/</guid>
      <description>In previous post, we replaced our Pure Dependency Injection with Dagger2. But, the conversion is without too much thoughts.
One improvement we can do is to follow Dagger&amp;rsquo;s convention of using Component as Injector.
 We can make the following mental models:
 Dagger&amp;rsquo;s @Module is for creating objects. Dagger&amp;rsquo;s @Component is for injecting objects into application classes.  </description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (2)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-2/</link>
      <pubDate>Sun, 02 May 2021 09:00:51 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-2/</guid>
      <description>Previous post we set up the so called Pure Dependency Injection. Now let&amp;rsquo;s replace that with Dagger2 balantly.
Convert the composition roots into dagger&amp;rsquo;s @Modules.
Create @Component to hold each @Module.
Create @Scopes and use it to scope the objects we want only 1 instance in the component.
Now it looks like this:
 </description>
    </item>
    
    <item>
      <title>Dependency Injection in Android With Dagger2 (1)</title>
      <link>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-1/</link>
      <pubDate>Fri, 30 Apr 2021 15:12:56 +0300</pubDate>
      
      <guid>https://www.lvguowei.me/post/dependency-injection-in-android-with-dagger2-1/</guid>
      <description>This series of posts are my summary notes from the online course Dependency Injection in Android with Dagger 2 and Hilt.
I do believe if you have any doubts about Dagger2 in Android, run to get that course and watch it 3 times, I bet you will be better than 90% of the android developers on the market on this topic.
The first 1/3 of the course introduces the so called Pure Dependency Injection, which means not using any library like Dagger.</description>
    </item>
    
  </channel>
</rss>
