Implement UI for warn-on-launch

Bug: 63909431
Test: atest CtsHarmfulAppWarningHostTestCases
Change-Id: Icabe31f3fb04692bac0313cbeb1cafb64388d5f1
diff --git a/Android.bp b/Android.bp
index 04e1dd6..3c60e94 100644
--- a/Android.bp
+++ b/Android.bp
@@ -592,6 +592,7 @@
         "core/java/android/speech/tts/EventLogTags.logtags",
         "core/java/android/net/EventLogTags.logtags",
         "core/java/android/webkit/EventLogTags.logtags",
+        "core/java/com/android/internal/app/EventLogTags.logtags",
         "core/java/com/android/internal/logging/EventLogTags.logtags",
         "core/java/com/android/server/DropboxLogTags.logtags",
         "core/java/org/chromium/arc/EventLogTags.logtags",
diff --git a/core/java/com/android/internal/app/EventLogTags.logtags b/core/java/com/android/internal/app/EventLogTags.logtags
new file mode 100644
index 0000000..d681a8d
--- /dev/null
+++ b/core/java/com/android/internal/app/EventLogTags.logtags
@@ -0,0 +1,6 @@
+# See system/core/logcat/event.logtags for a description of the format of this file.
+
+option java_package com.android.internal.app;
+
+53000 harmful_app_warning_uninstall (package_name|3)
+53001 harmful_app_warning_launch_anyway (package_name|3)
\ No newline at end of file
diff --git a/core/java/com/android/internal/app/HarmfulAppWarningActivity.java b/core/java/com/android/internal/app/HarmfulAppWarningActivity.java
index 042da36..9966626 100644
--- a/core/java/com/android/internal/app/HarmfulAppWarningActivity.java
+++ b/core/java/com/android/internal/app/HarmfulAppWarningActivity.java
@@ -20,8 +20,12 @@
 import android.content.DialogInterface;
 import android.content.Intent;
 import android.content.IntentSender;
+import android.content.pm.ApplicationInfo;
+import android.content.pm.PackageManager;
 import android.os.Bundle;
 import android.util.Log;
+import android.view.View;
+import android.widget.TextView;
 import com.android.internal.R;
 
 /**
@@ -31,7 +35,7 @@
  */
 public class HarmfulAppWarningActivity extends AlertActivity implements
         DialogInterface.OnClickListener {
-    private static final String TAG = "HarmfulAppWarningActivity";
+    private static final String TAG = HarmfulAppWarningActivity.class.getSimpleName();
 
     private static final String EXTRA_HARMFUL_APP_WARNING = "harmful_app_warning";
 
@@ -39,13 +43,11 @@
     private String mHarmfulAppWarning;
     private IntentSender mTarget;
 
-    // [b/63909431] STOPSHIP replace placeholder UI with final Harmful App Warning UI
-
     @Override
     protected void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
 
-        Intent intent = getIntent();
+        final Intent intent = getIntent();
         mPackageName = intent.getStringExtra(Intent.EXTRA_PACKAGE_NAME);
         mTarget = intent.getParcelableExtra(Intent.EXTRA_INTENT);
         mHarmfulAppWarning = intent.getStringExtra(EXTRA_HARMFUL_APP_WARNING);
@@ -55,33 +57,56 @@
             finish();
         }
 
-        AlertController.AlertParams p = mAlertParams;
+        final ApplicationInfo applicationInfo;
+        try {
+            applicationInfo = getPackageManager().getApplicationInfo(mPackageName, 0 /*flags*/);
+        } catch (PackageManager.NameNotFoundException e) {
+            Log.e(TAG, "Could not show warning because package does not exist ", e);
+            finish();
+            return;
+        }
+
+        final AlertController.AlertParams p = mAlertParams;
         p.mTitle = getString(R.string.harmful_app_warning_title);
-        p.mMessage = mHarmfulAppWarning;
-        p.mPositiveButtonText = getString(R.string.harmful_app_warning_launch_anyway);
+        p.mView = createView(applicationInfo);
+
+        p.mPositiveButtonText = getString(R.string.harmful_app_warning_uninstall);
         p.mPositiveButtonListener = this;
