sysui: refactor for extensibility.

Bug: 28466607
Change-Id: I73b017240d86dd3d1be9f76bad284ef6f3c91c9f
(cherry picked from commit a78c415c79287f5d03086d0ebd9a7d970ac5360c)
diff --git a/packages/SystemUI/res/layout/qs_detail_items.xml b/packages/SystemUI/res/layout/qs_detail_items.xml
index f1a8d63..5ca4857 100644
--- a/packages/SystemUI/res/layout/qs_detail_items.xml
+++ b/packages/SystemUI/res/layout/qs_detail_items.xml
@@ -28,7 +28,8 @@
         android:layout_width="match_parent"
         android:layout_height="match_parent"
         android:orientation="vertical"
-        sysui:itemHeight="@dimen/qs_detail_item_height" />
+        sysui:itemHeight="@dimen/qs_detail_item_height"
+        style="@style/AutoSizingList" />
 
     <LinearLayout
         android:id="@android:id/empty"
diff --git a/packages/SystemUI/res/values/attrs.xml b/packages/SystemUI/res/values/attrs.xml
index 0f24b67..ac04ae5 100644
--- a/packages/SystemUI/res/values/attrs.xml
+++ b/packages/SystemUI/res/values/attrs.xml
@@ -75,6 +75,12 @@
         <attr name="horizontalSpacing" format="dimension" />
     </declare-styleable>
 
+    <declare-styleable name="AutoSizingList">
+        <!-- Whether AutoSizingList will show only as many items as fit on screen and
+             remove extra items instead of scrolling. -->
+        <attr name="enableAutoSizing" format="boolean" />
+    </declare-styleable>
+
     <!-- Theme for icons in the status bar (light/dark). background/fillColor is used for dual tone
          icons like wifi and signal, and singleToneColor is used for icons with only one tone.
          Contract: Pixel with fillColor blended over backgroundColor blended over translucent should
diff --git a/packages/SystemUI/res/values/styles.xml b/packages/SystemUI/res/values/styles.xml
index aeb484f..5d2301c 100644
--- a/packages/SystemUI/res/values/styles.xml
+++ b/packages/SystemUI/res/values/styles.xml
@@ -256,6 +256,9 @@
         <item name="numColumns">3</item>
     </style>
 
+    <style name="AutoSizingList">
+        <item name="enableAutoSizing">true</item>
+    </style>
     <style name="Theme.AlertDialogHost" parent="android:Theme.DeviceDefault">
         <item name="android:windowIsTranslucent">true</item>
         <item name="android:windowBackground">@android:color/transparent</item>
diff --git a/packages/SystemUI/src/com/android/systemui/qs/AutoSizingList.java b/packages/SystemUI/src/com/android/systemui/qs/AutoSizingList.java
index 00e6221..767fd9e 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/AutoSizingList.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/AutoSizingList.java
@@ -37,6 +37,7 @@
 
     private ListAdapter mAdapter;
     private int mCount;
+    private boolean mEnableAutoSizing;
 
     public AutoSizingList(Context context, @Nullable AttributeSet attrs) {
         super(context, attrs);
@@ -44,6 +45,8 @@
         mHandler = new Handler();
         TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.AutoSizingList);
         mItemSize = a.getDimensionPixelSize(R.styleable.AutoSizingList_itemHeight, 0);
