blob: 746515a816b33bee7dd308f814ae779dec61d9c3 [file] [log] [blame]
Dave Mankoff2ea5a832019-07-03 13:26:55 -04001/*
2 * Copyright (C) 2019 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package com.android.systemui;
18
Dave Mankoffeb593ae2019-09-04 11:31:55 -040019import android.app.Activity;
Dave Mankoff2ea5a832019-07-03 13:26:55 -040020import android.app.Application;
21import android.app.Service;
Dave Mankoffa4a71362019-08-27 14:40:05 -040022import android.content.ContentProvider;
23import android.content.Context;
Dave Mankoff2ea5a832019-07-03 13:26:55 -040024import android.content.Intent;
25
Dave Mankoffa4a71362019-08-27 14:40:05 -040026import androidx.annotation.NonNull;
Dave Mankoffeb593ae2019-09-04 11:31:55 -040027import androidx.annotation.Nullable;
Dave Mankoffa4a71362019-08-27 14:40:05 -040028import androidx.core.app.AppComponentFactory;
Dave Mankoff2ea5a832019-07-03 13:26:55 -040029
Dave Mankofff4736812019-10-18 17:25:50 -040030import com.android.systemui.dagger.ContextComponentHelper;
31
Dave Mankoff2ea5a832019-07-03 13:26:55 -040032import javax.inject.Inject;
33
34/**
35 * Implementation of AppComponentFactory that injects into constructors.
Dave Mankoffa4a71362019-08-27 14:40:05 -040036 *
37 * This class sets up dependency injection when creating our application.
38 *
39 * Services support dependency injection into their constructors.
40 *
41 * ContentProviders support injection into member variables - _not_ constructors.
Dave Mankoff2ea5a832019-07-03 13:26:55 -040042 */
Dave Mankoffa4a71362019-08-27 14:40:05 -040043public class SystemUIAppComponentFactory extends AppComponentFactory {
Dave Mankoff2ea5a832019-07-03 13:26:55 -040044
Dave Mankoff61170782019-09-10 13:28:42 -040045 private static final String TAG = "AppComponentFactory";
Dave Mankoff2ea5a832019-07-03 13:26:55 -040046 @Inject
47 public ContextComponentHelper mComponentHelper;
48
49 public SystemUIAppComponentFactory() {
50 super();
51 }
52
Dave Mankoffa4a71362019-08-27 14:40:05 -040053 @NonNull
Dave Mankoff2ea5a832019-07-03 13:26:55 -040054 @Override
Dave Mankoffa4a71362019-08-27 14:40:05 -040055 public Application instantiateApplicationCompat(
56 @NonNull ClassLoader cl, @NonNull String className)
Dave Mankoff2ea5a832019-07-03 13:26:55 -040057 throws InstantiationException, IllegalAccessException, ClassNotFoundException {
Dave Mankoffa4a71362019-08-27 14:40:05 -040058 Application app = super.instantiateApplicationCompat(cl, className);
Dave Mankoffe2294692019-08-14 11:53:13 -040059 if (app instanceof ContextInitializer) {
60 ((ContextInitializer) app).setContextAvailableCallback(
Dave Mankoff2ea5a832019-07-03 13:26:55 -040061 context -> {
62 SystemUIFactory.createFromConfig(context);
63 SystemUIFactory.getInstance().getRootComponent().inject(
64 SystemUIAppComponentFactory.this);
65 }
66 );
67 }
68
69 return app;
70 }
71
Dave Mankoffa4a71362019-08-27 14:40:05 -040072 @NonNull
Dave Mankoff2ea5a832019-07-03 13:26:55 -040073 @Override
Dave Mankoffa4a71362019-08-27 14:40:05 -040074 public ContentProvider instantiateProviderCompat(
75 @NonNull ClassLoader cl, @NonNull String className)
Dave Mankoff2ea5a832019-07-03 13:26:55 -040076 throws InstantiationException, IllegalAccessException, ClassNotFoundException {
Dave Mankoffa4a71362019-08-27 14:40:05 -040077
78 ContentProvider contentProvider = super.instantiateProviderCompat(cl, className);
Dave Mankoffe2294692019-08-14 11:53:13 -040079 if (contentProvider instanceof ContextInitializer) {
80 ((ContextInitializer) contentProvider).setContextAvailableCallback(
Dave Mankoffa4a71362019-08-27 14:40:05 -040081 context -> {
82 SystemUIFactory.createFromConfig(context);
83 SystemUIFactory.getInstance().getRootComponent().inject(
84 contentProvider);
85 }
86 );
Dave Mankoff2ea5a832019-07-03 13:26:55 -040087 }
Dave Mankoffa4a71362019-08-27 14:40:05 -040088
89 return contentProvider;
Dave Mankoff2ea5a832019-07-03 13:26:55 -040090 }
91
Dave Mankoffa4a71362019-08-27 14:40:05 -040092 @NonNull
93 @Override
Dave Mankoffeb593ae2019-09-04 11:31:55 -040094 public Activity instantiateActivityCompat(@NonNull ClassLoader cl, @NonNull String className,
95 @Nullable Intent intent)
96 throws InstantiationException, IllegalAccessException, ClassNotFoundException {
Dave Mankoff730f01a62019-09-25 10:18:36 -040097 if (mComponentHelper == null) {
98 // This shouldn't happen, but is seen on occasion.
99 // Bug filed against framework to take a look: http://b/141008541
100 SystemUIFactory.getInstance().getRootComponent().inject(
101 SystemUIAppComponentFactory.this);
102 }
Dave Mankoffeb593ae2019-09-04 11:31:55 -0400103 Activity activity = mComponentHelper.resolveActivity(className);
104 if (activity != null) {
105 return activity;
106 }
107 return super.instantiateActivityCompat(cl, className, intent);
108 }
109
110 @NonNull
111 @Override
Dave Mankoffa4a71362019-08-27 14:40:05 -0400112 public Service instantiateServiceCompat(
113 @NonNull ClassLoader cl, @NonNull String className, Intent intent)
114 throws InstantiationException, IllegalAccessException, ClassNotFoundException {
Dave Mankoff61170782019-09-10 13:28:42 -0400115 if (mComponentHelper == null) {
Dave Mankoff66c4c722019-09-13 14:35:15 -0400116 // This shouldn't happen, but does when a device is freshly formatted.
117 // Bug filed against framework to take a look: http://b/141008541
118 SystemUIFactory.getInstance().getRootComponent().inject(
119 SystemUIAppComponentFactory.this);
Dave Mankoff61170782019-09-10 13:28:42 -0400120 }
Dave Mankoffa4a71362019-08-27 14:40:05 -0400121 Service service = mComponentHelper.resolveService(className);
122 if (service != null) {
123 return service;
Dave Mankoff2ea5a832019-07-03 13:26:55 -0400124 }
Dave Mankoffa4a71362019-08-27 14:40:05 -0400125 return super.instantiateServiceCompat(cl, className, intent);
126 }
Dave Mankoff2ea5a832019-07-03 13:26:55 -0400127
Dave Mankoffe2294692019-08-14 11:53:13 -0400128 /**
129 * A callback that receives a Context when one is ready.
130 */
131 public interface ContextAvailableCallback {
Dave Mankoffa4a71362019-08-27 14:40:05 -0400132 void onContextAvailable(Context context);
133 }
134
Dave Mankoffe2294692019-08-14 11:53:13 -0400135 /**
136 * Implemented in classes that get started by the system before a context is available.
137 */
138 public interface ContextInitializer {
Dave Mankoffa4a71362019-08-27 14:40:05 -0400139 void setContextAvailableCallback(ContextAvailableCallback callback);
Dave Mankoff2ea5a832019-07-03 13:26:55 -0400140 }
141}