-        p.mNegativeButtonText = getString(R.string.harmful_app_warning_uninstall);
+        p.mNegativeButtonText = getString(R.string.harmful_app_warning_open_anyway);
         p.mNegativeButtonListener = this;
 
         mAlert.installContent(mAlertParams);
     }
 
+    private View createView(ApplicationInfo applicationInfo) {
+        final View view = getLayoutInflater().inflate(R.layout.harmful_app_warning_dialog,
+                null /*root*/);
+        ((TextView) view.findViewById(R.id.app_name_text))
+                .setText(applicationInfo.loadSafeLabel(getPackageManager()));
+        ((TextView) view.findViewById(R.id.message))
+                .setText(mHarmfulAppWarning);
+        return view;
+    }
+
     @Override
     public void onClick(DialogInterface dialog, int which) {
         switch (which) {
             case DialogInterface.BUTTON_POSITIVE:
-                getPackageManager().setHarmfulAppWarning(mPackageName, null);
-
-                IntentSender target = getIntent().getParcelableExtra(Intent.EXTRA_INTENT);
-                try {
-                    startIntentSenderForResult(target, -1, null, 0, 0, 0);
-                } catch (IntentSender.SendIntentException e) {
-                    // ignore..
-                }
+                getPackageManager().deletePackage(mPackageName, null /*observer*/, 0 /*flags*/);
+                EventLogTags.writeHarmfulAppWarningUninstall(mPackageName);
                 finish();
                 break;
             case DialogInterface.BUTTON_NEGATIVE:
-                getPackageManager().deletePackage(mPackageName, null, 0);
+                getPackageManager().setHarmfulAppWarning(mPackageName, null /*warning*/);
+
+                final IntentSender target = getIntent().getParcelableExtra(Intent.EXTRA_INTENT);
+                try {
+                    startIntentSenderForResult(target, -1 /*requestCode*/, null /*fillInIntent*/,
+                            0 /*flagsMask*/, 0 /*flagsValue*/, 0 /*extraFlags*/);
+                } catch (IntentSender.SendIntentException e) {
+                    Log.e(TAG, "Error while starting intent sender", e);
+                }
+                EventLogTags.writeHarmfulAppWarningLaunchAnyway(mPackageName);
                 finish();
                 break;
         }
@@ -89,7 +114,7 @@
 
     public static Intent createHarmfulAppWarningIntent(Context context, String targetPackageName,
             IntentSender target, CharSequence harmfulAppWarning) {
-        Intent intent = new Intent();
+        final Intent intent = new Intent();
         intent.setClass(context, HarmfulAppWarningActivity.class);
         intent.putExtra(Intent.EXTRA_PACKAGE_NAME, targetPackageName);
         intent.putExtra(Intent.EXTRA_INTENT, target);
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index ea791a5..9db8097 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -3958,6 +3958,7 @@
                   android:theme="@style/Theme.DeviceDefault.Light.Dialog.Alert"
                   android:excludeFromRecents="true"
                   android:process=":ui"
+                  android:label="@string/harmful_app_warning_title"
                   android:exported="false">
         </activity>
 
diff --git a/core/res/res/drawable/red_shield.xml b/core/res/res/drawable/red_shield.xml
new file mode 100644
index 0000000..7f425c7
--- /dev/null
+++ b/core/res/res/drawable/red_shield.xml
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="utf-8"?>
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+    android:width="34dp"
+    android:height="37dp"
+    android:viewportWidth="34"
+    android:viewportHeight="37">
+
+    <group
+            android:translateX="-3.000000"
+            android:translateY="-2.000000">
+        <path
+            android:fillType="evenOdd"
+            android:strokeWidth="1"
+            android:pathData="M 0 0 H 40 V 40 H 0 V 0 Z" />
+        <path
+            android:fillColor="#D0021B"
+            android:fillType="evenOdd"
+            android:strokeWidth="1"
+            android:pathData="M35.5858891,6.865 C27.841629,3.02166667 19.6666667,2 19.6666667,2 C19.6666667,2
+11.4917044,3.02166667 3.74744428,6.865 C3.25808614,8.915 3,11.0533333
+3,13.2533333 C3,15.515 3.27484498,17.715 3.79269315,19.8216667
+C4.89374895,24.3033333 7.09753645,28.355 10.1023965,31.6783333
+C12.7385621,34.5983333 15.9964806,36.955 19.6666667,38.5433333
+C23.3368527,36.955 26.5947712,34.5983333 29.2326127,31.6783333
+C32.2357969,28.355 34.4395844,24.3033333 35.5423161,19.8216667
+C36.0584884,17.715 36.3333333,15.515 36.3333333,13.2533333
+C36.3333333,11.0533333 36.0769231,8.915 35.5858891,6.865 M21.3333333,27.8333333
+L18,27.8333333 L18,24.5 L21.3333333,24.5 L21.3333333,27.8333333
+L21.3333333,27.8333333 Z M21.3333333,22 L18,22 L18,12 L21.3333333,12
+L21.3333333,22 L21.3333333,22 Z" />
+    </group>
+</vector>
\ No newline at end of file
diff --git a/core/res/res/layout/harmful_app_warning_dialog.xml b/core/res/res/layout/harmful_app_warning_dialog.xml
new file mode 100644
index 0000000..d41691f
--- /dev/null
+++ b/core/res/res/layout/harmful_app_warning_dialog.xml
@@ -0,0 +1,68 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/**
+ * Copyright (c) 2018, Google Inc.
+ *
+ * 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.
+ */
+-->
+
+<ScrollView
+        xmlns:android="http://schemas.android.com/apk/res/android"
+        xmlns:app="http://schemas.android.com/apk/res-auto"
+        android:layout_width="match_parent"
+        android:layout_height="match_parent"
+        android:fillViewport="true">
+    <LinearLayout
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:paddingTop="@dimen/harmful_app_padding_top"
+            android:orientation="vertical">
+
+        <LinearLayout
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:paddingBottom="@dimen/harmful_app_name_padding_bottom"
+                android:paddingLeft="@dimen/harmful_app_name_padding_left"
+                android:paddingRight="@dimen/harmful_app_name_padding_right"
+                android:paddingTop="@dimen/harmful_app_name_padding_top"
+                android:orientation="horizontal">
+
+            <ImageView
+                    android:layout_width="@dimen/harmful_app_icon_size"
+                    android:layout_height="@dimen/harmful_app_icon_size"
+                    android:scaleType="fitCenter"
+                    android:src="@drawable/red_shield"/>
+
+            <TextView
+                    android:id="@+id/app_name_text"
+                    android:layout_width="wrap_content"
+                    android:layout_height="match_parent"
+                    android:gravity="center_vertical"
+                    android:textColor="@color/primary_text_material_light"
+                    android:textSize="@dimen/text_size_subhead_material"
+                    android:paddingLeft="@dimen/harmful_app_icon_name_padding">
+            </TextView>
+        </LinearLayout>
+
+        <TextView
+                android:id="@+id/message"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:paddingLeft="@dimen/harmful_app_message_padding_left"
+                android:paddingRight="@dimen/harmful_app_message_padding_right"
+                android:paddingBottom="@dimen/harmful_app_message_padding_bottom"
+                android:lineSpacingMultiplier="@dimen/harmful_app_message_line_spacing_modifier"
+                android:textSize="@dimen/text_size_body_1_material"/>
+    </LinearLayout>
+</ScrollView>
\ No newline at end of file
diff --git a/core/res/res/values/dimens.xml b/core/res/res/values/dimens.xml
index 2c824ea0..e6c9879 100644
--- a/core/res/res/values/dimens.xml
+++ b/core/res/res/values/dimens.xml
@@ -635,4 +635,26 @@
     <!-- Size of thumbnail used in the cross profile apps animation -->
     <dimen name="cross_profile_apps_thumbnail_size">72dp</dimen>
 
+    <!-- Padding between the title and content in the harmful app dialog -->
+    <dimen name="harmful_app_padding_top">10dp</dimen>
+    <!-- Bottom padding for the "app name" section of the harmful app dialog -->
+    <dimen name="harmful_app_name_padding_bottom">20dp</dimen>
+    <!-- Left padding for the "app name" section of the harmful app dialog -->
+    <dimen name="harmful_app_name_padding_left">24dp</dimen>
+    <!-- Right padding for the "app name" section of the harmful app dialog -->
+    <dimen name="harmful_app_name_padding_right">24dp</dimen>
+    <!-- Top padding for the "app name" section of the harmful app dialog -->
+    <dimen name="harmful_app_name_padding_top">8dp</dimen>
+    <!-- Padding between the icon and app name in the harmful app dialog -->
+    <dimen name="harmful_app_icon_name_padding">20dp</dimen>
+    <!-- The size of the icon on the harmful app dialog -->
+    <dimen name="harmful_app_icon_size">44dp</dimen>
+    <!-- Left padding for the message section of the harmful app dialog -->
+    <dimen name="harmful_app_message_padding_left">24dp</dimen>
+    <!-- Right padding for the message section of the harmful app dialog -->
+    <dimen name="harmful_app_message_padding_right">24dp</dimen>
+    <!-- Bottom padding for the message section of the harmful app dialog -->
+    <dimen name="harmful_app_message_padding_bottom">24dp</dimen>
+    <!-- Line spacing modifier for the message field of the harmful app dialog -->
+    <item name="harmful_app_message_line_spacing_modifier" type="dimen">1.22</item>
 </resources>
diff --git a/core/res/res/values/strings.xml b/core/res/res/values/strings.xml
index 71e963a..39bc008 100644
--- a/core/res/res/values/strings.xml
+++ b/core/res/res/values/strings.xml
@@ -4820,12 +4820,12 @@
     <!--Battery saver warning. STOPSHIP: Remove it eventually. -->
     <string name="battery_saver_warning_title" translatable="false">Extreme battery saver</string>
 
-    <!-- Label for the uninstall button on the harmful app warning dialog. -->
-    <string name="harmful_app_warning_uninstall">Uninstall</string>
-    <!-- Label for the launch anyway button on the harmful app warning dialog. -->
-    <string name="harmful_app_warning_launch_anyway">Launch anyway</string>
-    <!-- Title for the harmful app warning dialog. -->
-    <string name="harmful_app_warning_title">Uninstall harmful app?</string>
+    <!-- Label for the uninstall button on the harmful app warning dialog. [CHAR LIMIT=20] -->
+    <string name="harmful_app_warning_uninstall">UNINSTALL</string>
+    <!-- Label for the open anyway button on the harmful app warning dialog. [CHAR LIMIT=20] -->
+    <string name="harmful_app_warning_open_anyway">OPEN ANYWAY</string>
+    <!-- Title for the harmful app warning dialog. [CHAR LIMIT=40] -->
+    <string name="harmful_app_warning_title">Harmful app detected</string>
 
     <!-- Text describing a permission request for one app to show another app's
          slices [CHAR LIMIT=NONE] -->
diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml
index ee20873..710e871 100644
--- a/core/res/res/values/symbols.xml
+++ b/core/res/res/values/symbols.xml
@@ -3221,8 +3221,9 @@
   <java-symbol type="string" name="shortcut_disabled_reason_unknown" />
 
   <java-symbol type="string" name="harmful_app_warning_uninstall" />
-  <java-symbol type="string" name="harmful_app_warning_launch_anyway" />
+  <java-symbol type="string" name="harmful_app_warning_open_anyway" />
   <java-symbol type="string" name="harmful_app_warning_title" />
+  <java-symbol type="layout" name="harmful_app_warning_dialog" />
 
   <java-symbol type="string" name="config_defaultAssistantAccessPackage" />