Merge "Migrate license display to HTMLViewer." into lmp-mr1-dev
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index a800b4b..5e10171 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -692,17 +692,6 @@
                 android:value="true" />
         </activity>
 
-        <activity android:name="SettingsSafetyLegalActivity"
-                android:label="@string/settings_safetylegal_activity_title"
-                android:theme="@*android:style/Theme.Material.Light.Dialog.Alert">
-            <intent-filter>
-                <action android:name="android.settings.SAFETY" />
-                <category android:name="android.intent.category.DEFAULT" />
-            </intent-filter>
-            <meta-data android:name="com.android.settings.PRIMARY_PROFILE_CONTROLLED"
-                android:value="true" />
-        </activity>
-
         <activity android:name="Settings$ManageApplicationsActivity"
                 android:label="@string/applications_settings"
                 android:taskAffinity="">
diff --git a/res/xml/device_info_settings.xml b/res/xml/device_info_settings.xml
index 2c47c40..45eda60 100644
--- a/res/xml/device_info_settings.xml
+++ b/res/xml/device_info_settings.xml
@@ -81,12 +81,6 @@
         </PreferenceScreen>
 
         <PreferenceScreen
-                android:key="safetylegal"
-                android:title="@string/settings_safetylegal_title">
-            <intent android:action="android.settings.SAFETY" />
-        </PreferenceScreen>
-
-        <PreferenceScreen
                 android:key="regulatory_info"
                 android:title="@string/regulatory_information">
             <intent android:action="android.settings.SHOW_REGULATORY_INFO" />
diff --git a/src/com/android/settings/SettingsLicenseActivity.java b/src/com/android/settings/SettingsLicenseActivity.java
index 3d66b77..52b48bb 100644
--- a/src/com/android/settings/SettingsLicenseActivity.java
+++ b/src/com/android/settings/SettingsLicenseActivity.java
@@ -16,205 +16,64 @@
 
 package com.android.settings;
 
