1 /*
2  * Copyright (C) 2014 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 
17 package com.android.systemui.qs.tiles;
18 
19 import android.app.ActivityManager;
20 import android.content.Intent;
21 import android.os.Handler;
22 import android.os.Looper;
23 import android.provider.MediaStore;
24 import android.service.quicksettings.Tile;
25 import android.view.View;
26 import android.widget.Switch;
27 
28 import androidx.annotation.Nullable;
29 
30 import com.android.internal.logging.MetricsLogger;
31 import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
32 import com.android.systemui.R;
33 import com.android.systemui.dagger.qualifiers.Background;
34 import com.android.systemui.dagger.qualifiers.Main;
35 import com.android.systemui.plugins.ActivityStarter;
36 import com.android.systemui.plugins.FalsingManager;
37 import com.android.systemui.plugins.qs.QSTile.BooleanState;
38 import com.android.systemui.plugins.statusbar.StatusBarStateController;
39 import com.android.systemui.qs.QSHost;
40 import com.android.systemui.qs.QsEventLogger;
41 import com.android.systemui.qs.logging.QSLogger;
42 import com.android.systemui.qs.tileimpl.QSTileImpl;
43 import com.android.systemui.statusbar.policy.FlashlightController;
44 
45 import javax.inject.Inject;
46 
47 /**
48  * Quick settings tile: Control flashlight
49  **/
50 public class FlashlightTile extends QSTileImpl<BooleanState> implements
51         FlashlightController.FlashlightListener {
52 
53     public static final String TILE_SPEC = "flashlight";
54     private final FlashlightController mFlashlightController;
55 
56     @Inject
FlashlightTile( QSHost host, QsEventLogger uiEventLogger, @Background Looper backgroundLooper, @Main Handler mainHandler, FalsingManager falsingManager, MetricsLogger metricsLogger, StatusBarStateController statusBarStateController, ActivityStarter activityStarter, QSLogger qsLogger, FlashlightController flashlightController )57     public FlashlightTile(
58             QSHost host,
59             QsEventLogger uiEventLogger,
60             @Background Looper backgroundLooper,
61             @Main Handler mainHandler,
62             FalsingManager falsingManager,
63             MetricsLogger metricsLogger,
64             StatusBarStateController statusBarStateController,
65             ActivityStarter activityStarter,
66             QSLogger qsLogger,
67             FlashlightController flashlightController
68     ) {
69         super(host, uiEventLogger, backgroundLooper, mainHandler, falsingManager, metricsLogger,
70                 statusBarStateController, activityStarter, qsLogger);
71         mFlashlightController = flashlightController;
72         mFlashlightController.observe(getLifecycle(), this);
73     }
74 
75     @Override
handleDestroy()76     protected void handleDestroy() {
77         super.handleDestroy();
78     }
79 
80     @Override
newTileState()81     public BooleanState newTileState() {
82         BooleanState state = new BooleanState();
83         state.handlesLongClick = false;
84         return state;
85     }
86 
87     @Override
handleUserSwitch(int newUserId)88     protected void handleUserSwitch(int newUserId) {
89     }
90 
91     @Override
getLongClickIntent()92     public Intent getLongClickIntent() {
93         return new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA);
94     }
95 
96     @Override
isAvailable()97     public boolean isAvailable() {
98         return mFlashlightController.hasFlashlight();
99     }
100 
101     @Override
handleClick(@ullable View view)102     protected void handleClick(@Nullable View view) {
103         if (ActivityManager.isUserAMonkey()) {
104             return;
105         }
106         boolean newState = !mState.value;
107         refreshState(newState);
108         mFlashlightController.setFlashlight(newState);
109     }
110 
111     @Override
getTileLabel()112     public CharSequence getTileLabel() {
113         return mContext.getString(R.string.quick_settings_flashlight_label);
114     }
115 
116     @Override
handleLongClick(@ullable View view)117     protected void handleLongClick(@Nullable View view) {
118         handleClick(view);
119     }
120 
121     @Override
handleUpdateState(BooleanState state, Object arg)122     protected void handleUpdateState(BooleanState state, Object arg) {
123         state.label = mHost.getContext().getString(R.string.quick_settings_flashlight_label);
124         state.secondaryLabel = "";
125         state.stateDescription = "";
126         if (!mFlashlightController.isAvailable()) {
127             state.secondaryLabel = mContext.getString(
128                     R.string.quick_settings_flashlight_camera_in_use);
129             state.stateDescription = state.secondaryLabel;
130             state.state = Tile.STATE_UNAVAILABLE;
131             state.icon = ResourceIcon.get(R.drawable.qs_flashlight_icon_off);
132             return;
133         }
134         if (arg instanceof Boolean) {
135             boolean value = (Boolean) arg;
136             if (value == state.value) {
137                 return;
138             }
139             state.value = value;
140         } else {
141             state.value = mFlashlightController.isEnabled();
142         }
143         state.contentDescription = mContext.getString(R.string.quick_settings_flashlight_label);
144         state.expandedAccessibilityClassName = Switch.class.getName();
145         state.state = state.value ? Tile.STATE_ACTIVE : Tile.STATE_INACTIVE;
146         state.icon = ResourceIcon.get(state.value
147                 ? R.drawable.qs_flashlight_icon_on : R.drawable.qs_flashlight_icon_off);
148     }
149 
150     @Override
getMetricsCategory()151     public int getMetricsCategory() {
152         return MetricsEvent.QS_FLASHLIGHT;
153     }
154 
155     @Override
onFlashlightChanged(boolean enabled)156     public void onFlashlightChanged(boolean enabled) {
157         refreshState(enabled);
158     }
159 
160     @Override
onFlashlightError()161     public void onFlashlightError() {
162         refreshState(false);
163     }
164 
165     @Override
onFlashlightAvailabilityChanged(boolean available)166     public void onFlashlightAvailabilityChanged(boolean available) {
167         refreshState();
168     }
169 }
170