+        mEnableAutoSizing = a.getBoolean(R.styleable.AutoSizingList_enableAutoSizing, true);
+        a.recycle();
     }
 
     public void setAdapter(ListAdapter adapter) {
@@ -60,7 +63,7 @@
     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
         int requestedHeight = MeasureSpec.getSize(heightMeasureSpec);
         if (requestedHeight != 0) {
-            int count = Math.min(requestedHeight / mItemSize, getDesiredCount());
+            int count = getItemCount(requestedHeight);
             if (mCount != count) {
                 postRebindChildren();
                 mCount = count;
@@ -69,6 +72,12 @@
         super.onMeasure(widthMeasureSpec, heightMeasureSpec);
     }
 
+    private int getItemCount(int requestedHeight) {
+        int desiredCount = getDesiredCount();
+        return mEnableAutoSizing ? Math.min(requestedHeight / mItemSize, desiredCount)
+                : desiredCount;
+    }
+
     private int getDesiredCount() {
         return mAdapter != null ? mAdapter.getCount() : 0;
     }
diff --git a/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java b/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java
index f4b4968..db535d8 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java
@@ -54,7 +54,7 @@
 
     protected View mQsDetailHeader;
     protected TextView mQsDetailHeaderTitle;
-    private Switch mQsDetailHeaderSwitch;
+    protected Switch mQsDetailHeaderSwitch;
     private ImageView mQsDetailHeaderProgress;
 
     protected QSTileHost mHost;
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java
index 99eae02..c485a9e 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java
@@ -40,6 +40,8 @@
  */
 public class UserDetailItemView extends LinearLayout {
 
+    protected static int layoutResId = R.layout.qs_user_detail_item;
+
     private UserAvatarView mAvatar;
     private TextView mName;
     private Typeface mRegularTypeface;
@@ -83,7 +85,7 @@
             ViewGroup root) {
         if (!(convertView instanceof UserDetailItemView)) {
             convertView = LayoutInflater.from(context).inflate(
-                    R.layout.qs_user_detail_item, root, false);
+                    layoutResId, root, false);
         }
         return (UserDetailItemView) convertView;
     }
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java
index d4fa765..cd09231c 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java
@@ -34,7 +34,7 @@
  */
 public class UserDetailView extends PseudoGridView {
 
-    private Adapter mAdapter;
+    protected Adapter mAdapter;
 
     public UserDetailView(Context context, AttributeSet attrs) {
         super(context, attrs);
@@ -58,7 +58,7 @@
             implements OnClickListener {
 
         private final Context mContext;
-        private final UserSwitcherController mController;
+        protected UserSwitcherController mController;
 
         public Adapter(Context context, UserSwitcherController controller) {
             super(controller);
@@ -69,6 +69,11 @@
         @Override
         public View getView(int position, View convertView, ViewGroup parent) {
             UserSwitcherController.UserRecord item = getItem(position);
+            return createUserDetailItemView(convertView, parent, item);
+        }
+
+        public UserDetailItemView createUserDetailItemView(View convertView, ViewGroup parent,
+                UserSwitcherController.UserRecord item) {
             UserDetailItemView v = UserDetailItemView.convertOrInflate(
                     mContext, convertView, parent);
             if (v != convertView) {
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/MultiUserSwitch.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/MultiUserSwitch.java
index 0186d34..0de06c9 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/MultiUserSwitch.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/MultiUserSwitch.java
@@ -32,6 +32,7 @@
 
 import com.android.systemui.R;
 import com.android.systemui.qs.QSPanel;
+import com.android.systemui.qs.QSTile;
 import com.android.systemui.statusbar.policy.KeyguardUserSwitcher;
 import com.android.systemui.statusbar.policy.UserSwitcherController;
 
@@ -40,7 +41,7 @@
  */
 public class MultiUserSwitch extends FrameLayout implements View.OnClickListener {
 
-    private QSPanel mQsPanel;
+    protected QSPanel mQsPanel;
     private KeyguardUserSwitcher mKeyguardUserSwitcher;
     private boolean mKeyguardMode;
     private UserSwitcherController.BaseUserAdapter mUserListener;
@@ -49,7 +50,7 @@
 
     private final int[] mTmpInt2 = new int[2];
 
-    private UserSwitcherController mUserSwitcherController;
+    protected UserSwitcherController mUserSwitcherController;
 
     public MultiUserSwitch(Context context, AttributeSet attrs) {
         super(context, attrs);
@@ -126,7 +127,7 @@
                 mTmpInt2[1] += center.getHeight() / 2;
 
                 mQsPanel.showDetailAdapter(true,
-                        mUserSwitcherController.userDetailAdapter,
+                        getUserDetailAdapter(),
                         mTmpInt2);
             }
         } else {
@@ -182,4 +183,7 @@
         return false;
     }
 
+    protected QSTile.DetailAdapter getUserDetailAdapter() {
+        return mUserSwitcherController.userDetailAdapter;
+    }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
index f439f6a..559b1e7 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
@@ -397,7 +397,7 @@
         mExitGuestDialog.show();
     }
 
-    private void showAddUserDialog() {
+    public void showAddUserDialog() {
         if (mAddUserDialog != null && mAddUserDialog.isShowing()) {
             mAddUserDialog.cancel();
         }