@AndroidEntryPoint用于修饰ComponentActivity、Service、Broadcast、service、Fragment、View。@HiltAndroidApp用于修饰Application;
节点使用@HiltAndroidApp或@AndroidEntryPoint注解修饰有且仅有一个;
@HiltAndroidApp或@AndroidEntryPoint注解只能用于修饰类,而不能用于修饰接口;
@HiltAndroidApp或@AndroidEntryPoint注解修饰的类不能使用泛型;
@HiltAndroidApp或@AndroidEntryPoint注解value值默认使用Void.class,我们最好不要去改动;
一个项目中@HiltAndroidApp只允许出现一次;
baseElement表示@HiltAndroidApp或@AndroidEntryPoint注解修饰的类的父类,如果baseElement使用了@AndroidEntryPoint注解修饰:
(1) @AndroidEntryPoint注解修饰的类 和 其baseElement节点要么都使用@WithFragmentBindings注解修饰,要么都不要使用该注解;
(2) @AndroidEntryPoint注解修饰的类不要使用@OptionalInject修饰的注解修饰 || baseElement类型使用@OptionalInject修饰的注解修饰;
@HiltAndroidApp只能用于修饰Application的继承类;
@AndroidEntryPoint可用于修饰Activity、Service、Broadcast_service,Fragment,View:
(1)@AndroidEntryPoint用于修饰Activity时,只能修饰androidx.activity.ComponentActivity的继承节点;
(2)@AndroidEntryPoint不能用于修饰Application的继承类。
只要使用@HiltAndroidApp或@AndroidEntryPoint修饰的节点都会生成xx_GeneratedInjector类。
demo:
@AndroidEntryPoint
class UserListFragment : Fragment() {...}
生成的类:
@OriginatingElement(
topLevelClass = UserListFragment.class
)
@GeneratedEntryPoint
@InstallIn(FragmentComponent.class)
public interface UserListFragment_GeneratedInjector {
void injectUserListFragment(UserListFragment userListFragment);
}
生成Hilt_xx类。这个类的作用是实现依赖注入到@HiltAndroidApp修饰的Application类中。
demo:
@HiltAndroidApp
class MyApplication : Application() {...}
生成Hilt_MyApplication类:
//A generated base class to be extended by the @HiltAndroidApp annotated class. If using the Gradle plugin, this is swapped as the base class via bytecode transformation.
@Generated("ApplicationGenerator")
abstract class Hilt_MyApplication extends Application implements GeneratedComponentManagerHolder {
private final ApplicationComponentManager componentManager =
new ApplicationComponentManager(
new ComponentSupplier() {
@Override
public Object get() {
//_com_aregyan_github_Application_HiltComponents内部类SingletonComponent生成的,该类后面生成。
return Dagger_com_aregyan_github_MyApplication_HiltComponents_SingletonComponent.builder()
.applicationContextModule(new ApplicationContextModule(Hilt_MyApplication.this))
.build();
}
}
);
@Override
public final ApplicationComponentManager componentManager() {
return componentManager;
}
@Override
public final Object generatedComponent() {
return this.componentManager().generatedComponent();
}
@CallSuper
@Override
public void onCreate() {
// This is a known unsafe cast, but is safe in the only correct use case:
// $APP extends Hilt_$APP
((MyApplication_GeneratedInjector)generatedComponent()).injectMyApplication((MyApplication) this);
super.onCreate();
}
}
ApplicationComponentManager类是使用单例创建自己,该类的目的是创建SingtonComponent实现类。
在Hilt_MyApplication实现了注入工作,那么一定有一个component容器:
@Component
@Singleton
public static abstract class SingletonComponent
implements Application_GeneratedInjector
{
//Application_GeneratedInjector类中的方法
//void injectApplication(Application application);
//实际是ActivityRetainedComponent,方便讲解我们暂用ActivityRetainedComponent
ActivityComponent.Builder componentBuilder();
@Component.Builder
public static interface Builder{
Builder applicationContextModule(ApplicationContextModule context);
SingletonComponent build();
}
}
生成Hilt_xx类。这个类有两个目的:
将依赖注入到 @AndroidEntryPoint修饰的ComponentActivity类中;
提供ViewModelProvider.Factory,将我们自定义的ViewModel类实例化并且提供给ViewModel的工厂。(暂时不进行讲解,后面会说到)
demo:
@AndroidEntryPoint
class MainActivity : AppCompatActivity(R.layout.activity_main)
MainActivity生成Hilt_MainActivity类:
/**
* A generated base class to be extended by the @dagger.hilt.android.AndroidEntryPoint annotated class. If using the Gradle plugin, this is swapped as the base class via bytecode transformation.
*/
public abstract class Hilt_MainActivity extends AppCompatActivity implements GeneratedComponentManagerHolder {
private volatile ActivityComponentManager componentManager;
private final Object componentManagerLock = new Object();
private boolean injected = false;
Hilt_MainActivity() {
super();
_initHiltInternal();
}
Hilt_MainActivity(int contentLayoutId) {
super(contentLayoutId);
_initHiltInternal();
}
private void _initHiltInternal() {
addOnContextAvailableListener(new OnContextAvailableListener() {
@Override
public void onContextAvailable(Context context) {
inject();
}
});
}
@Override
public final Object generatedComponent() {
return this.componentManager().generatedComponent();
}
protected ActivityComponentManager createComponentManager() {
return new ActivityComponentManager(this);
}
@Override
public final ActivityComponentManager componentManager() {
if (componentManager == null) {
synchronized (componentManagerLock) {
if (componentManager == null) {
componentManager = createComponentManager();
}
}
}
return componentManager;
}
protected void inject() {
if (!injected) {
injected = true;
((MainActivity_GeneratedInjector) this.generatedComponent()).injectMainActivity(UnsafeCasts.unsafeCast(this));
}
}
@Override
public ViewModelProvider.Factory getDefaultViewModelProviderFactory() {
return DefaultViewModelFactories.getActivityFactory(this, super.getDefaultViewModelProviderFactory());
}
}
如上代码所示,inject()
实现依赖注入工作,getDefaultViewModelProviderFactory方法提供hilt源码中自定义的ViewModelProvider.Factory类。@AndroidEntryPoint修饰的ComponentActivity类使用ActivityComponent容器:
@subComponent
@ActivityScoped
public static abstract class ActivityComponent
implements
MainActivity_GeneratedInjector
{
//MainActivity_GeneratedInjector中的方法
//void injectMainActivity(MainActivity mainActivity);
ViewModelComponent.Builder getViewModelComponentBuilder();
FragmentComponent.Builder fragmentComponentBuilder();
@SubComponent.Builder
static interface Builder{
Builder activity(
@BindsInstance
Activity activity);
ActivityComponent build();
}
}
@AndroidEntryPoint修饰的BroadcastReceiver实现类生成代码。
生成的代码如下:
@Generated("BroadcastReceiverGenerator")
abstract class Hilt_$CLASS extends $BASE {
private volatile boolean injected = false;
private final Object injectedLock = new Object();
protected void inject(Context context) {
if (!injected) {
synchronized (injectedLock){
if (!injected){
(($CLASS_GeneratedInjector)BroadcastReceiverComponentManager.generatedComponent(context)).inject$CLASS(($CLASS) this);
}
}
injected = true;
}
}
@CallSuper
@Override
public void onReceive(Context context, Intent intent) {
inject(context);
super.onReceive(context, intent);
}
}
生成Hilt_xx类。这个类有两个目的:
将依赖注入到 @AndroidEntryPoint修饰的Fragment类中;
提供ViewModelProvider.Factory,将我们自定义的ViewModel类实例化并且提供给ViewModel的工厂。(暂时不进行讲解,后面会说到)
demo:
@AndroidEntryPoint
class UserListFragment : Fragment() {...}
生成Hilt_xx类:
/**
* A generated base class to be extended by the @dagger.hilt.android.AndroidEntryPoint annotated class. If using the Gradle plugin, this is swapped as the base class via bytecode transformation.
*/
public abstract class Hilt_UserListFragment extends Fragment implements GeneratedComponentManagerHolder {
private ContextWrapper componentContext;
private boolean disableGetContextFix;
private volatile FragmentComponentManager componentManager;
private final Object componentManagerLock = new Object();
private boolean injected = false;
Hilt_UserListFragment() {
super();
}
Hilt_UserListFragment(int contentLayoutId) {
super(contentLayoutId);
}
@Override
@CallSuper
public void onAttach(Context context) {
super.onAttach(context);
initializeComponentContext();
inject();
}
@Override
@SuppressWarnings("deprecation")
@CallSuper
@MainThread
public void onAttach(Activity activity) {
super.onAttach(activity);
Preconditions.checkState(componentContext == null || FragmentComponentManager.findActivity(componentContext) == activity, "onAttach called multiple times with different Context! Hilt Fragments should not be retained.");
initializeComponentContext();
inject();
}
private void initializeComponentContext() {
if (componentContext == null) {
// Note: The LayoutInflater provided by this componentContext may be different from super Fragment's because we getting it from base context instead of cloning from the super Fragment's LayoutInflater.
componentContext = FragmentComponentManager.createContextWrapper(super.getContext(), this);
disableGetContextFix = FragmentGetContextFix.isFragmentGetContextFixDisabled(super.getContext());
}
}
@Override
public Context getContext() {
if (super.getContext() == null && !disableGetContextFix) {
return null;
}
initializeComponentContext();
return componentContext;
}
@Override
public LayoutInflater onGetLayoutInflater(Bundle savedInstanceState) {
LayoutInflater inflater = super.onGetLayoutInflater(savedInstanceState);
return LayoutInflater.from(FragmentComponentManager.createContextWrapper(inflater, this));
}
@Override
public final Object generatedComponent() {
return this.componentManager().generatedComponent();
}
protected FragmentComponentManager createComponentManager() {
return new FragmentComponentManager(this);
}
@Override
public final FragmentComponentManager componentManager() {
if (componentManager == null) {
synchronized (componentManagerLock) {
if (componentManager == null) {
componentManager = createComponentManager();
}
}
}
return componentManager;
}
protected void inject() {
if (!injected) {
injected = true;
((UserListFragment_GeneratedInjector) this.generatedComponent()).injectUserListFragment(UnsafeCasts.unsafeCast(this));
}
}
@Override
public ViewModelProvider.Factory getDefaultViewModelProviderFactory() {
return DefaultViewModelFactories.getFragmentFactory(this, super.getDefaultViewModelProviderFactory());
}
}
AndroidEntryPoint修饰的Service实现类生成代码如下:
//A generated base class to be extended by the @AndroidEntryPoint annotated class. If using the Gradle plugin, this is swapped as the base class via bytecode transformation.
@Generated("ServiceGenerator")
abstract class Hilt_$CLASS extends $BASE {
private boolean injected = false;
protected void inject() {
if (!injected) {
generatedComponent().inject$CLASS(($CLASS) this);
injected = true;
}
}
private final Object componentManagerLock = new Object();
private volatile ServiceComponentManager componentManager;
protected ServiceComponentManager createComponentManager() {
return new ServiceComponentManager(this);
}
@Override
public ServiceComponentManager componentManager() {
if (componentManager == null) {
synchronize (componentManagerLock) {
if (componentManager == null) {
componentManager = createComponentManager();
}
}
}
return componentManager;
}
@CallSuper
@Override
public void onCreate() {
inject();
super.onCreate();
}
@Override
public final Object generatedComponent() {
return this.componentManager().generatedComponent();
}
}
AndroidEntryPoint修饰的View实现类生成代码如下:
//A generated base class to be extended by the @AndroidEntryPoint annotated class. If using the Gradle plugin, this is swapped as the base class via bytecode transformation.
@Generated("ViewGenerator")
abstract class Hilt_$CLASS extends $BASE implements GeneratedComponentManagerHolder {
private boolean injected;
protected void inject() {
if (!injected) {
(($CLASS_GeneratedInjector)this.generatedComponent()).inject$CLASS(($CLASS) this);
injected = true;
}
}
private volatile ViewComponentManager componentManager;
protected ViewComponentManager createComponentManager() {
return new ViewComponentManager(this,true);
}
@Override
public ViewComponentManager componentManager() {
componentManager = createComponentManager();
return componentManager;
}
@Override
public final Object generatedComponent() {
return this.componentManager().generatedComponent();
}
}
我们只是使用了@AndroidEntryPoint和@HiltAndroidApp修饰。但是hilt实际给我们做了很多的工作。