diff --git a/samples/ApiDemos/res/layout/device_admin_sample.xml b/samples/ApiDemos/res/layout/device_admin_sample.xml
index 9c2f323ed..23f065ad5 100644
--- a/samples/ApiDemos/res/layout/device_admin_sample.xml
+++ b/samples/ApiDemos/res/layout/device_admin_sample.xml
@@ -140,6 +140,24 @@
+
+
+
+
+
+
+
+
+
diff --git a/samples/ApiDemos/res/values/strings.xml b/samples/ApiDemos/res/values/strings.xml
index 93f145dc1..eb508349a 100644
--- a/samples/ApiDemos/res/values/strings.xml
+++ b/samples/ApiDemos/res/values/strings.xml
@@ -49,7 +49,7 @@
orientation modes. Often you want to set the desired mode in your manifest
instead of programmatically.
Screen Orientation
-
+
App/Activity/Translucent
Example of how you can make an
activity have a translucent background, compositing over
@@ -76,7 +76,7 @@
can resize to adjust for the IME.
Text editor.\n\nTap to show the IME,
which will cause this window to resize as requested.
-
+
App/Activity/Persistent State
Demonstration of persistent activity state with getPreferences(0).edit() and getPreferences(0).
@@ -540,6 +540,8 @@
Minimum Numeric
Minimum Non-Letter
Password History Length
+ Password Expiration Timeout (minutes)
+ Update
Set Password
Password
Reset Password
diff --git a/samples/ApiDemos/res/xml/device_admin_sample.xml b/samples/ApiDemos/res/xml/device_admin_sample.xml
index 7b7551345..432bbcd4d 100644
--- a/samples/ApiDemos/res/xml/device_admin_sample.xml
+++ b/samples/ApiDemos/res/xml/device_admin_sample.xml
@@ -4,9 +4,9 @@
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
-
+
http://www.apache.org/licenses/LICENSE-2.0
-
+
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@@ -23,6 +23,7 @@
+
diff --git a/samples/ApiDemos/src/com/example/android/apis/app/DeviceAdminSample.java b/samples/ApiDemos/src/com/example/android/apis/app/DeviceAdminSample.java
index 59baefc5f..94c0ead88 100644
--- a/samples/ApiDemos/src/com/example/android/apis/app/DeviceAdminSample.java
+++ b/samples/ApiDemos/src/com/example/android/apis/app/DeviceAdminSample.java
@@ -18,6 +18,7 @@ package com.example.android.apis.app;
import com.example.android.apis.R;
+import android.R.menu;
import android.app.Activity;
import android.app.ActivityManager;
import android.app.AlertDialog;
@@ -44,7 +45,9 @@ import android.widget.AdapterView.OnItemSelectedListener;
import java.net.InetSocketAddress;
import java.net.Proxy;
+import java.text.DateFormat;
import java.util.Arrays;
+import java.util.Date;
import java.util.List;
/**
@@ -53,6 +56,11 @@ import java.util.List;
*/
public class DeviceAdminSample extends DeviceAdminReceiver {
+ private static final String TAG = "DeviceAdminSample";
+ private static final long MS_PER_DAY = 86400 * 1000;
+ private static final long MS_PER_HOUR = 3600 * 1000;
+ private static final long MS_PER_MINUTE = 60 * 1000;
+
static SharedPreferences getSamplePreferences(Context context) {
return context.getSharedPreferences(DeviceAdminReceiver.class.getName(), 0);
}
@@ -66,15 +74,16 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
static String PREF_PASSWORD_MINIMUM_SYMBOLS = "password_minimum_symbols";
static String PREF_PASSWORD_MINIMUM_NONLETTER = "password_minimum_nonletter";
static String PREF_PASSWORD_HISTORY_LENGTH = "password_history_length";
+ static String PREF_PASSWORD_EXPIRATION_TIMEOUT = "password_expiration_timeout";
static String PREF_MAX_FAILED_PW = "max_failed_pw";
void showToast(Context context, CharSequence msg) {
- Toast.makeText(context, msg, Toast.LENGTH_SHORT).show();
+ Toast.makeText(context, "Sample Device Admin: " + msg, Toast.LENGTH_SHORT).show();
}
@Override
public void onEnabled(Context context, Intent intent) {
- showToast(context, "Sample Device Admin: enabled");
+ showToast(context, "enabled");
}
@Override
@@ -84,22 +93,43 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
@Override
public void onDisabled(Context context, Intent intent) {
- showToast(context, "Sample Device Admin: disabled");
+ showToast(context, "disabled");
}
@Override
public void onPasswordChanged(Context context, Intent intent) {
- showToast(context, "Sample Device Admin: pw changed");
+ showToast(context, "pw changed");
}
@Override
public void onPasswordFailed(Context context, Intent intent) {
- showToast(context, "Sample Device Admin: pw failed");
+ showToast(context, "pw failed");
}
@Override
public void onPasswordSucceeded(Context context, Intent intent) {
- showToast(context, "Sample Device Admin: pw succeeded");
+ showToast(context, "pw succeeded");
+ }
+
+ static String countdownString(long time) {
+ long days = time / MS_PER_DAY;
+ long hours = (time / MS_PER_HOUR) % 24;
+ long minutes = (time / MS_PER_MINUTE) % 60;
+ return days + "d" + hours + "h" + minutes + "m";
+ }
+
+ @Override
+ public void onPasswordExpiring(Context context, Intent intent) {
+ DevicePolicyManager dpm = (DevicePolicyManager) context.getSystemService(
+ Context.DEVICE_POLICY_SERVICE);
+ long expr = dpm.getPasswordExpiration(new ComponentName(context, DeviceAdminSample.class));
+ long delta = expr - System.currentTimeMillis();
+ boolean expired = delta < 0L;
+ String msg = expired ? "Password expired " : "Password will expire "
+ + countdownString(Math.abs(delta))
+ + (expired ? " ago" : " from now");
+ showToast(context, msg);
+ Log.v(TAG, msg);
}
/**
@@ -112,6 +142,7 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
*/
public static class Controller extends Activity {
static final int RESULT_ENABLE = 1;
+ private static final long MS_PER_MINUTE = 60*1000;
DevicePolicyManager mDPM;
ActivityManager mAM;
@@ -130,6 +161,7 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
DevicePolicyManager.PASSWORD_QUALITY_ALPHANUMERIC,
DevicePolicyManager.PASSWORD_QUALITY_COMPLEX
};
+
Spinner mPasswordQuality;
EditText mPasswordLength;
EditText mPasswordMinimumLetters;
@@ -139,6 +171,7 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
EditText mPasswordMinimumSymbols;
EditText mPasswordMinimumNonLetter;
EditText mPasswordHistoryLength;
+ EditText mPasswordExpirationTimeout;
Button mSetPasswordButton;
EditText mPassword;
@@ -158,6 +191,8 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
EditText mProxyList;
Button mProxyButton;
+ private Button mPasswordExpirationButton;
+
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
@@ -294,6 +329,16 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
}
}
});
+
+ mPasswordExpirationTimeout = (EditText)findViewById(R.id.password_expiration);
+ mPasswordExpirationButton = (Button) findViewById(R.id.update_expiration_button);
+ mPasswordExpirationButton.setOnClickListener(new OnClickListener() {
+ public void onClick(View v) {
+ setPasswordExpiration(
+ Long.parseLong(mPasswordExpirationTimeout.getText().toString()));
+ }
+ });
+
mSetPasswordButton = (Button)findViewById(R.id.set_password);
mSetPasswordButton.setOnClickListener(mSetPasswordListener);
@@ -390,6 +435,7 @@ public class DeviceAdminSample extends DeviceAdminReceiver {
final int pwMinSymbols = prefs.getInt(PREF_PASSWORD_MINIMUM_SYMBOLS, 0);
final int pwMinNonLetter = prefs.getInt(PREF_PASSWORD_MINIMUM_NONLETTER, 0);
final int pwHistoryLength = prefs.getInt(PREF_PASSWORD_HISTORY_LENGTH, 0);
+ final long pwExpirationTimeout = prefs.getLong(PREF_PASSWORD_EXPIRATION_TIMEOUT, 0L);
final int maxFailedPw = prefs.getInt(PREF_MAX_FAILED_PW, 0);
for (int i=0; i