1 /* 2 * Copyright (C) 2017 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.googlecode.android_scripting.facade; 18 19 import android.app.AlarmManager; 20 import android.app.NotificationManager; 21 import android.app.Service; 22 import android.content.Context; 23 import android.content.Intent; 24 import android.media.AudioManager; 25 import android.os.PowerManager; 26 import android.os.SystemClock; 27 import android.os.UserHandle; 28 import android.provider.Settings; 29 import android.provider.Settings.SettingNotFoundException; 30 import android.telephony.SubscriptionManager; 31 import android.telephony.TelephonyManager; 32 import android.view.WindowManager; 33 34 import com.android.internal.widget.LockPatternUtils; 35 import com.android.internal.widget.LockscreenCredential; 36 37 import com.googlecode.android_scripting.BaseApplication; 38 import com.googlecode.android_scripting.FutureActivityTaskExecutor; 39 import com.googlecode.android_scripting.Log; 40 import com.googlecode.android_scripting.future.FutureActivityTask; 41 import com.googlecode.android_scripting.jsonrpc.RpcReceiver; 42 import com.googlecode.android_scripting.rpc.Rpc; 43 import com.googlecode.android_scripting.rpc.RpcDefault; 44 import com.googlecode.android_scripting.rpc.RpcOptional; 45 import com.googlecode.android_scripting.rpc.RpcParameter; 46 47 /** 48 * Exposes phone settings functionality. 49 * 50 */ 51 public class SettingsFacade extends RpcReceiver { 52 53 private final Service mService; 54 private final AndroidFacade mAndroidFacade; 55 private final AudioManager mAudio; 56 private final PowerManager mPower; 57 private final AlarmManager mAlarm; 58 private final LockPatternUtils mLockPatternUtils; 59 private final NotificationManager mNotificationManager; 60 private final DataUsageController mDataController; 61 private final TelephonyManager mTelephonyManager; 62 63 /** 64 * Creates a new SettingsFacade. 65 * 66 * @param manager is the {@link Context} the APIs will run under 67 */ SettingsFacade(FacadeManager manager)68 public SettingsFacade(FacadeManager manager) { 69 super(manager); 70 mService = manager.getService(); 71 mAndroidFacade = manager.getReceiver(AndroidFacade.class); 72 mAudio = (AudioManager) mService.getSystemService(Context.AUDIO_SERVICE); 73 mPower = (PowerManager) mService.getSystemService(Context.POWER_SERVICE); 74 mAlarm = (AlarmManager) mService.getSystemService(Context.ALARM_SERVICE); 75 mLockPatternUtils = new LockPatternUtils(mService); 76 mNotificationManager = 77 (NotificationManager) mService.getSystemService(Context.NOTIFICATION_SERVICE); 78 if (!mNotificationManager.isNotificationPolicyAccessGranted()) { 79 Intent intent = new Intent(Settings.ACTION_NOTIFICATION_POLICY_ACCESS_SETTINGS); 80 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 81 mService.startActivity(intent); 82 } 83 mDataController = new DataUsageController(mService); 84 mTelephonyManager = 85 (TelephonyManager) mService.getSystemService(Context.TELEPHONY_SERVICE); 86 } 87 88 @Rpc(description = "Sets the screen timeout to this number of seconds.", 89 returns = "The original screen timeout.") setScreenTimeout(@pcParametername = "value") Integer value)90 public Integer setScreenTimeout(@RpcParameter(name = "value") Integer value) { 91 Integer oldValue = getScreenTimeout(); 92 android.provider.Settings.System.putInt(mService.getContentResolver(), 93 android.provider.Settings.System.SCREEN_OFF_TIMEOUT, value * 1000); 94 return oldValue; 95 } 96 97 @Rpc(description = "Returns the current screen timeout in seconds.", 98 returns = "the current screen timeout in seconds.") getScreenTimeout()99 public Integer getScreenTimeout() { 100 try { 101 return android.provider.Settings.System.getInt(mService.getContentResolver(), 102 android.provider.Settings.System.SCREEN_OFF_TIMEOUT) / 1000; 103 } catch (SettingNotFoundException e) { 104 return 0; 105 } 106 } 107 108 @Rpc(description = "Checks the ringer silent mode setting.", 109 returns = "True if ringer silent mode is enabled.") checkRingerSilentMode()110 public Boolean checkRingerSilentMode() { 111 return mAudio.getRingerMode() == AudioManager.RINGER_MODE_SILENT; 112 } 113 114 @Rpc(description = "Toggles ringer silent mode on and off.", 115 returns = "True if ringer silent mode is enabled.") toggleRingerSilentMode( @pcParametername = "enabled") @pcOptional Boolean enabled)116 public Boolean toggleRingerSilentMode( 117 @RpcParameter(name = "enabled") @RpcOptional Boolean enabled) { 118 if (enabled == null) { 119 enabled = !checkRingerSilentMode(); 120 } 121 mAudio.setRingerMode(enabled ? AudioManager.RINGER_MODE_SILENT 122 : AudioManager.RINGER_MODE_NORMAL); 123 return enabled; 124 } 125 126 @Rpc(description = "Set the ringer to a specified mode") setRingerMode(@pcParametername = "mode") Integer mode)127 public void setRingerMode(@RpcParameter(name = "mode") Integer mode) throws Exception { 128 if (AudioManager.isValidRingerMode(mode)) { 129 mAudio.setRingerMode(mode); 130 } else { 131 throw new Exception("Ringer mode " + mode + " does not exist."); 132 } 133 } 134 135 @Rpc(description = "Returns the current ringtone mode.", 136 returns = "An integer representing the current ringer mode") getRingerMode()137 public Integer getRingerMode() { 138 return mAudio.getRingerMode(); 139 } 140 141 @Rpc(description = "Returns the maximum ringer volume.") getMaxRingerVolume()142 public int getMaxRingerVolume() { 143 return mAudio.getStreamMaxVolume(AudioManager.STREAM_RING); 144 } 145 146 @Rpc(description = "Returns the current ringer volume.") getRingerVolume()147 public int getRingerVolume() { 148 return mAudio.getStreamVolume(AudioManager.STREAM_RING); 149 } 150 151 @Rpc(description = "Sets the ringer volume.") setRingerVolume(@pcParametername = "volume") Integer volume)152 public void setRingerVolume(@RpcParameter(name = "volume") Integer volume) { 153 mAudio.setStreamVolume(AudioManager.STREAM_RING, volume, 0); 154 } 155 156 @Rpc(description = "Returns the maximum media volume.") getMaxMediaVolume()157 public int getMaxMediaVolume() { 158 return mAudio.getStreamMaxVolume(AudioManager.STREAM_MUSIC); 159 } 160 161 @Rpc(description = "Returns the current media volume.") getMediaVolume()162 public int getMediaVolume() { 163 return mAudio.getStreamVolume(AudioManager.STREAM_MUSIC); 164 } 165 166 @Rpc(description = "Sets the media volume.") setMediaVolume(@pcParametername = "volume") Integer volume)167 public void setMediaVolume(@RpcParameter(name = "volume") Integer volume) { 168 mAudio.setStreamVolume(AudioManager.STREAM_MUSIC, volume, 0); 169 } 170 171 /** 172 * Sets the voice call volume. 173 * @param volume the volume number to be set for voice call. 174 */ 175 @Rpc(description = "Sets the voice call volume.") setVoiceCallVolume(@pcParametername = "volume") Integer volume)176 public void setVoiceCallVolume(@RpcParameter(name = "volume") Integer volume) { 177 mAudio.setStreamVolume(AudioManager.STREAM_VOICE_CALL, volume, 0); 178 } 179 180 /** 181 * Sets the alarm volume. 182 * @param volume the volume number to be set for alarm. 183 */ 184 @Rpc(description = "Sets the alarm volume.") setAlarmVolume(@pcParametername = "volume") Integer volume)185 public void setAlarmVolume(@RpcParameter(name = "volume") Integer volume) { 186 mAudio.setStreamVolume(AudioManager.STREAM_ALARM, volume, 0); 187 } 188 189 @Rpc(description = "Returns the screen backlight brightness.", 190 returns = "the current screen brightness between 0 and 255") getScreenBrightness()191 public Integer getScreenBrightness() { 192 try { 193 return android.provider.Settings.System.getInt(mService.getContentResolver(), 194 android.provider.Settings.System.SCREEN_BRIGHTNESS); 195 } catch (SettingNotFoundException e) { 196 return 0; 197 } 198 } 199 200 @Rpc(description = "return the system time since boot in nanoseconds") getSystemElapsedRealtimeNanos()201 public long getSystemElapsedRealtimeNanos() { 202 return SystemClock.elapsedRealtimeNanos(); 203 } 204 205 @Rpc(description = "Sets the the screen backlight brightness.", 206 returns = "the original screen brightness.") setScreenBrightness( @pcParametername = "value", description = "brightness value between 0 and 255") Integer value)207 public Integer setScreenBrightness( 208 @RpcParameter(name = "value", description = "brightness value between 0 and 255") Integer value) { 209 if (value < 0) { 210 value = 0; 211 } else if (value > 255) { 212 value = 255; 213 } 214 final int brightness = value; 215 Integer oldValue = getScreenBrightness(); 216 android.provider.Settings.System.putInt(mService.getContentResolver(), 217 android.provider.Settings.System.SCREEN_BRIGHTNESS, brightness); 218 219 FutureActivityTask<Object> task = new FutureActivityTask<Object>() { 220 @Override 221 public void onCreate() { 222 super.onCreate(); 223 WindowManager.LayoutParams lp = getActivity().getWindow().getAttributes(); 224 lp.screenBrightness = brightness * 1.0f / 255; 225 getActivity().getWindow().setAttributes(lp); 226 setResult(null); 227 finish(); 228 } 229 }; 230 231 FutureActivityTaskExecutor taskExecutor = 232 ((BaseApplication) mService.getApplication()).getTaskExecutor(); 233 taskExecutor.execute(task); 234 235 return oldValue; 236 } 237 238 @Rpc(description = "Returns true if the device is in an interactive state.") isDeviceInteractive()239 public Boolean isDeviceInteractive() throws Exception { 240 return mPower.isInteractive(); 241 } 242 243 @Rpc(description = "Issues a request to put the device to sleep after a delay.") goToSleep(Integer delay)244 public void goToSleep(Integer delay) { 245 mPower.goToSleep(SystemClock.uptimeMillis() + delay); 246 } 247 248 @Rpc(description = "Issues a request to put the device to sleep right away.") goToSleepNow()249 public void goToSleepNow() { 250 mPower.goToSleep(SystemClock.uptimeMillis()); 251 } 252 253 @Rpc(description = "Issues a request to wake the device up right away.") wakeUpNow()254 public void wakeUpNow() { 255 mPower.wakeUp(SystemClock.uptimeMillis()); 256 } 257 258 @Rpc(description = "Get Up time of device.", 259 returns = "Long value of device up time in milliseconds.") getDeviceUpTime()260 public long getDeviceUpTime() throws Exception { 261 return SystemClock.elapsedRealtime(); 262 } 263 264 @Rpc(description = "Set a string password to the device.") setDevicePassword(@pcParametername = "password") String password, @RpcParameter(name = "previousPassword") @RpcDefault("") @RpcOptional String previousPassword)265 public void setDevicePassword(@RpcParameter(name = "password") String password, 266 @RpcParameter(name = "previousPassword") 267 @RpcDefault("") 268 @RpcOptional 269 String previousPassword) { 270 // mLockPatternUtils.setLockPatternEnabled(true, UserHandle.myUserId()); 271 mLockPatternUtils.setLockScreenDisabled(false, UserHandle.myUserId()); 272 mLockPatternUtils.setCredentialRequiredToDecrypt(true); 273 mLockPatternUtils.setLockCredential(LockscreenCredential.createPassword(password), 274 LockscreenCredential.createPasswordOrNone(previousPassword), 275 UserHandle.myUserId()); 276 } 277 278 @Rpc(description = "Disable screen lock password on the device. Note that disabling the " + 279 "screen lock while the screen is locked will still require the screen to be " + 280 "unlocked via pressing the back button and swiping up. To get around this, make sure " + 281 "the screen is on/unlocked when calling this method.") disableDevicePassword( @pcParametername = "currentPassword", description = "The current password used to lock the device") @pcDefault"1111") @pcOptional String currentPassword)282 public void disableDevicePassword( 283 @RpcParameter(name = "currentPassword", 284 description = "The current password used to lock the device") 285 @RpcDefault("1111") 286 @RpcOptional String currentPassword) { 287 mLockPatternUtils.setLockCredential(LockscreenCredential.createNone(), 288 LockscreenCredential.createPasswordOrNone(currentPassword), 289 UserHandle.myUserId()); 290 mLockPatternUtils.setLockScreenDisabled(true, UserHandle.myUserId()); 291 } 292 293 @Rpc(description = "Set the system time in epoch.") setTime(Long currentTime)294 public void setTime(Long currentTime) { 295 mAlarm.setTime(currentTime); 296 } 297 298 @Rpc(description = "Set the system time zone.") setTimeZone(@pcParametername = "timeZone") String timeZone)299 public void setTimeZone(@RpcParameter(name = "timeZone") String timeZone) { 300 mAlarm.setTimeZone(timeZone); 301 } 302 303 @Rpc(description = "Show Home Screen") showHomeScreen()304 public void showHomeScreen() { 305 Intent intent = new Intent(Intent.ACTION_MAIN); 306 intent.addCategory(Intent.CATEGORY_HOME); 307 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 308 try { 309 mAndroidFacade.startActivityIntent(intent, false); 310 } catch (RuntimeException e) { 311 Log.d("showHomeScreen RuntimeException" + e); 312 } catch (Exception e){ 313 Log.d("showHomeScreen exception" + e); 314 } 315 } 316 317 @Rpc(description = "Set private DNS mode") setPrivateDnsMode(@pcParametername = "useTls") Boolean useTls, @RpcParameter(name = "hostname") @RpcOptional String hostname)318 public void setPrivateDnsMode(@RpcParameter(name = "useTls") Boolean useTls, 319 @RpcParameter(name = "hostname") @RpcOptional String hostname) { 320 String dnsMode = ConnectivityConstants.PrivateDnsModeOpportunistic; 321 if(useTls == false) dnsMode = ConnectivityConstants.PrivateDnsModeOff; 322 if(hostname != null) dnsMode = ConnectivityConstants.PrivateDnsModeStrict; 323 android.provider.Settings.Global.putString(mService.getContentResolver(), 324 android.provider.Settings.Global.PRIVATE_DNS_MODE, dnsMode); 325 if(hostname != null) 326 android.provider.Settings.Global.putString(mService.getContentResolver(), 327 android.provider.Settings.Global.PRIVATE_DNS_SPECIFIER, hostname); 328 } 329 330 @Rpc(description = "Get private DNS mode", returns = "Private DNS mode setting") getPrivateDnsMode()331 public String getPrivateDnsMode() { 332 return android.provider.Settings.Global.getString(mService.getContentResolver(), 333 android.provider.Settings.Global.PRIVATE_DNS_MODE); 334 } 335 336 @Rpc(description = "Get private DNS specifier", returns = "DNS hostname set in strict mode") getPrivateDnsSpecifier()337 public String getPrivateDnsSpecifier() { 338 if(!getPrivateDnsMode().equals(ConnectivityConstants.PrivateDnsModeStrict)) return null; 339 return android.provider.Settings.Global.getString(mService.getContentResolver(), 340 android.provider.Settings.Global.PRIVATE_DNS_SPECIFIER); 341 } 342 343 /** 344 * Enable or disable mobile data. 345 * @param enabled Enable data: True: Disable data: False. 346 */ 347 @Rpc(description = "Set Mobile Data Enabled.") setMobileDataEnabled(@pcParametername = "enabled") @pcOptional @pcDefaultvalue = "true") Boolean enabled)348 public void setMobileDataEnabled(@RpcParameter(name = "enabled") 349 @RpcOptional @RpcDefault(value = "true") Boolean enabled) { 350 mDataController.setMobileDataEnabled(enabled); 351 } 352 353 /** 354 * Get mobile data usage info for subscription. 355 * @return DataUsageInfo: The Mobile data usage information. 356 */ 357 @Rpc(description = "Get mobile data usage info", returns = "Mobile Data DataUsageInfo") getMobileDataUsageInfo( @pcOptional @pcParametername = "subId") Integer subId)358 public DataUsageController.DataUsageInfo getMobileDataUsageInfo( 359 @RpcOptional @RpcParameter(name = "subId") Integer subId) { 360 if (subId == null) { 361 subId = SubscriptionManager.getDefaultDataSubscriptionId(); 362 } 363 String subscriberId = mTelephonyManager.getSubscriberId(subId); 364 return mDataController.getMobileDataUsageInfoForSubscriber(subscriberId); 365 } 366 367 /** 368 * Get mobile data usage info for for uid. 369 * @return DataUsageInfo: The Mobile data usage information. 370 */ 371 @Rpc(description = "Get mobile data usage info", returns = "Mobile Data DataUsageInfo") getMobileDataUsageInfoForUid( @pcParametername = "uId") Integer uId, @RpcOptional @RpcParameter(name = "subId") Integer subId)372 public DataUsageController.DataUsageInfo getMobileDataUsageInfoForUid( 373 @RpcParameter(name = "uId") Integer uId, 374 @RpcOptional @RpcParameter(name = "subId") Integer subId) { 375 if (subId == null) { 376 subId = SubscriptionManager.getDefaultDataSubscriptionId(); 377 } 378 String subscriberId = mTelephonyManager.getSubscriberId(subId); 379 return mDataController.getMobileDataUsageInfoForUid(uId, subscriberId); 380 } 381 382 /** 383 * Get Wifi data usage info. 384 * @return DataUsageInfo: The Wifi data usage information. 385 */ 386 @Rpc(description = "Get wifi data usage info", returns = "Wifi Data DataUsageInfo") getWifiDataUsageInfo()387 public DataUsageController.DataUsageInfo getWifiDataUsageInfo() { 388 return mDataController.getWifiDataUsageInfo(); 389 } 390 391 @Override shutdown()392 public void shutdown() { 393 // Nothing to do yet. 394 } 395 } 396