diff --git a/samples/training/device-management-policy/AndroidManifest.xml b/samples/training/device-management-policy/AndroidManifest.xml
new file mode 100644
index 000000000..30c15c45f
--- /dev/null
+++ b/samples/training/device-management-policy/AndroidManifest.xml
@@ -0,0 +1,44 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/samples/training/device-management-policy/_index.html b/samples/training/device-management-policy/_index.html
new file mode 100755
index 000000000..7799330e7
--- /dev/null
+++ b/samples/training/device-management-policy/_index.html
@@ -0,0 +1,3 @@
+
This is a security-aware sample application that demonstrates the enforcement of device administration policies on Android 2.2 or above platforms.
+
+Refer to the Enhancing Security with Device Management Policies class for detail.
diff --git a/samples/training/device-management-policy/res/layout/activity_policy_setup.xml b/samples/training/device-management-policy/res/layout/activity_policy_setup.xml
new file mode 100644
index 000000000..cf36ba094
--- /dev/null
+++ b/samples/training/device-management-policy/res/layout/activity_policy_setup.xml
@@ -0,0 +1,93 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/samples/training/device-management-policy/res/layout/activity_secure.xml b/samples/training/device-management-policy/res/layout/activity_secure.xml
new file mode 100644
index 000000000..779057462
--- /dev/null
+++ b/samples/training/device-management-policy/res/layout/activity_secure.xml
@@ -0,0 +1,26 @@
+
+
+
+
+
diff --git a/samples/training/device-management-policy/res/layout/activity_view_policy.xml b/samples/training/device-management-policy/res/layout/activity_view_policy.xml
new file mode 100644
index 000000000..5a7c21418
--- /dev/null
+++ b/samples/training/device-management-policy/res/layout/activity_view_policy.xml
@@ -0,0 +1,89 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/samples/training/device-management-policy/res/values-v11/arrays.xml b/samples/training/device-management-policy/res/values-v11/arrays.xml
new file mode 100644
index 000000000..45b23c1b7
--- /dev/null
+++ b/samples/training/device-management-policy/res/values-v11/arrays.xml
@@ -0,0 +1,26 @@
+
+
+
+
+
+ - Anything
+ - Something
+ - Numeric
+ - Alphabetic
+ - Alphanumeric
+ - Complex
+
+
diff --git a/samples/training/device-management-policy/res/values-xlarge/dimens.xml b/samples/training/device-management-policy/res/values-xlarge/dimens.xml
new file mode 100644
index 000000000..de75d95e1
--- /dev/null
+++ b/samples/training/device-management-policy/res/values-xlarge/dimens.xml
@@ -0,0 +1,26 @@
+
+
+
+
+ 60dp
+ 100dp
+
+
+ 18sp
+ 24sp
+ 26sp
+
diff --git a/samples/training/device-management-policy/res/values/arrays.xml b/samples/training/device-management-policy/res/values/arrays.xml
new file mode 100644
index 000000000..09f3eac88
--- /dev/null
+++ b/samples/training/device-management-policy/res/values/arrays.xml
@@ -0,0 +1,25 @@
+
+
+
+
+
+ - Anything
+ - Something
+ - Numeric
+ - Alphabetic
+ - Alphanumeric
+
+
\ No newline at end of file
diff --git a/samples/training/device-management-policy/res/values/attrs.xml b/samples/training/device-management-policy/res/values/attrs.xml
new file mode 100644
index 000000000..e781a0cc4
--- /dev/null
+++ b/samples/training/device-management-policy/res/values/attrs.xml
@@ -0,0 +1,50 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/samples/training/device-management-policy/res/values/colors.xml b/samples/training/device-management-policy/res/values/colors.xml
new file mode 100644
index 000000000..8c3bec784
--- /dev/null
+++ b/samples/training/device-management-policy/res/values/colors.xml
@@ -0,0 +1,19 @@
+
+
+
+ #224894
+
diff --git a/samples/training/device-management-policy/res/values/dimens.xml b/samples/training/device-management-policy/res/values/dimens.xml
new file mode 100644
index 000000000..6f84ef6a4
--- /dev/null
+++ b/samples/training/device-management-policy/res/values/dimens.xml
@@ -0,0 +1,26 @@
+
+
+
+
+ 10dp
+ 5dp
+
+
+ 14sp
+ 18sp
+ 20sp
+
diff --git a/samples/training/device-management-policy/res/values/strings.xml b/samples/training/device-management-policy/res/values/strings.xml
new file mode 100644
index 000000000..5a37bd1d5
--- /dev/null
+++ b/samples/training/device-management-policy/res/values/strings.xml
@@ -0,0 +1,43 @@
+
+
+
+ Device Admin Lesson
+ Policy Admin Receiver
+
+
+ Set up device administration policy:
+ Select a password quality
+ Set min. pw. length
+ Set min. pw. uppercase
+ Activate
+ Press button to activate the device administrator
+ Enforce Policy
+ Press button to enforce specified policy.
+ Update Password
+ Current password doesn\'t conform to the policy.\nPress button to update password.
+ Go
+ Current password conforms to policy. Device is protected.\nPress button to access secured content.
+
+
+ Review device administration policy:
+ Password quality:
+ Minimum password length:
+ Minimum password upper case:
+
+ Device is properly secured. Access is granted to secured content
+ Provide a message here explaining why an application needs to become a device administrator.
+
diff --git a/samples/training/device-management-policy/res/xml/device_admin.xml b/samples/training/device-management-policy/res/xml/device_admin.xml
new file mode 100644
index 000000000..af1e66473
--- /dev/null
+++ b/samples/training/device-management-policy/res/xml/device_admin.xml
@@ -0,0 +1,21 @@
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/samples/training/device-management-policy/src/com/example/training/deviceadmin/Policy.java b/samples/training/device-management-policy/src/com/example/training/deviceadmin/Policy.java
new file mode 100644
index 000000000..4cf63f5dc
--- /dev/null
+++ b/samples/training/device-management-policy/src/com/example/training/deviceadmin/Policy.java
@@ -0,0 +1,168 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * 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.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.training.deviceadmin;
+
+import android.app.Activity;
+import android.app.admin.DeviceAdminReceiver;
+import android.app.admin.DevicePolicyManager;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.os.Build;
+
+public class Policy {
+ public static final int REQUEST_ADD_DEVICE_ADMIN = 1;
+
+ private static final String APP_PREF = "APP_PREF";
+ private static final String KEY_PASSWORD_LENGTH = "PW_LENGTH";
+ private static final String KEY_PASSWORD_QUALITY = "PW_QUALITY";
+ private static final String KEY_PASSWORD_MIN_UPPERCASE = "PW_MIN_UPPERCASE";
+
+ // Password quality values. This list must match the list
+ // found in res/values/arrays.xml
+ final static int[] PASSWORD_QUALITY_VALUES = new int[] {
+ DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED,
+ DevicePolicyManager.PASSWORD_QUALITY_SOMETHING,
+ DevicePolicyManager.PASSWORD_QUALITY_NUMERIC,
+ DevicePolicyManager.PASSWORD_QUALITY_ALPHABETIC,
+ DevicePolicyManager.PASSWORD_QUALITY_ALPHANUMERIC,
+ DevicePolicyManager.PASSWORD_QUALITY_COMPLEX
+ };
+
+ private int mPasswordQuality;
+ private int mPasswordLength;
+ private int mPasswordMinUpperCase;
+ private Context mContext;
+ private DevicePolicyManager mDPM;
+ private ComponentName mPolicyAdmin;
+
+ public Policy(Context context) {
+ mContext = context;
+ mPasswordQuality = -1;
+ mPasswordLength = 0;
+ mPasswordMinUpperCase = 0;
+ mDPM = (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE);
+ mPolicyAdmin = new ComponentName(context, PolicyAdmin.class);
+ }
+
+ /**
+ * Saves the policy parameters.
+ *
+ * @param passwordQuality Password quality.
+ * @param passwordLength Password minimum length.
+ * @param passwordUppercase Password minimum number of upper case alphabets.
+ */
+ public void saveToLocal(int passwordQuality, int passwordLength, int passwordMinUppercase) {
+ SharedPreferences.Editor editor =
+ mContext.getSharedPreferences(APP_PREF, Context.MODE_PRIVATE).edit();
+ if (mPasswordQuality != passwordQuality) {
+ editor.putInt(KEY_PASSWORD_QUALITY, passwordQuality);
+ mPasswordQuality = passwordQuality;
+ }
+ if (mPasswordLength != passwordLength) {
+ editor.putInt(KEY_PASSWORD_LENGTH, passwordLength);
+ mPasswordLength = passwordLength;
+ }
+ if (mPasswordMinUpperCase != passwordMinUppercase) {
+ editor.putInt(KEY_PASSWORD_MIN_UPPERCASE, passwordMinUppercase);
+ mPasswordMinUpperCase = passwordMinUppercase;
+ }
+ editor.commit();
+ }
+
+ public void readFromLocal() {
+ SharedPreferences prefs = mContext.getSharedPreferences(APP_PREF, Context.MODE_PRIVATE);
+ mPasswordQuality = prefs.getInt(KEY_PASSWORD_QUALITY, -1);
+ mPasswordLength = prefs.getInt(KEY_PASSWORD_LENGTH, -1);
+ mPasswordMinUpperCase = prefs.getInt(KEY_PASSWORD_MIN_UPPERCASE, -1);
+ }
+
+ /**
+ * Getter for password quality.
+ *
+ * @return
+ */
+ public int getPasswordQuality() { return mPasswordQuality; }
+
+ /**
+ * Getter for password length.
+ *
+ * @return
+ */
+ public int getPasswordLength() { return mPasswordLength; }
+
+ /**
+ * Getter for password minimum upper case alphabets.
+ *
+ * @return
+ */
+ public int getPasswordMinUpperCase() { return mPasswordMinUpperCase; }
+
+ /**
+ * Getter for the policy administrator ComponentName object.
+ *
+ * @return
+ */
+ public ComponentName getPolicyAdmin() { return mPolicyAdmin; }
+
+ /**
+ * Indicates whether the device administrator is currently active.
+ *
+ * @return
+ */
+ public boolean isAdminActive() {
+ return mDPM.isAdminActive(mPolicyAdmin);
+ }
+
+ public boolean isActivePasswordSufficient() {
+ return mDPM.isActivePasswordSufficient();
+ }
+
+ public boolean isDeviceSecured() {
+ return isAdminActive() && isActivePasswordSufficient();
+ }
+
+ /**
+ * Configure policy defined in the object.
+ */
+ public void configurePolicy() {
+ mDPM.setPasswordQuality(mPolicyAdmin, PASSWORD_QUALITY_VALUES[mPasswordQuality]);
+ mDPM.setPasswordMinimumLength(mPolicyAdmin, mPasswordLength);
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
+ mDPM.setPasswordMinimumUpperCase(mPolicyAdmin, mPasswordMinUpperCase);
+ }
+ }
+
+ /**
+ * Through the PolicyAdmin receiver, the app can use this to trap various device
+ * administration events, such as password change, incorrect password entry, etc.
+ *
+ */
+ public static class PolicyAdmin extends DeviceAdminReceiver {
+
+ @Override
+ public void onDisabled(Context context, Intent intent) {
+ // Called when the app is about to be deactivated as a device administrator.
+ // Deletes previously stored password policy.
+ super.onDisabled(context, intent);
+ SharedPreferences prefs = context.getSharedPreferences(APP_PREF, Activity.MODE_PRIVATE);
+ prefs.edit().clear().commit();
+ }
+ }
+}
+
diff --git a/samples/training/device-management-policy/src/com/example/training/deviceadmin/PolicySetupActivity.java b/samples/training/device-management-policy/src/com/example/training/deviceadmin/PolicySetupActivity.java
new file mode 100644
index 000000000..8c7381bf2
--- /dev/null
+++ b/samples/training/device-management-policy/src/com/example/training/deviceadmin/PolicySetupActivity.java
@@ -0,0 +1,275 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * 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.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.training.deviceadmin;
+
+import android.app.Activity;
+import android.app.admin.DevicePolicyManager;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.os.Bundle;
+import android.view.View;
+import android.widget.AdapterView;
+import android.widget.ArrayAdapter;
+import android.widget.Button;
+import android.widget.EditText;
+import android.widget.LinearLayout;
+import android.widget.Spinner;
+import android.widget.TextView;
+
+/**
+ * Main Activity for the sample application.
+ *
+ * The Activity maintains and presents 2 different
+ * screens to the user -- a screen for configuring device administration policy and another screen
+ * for viewing configured policy. When it is detected that the screen-lock password satisfies
+ * the password strength required by the policy, the user is sent to an Activity containing
+ * protected content.
+ */
+public class PolicySetupActivity extends Activity {
+ private static final int REQ_ACTIVATE_DEVICE_ADMIN = 10;
+ private static final String SCREEN_ID_KEY = "LAYOUT_ID";
+
+ private static final String APP_PREF = "APP_PREF";
+ private static final int UNKNOWN_SCREEN_ID = -1;
+
+ // UI controls in policy setup screen.
+ private Spinner mPasswordQualityInputField;
+ private EditText mPasswordLengthInputField;
+ private EditText mPasswordMinUppercaseInputField;
+
+ private Policy mPolicy;
+ private int mCurrentScreenId;
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ mPolicy = new Policy(this);
+ }
+
+ @Override
+ protected void onResume() {
+ super.onResume();
+
+ SharedPreferences prefs = getSharedPreferences(APP_PREF, MODE_PRIVATE);
+ final int savedScreenId = prefs.getInt(SCREEN_ID_KEY, UNKNOWN_SCREEN_ID);
+ if (savedScreenId == UNKNOWN_SCREEN_ID || !mPolicy.isAdminActive()) {
+ setScreenContent(R.layout.activity_policy_setup);
+ } else {
+ setScreenContent(savedScreenId);
+ }
+ }
+
+ private void setScreenContent(final int screenId) {
+ mCurrentScreenId = screenId;
+ setContentView(mCurrentScreenId);
+ getSharedPreferences(APP_PREF, MODE_PRIVATE).edit().putInt(
+ SCREEN_ID_KEY, mCurrentScreenId).commit();
+ switch (mCurrentScreenId) {
+ case R.layout.activity_policy_setup:
+ initPolicySetupScreen();
+ initNavigation();
+ break;
+ case R.layout.activity_view_policy:
+ initViewPolicyScreen();
+ initNavigation();
+ break;
+ }
+ }
+
+ @Override
+ protected void onPause() {
+ super.onPause();
+ if (mCurrentScreenId == R.layout.activity_policy_setup) writePolicy();
+ }
+
+ @Override
+ protected void onActivityResult(int requestCode, int resultCode, Intent data) {
+ if (requestCode == REQ_ACTIVATE_DEVICE_ADMIN && resultCode == RESULT_OK) {
+ // User just activated the application as a device administrator.
+ setScreenContent(mCurrentScreenId);
+ } else {
+ super.onActivityResult(requestCode, resultCode, data);
+ }
+ }
+
+ @Override
+ public void onBackPressed() {
+ if (mCurrentScreenId == R.layout.activity_view_policy) {
+ setScreenContent(R.layout.activity_policy_setup);
+ return;
+ }
+ super.onBackPressed();
+ }
+
+ // Initialize policy set up screen.
+ private void initPolicySetupScreen() {
+ mPasswordQualityInputField = (Spinner) findViewById(R.id.policy_password_quality);
+ mPasswordLengthInputField = (EditText) findViewById(R.id.policy_password_length);
+ mPasswordMinUppercaseInputField = (EditText) findViewById(R.id.policy_password_uppercase);
+ ArrayAdapter adapter = ArrayAdapter.createFromResource(this,
+ R.array.password_types, android.R.layout.simple_spinner_item);
+ adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
+ mPasswordQualityInputField.setAdapter(adapter);
+ mPasswordQualityInputField.setOnItemSelectedListener(
+ new AdapterView.OnItemSelectedListener() {
+ public void onItemSelected(AdapterView> parent, View view, int pos, long id) {
+ LinearLayout passwordMinUppercaseView =
+ (LinearLayout) findViewById(R.id.password_uppercase_view);
+ // The minimum number of upper case field is only applicable for password
+ // qualities: alpha, alphanumeric, or complex.
+ if (pos > 2)
+ passwordMinUppercaseView.setVisibility(View.VISIBLE);
+ else
+ passwordMinUppercaseView.setVisibility(View.GONE);
+ }
+
+ public void onNothingSelected(AdapterView> parent) {}
+ });
+
+ // Read previously saved policy and populate on the UI.
+ mPolicy.readFromLocal();
+ mPasswordQualityInputField.setSelection(mPolicy.getPasswordQuality());
+ if (mPolicy.getPasswordLength() > 0) {
+ mPasswordLengthInputField.setText(String.valueOf(mPolicy.getPasswordLength()));
+ } else {
+ mPasswordLengthInputField.setText("");
+ }
+
+ if (mPolicy.getPasswordMinUpperCase() > 0) {
+ mPasswordMinUppercaseInputField.setText(
+ String.valueOf(mPolicy.getPasswordMinUpperCase()));
+ } else {
+ mPasswordMinUppercaseInputField.setText("");
+ }
+ }
+
+ // Initialize policy viewing screen.
+ private void initViewPolicyScreen() {
+ TextView passwordQualityView = (TextView) findViewById(R.id.policy_password_quality);
+ TextView passwordLengthView = (TextView) findViewById(R.id.policy_password_length);
+
+ // Read previously saved policy and populate on the UI.
+ mPolicy.readFromLocal();
+ int passwordQualitySelection = mPolicy.getPasswordQuality();
+ passwordQualityView.setText(
+ getResources().getStringArray(R.array.password_types)[passwordQualitySelection]);
+ passwordLengthView.setText(String.valueOf(mPolicy.getPasswordLength()));
+ if (passwordQualitySelection > 2) {
+ LinearLayout passwordMinUppercaseView =
+ (LinearLayout) findViewById(R.id.password_uppercase_view);
+ passwordMinUppercaseView.setVisibility(View.VISIBLE);
+ ((TextView) findViewById(R.id.policy_password_uppercase)).setText(
+ String.valueOf(mPolicy.getPasswordMinUpperCase()));
+ }
+ }
+
+ // Set up navigation message and action button.
+ private void initNavigation() {
+ if (!mPolicy.isAdminActive()) {
+ // Activates device administrator.
+ setupNavigation(R.string.setup_message_activate,
+ R.string.setup_action_activate,
+ mActivateButtonListener);
+ } else if (mCurrentScreenId == R.layout.activity_policy_setup) {
+ setupNavigation(R.string.setup_message_set_policy,
+ R.string.setup_action_set_policy,
+ new View.OnClickListener() {
+ public void onClick(View view) {
+ writePolicy();
+ mPolicy.configurePolicy();
+ setScreenContent(R.layout.activity_view_policy);
+ }
+ });
+ }
+ else if (!mPolicy.isActivePasswordSufficient()) {
+ // Launches password set-up screen in Settings.
+ setupNavigation(R.string.setup_message_enforce_policy,
+ R.string.setup_action_enforce_policy,
+ mEnforcePolicyListener);
+ } else {
+ // Grants access to secure content.
+ setupNavigation(R.string.setup_message_go_secured,
+ R.string.setup_action_go_secured,
+ new View.OnClickListener() {
+ public void onClick(View view) {
+ startActivity(new Intent(view.getContext(), SecureActivity.class));
+ }
+ });
+ }
+ }
+
+ private View.OnClickListener mActivateButtonListener = new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ // First, persist the policy. Then, launch intent to trigger the system screen
+ // requesting user to confirm the activation of the device administrator.
+ writePolicy();
+ Intent activateDeviceAdminIntent =
+ new Intent(DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN);
+ activateDeviceAdminIntent.putExtra(DevicePolicyManager.EXTRA_DEVICE_ADMIN,
+ mPolicy.getPolicyAdmin());
+ // It is good practice to include the optional explanation text to explain to
+ // user why the application is requesting to be a device administrator. The system
+ // will display this message on the activation screen.
+ activateDeviceAdminIntent.putExtra(DevicePolicyManager.EXTRA_ADD_EXPLANATION,
+ getResources().getString(R.string.device_admin_activation_message));
+ startActivityForResult(activateDeviceAdminIntent, REQ_ACTIVATE_DEVICE_ADMIN);
+ }
+ };
+
+ private View.OnClickListener mEnforcePolicyListener = new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ writePolicy();
+ // The device administration API does not "fix" the password if it is
+ // determined that the current password does not conform to what is requested
+ // by the policy. The caller is responsible for triggering the password set up
+ // screen via the below intent.
+ Intent intent = new Intent(DevicePolicyManager.ACTION_SET_NEW_PASSWORD);
+ startActivity(intent);
+ }
+ };
+
+ // Setup action button text and listener.
+ private void setupNavigation(int messageResId, int buttonTextResId,
+ View.OnClickListener listener) {
+ TextView setupMessage = (TextView) findViewById(R.id.setup_message);
+ setupMessage.setText(messageResId);
+ Button actionBtn = (Button) findViewById(R.id.setup_action_btn);
+ actionBtn.setText(buttonTextResId);
+ actionBtn.setOnClickListener(listener);
+ }
+
+ // Save policy to shared preferences.
+ private void writePolicy() {
+ int passwordQuality = (int) mPasswordQualityInputField.getSelectedItemId();
+
+ int passwordLength = 0;
+ try {
+ passwordLength = Integer.valueOf(mPasswordLengthInputField.getText().toString());
+ } catch (NumberFormatException nfe) {} // Defaults to 0.
+
+ int passwordMinUppercase = 0;
+ try {
+ passwordMinUppercase =
+ Integer.valueOf(mPasswordMinUppercaseInputField.getText().toString());
+ } catch (NumberFormatException nfe) {} // Defaults to 0.
+
+ mPolicy.saveToLocal(passwordQuality, passwordLength, passwordMinUppercase);
+ }
+}
+
diff --git a/samples/training/device-management-policy/src/com/example/training/deviceadmin/SecureActivity.java b/samples/training/device-management-policy/src/com/example/training/deviceadmin/SecureActivity.java
new file mode 100644
index 000000000..d2ae34c80
--- /dev/null
+++ b/samples/training/device-management-policy/src/com/example/training/deviceadmin/SecureActivity.java
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * 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.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.training.deviceadmin;
+
+import android.app.Activity;
+import android.content.Intent;
+
+public class SecureActivity extends Activity {
+
+ @Override
+ protected void onResume() {
+ super.onResume();
+ // Check to see if the device is properly secured as per the policy. Send user
+ // back to policy set up screen if necessary.
+ Policy policy = new Policy(this);
+ policy.readFromLocal();
+ if (!policy.isDeviceSecured()) {
+ Intent intent = new Intent();
+ intent.setClass(this, PolicySetupActivity.class);
+ intent.setFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP |
+ Intent.FLAG_ACTIVITY_CLEAR_TASK);
+ startActivity(intent);
+ finish();
+ }
+ setContentView(R.layout.activity_secure);
+ }
+}
+