diff options
6 files changed, 112 insertions, 17 deletions
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java index 3258585ad583..ce2d80691270 100644 --- a/core/java/android/app/ActivityThread.java +++ b/core/java/android/app/ActivityThread.java @@ -71,6 +71,7 @@ import android.os.Trace; import android.os.UserHandle; import android.transition.Scene; import android.transition.TransitionManager; +import android.provider.Settings; import android.util.AndroidRuntimeException; import android.util.ArrayMap; import android.util.DisplayMetrics; @@ -110,6 +111,7 @@ import java.io.PrintWriter; import java.lang.ref.WeakReference; import java.net.InetAddress; import java.security.Security; +import java.text.DateFormat; import java.util.ArrayList; import java.util.List; import java.util.Locale; @@ -1103,6 +1105,11 @@ public final class ActivityThread { public void scheduleInstallProvider(ProviderInfo provider) { sendMessage(H.INSTALL_PROVIDER, provider); } + + @Override + public final void updateTimePrefs(boolean is24Hour) { + DateFormat.set24HourTimePref(is24Hour); + } } private class H extends Handler { @@ -1152,6 +1159,7 @@ public final class ActivityThread { public static final int REQUEST_ASSIST_CONTEXT_EXTRAS = 143; public static final int TRANSLUCENT_CONVERSION_COMPLETE = 144; public static final int INSTALL_PROVIDER = 145; + String codeToString(int code) { if (DEBUG_MESSAGES) { switch (code) { @@ -4215,6 +4223,11 @@ public final class ActivityThread { Log.e(TAG, "Unable to setupGraphicsSupport due to missing cache directory"); } } + + + final boolean is24Hr = "24".equals(mCoreSettings.getString(Settings.System.TIME_12_24)); + DateFormat.set24HourTimePref(is24Hr); + /** * For system applications on userdebug/eng builds, log stack * traces of disk and network access to dropbox for analysis. diff --git a/core/java/android/app/ApplicationThreadNative.java b/core/java/android/app/ApplicationThreadNative.java index 20198f9c2034..f1c632e4e727 100644 --- a/core/java/android/app/ApplicationThreadNative.java +++ b/core/java/android/app/ApplicationThreadNative.java @@ -630,6 +630,15 @@ public abstract class ApplicationThreadNative extends Binder reply.writeNoException(); return true; } + + case UPDATE_TIME_PREFS_TRANSACTION: + { + data.enforceInterface(IApplicationThread.descriptor); + byte is24Hour = data.readByte(); + updateTimePrefs(is24Hour == (byte) 1); + reply.writeNoException(); + return true; + } } return super.onTransact(code, data, reply, flags); @@ -1273,4 +1282,13 @@ class ApplicationThreadProxy implements IApplicationThread { mRemote.transact(SCHEDULE_INSTALL_PROVIDER_TRANSACTION, data, null, IBinder.FLAG_ONEWAY); data.recycle(); } + + @Override + public void updateTimePrefs(boolean is24Hour) throws RemoteException { + Parcel data = Parcel.obtain(); + data.writeInterfaceToken(IApplicationThread.descriptor); + data.writeByte(is24Hour ? (byte) 1 : (byte) 0); + mRemote.transact(UPDATE_TIME_PREFS_TRANSACTION, data, null, IBinder.FLAG_ONEWAY); + data.recycle(); + } } diff --git a/core/java/android/app/IApplicationThread.java b/core/java/android/app/IApplicationThread.java index 1ea9d877bca7..ac8ac8fe827f 100644 --- a/core/java/android/app/IApplicationThread.java +++ b/core/java/android/app/IApplicationThread.java @@ -139,6 +139,7 @@ public interface IApplicationThread extends IInterface { throws RemoteException; void setProcessState(int state) throws RemoteException; void scheduleInstallProvider(ProviderInfo provider) throws RemoteException; + void updateTimePrefs(boolean is24Hour) throws RemoteException; String descriptor = "android.app.IApplicationThread"; @@ -192,4 +193,5 @@ public interface IApplicationThread extends IInterface { int SCHEDULE_TRANSLUCENT_CONVERSION_COMPLETE_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+48; int SET_PROCESS_STATE_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+49; int SCHEDULE_INSTALL_PROVIDER_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+50; + int UPDATE_TIME_PREFS_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+51; } diff --git a/core/java/android/content/Intent.java b/core/java/android/content/Intent.java index 3fdb6e722132..f0b7ca80ea18 100644 --- a/core/java/android/content/Intent.java +++ b/core/java/android/content/Intent.java @@ -3334,6 +3334,15 @@ public class Intent implements Parcelable, Cloneable { public static final String EXTRA_SHUTDOWN_USERSPACE_ONLY = "android.intent.extra.SHUTDOWN_USERSPACE_ONLY"; + /** + * Optional boolean extra for {@link #ACTION_TIME_CHANGED} that indicates the + * user has set their time format preferences to the 24 hour format. + * + * @hide for internal use only. + */ + public static final String EXTRA_TIME_PREF_24_HOUR_FORMAT = + "android.intent.extra.TIME_PREF_24_HOUR_FORMAT"; + // --------------------------------------------------------------------- // --------------------------------------------------------------------- // Intent flags (see mFlags variable). diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java index b23ab25fd768..d91086156b9e 100644 --- a/services/core/java/com/android/server/am/ActivityManagerService.java +++ b/services/core/java/com/android/server/am/ActivityManagerService.java @@ -1074,6 +1074,7 @@ public final class ActivityManagerService extends ActivityManagerNative static final int PERSIST_URI_GRANTS_MSG = 38; static final int REQUEST_ALL_PSS_MSG = 39; static final int START_RELATED_USERS_MSG = 40; + static final int UPDATE_TIME = 41; static final int FIRST_ACTIVITY_STACK_MSG = 100; static final int FIRST_BROADCAST_QUEUE_MSG = 200; @@ -1693,6 +1694,21 @@ public final class ActivityManagerService extends ActivityManagerNative } break; } + case UPDATE_TIME: { + synchronized (ActivityManagerService.this) { + for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { + ProcessRecord r = mLruProcesses.get(i); + if (r.thread != null) { + try { + r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); + } catch (RemoteException ex) { + Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); + } + } + } + } + break; + } } } }; @@ -13446,11 +13462,20 @@ public final class ActivityManagerService extends ActivityManagerNative * of all currently running processes. This message will get queued up before the broadcast * happens. */ - if (intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { + if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); } - if (intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { + /* + * If the user set the time, let all running processes know. + */ + if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { + final int is24Hour = intent.getBooleanExtra( + Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; + mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); + } + + if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); } diff --git a/services/core/java/com/android/server/am/CoreSettingsObserver.java b/services/core/java/com/android/server/am/CoreSettingsObserver.java index 10ea67c34465..4c887dd8e9d1 100644 --- a/services/core/java/com/android/server/am/CoreSettingsObserver.java +++ b/services/core/java/com/android/server/am/CoreSettingsObserver.java @@ -37,11 +37,16 @@ final class CoreSettingsObserver extends ContentObserver { private static final String LOG_TAG = CoreSettingsObserver.class.getSimpleName(); // mapping form property name to its type - private static final Map<String, Class<?>> sCoreSettingToTypeMap = new HashMap< + private static final Map<String, Class<?>> sSecureSettingToTypeMap = new HashMap< + String, Class<?>>(); + private static final Map<String, Class<?>> sSystemSettingToTypeMap = new HashMap< String, Class<?>>(); static { - sCoreSettingToTypeMap.put(Settings.Secure.LONG_PRESS_TIMEOUT, int.class); - // add other core settings here... + sSecureSettingToTypeMap.put(Settings.Secure.LONG_PRESS_TIMEOUT, int.class); + // add other secure settings here... + + sSystemSettingToTypeMap.put(Settings.System.TIME_12_24, String.class); + // add other system settings here... } private final Bundle mCoreSettings = new Bundle(); @@ -67,39 +72,62 @@ final class CoreSettingsObserver extends ContentObserver { } private void sendCoreSettings() { - populateCoreSettings(mCoreSettings); + populateSettings(mCoreSettings, sSecureSettingToTypeMap); + populateSettings(mCoreSettings, sSystemSettingToTypeMap); mActivityManagerService.onCoreSettingsChange(mCoreSettings); } private void beginObserveCoreSettings() { - for (String setting : sCoreSettingToTypeMap.keySet()) { + for (String setting : sSecureSettingToTypeMap.keySet()) { Uri uri = Settings.Secure.getUriFor(setting); mActivityManagerService.mContext.getContentResolver().registerContentObserver( uri, false, this); } + + for (String setting : sSystemSettingToTypeMap.keySet()) { + Uri uri = Settings.System.getUriFor(setting); + mActivityManagerService.mContext.getContentResolver().registerContentObserver( + uri, false, this); + } } - private void populateCoreSettings(Bundle snapshot) { + private void populateSettings(Bundle snapshot, Map<String, Class<?>> map) { Context context = mActivityManagerService.mContext; - for (Map.Entry<String, Class<?>> entry : sCoreSettingToTypeMap.entrySet()) { + for (Map.Entry<String, Class<?>> entry : map.entrySet()) { String setting = entry.getKey(); Class<?> type = entry.getValue(); try { if (type == String.class) { - String value = Settings.Secure.getString(context.getContentResolver(), - setting); + final String value; + if (map == sSecureSettingToTypeMap) { + value = Settings.Secure.getString(context.getContentResolver(), setting); + } else { + value = Settings.System.getString(context.getContentResolver(), setting); + } snapshot.putString(setting, value); } else if (type == int.class) { - int value = Settings.Secure.getInt(context.getContentResolver(), - setting); + final int value; + if (map == sSecureSettingToTypeMap) { + value = Settings.Secure.getInt(context.getContentResolver(), setting); + } else { + value = Settings.System.getInt(context.getContentResolver(), setting); + } snapshot.putInt(setting, value); } else if (type == float.class) { - float value = Settings.Secure.getFloat(context.getContentResolver(), - setting); + final float value; + if (map == sSecureSettingToTypeMap) { + value = Settings.Secure.getFloat(context.getContentResolver(), setting); + } else { + value = Settings.System.getFloat(context.getContentResolver(), setting); + } snapshot.putFloat(setting, value); } else if (type == long.class) { - long value = Settings.Secure.getLong(context.getContentResolver(), - setting); + final long value; + if (map == sSecureSettingToTypeMap) { + value = Settings.Secure.getLong(context.getContentResolver(), setting); + } else { + value = Settings.System.getLong(context.getContentResolver(), setting); + } snapshot.putLong(setting, value); } } catch (SettingNotFoundException snfe) { |