+import android.app.Activity;
+import android.content.ActivityNotFoundException;
+import android.content.Intent;
+import android.net.Uri;
 import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
 import android.os.SystemProperties;
 import android.text.TextUtils;
 import android.util.Log;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
 import android.widget.Toast;
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.app.ProgressDialog;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnDismissListener;
-import android.content.res.Configuration;
 
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.FileReader;
-import java.io.IOException;
-import java.io.InputStreamReader;
-import java.util.zip.GZIPInputStream;
+import java.io.File;
 
 /**
  * The "dialog" that shows from "License" in the Settings app.
  */
 public class SettingsLicenseActivity extends Activity {
-
     private static final String TAG = "SettingsLicenseActivity";
-    private static final boolean LOGV = false || false;
 
     private static final String DEFAULT_LICENSE_PATH = "/system/etc/NOTICE.html.gz";
     private static final String PROPERTY_LICENSE_PATH = "ro.config.license_path";
 
-    private Handler mHandler;
-    private WebView mWebView;
-    private ProgressDialog mSpinnerDlg;
-    private AlertDialog mTextDlg;
-
-    private class LicenseFileLoader implements Runnable {
-
-        private static final String INNER_TAG = "SettingsLicenseActivity.LicenseFileLoader";
-        public static final int STATUS_OK = 0;
-        public static final int STATUS_NOT_FOUND = 1;
-        public static final int STATUS_READ_ERROR = 2;
-        public static final int STATUS_EMPTY_FILE = 3;
-
-        private String mFileName;
-        private Handler mHandler;
-
-        public LicenseFileLoader(String fileName, Handler handler) {
-            mFileName = fileName;
-            mHandler = handler;
-        }
-
-        public void run() {
-
-            int status = STATUS_OK;
-
-            InputStreamReader inputReader = null;
-            StringBuilder data = new StringBuilder(2048);
-            try {
-                char[] tmp = new char[2048];
-                int numRead;
-                if (mFileName.endsWith(".gz")) {
-                    inputReader = new InputStreamReader(
-                        new GZIPInputStream(new FileInputStream(mFileName)));
-                } else {
-                    inputReader = new FileReader(mFileName);
-                }
-
-                while ((numRead = inputReader.read(tmp)) >= 0) {
-                    data.append(tmp, 0, numRead);
-                }
-            } catch (FileNotFoundException e) {
-                Log.e(INNER_TAG, "License HTML file not found at " + mFileName, e);
-                status = STATUS_NOT_FOUND;
-            } catch (IOException e) {
-                Log.e(INNER_TAG, "Error reading license HTML file at " + mFileName, e);
-                status = STATUS_READ_ERROR;
-            } finally {
-                try {
-                    if (inputReader != null) {
-                        inputReader.close();
-                    }
-                } catch (IOException e) {
-                }
-            }
-
-            if ((status == STATUS_OK) && TextUtils.isEmpty(data)) {
-                Log.e(INNER_TAG, "License HTML is empty (from " + mFileName + ")");
-                status = STATUS_EMPTY_FILE;
-            }
-
-            // Tell the UI thread that we are finished.
-            Message msg = mHandler.obtainMessage(status, null);
-            if (status == STATUS_OK) {
-                msg.obj = data.toString();
-            }
-            mHandler.sendMessage(msg);
-        }
-    }
-
-    public SettingsLicenseActivity() {
-        super();
-        mHandler = null;
-        mWebView = null;
-        mSpinnerDlg = null;
-        mTextDlg = null;
-    }
-
     @Override
     protected void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
 
-        String fileName = SystemProperties.get(PROPERTY_LICENSE_PATH, DEFAULT_LICENSE_PATH);
-        if (TextUtils.isEmpty(fileName)) {
-            Log.e(TAG, "The system property for the license file is empty.");
+        final String path = SystemProperties.get(PROPERTY_LICENSE_PATH, DEFAULT_LICENSE_PATH);
+        if (TextUtils.isEmpty(path)) {
+            Log.e(TAG, "The system property for the license file is empty");
             showErrorAndFinish();
             return;
         }
 
-        // The activity does not have any view itself,
-        // so set it invisible to avoid displaying the title text in the background.
-        setVisible(false);
-
-        mWebView = new WebView(this);
-
-        mHandler = new Handler() {
-
-            @Override
-            public void handleMessage(Message msg) {
-                super.handleMessage(msg);
-
-                if (msg.what == LicenseFileLoader.STATUS_OK) {
-                    String text = (String) msg.obj;
-                    showPageOfText(text);
-                } else {
-                    showErrorAndFinish();
-                }
-            }
-        };
-
-        CharSequence title = getText(R.string.settings_license_activity_title);
-        CharSequence msg = getText(R.string.settings_license_activity_loading);
-
-        ProgressDialog pd = ProgressDialog.show(this, title, msg, true, false);
-        pd.setProgressStyle(ProgressDialog.STYLE_SPINNER);
-        mSpinnerDlg = pd;
-
-        // Start separate thread to do the actual loading.
-        Thread thread = new Thread(new LicenseFileLoader(fileName, mHandler));
-        thread.start();
-    }
-
-    @Override
-    protected void onDestroy() {
-        if (mTextDlg != null && mTextDlg.isShowing()) {
-            mTextDlg.dismiss();
+        final File file = new File(path);
+        if (!file.exists() || file.length() == 0) {
+            Log.e(TAG, "License file " + path + " does not exist");
+            showErrorAndFinish();
+            return;
         }
-        if (mSpinnerDlg != null && mSpinnerDlg.isShowing()) {
-            mSpinnerDlg.dismiss();
+
+        // Kick off external viewer due to WebView security restrictions; we
+        // carefully point it at HTMLViewer, since it offers to decompress
+        // before viewing.
+        final Intent intent = new Intent(Intent.ACTION_VIEW);
+        intent.setDataAndType(Uri.fromFile(file), "text/html");
+        intent.putExtra(Intent.EXTRA_TITLE, getString(R.string.settings_license_activity_title));
+        intent.addCategory(Intent.CATEGORY_DEFAULT);
+        intent.setPackage("com.android.htmlviewer");
+
+        try {
+            startActivity(intent);
+            finish();
+        } catch (ActivityNotFoundException e) {
+            Log.e(TAG, "Failed to find viewer", e);
+            showErrorAndFinish();
         }
-        super.onDestroy();
-    }
-
-    private void showPageOfText(String text) {
-        // Create an AlertDialog to display the WebView in.
-        AlertDialog.Builder builder = new AlertDialog.Builder(SettingsLicenseActivity.this);
-        builder.setCancelable(true)
-               .setView(mWebView)
-               .setTitle(R.string.settings_license_activity_title);
-
-        mTextDlg = builder.create();
-        mTextDlg.setOnDismissListener(new OnDismissListener() {
-
-            public void onDismiss(DialogInterface dlgi) {
-                SettingsLicenseActivity.this.finish();
-            }
-        });
-
-        // Begin the loading.  This will be done in a separate thread in WebView.
-        mWebView.loadDataWithBaseURL(null, text, "text/html", "utf-8", null);
-        mWebView.setWebViewClient(new WebViewClient() {
-            @Override
-            public void onPageFinished(WebView view, String url) {
-                mSpinnerDlg.dismiss();
-                if (SettingsLicenseActivity.this.isResumed()) {
-                    mTextDlg.show();
-                }
-            }
-        });
-
-        mWebView = null;
     }
 
     private void showErrorAndFinish() {
-        mSpinnerDlg.dismiss();
-        mSpinnerDlg = null;
         Toast.makeText(this, R.string.settings_license_activity_unavailable, Toast.LENGTH_LONG)
                 .show();
         finish();
diff --git a/src/com/android/settings/SettingsSafetyLegalActivity.java b/src/com/android/settings/SettingsSafetyLegalActivity.java
deleted file mode 100644
index 368ee1d..0000000
--- a/src/com/android/settings/SettingsSafetyLegalActivity.java
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * Copyright (C) 2009 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.android.settings;
-
-import android.app.AlertDialog;
-import android.content.Context;
-import android.content.res.Configuration;
-import android.os.Build;
-import android.os.Bundle;
-import android.os.SystemProperties;
-import android.telephony.TelephonyManager;
-import android.text.TextUtils;
-import android.view.KeyEvent;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
-import com.android.internal.app.AlertActivity;
-import com.android.internal.app.AlertController;
-import android.content.DialogInterface;
-
-/**
- * The "dialog" that shows from "Safety information" in the Settings app.
- */
-public class SettingsSafetyLegalActivity extends AlertActivity 
-        implements DialogInterface.OnCancelListener, DialogInterface.OnClickListener {
-    private static final String PROPERTY_LSAFETYLEGAL_URL = "ro.url.safetylegal";
-
-    private WebView mWebView;
-
-    private AlertDialog mErrorDialog = null;
-
-    @Override
-    protected void onCreate(Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-
-        String userSafetylegalUrl = SystemProperties.get(PROPERTY_LSAFETYLEGAL_URL);
-
-        final Configuration configuration = getResources().getConfiguration();
-        final String language = configuration.locale.getLanguage();
-        final String country = configuration.locale.getCountry();
-
-        String loc = String.format("locale=%s-%s", language, country);
-
-        userSafetylegalUrl = String.format("%s&%s", userSafetylegalUrl, loc);
-
-        mWebView = new WebView(this);
-
-        // Begin accessing
-        mWebView.getSettings().setJavaScriptEnabled(true);
-        if (savedInstanceState == null) {
-            mWebView.loadUrl(userSafetylegalUrl);
-        } else {
-            mWebView.restoreState(savedInstanceState);
-        }
-        mWebView.setWebViewClient(new WebViewClient() {
-            @Override
-            public void onPageFinished(WebView view, String url) {
-                // Change from 'Loading...' to the real title
-                mAlert.setTitle(getString(R.string.settings_safetylegal_activity_title));
-            }
-
-            @Override
-            public void onReceivedError(WebView view, int errorCode,
-                    String description, String failingUrl) {
-                showErrorAndFinish(failingUrl);
-            }
-        });
-
-        final AlertController.AlertParams p = mAlertParams;
-        p.mTitle = getString(R.string.settings_safetylegal_activity_loading);
-        p.mView = mWebView;
-        p.mForceInverseBackground = true;
-        setupAlert();
-    }
-
-    private void showErrorAndFinish(String url) {
-        if (mErrorDialog == null) {
-            mErrorDialog = new AlertDialog.Builder(this)
-                    .setTitle(R.string.settings_safetylegal_activity_title)
-                    .setPositiveButton(android.R.string.ok, this)
-                    .setOnCancelListener(this)
-                    .setCancelable(true)
-                    .create();
-        } else {
-            if (mErrorDialog.isShowing()) {
-                mErrorDialog.dismiss();
-            }
-        }
-        mErrorDialog.setMessage(getResources()
-                .getString(R.string.settings_safetylegal_activity_unreachable, url));
-        mErrorDialog.show();
-    }
-
-    @Override
-    protected void onDestroy() {
-        super.onDestroy();
-
-        if (mErrorDialog != null) {
-            mErrorDialog.dismiss();
-            mErrorDialog = null;
-        }
-    }
-
-    @Override
-    public boolean dispatchKeyEvent(KeyEvent event) {
-        if (event.getKeyCode() == KeyEvent.KEYCODE_BACK 
-                && event.getAction() == KeyEvent.ACTION_DOWN) {
-            if (mWebView.canGoBack()) {
-                mWebView.goBack();
-                return true;
-            }
-        }
-        return super.dispatchKeyEvent(event);
-    }
-
-    public void onClick(DialogInterface dialog, int whichButton) {
-        finish();
-    }
-
-    public void onCancel(DialogInterface dialog) {
-        finish();
-    }
-
-    @Override
-    public void onSaveInstanceState(Bundle icicle) {
-        mWebView.saveState(icicle);
-        super.onSaveInstanceState(icicle);
-    }
-}
diff --git a/src/com/android/settings/TetherSettings.java b/src/com/android/settings/TetherSettings.java
index c611772..230bbb2 100644
--- a/src/com/android/settings/TetherSettings.java
+++ b/src/com/android/settings/TetherSettings.java
@@ -16,11 +16,7 @@
 
 package com.android.settings;
 
-import com.android.settings.wifi.WifiApEnabler;
-import com.android.settings.wifi.WifiApDialog;
-
 import android.app.Activity;
-import android.app.AlertDialog;
 import android.app.Dialog;
 import android.bluetooth.BluetoothAdapter;
 import android.bluetooth.BluetoothPan;
@@ -31,7 +27,6 @@
 import android.content.Intent;
 import android.content.IntentFilter;
 import android.content.pm.PackageManager;
-import android.content.res.AssetManager;
 import android.hardware.usb.UsbManager;
 import android.net.ConnectivityManager;
 import android.net.wifi.WifiConfiguration;
@@ -44,16 +39,13 @@
 import android.preference.Preference;
 import android.preference.PreferenceScreen;
 import android.preference.SwitchPreference;
-import android.text.TextUtils;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-import android.webkit.WebView;
 import android.widget.TextView;
 
-import java.io.InputStream;
+import com.android.settings.wifi.WifiApDialog;
+import com.android.settings.wifi.WifiApEnabler;
+
 import java.util.ArrayList;
 import java.util.concurrent.atomic.AtomicReference;
-import java.util.Locale;
 
 /*
  * Displays preferences for Tethering.
@@ -69,7 +61,6 @@
 
     private static final int DIALOG_AP_SETTINGS = 1;
 
-    private WebView mView;
     private SwitchPreference mUsbTether;
 
     private WifiApEnabler mWifiApEnabler;
@@ -182,8 +173,6 @@
 
         mProvisionApp = getResources().getStringArray(
                 com.android.internal.R.array.config_mobile_hotspot_provision_app);
-
-        mView = new WebView(activity);
     }
 
     @Override