Keyguard slice layout fixes

Fixes a series of line break and text layout issues.
Now we have proper text length limit and ellipsize it
correctly.

Change-Id: Idf915b56ee6ee923ce4f1cc21a0c57ff5d0a99ca
Fixes: 71634498
Fixes: 71599239
Fixes: 71476950
Fixes: 71576197
Test: Visual
diff --git a/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml b/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml
index b154d46..5e09e75 100644
--- a/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml
+++ b/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml
@@ -32,6 +32,8 @@
               android:layout_width="match_parent"
               android:layout_height="wrap_content"
               android:layout_marginBottom="@dimen/widget_vertical_padding"
+              android:paddingStart="64dp"
+              android:paddingEnd="64dp"
               android:theme="@style/TextAppearance.Keyguard"
     />
     <LinearLayout android:id="@+id/row"
diff --git a/packages/SystemUI/res-keyguard/values/dimens.xml b/packages/SystemUI/res-keyguard/values/dimens.xml
index 463af61..04cf6b0 100644
--- a/packages/SystemUI/res-keyguard/values/dimens.xml
+++ b/packages/SystemUI/res-keyguard/values/dimens.xml
@@ -57,7 +57,7 @@
     <dimen name="widget_separator_thickness">2dp</dimen>
     <dimen name="widget_horizontal_padding">8dp</dimen>
     <dimen name="widget_icon_size">16dp</dimen>
-    <dimen name="widget_icon_padding">4dp</dimen>
+    <dimen name="widget_icon_padding">8dp</dimen>
 
     <!-- The y translation to apply at the start in appear animations. -->
     <dimen name="appear_y_translation_start">32dp</dimen>
diff --git a/packages/SystemUI/res-keyguard/values/styles.xml b/packages/SystemUI/res-keyguard/values/styles.xml
index d50bab5..5f52e2a 100644
--- a/packages/SystemUI/res-keyguard/values/styles.xml
+++ b/packages/SystemUI/res-keyguard/values/styles.xml
@@ -83,13 +83,13 @@
         <item name="android:gravity">center</item>
         <item name="android:ellipsize">end</item>
         <item name="android:maxLines">2</item>
+        <item name="android:fontFamily">@*android:string/config_headlineFontFamilyLight</item>
     </style>
 
     <style name="TextAppearance.Keyguard.Secondary">
         <item name="android:layout_width">wrap_content</item>
         <item name="android:layout_height">wrap_content</item>
         <item name="android:textSize">@dimen/widget_label_font_size</item>
-        <item name="android:singleLine">true</item>
     </style>
 
 </resources>
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java
index b8adb6a..8135c61 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java
@@ -26,6 +26,9 @@
 import android.graphics.drawable.Drawable;
 import android.net.Uri;
 import android.provider.Settings;
+import android.text.Layout;
+import android.text.TextUtils;
+import android.text.TextUtils.TruncateAt;
 import android.util.AttributeSet;
 import android.util.Log;
 import android.view.View;
@@ -40,6 +43,7 @@
 import com.android.systemui.keyguard.KeyguardSliceProvider;
 import com.android.systemui.tuner.TunerService;
 
+import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
 import java.util.function.Consumer;
@@ -129,7 +133,20 @@
                     android.app.slice.SliceItem.FORMAT_TEXT,
                     new String[]{android.app.slice.Slice.HINT_TITLE},
                     null /* nonHints */);
-            mTitle.setText(mainTitle.getText());
+            CharSequence title = mainTitle.getText();
+            mTitle.setText(title);
+
+            // Check if we're already ellipsizing the text.
+            // We're going to figure out the best possible line break if not.
+            Layout layout = mTitle.getLayout();
+            if (layout != null){
+                final int lineCount = layout.getLineCount();
+                if (lineCount > 0) {
+                    if (layout.getEllipsisCount(lineCount - 1) == 0) {
+                        mTitle.setText(findBestLineBreak(title));
+                    }
+                }
+            }
         }
 
         mClickActions.clear();
@@ -195,6 +212,46 @@
         mListener.accept(mHasHeader);
     }
 
+    /**
+     * Breaks a string in 2 lines where both have similar character count
+     * but first line is always longer.
+     *
+     * @param charSequence Original text.
+     * @return Optimal string.
+     */
+    private CharSequence findBestLineBreak(CharSequence charSequence) {
+        if (TextUtils.isEmpty(charSequence)) {
+            return charSequence;
+        }
+
+        String source = charSequence.toString();
+        // Ignore if there is only 1 word,
+        // or if line breaks were manually set.
+        if (source.contains("\n") || !source.contains(" ")) {
+            return source;
+        }
+
+        final String[] words = source.split(" ");
+        final StringBuilder optimalString = new StringBuilder(source.length());
+        int current = 0;
+        while (optimalString.length() < source.length() - optimalString.length()) {
+            optimalString.append(words[current]);
+            if (current < words.length - 1) {
+                optimalString.append(" ");
+            }
+            current++;
+        }
+        optimalString.append("\n");
+        for (int i = current; i < words.length; i++) {
+            optimalString.append(words[i]);
+            if (current < words.length - 1) {
+                optimalString.append(" ");
+            }
+        }
+
+        return optimalString.toString();
+    }
+
     public void setDark(float darkAmount) {
         mDarkAmount = darkAmount;
         updateTextColors();
@@ -287,6 +344,9 @@
             setPadding(horizontalPadding, 0, horizontalPadding, 0);
             setCompoundDrawablePadding((int) context.getResources()
                     .getDimension(R.dimen.widget_icon_padding));
+            setMaxWidth(KeyguardSliceView.this.getWidth() / 2);
+            setMaxLines(1);
+            setEllipsize(TruncateAt.END);
         }
 
         public void setHasDivider(boolean hasDivider) {