UiModeManagerService.java revision c093bf26456e55c09ed4e61ad36999d07a86be1f
17299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn/* 27299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * Copyright (C) 2008 The Android Open Source Project 37299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * 47299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * Licensed under the Apache License, Version 2.0 (the "License"); 57299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * you may not use this file except in compliance with the License. 67299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * You may obtain a copy of the License at 77299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * 87299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * http://www.apache.org/licenses/LICENSE-2.0 97299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * 107299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * Unless required by applicable law or agreed to in writing, software 117299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * distributed under the License is distributed on an "AS IS" BASIS, 127299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 137299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * See the License for the specific language governing permissions and 147299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn * limitations under the License. 157299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn */ 167299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 177299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornpackage com.android.server; 187299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 197299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.Activity; 2062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brownimport android.app.ActivityManager; 217299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.ActivityManagerNative; 227299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.IUiModeManager; 237299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.Notification; 247299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.NotificationManager; 257299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.PendingIntent; 267299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.StatusBarManager; 277299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.app.UiModeManager; 287299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.content.BroadcastReceiver; 297299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.content.Context; 307299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.content.Intent; 317299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.content.IntentFilter; 327299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.content.pm.PackageManager; 337299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.content.res.Configuration; 34e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwoodimport android.os.BatteryManager; 357299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.os.Binder; 367299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.os.Handler; 37182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinskiimport android.os.IBinder; 38e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwoodimport android.os.PowerManager; 397299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.os.RemoteException; 405ac72a29593ab9a20337a2225df52bdf4754be02Dianne Hackbornimport android.os.UserHandle; 412ccda4dc8d800c3592b4bd4d1d70a064d98dd4feDianne Hackbornimport android.provider.Settings; 4211159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brownimport android.service.dreams.Sandman; 437299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport android.util.Slog; 447299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 457299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport java.io.FileDescriptor; 467299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport java.io.PrintWriter; 477299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 487299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport com.android.internal.R; 497299c41630935a2b106e73e5603579a7747f7535Dianne Hackbornimport com.android.internal.app.DisableCarModeActivity; 50182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinskiimport com.android.server.twilight.TwilightListener; 51182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinskiimport com.android.server.twilight.TwilightManager; 52182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinskiimport com.android.server.twilight.TwilightState; 537299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 54182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinskifinal class UiModeManagerService extends SystemService { 557299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private static final String TAG = UiModeManager.class.getSimpleName(); 567299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private static final boolean LOG = false; 577299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 5811ddf533a2165ca68002d3b48e312271b3d0dedbDaniel Sandler // Enable launching of applications when entering the dock. 5911ddf533a2165ca68002d3b48e312271b3d0dedbDaniel Sandler private static final boolean ENABLE_LAUNCH_CAR_DOCK_APP = true; 60960779d3bbc6f2c767432ce48aca1e12cb0093b7John Spurlock private static final boolean ENABLE_LAUNCH_DESK_DOCK_APP = true; 6111ddf533a2165ca68002d3b48e312271b3d0dedbDaniel Sandler 627299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn final Object mLock = new Object(); 637299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private int mDockState = Intent.EXTRA_DOCK_STATE_UNDOCKED; 64182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 657299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private int mLastBroadcastState = Intent.EXTRA_DOCK_STATE_UNDOCKED; 66182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski int mNightMode = UiModeManager.MODE_NIGHT_NO; 67ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 687299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private boolean mCarModeEnabled = false; 69e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood private boolean mCharging = false; 70182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private int mDefaultUiModeType; 71182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private boolean mCarModeKeepsScreenOn; 72182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private boolean mDeskModeKeepsScreenOn; 73182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private boolean mTelevision; 746c191299a73388cd593809c0b66bafbd08fd2982John Spurlock private boolean mWatch; 757299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private boolean mComputedNightMode; 761d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung private int mCarModeEnableFlags; 77ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 78182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski int mCurUiMode = 0; 79182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private int mSetUiMode = 0; 80b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn private boolean mHoldingConfiguration = false; 81182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 827299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private Configuration mConfiguration = new Configuration(); 83182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski boolean mSystemReady; 84ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 85182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private final Handler mHandler = new Handler(); 867299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 87182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private TwilightManager mTwilightManager; 887299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private NotificationManager mNotificationManager; 897299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private StatusBarManager mStatusBarManager; 909fca9e96989bb70c3a5fa9de37681c9228c88ae6Jeff Brown 91182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private PowerManager.WakeLock mWakeLock; 927299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 93b880d880c6cd989eacc28c365fc9a41d31900da1Jeff Brown public UiModeManagerService(Context context) { 94b880d880c6cd989eacc28c365fc9a41d31900da1Jeff Brown super(context); 95b880d880c6cd989eacc28c365fc9a41d31900da1Jeff Brown } 96b880d880c6cd989eacc28c365fc9a41d31900da1Jeff Brown 97182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private static Intent buildHomeIntent(String category) { 98f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn Intent intent = new Intent(Intent.ACTION_MAIN); 99f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn intent.addCategory(category); 100f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK 101f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn | Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED); 102f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn return intent; 103f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn } 104960779d3bbc6f2c767432ce48aca1e12cb0093b7John Spurlock 1057299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // The broadcast receiver which receives the result of the ordered broadcast sent when 1067299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // the dock state changes. The original ordered broadcast is sent with an initial result 1077299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // code of RESULT_OK. If any of the registered broadcast receivers changes this value, e.g., 1087299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // to RESULT_CANCELED, then the intent to start a dock app will not be sent. 1097299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private final BroadcastReceiver mResultReceiver = new BroadcastReceiver() { 1107299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn @Override 1117299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn public void onReceive(Context context, Intent intent) { 1127299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (getResultCode() != Activity.RESULT_OK) { 11369a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler if (LOG) { 114960779d3bbc6f2c767432ce48aca1e12cb0093b7John Spurlock Slog.v(TAG, "Handling broadcast result for action " + intent.getAction() 11569a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler + ": canceled: " + getResultCode()); 11669a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler } 1177299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn return; 1187299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 1197299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 12062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown final int enableFlags = intent.getIntExtra("enableFlags", 0); 12162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown final int disableFlags = intent.getIntExtra("disableFlags", 0); 122b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn synchronized (mLock) { 12362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown updateAfterBroadcastLocked(intent.getAction(), enableFlags, disableFlags); 1247299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 1257299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 1267299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn }; 1277299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 1287299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private final BroadcastReceiver mDockModeReceiver = new BroadcastReceiver() { 1297299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn @Override 1307299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn public void onReceive(Context context, Intent intent) { 1317299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn int state = intent.getIntExtra(Intent.EXTRA_DOCK_STATE, 1327299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn Intent.EXTRA_DOCK_STATE_UNDOCKED); 1337299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn updateDockState(state); 1347299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 1357299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn }; 1367299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 137e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood private final BroadcastReceiver mBatteryReceiver = new BroadcastReceiver() { 138e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood @Override 139e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood public void onReceive(Context context, Intent intent) { 140e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood mCharging = (intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, 0) != 0); 141e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood synchronized (mLock) { 142e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood if (mSystemReady) { 143f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn updateLocked(0, 0); 144e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood } 145e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood } 146e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood } 147e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood }; 148e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood 149182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private final TwilightListener mTwilightListener = new TwilightListener() { 15057f4503e1a129d6a648f2378d36a060998a577a0Dianne Hackborn @Override 1512416e09649eb6ab767eba458796e126196c77a34Jeff Brown public void onTwilightStateChanged() { 1522416e09649eb6ab767eba458796e126196c77a34Jeff Brown updateTwilight(); 1537299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 1547299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn }; 1557299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 156182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 157182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public void onStart() { 158182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final Context context = getContext(); 159182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mTwilightManager = getLocalService(TwilightManager.class); 160182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final PowerManager powerManager = 161182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski (PowerManager) context.getSystemService(Context.POWER_SERVICE); 162182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mWakeLock = powerManager.newWakeLock(PowerManager.FULL_WAKE_LOCK, TAG); 163182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 164182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context.registerReceiver(mDockModeReceiver, 1657299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn new IntentFilter(Intent.ACTION_DOCK_EVENT)); 166182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context.registerReceiver(mBatteryReceiver, 167e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood new IntentFilter(Intent.ACTION_BATTERY_CHANGED)); 168e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood 1697299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn mConfiguration.setToDefaults(); 170e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood 17144fcb83b38b062a650ddf556fe7f5e34905df9eaJoe Onorato mDefaultUiModeType = context.getResources().getInteger( 17244fcb83b38b062a650ddf556fe7f5e34905df9eaJoe Onorato com.android.internal.R.integer.config_defaultUiModeType); 173e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood mCarModeKeepsScreenOn = (context.getResources().getInteger( 174e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood com.android.internal.R.integer.config_carDockKeepsScreenOn) == 1); 175e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood mDeskModeKeepsScreenOn = (context.getResources().getInteger( 176e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood com.android.internal.R.integer.config_deskDockKeepsScreenOn) == 1); 1770cf2c8a53350a800055e76c1c9bf0a6d44480768Dianne Hackborn mTelevision = context.getPackageManager().hasSystemFeature( 1780722968c590d814036a67133949d52d0b20ecc0dTim Kilbourn PackageManager.FEATURE_TELEVISION) || 1790722968c590d814036a67133949d52d0b20ecc0dTim Kilbourn context.getPackageManager().hasSystemFeature( 1800722968c590d814036a67133949d52d0b20ecc0dTim Kilbourn PackageManager.FEATURE_LEANBACK); 1816c191299a73388cd593809c0b66bafbd08fd2982John Spurlock mWatch = context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_WATCH); 1820cf2c8a53350a800055e76c1c9bf0a6d44480768Dianne Hackborn 183182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mNightMode = Settings.Secure.getInt(context.getContentResolver(), 1842ccda4dc8d800c3592b4bd4d1d70a064d98dd4feDianne Hackborn Settings.Secure.UI_NIGHT_MODE, UiModeManager.MODE_NIGHT_AUTO); 1852416e09649eb6ab767eba458796e126196c77a34Jeff Brown 186182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mTwilightManager.registerListener(mTwilightListener, mHandler); 187182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 188182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski publishBinderService(Context.UI_MODE_SERVICE, mService); 1897299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 1907299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 191182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski private final IBinder mService = new IUiModeManager.Stub() { 192182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 193182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public void enableCarMode(int flags) { 194182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final long ident = Binder.clearCallingIdentity(); 195182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski try { 196182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski synchronized (mLock) { 1971d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung setCarModeLocked(true, flags); 198182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski if (mSystemReady) { 199182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski updateLocked(flags, 0); 200182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 201487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 202182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } finally { 203182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Binder.restoreCallingIdentity(ident); 204924e164a83056600642a3181f19094b3ecb5262dMike Lockwood } 2057299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 2067299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 207182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 208182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public void disableCarMode(int flags) { 209182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final long ident = Binder.clearCallingIdentity(); 210182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski try { 211182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski synchronized (mLock) { 2121d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung setCarModeLocked(false, 0); 213182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski if (mSystemReady) { 214182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski updateLocked(0, flags); 215182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 216487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 217182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } finally { 218182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Binder.restoreCallingIdentity(ident); 219924e164a83056600642a3181f19094b3ecb5262dMike Lockwood } 2207299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 2217299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 222182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 223182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public int getCurrentModeType() { 224182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final long ident = Binder.clearCallingIdentity(); 225182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski try { 226182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski synchronized (mLock) { 227182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski return mCurUiMode & Configuration.UI_MODE_TYPE_MASK; 228182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 229182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } finally { 230182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Binder.restoreCallingIdentity(ident); 231487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 2327299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 233ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 234182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 235182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public void setNightMode(int mode) { 236182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski switch (mode) { 237182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski case UiModeManager.MODE_NIGHT_NO: 238182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski case UiModeManager.MODE_NIGHT_YES: 239182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski case UiModeManager.MODE_NIGHT_AUTO: 240182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski break; 241182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski default: 242182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski throw new IllegalArgumentException("Unknown mode: " + mode); 243182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 244182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 245182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final long ident = Binder.clearCallingIdentity(); 246182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski try { 247182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski synchronized (mLock) { 248182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski if (isDoingNightModeLocked() && mNightMode != mode) { 249182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Settings.Secure.putInt(getContext().getContentResolver(), 250182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Settings.Secure.UI_NIGHT_MODE, mode); 251182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mNightMode = mode; 252182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski updateLocked(0, 0); 253182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 254182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 255182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } finally { 256182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Binder.restoreCallingIdentity(ident); 257182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 258487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 259ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 260182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 261182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public int getNightMode() { 262487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown synchronized (mLock) { 263182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski return mNightMode; 2647299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 2657299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 266ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 267182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 268182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 269182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski if (getContext().checkCallingOrSelfPermission(android.Manifest.permission.DUMP) 270182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski != PackageManager.PERMISSION_GRANTED) { 271182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 272182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.println("Permission Denial: can't dump uimode service from from pid=" 273182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski + Binder.getCallingPid() 274182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski + ", uid=" + Binder.getCallingUid()); 275182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski return; 276182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 277182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 278182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski dumpImpl(pw); 279182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 280182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski }; 281182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski 282182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski void dumpImpl(PrintWriter pw) { 283487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown synchronized (mLock) { 284182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.println("Current UI Mode Service state:"); 285182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mDockState="); pw.print(mDockState); 286182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mLastBroadcastState="); pw.println(mLastBroadcastState); 287182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mNightMode="); pw.print(mNightMode); 288182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mCarModeEnabled="); pw.print(mCarModeEnabled); 2891d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung pw.print(" mComputedNightMode="); pw.print(mComputedNightMode); 2901d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung pw.print(" mCarModeEnableFlags="); pw.println(mCarModeEnableFlags); 291182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mCurUiMode=0x"); pw.print(Integer.toHexString(mCurUiMode)); 292182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mSetUiMode=0x"); pw.println(Integer.toHexString(mSetUiMode)); 293182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mHoldingConfiguration="); pw.print(mHoldingConfiguration); 294182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mSystemReady="); pw.println(mSystemReady); 295182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.print(" mTwilightService.getCurrentState()="); 296182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski pw.println(mTwilightManager.getCurrentState()); 297487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 2987299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 299ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 300182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski @Override 301182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski public void onBootPhase(int phase) { 302182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski if (phase == SystemService.PHASE_SYSTEM_SERVICES_READY) { 303182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski synchronized (mLock) { 304182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mSystemReady = true; 305182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski mCarModeEnabled = mDockState == Intent.EXTRA_DOCK_STATE_CAR; 306182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski updateComputedNightModeLocked(); 307182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski updateLocked(0, 0); 308182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski } 3097299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3107299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3117299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 312182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski boolean isDoingNightModeLocked() { 3137299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn return mCarModeEnabled || mDockState != Intent.EXTRA_DOCK_STATE_UNDOCKED; 3147299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 315ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 3161d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung void setCarModeLocked(boolean enabled, int flags) { 3177299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mCarModeEnabled != enabled) { 3187299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn mCarModeEnabled = enabled; 3197299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3201d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung mCarModeEnableFlags = flags; 3217299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3227299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 323487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown private void updateDockState(int newState) { 3247299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn synchronized (mLock) { 3257299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (newState != mDockState) { 3267299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn mDockState = newState; 3271d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung setCarModeLocked(mDockState == Intent.EXTRA_DOCK_STATE_CAR, 0); 3287299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mSystemReady) { 329f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn updateLocked(UiModeManager.ENABLE_CAR_MODE_GO_CAR_HOME, 0); 3307299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3317299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3327299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 3337299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 334e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood 335487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown private static boolean isDeskDockState(int state) { 33669a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler switch (state) { 33769a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler case Intent.EXTRA_DOCK_STATE_DESK: 33869a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler case Intent.EXTRA_DOCK_STATE_LE_DESK: 33969a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler case Intent.EXTRA_DOCK_STATE_HE_DESK: 34069a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler return true; 34169a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler default: 34269a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler return false; 34369a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler } 34469a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler } 34569a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler 346487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown private void updateConfigurationLocked() { 3476c191299a73388cd593809c0b66bafbd08fd2982John Spurlock int uiMode = mDefaultUiModeType; 3486c191299a73388cd593809c0b66bafbd08fd2982John Spurlock if (mTelevision) { 3496c191299a73388cd593809c0b66bafbd08fd2982John Spurlock uiMode = Configuration.UI_MODE_TYPE_TELEVISION; 3506c191299a73388cd593809c0b66bafbd08fd2982John Spurlock } else if (mWatch) { 3516c191299a73388cd593809c0b66bafbd08fd2982John Spurlock uiMode = Configuration.UI_MODE_TYPE_WATCH; 3526c191299a73388cd593809c0b66bafbd08fd2982John Spurlock } else if (mCarModeEnabled) { 353b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn uiMode = Configuration.UI_MODE_TYPE_CAR; 35469a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler } else if (isDeskDockState(mDockState)) { 355b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn uiMode = Configuration.UI_MODE_TYPE_DESK; 356b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn } 3579c9c532d3625ba2485eb4ea6924ed0a0163fd958Dianne Hackborn if (mCarModeEnabled) { 358b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn if (mNightMode == UiModeManager.MODE_NIGHT_AUTO) { 3592416e09649eb6ab767eba458796e126196c77a34Jeff Brown updateComputedNightModeLocked(); 360b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn uiMode |= mComputedNightMode ? Configuration.UI_MODE_NIGHT_YES 361b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn : Configuration.UI_MODE_NIGHT_NO; 3627299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } else { 363b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn uiMode |= mNightMode << 4; 3647299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 365b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn } else { 366b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn // Disabling the car mode clears the night mode. 3678daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler uiMode = (uiMode & ~Configuration.UI_MODE_NIGHT_MASK) | Configuration.UI_MODE_NIGHT_NO; 3688daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler } 3698daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler 3708daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler if (LOG) { 371960779d3bbc6f2c767432ce48aca1e12cb0093b7John Spurlock Slog.d(TAG, 372960779d3bbc6f2c767432ce48aca1e12cb0093b7John Spurlock "updateConfigurationLocked: mDockState=" + mDockState 3738daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler + "; mCarMode=" + mCarModeEnabled 3748daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler + "; mNightMode=" + mNightMode 3758daf2a47995b4522bceb38eef8c310268b1d91b0Daniel Sandler + "; uiMode=" + uiMode); 376b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn } 377ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 378b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn mCurUiMode = uiMode; 37962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (!mHoldingConfiguration) { 3802ccda4dc8d800c3592b4bd4d1d70a064d98dd4feDianne Hackborn mConfiguration.uiMode = uiMode; 38162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 38262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 383ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 384487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown private void sendConfigurationLocked() { 38562c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (mSetUiMode != mConfiguration.uiMode) { 38662c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown mSetUiMode = mConfiguration.uiMode; 38762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 38862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown try { 38962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown ActivityManagerNative.getDefault().updateConfiguration(mConfiguration); 39062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } catch (RemoteException e) { 39162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown Slog.w(TAG, "Failure communicating with activity manager", e); 3927299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 393b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn } 394b8b11a0b1d82e24f7a79f2e1672e7f5cf1611a55Dianne Hackborn } 395ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 396182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski void updateLocked(int enableFlags, int disableFlags) { 397487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown String action = null; 398487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown String oldAction = null; 399487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (mLastBroadcastState == Intent.EXTRA_DOCK_STATE_CAR) { 400487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown adjustStatusBarCarModeLocked(); 401487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown oldAction = UiModeManager.ACTION_EXIT_CAR_MODE; 402487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else if (isDeskDockState(mLastBroadcastState)) { 403487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown oldAction = UiModeManager.ACTION_EXIT_DESK_MODE; 404487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 405ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 406487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (mCarModeEnabled) { 407487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (mLastBroadcastState != Intent.EXTRA_DOCK_STATE_CAR) { 408780b2603041a56800ff6e49fb14535c1b1ca8907Tobias Haamel adjustStatusBarCarModeLocked(); 409ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 410487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (oldAction != null) { 411182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski getContext().sendBroadcastAsUser(new Intent(oldAction), UserHandle.ALL); 4127299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 413487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mLastBroadcastState = Intent.EXTRA_DOCK_STATE_CAR; 414487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown action = UiModeManager.ACTION_ENTER_CAR_MODE; 415487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 416487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else if (isDeskDockState(mDockState)) { 417487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (!isDeskDockState(mLastBroadcastState)) { 418487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (oldAction != null) { 419182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski getContext().sendBroadcastAsUser(new Intent(oldAction), UserHandle.ALL); 4207299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 421487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mLastBroadcastState = mDockState; 422487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown action = UiModeManager.ACTION_ENTER_DESK_MODE; 4237299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 424487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else { 425487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mLastBroadcastState = Intent.EXTRA_DOCK_STATE_UNDOCKED; 426487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown action = oldAction; 427487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 428ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 429487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (action != null) { 430487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (LOG) { 431487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown Slog.v(TAG, String.format( 432487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown "updateLocked: preparing broadcast: action=%s enable=0x%08x disable=0x%08x", 433487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown action, enableFlags, disableFlags)); 434487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 43569a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler 436487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // Send the ordered broadcast; the result receiver will receive after all 437487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // broadcasts have been sent. If any broadcast receiver changes the result 438487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // code from the initial value of RESULT_OK, then the result receiver will 439487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // not launch the corresponding dock application. This gives apps a chance 440487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // to override the behavior and stay in their app even when the device is 441487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // placed into a dock. 442487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown Intent intent = new Intent(action); 443487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown intent.putExtra("enableFlags", enableFlags); 444487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown intent.putExtra("disableFlags", disableFlags); 445182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski getContext().sendOrderedBroadcastAsUser(intent, UserHandle.CURRENT, null, 446487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mResultReceiver, null, Activity.RESULT_OK, null, null); 447487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown 448487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // Attempting to make this transition a little more clean, we are going 449487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // to hold off on doing a configuration change until we have finished 450487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // the broadcast and started the home activity. 451487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mHoldingConfiguration = true; 452487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown updateConfigurationLocked(); 453487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else { 454487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown String category = null; 455487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (mCarModeEnabled) { 456487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (ENABLE_LAUNCH_CAR_DOCK_APP 457487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown && (enableFlags & UiModeManager.ENABLE_CAR_MODE_GO_CAR_HOME) != 0) { 458487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown category = Intent.CATEGORY_CAR_DOCK; 459f5c5d22c471f399f215662a8e471bf02b5b6bcfaDianne Hackborn } 460487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else if (isDeskDockState(mDockState)) { 461487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (ENABLE_LAUNCH_DESK_DOCK_APP 462487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown && (enableFlags & UiModeManager.ENABLE_CAR_MODE_GO_CAR_HOME) != 0) { 463487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown category = Intent.CATEGORY_DESK_DOCK; 464487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 465487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else { 466487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if ((disableFlags & UiModeManager.DISABLE_CAR_MODE_GO_HOME) != 0) { 467487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown category = Intent.CATEGORY_HOME; 46869a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler } 469487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 47069a1da4ddec90db501a54f0c4de94e9557aebd2eDaniel Sandler 471487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (LOG) { 472487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown Slog.v(TAG, "updateLocked: null action, mDockState=" 473487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown + mDockState +", category=" + category); 474d49258fed489bcd72a2b2a6ce3a3c38d4b2531e6Dianne Hackborn } 475e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood 476487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown sendConfigurationAndStartDreamOrDockAppLocked(category); 477487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } 478487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown 479487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown // keep screen on when charging and in car mode 480487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown boolean keepScreenOn = mCharging && 4811d0a7ccd007e7ce62588212f76db09d2e593b742keunyoung ((mCarModeEnabled && mCarModeKeepsScreenOn && 482c093bf26456e55c09ed4e61ad36999d07a86be1fkeunyoung (mCarModeEnableFlags & UiModeManager.ENABLE_CAR_MODE_ALLOW_SLEEP) == 0) || 483487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown (mCurUiMode == Configuration.UI_MODE_TYPE_DESK && mDeskModeKeepsScreenOn)); 484487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (keepScreenOn != mWakeLock.isHeld()) { 485487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (keepScreenOn) { 486487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mWakeLock.acquire(); 487487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown } else { 488487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mWakeLock.release(); 489e29db6a2d2ba8d9458c88fe6c6dbb2164462773eMike Lockwood } 4907299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 4917299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 4927299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 49362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown private void updateAfterBroadcastLocked(String action, int enableFlags, int disableFlags) { 49462c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Launch a dock activity 49562c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown String category = null; 49662c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (UiModeManager.ACTION_ENTER_CAR_MODE.equals(action)) { 49762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Only launch car home when car mode is enabled and the caller 49862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // has asked us to switch to it. 49962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (ENABLE_LAUNCH_CAR_DOCK_APP 50062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown && (enableFlags & UiModeManager.ENABLE_CAR_MODE_GO_CAR_HOME) != 0) { 50162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown category = Intent.CATEGORY_CAR_DOCK; 50262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 50362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } else if (UiModeManager.ACTION_ENTER_DESK_MODE.equals(action)) { 50462c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Only launch car home when desk mode is enabled and the caller 50562c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // has asked us to switch to it. Currently re-using the car 50662c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // mode flag since we don't have a formal API for "desk mode". 50762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (ENABLE_LAUNCH_DESK_DOCK_APP 50862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown && (enableFlags & UiModeManager.ENABLE_CAR_MODE_GO_CAR_HOME) != 0) { 50962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown category = Intent.CATEGORY_DESK_DOCK; 51062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 51162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } else { 51262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Launch the standard home app if requested. 51362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if ((disableFlags & UiModeManager.DISABLE_CAR_MODE_GO_HOME) != 0) { 51462c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown category = Intent.CATEGORY_HOME; 51562c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 51662c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 51762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 51862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (LOG) { 51962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown Slog.v(TAG, String.format( 52062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown "Handling broadcast result for action %s: enable=0x%08x, disable=0x%08x, " 52162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown + "category=%s", 52262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown action, enableFlags, disableFlags, category)); 52362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 52462c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 52562c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown sendConfigurationAndStartDreamOrDockAppLocked(category); 52662c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 52762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 52862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown private void sendConfigurationAndStartDreamOrDockAppLocked(String category) { 52962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Update the configuration but don't send it yet. 53062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown mHoldingConfiguration = false; 53162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown updateConfigurationLocked(); 53262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 53362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Start the dock app, if there is one. 53462c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown boolean dockAppStarted = false; 53562c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown if (category != null) { 53662c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Now we are going to be careful about switching the 53762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // configuration and starting the activity -- we need to 53862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // do this in a specific order under control of the 53962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // activity manager, to do it cleanly. So compute the 54062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // new config, but don't set it yet, and let the 54162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // activity manager take care of both the start and config 54262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // change. 54362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown Intent homeIntent = buildHomeIntent(category); 544182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski if (Sandman.shouldStartDockApp(getContext(), homeIntent)) { 54511159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown try { 54611159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown int result = ActivityManagerNative.getDefault().startActivityWithConfig( 547f265ea9d8307282ff1da3915978625a94fc2859eDianne Hackborn null, null, homeIntent, null, null, null, 0, 0, 54811159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown mConfiguration, null, UserHandle.USER_CURRENT); 54911159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown if (result >= ActivityManager.START_SUCCESS) { 55011159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown dockAppStarted = true; 55111159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown } else if (result != ActivityManager.START_INTENT_NOT_RESOLVED) { 55211159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown Slog.e(TAG, "Could not start dock app: " + homeIntent 55311159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown + ", startActivityWithConfig result " + result); 55411159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown } 55511159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown } catch (RemoteException ex) { 55611159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown Slog.e(TAG, "Could not start dock app: " + homeIntent, ex); 55762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 55862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 55962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 56062c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 56162c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // Send the new configuration. 56262c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown sendConfigurationLocked(); 56362c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 56462c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown // If we did not start a dock app, then start dreaming if supported. 56511159e9a785a143c9f3765bdf5a5ccfd77842d7aJeff Brown if (category != null && !dockAppStarted) { 566182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Sandman.startDreamWhenDockedIfAppropriate(getContext()); 56762c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 56862c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown } 56962c82e4d92cc0b856059f905d81885f7808a0e7dJeff Brown 5707299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn private void adjustStatusBarCarModeLocked() { 571182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski final Context context = getContext(); 5727299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mStatusBarManager == null) { 573487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown mStatusBarManager = (StatusBarManager) 574182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context.getSystemService(Context.STATUS_BAR_SERVICE); 5757299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 5767299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 577089de88fc2f08d284cf8031aa33cff06011a4162Joe Onorato // Fear not: StatusBarManagerService manages a list of requests to disable 5787299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // features of the status bar; these are ORed together to form the 5797299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // active disabled list. So if (for example) the device is locked and 5807299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // the status bar should be totally disabled, the calls below will 5817299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn // have no effect until the device is unlocked. 5827299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mStatusBarManager != null) { 5837299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn mStatusBarManager.disable(mCarModeEnabled 5847299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn ? StatusBarManager.DISABLE_NOTIFICATION_TICKER 5857299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn : StatusBarManager.DISABLE_NONE); 5867299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 5877299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 5887299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mNotificationManager == null) { 5897299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn mNotificationManager = (NotificationManager) 590182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context.getSystemService(Context.NOTIFICATION_SERVICE); 5917299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 5927299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 5937299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mNotificationManager != null) { 5947299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn if (mCarModeEnabled) { 595182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski Intent carModeOffIntent = new Intent(context, DisableCarModeActivity.class); 5967299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 5977299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn Notification n = new Notification(); 5987299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn n.icon = R.drawable.stat_notify_car_mode; 5997299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn n.defaults = Notification.DEFAULT_LIGHTS; 6007299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn n.flags = Notification.FLAG_ONGOING_EVENT; 6017299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn n.when = 0; 6027299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn n.setLatestEventInfo( 603182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context, 604182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context.getString(R.string.car_mode_disable_notification_title), 605182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski context.getString(R.string.car_mode_disable_notification_message), 606182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski PendingIntent.getActivityAsUser(context, 0, carModeOffIntent, 0, 60750cdf7c3069eb2cf82acbad73c322b7a5f3af4b1Dianne Hackborn null, UserHandle.CURRENT)); 60850cdf7c3069eb2cf82acbad73c322b7a5f3af4b1Dianne Hackborn mNotificationManager.notifyAsUser(null, 60950cdf7c3069eb2cf82acbad73c322b7a5f3af4b1Dianne Hackborn R.string.car_mode_disable_notification_title, n, UserHandle.ALL); 6107299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } else { 61150cdf7c3069eb2cf82acbad73c322b7a5f3af4b1Dianne Hackborn mNotificationManager.cancelAsUser(null, 61250cdf7c3069eb2cf82acbad73c322b7a5f3af4b1Dianne Hackborn R.string.car_mode_disable_notification_title, UserHandle.ALL); 6137299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 6147299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 6157299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 6167299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 617182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski void updateTwilight() { 6182416e09649eb6ab767eba458796e126196c77a34Jeff Brown synchronized (mLock) { 619487bb6e20b96aa6920e08669a260118a40e604d5Jeff Brown if (isDoingNightModeLocked() && mNightMode == UiModeManager.MODE_NIGHT_AUTO) { 6202416e09649eb6ab767eba458796e126196c77a34Jeff Brown updateComputedNightModeLocked(); 6212416e09649eb6ab767eba458796e126196c77a34Jeff Brown updateLocked(0, 0); 6227299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 6237299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 6242416e09649eb6ab767eba458796e126196c77a34Jeff Brown } 6257299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn 6262416e09649eb6ab767eba458796e126196c77a34Jeff Brown private void updateComputedNightModeLocked() { 627182f73fc4da13a6417e5086ec9ecce80eb8423caAdam Lesinski TwilightState state = mTwilightManager.getCurrentState(); 6282416e09649eb6ab767eba458796e126196c77a34Jeff Brown if (state != null) { 6292416e09649eb6ab767eba458796e126196c77a34Jeff Brown mComputedNightMode = state.isNight(); 6307299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 6317299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn } 632ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 633ba9ab183186cb2ef704759485a8481d5b8c8a650Bernd Holzhey 6347299c41630935a2b106e73e5603579a7747f7535Dianne Hackborn} 635