Change AlertDialogs to use button groups.
Ditch dumb prototype implementation of ButtonGroup.
Change-Id: I803ef51b0bf4059936ddeb9145ca37ee53cd24b9
diff --git a/api/current.xml b/api/current.xml
index 914dc26..b1f8f45 100644
--- a/api/current.xml
+++ b/api/current.xml
@@ -2235,7 +2235,7 @@
type="int"
transient="false"
volatile="false"
- value="16843601"
+ value="16843602"
static="true"
final="true"
deprecated="not deprecated"
@@ -2246,7 +2246,7 @@
type="int"
transient="false"
volatile="false"
- value="16843600"
+ value="16843601"
static="true"
final="true"
deprecated="not deprecated"
@@ -2257,7 +2257,7 @@
type="int"
transient="false"
volatile="false"
- value="16843602"
+ value="16843603"
static="true"
final="true"
deprecated="not deprecated"
@@ -2374,6 +2374,17 @@
visibility="public"
>
</field>
+<field name="alertDialogButtonGroupStyle"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="16843600"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
<field name="alertDialogStyle"
type="int"
transient="false"
@@ -230694,6 +230705,30 @@
<parameter name="defStyleRes" type="int">
</parameter>
</constructor>
+<method name="dispatchDraw"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="canvas" type="android.graphics.Canvas">
+</parameter>
+</method>
+<method name="getDividerDrawable"
+ return="android.graphics.drawable.Drawable"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
<method name="getShowDividers"
return="int"
abstract="false"
@@ -230705,6 +230740,55 @@
visibility="public"
>
</method>
+<method name="onLayout"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="changed" type="boolean">
+</parameter>
+<parameter name="l" type="int">
+</parameter>
+<parameter name="t" type="int">
+</parameter>
+<parameter name="r" type="int">
+</parameter>
+<parameter name="b" type="int">
+</parameter>
+</method>
+<method name="onMeasure"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="widthMeasureSpec" type="int">
+</parameter>
+<parameter name="heightMeasureSpec" type="int">
+</parameter>
+</method>
+<method name="setDividerDrawable"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="divider" type="android.graphics.drawable.Drawable">
+</parameter>
+</method>
<method name="setShowDividers"
return="void"
abstract="false"
diff --git a/core/java/android/widget/ButtonGroup.java b/core/java/android/widget/ButtonGroup.java
index 5fda408..81647dd 100644
--- a/core/java/android/widget/ButtonGroup.java
+++ b/core/java/android/widget/ButtonGroup.java
@@ -18,14 +18,21 @@
import android.content.Context;
import android.content.res.TypedArray;
+import android.graphics.Canvas;
+import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
+import android.util.Log;
import android.view.View;
import android.view.ViewGroup;
public class ButtonGroup extends LinearLayout {
+ private static final String LOG = "ButtonGroup";
+
private Drawable mDivider;
- private Drawable mButtonBackground;
+ private int mDividerWidth;
+ private int mDividerHeight;
+ private int mButtonBackgroundRes;
private int mShowDividers;
/**
@@ -45,6 +52,8 @@
*/
public static final int SHOW_DIVIDER_END = 4;
+ private final Rect mTempRect = new Rect();
+
public ButtonGroup(Context context) {
this(context, null);
}
@@ -59,11 +68,11 @@
TypedArray a = context.obtainStyledAttributes(attrs,
com.android.internal.R.styleable.ButtonGroup, defStyleRes, 0);
- mDivider = a.getDrawable(com.android.internal.R.styleable.ButtonGroup_divider);
- mButtonBackground = a.getDrawable(
- com.android.internal.R.styleable.ButtonGroup_buttonBackground);
- mShowDividers = a.getInt(com.android.internal.R.styleable.ButtonGroup_showDividers,
- SHOW_DIVIDER_MIDDLE);
+ setDividerDrawable(a.getDrawable(com.android.internal.R.styleable.ButtonGroup_divider));
+ mButtonBackgroundRes = a.getResourceId(
+ com.android.internal.R.styleable.ButtonGroup_buttonBackground, 0);
+ setShowDividers(a.getInt(com.android.internal.R.styleable.ButtonGroup_showDividers,
+ SHOW_DIVIDER_MIDDLE));
a.recycle();
}
@@ -75,6 +84,9 @@
* or {@link #SHOW_DIVIDER_NONE} to show no dividers.
*/
public void setShowDividers(int showDividers) {
+ if (showDividers != mShowDividers) {
+ requestLayout();
+ }
mShowDividers = showDividers;
}
@@ -86,60 +98,148 @@
return mShowDividers;
}
+ /**
+ * Set a drawable to be used as a divider between items.
+ * @param divider Drawable that will divide each item.
+ */
+ public void setDividerDrawable(Drawable divider) {
+ if (divider == mDivider) {
+ return;
+ }
+ mDivider = divider;
+ mDividerWidth = divider.getIntrinsicWidth();
+ mDividerHeight = divider.getIntrinsicHeight();
+ requestLayout();
+ }
+
+ /**
+ * Retrieve the drawable used to draw dividers between items.
+ * @return The divider drawable
+ */
+ public Drawable getDividerDrawable() {
+ return mDivider;
+ }
+
@Override
public void addView(View child, int index, ViewGroup.LayoutParams params) {
- if (!hasDividerBefore(index)) {
- if (((getChildCount() > 0
- && (mShowDividers & SHOW_DIVIDER_MIDDLE) == SHOW_DIVIDER_MIDDLE)
- || (mShowDividers & SHOW_DIVIDER_BEGINNING) == SHOW_DIVIDER_BEGINNING)) {
- super.addView(new DividerView(mContext), index, makeDividerLayoutParams());
- if (index >= 0) {
- index++;
+ if (mButtonBackgroundRes != 0) {
+ // Preserve original padding as we change the background
+ final int paddingLeft = child.getPaddingLeft();
+ final int paddingRight = child.getPaddingRight();
+ final int paddingTop = child.getPaddingTop();
+ final int paddingBottom = child.getPaddingBottom();
+ child.setBackgroundResource(mButtonBackgroundRes);
+ child.setPadding(paddingLeft, paddingTop, paddingRight, paddingBottom);
+ }
+
+ super.addView(child, index, params);
+ }
+
+ @Override
+ public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+ super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+
+ // Add the extra size that dividers contribute.
+ int dividerCount = 0;
+ if ((mShowDividers & SHOW_DIVIDER_MIDDLE) == SHOW_DIVIDER_MIDDLE) {
+ final int childCount = getChildCount();
+ for (int i = 0; i < childCount; i++) {
+ if (getChildAt(i).getVisibility() != GONE) {
+ dividerCount++;
+ }
+ }
+ dividerCount = Math.max(0, dividerCount);
+ }
+ if ((mShowDividers & SHOW_DIVIDER_BEGINNING) == SHOW_DIVIDER_BEGINNING) {
+ dividerCount++;
+ }
+ if ((mShowDividers & SHOW_DIVIDER_END) == SHOW_DIVIDER_END) {
+ dividerCount++;
+ }
+
+ if (getOrientation() == VERTICAL) {
+ final int dividerSize = mDividerHeight * dividerCount;
+ setMeasuredDimension(getMeasuredWidth(),
+ resolveSize(getMeasuredHeight() + dividerSize, heightMeasureSpec));
+ } else {
+ final int dividerSize = mDividerWidth * dividerCount;
+ setMeasuredDimension(resolveSize(getMeasuredWidth() + dividerSize, widthMeasureSpec),
+ getMeasuredHeight());
+ }
+ }
+
+ @Override
+ public void onLayout(boolean changed, int l, int t, int r, int b) {
+ super.onLayout(changed, l, t, r, b);
+
+ final boolean begin = (mShowDividers & SHOW_DIVIDER_BEGINNING) == SHOW_DIVIDER_BEGINNING;
+ final boolean middle = (mShowDividers & SHOW_DIVIDER_MIDDLE) == SHOW_DIVIDER_MIDDLE;
+
+ // Offset children to leave space for dividers.
+ if (getOrientation() == VERTICAL) {
+ int offset = begin ? mDividerHeight : 0;
+ final int childCount = getChildCount();
+ for (int i = 0; i < childCount; i++) {
+ View child = getChildAt(i);
+ child.offsetTopAndBottom(offset);
+ if (middle && child.getVisibility() != GONE) {
+ offset += mDividerHeight;
+ }
+ }
+ } else {
+ int offset = begin ? mDividerWidth : 0;
+ final int childCount = getChildCount();
+ for (int i = 0; i < childCount; i++) {
+ View child = getChildAt(i);
+ child.offsetLeftAndRight(offset);
+ if (middle && child.getVisibility() != GONE) {
+ offset += mDividerWidth;
}
}
}
-
- // Preserve original padding as we change the background
- final int paddingLeft = child.getPaddingLeft();
- final int paddingRight = child.getPaddingRight();
- final int paddingTop = child.getPaddingTop();
- final int paddingBottom = child.getPaddingBottom();
- child.setBackgroundDrawable(mButtonBackground);
- child.setPadding(paddingLeft, paddingTop, paddingRight, paddingBottom);
-
- final boolean isLast = index < 0 || index == getChildCount();
- super.addView(child, index, params);
-
- if (index >= 0) {
- index++;
- }
- if ((isLast && (mShowDividers & SHOW_DIVIDER_END) == SHOW_DIVIDER_END) ||
- ((mShowDividers & SHOW_DIVIDER_MIDDLE) == SHOW_DIVIDER_MIDDLE &&
- !(getChildAt(index) instanceof DividerView))) {
- super.addView(new DividerView(mContext), index, makeDividerLayoutParams());
- }
- }
-
- private boolean hasDividerBefore(int index) {
- if (index == -1) {
- index = getChildCount();
- }
- index--;
- if (index < 0) {
- return false;
- }
- return getChildAt(index) instanceof DividerView;
}
- private LayoutParams makeDividerLayoutParams() {
- return new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.MATCH_PARENT);
- }
+ @Override
+ public void dispatchDraw(Canvas canvas) {
+ final boolean begin = (mShowDividers & SHOW_DIVIDER_BEGINNING) == SHOW_DIVIDER_BEGINNING;
+ final boolean middle = (mShowDividers & SHOW_DIVIDER_MIDDLE) == SHOW_DIVIDER_MIDDLE;
+ final boolean end = (mShowDividers & SHOW_DIVIDER_END) == SHOW_DIVIDER_END;
+ final boolean vertical = getOrientation() == VERTICAL;
- private class DividerView extends ImageView {
- public DividerView(Context context) {
- super(context);
- setImageDrawable(mDivider);
- setScaleType(ImageView.ScaleType.FIT_XY);
+ final Rect bounds = mTempRect;
+ bounds.left = mPaddingLeft;
+ bounds.right = mRight - mLeft - mPaddingRight;
+ bounds.top = mPaddingTop;
+ bounds.bottom = mBottom - mTop - mPaddingBottom;
+
+ if (begin) {
+ if (vertical) {
+ bounds.bottom = bounds.top + mDividerHeight;
+ } else {
+ bounds.right = bounds.left + mDividerWidth;
+ }
+ mDivider.setBounds(bounds);
+ mDivider.draw(canvas);
}
+
+ final int childCount = getChildCount();
+ int i = 0;
+ while (i < childCount) {
+ final View child = getChildAt(i);
+ i++;
+ if ((middle && i < childCount && child.getVisibility() != GONE) || end) {
+ if (vertical) {
+ bounds.top = child.getBottom();
+ bounds.bottom = bounds.top + mDividerHeight;
+ } else {
+ bounds.left = child.getRight();
+ bounds.right = bounds.left + mDividerWidth;
+ }
+ mDivider.setBounds(bounds);
+ mDivider.draw(canvas);
+ }
+ }
+
+ super.dispatchDraw(canvas);
}
}
diff --git a/core/res/res/drawable-hdpi/dialog_divider_horizontal_holo_dark.9.png b/core/res/res/drawable-hdpi/dialog_divider_horizontal_holo_dark.9.png
new file mode 100644
index 0000000..77b0999
--- /dev/null
+++ b/core/res/res/drawable-hdpi/dialog_divider_horizontal_holo_dark.9.png
Binary files differ
diff --git a/core/res/res/drawable-hdpi/dialog_divider_horizontal_holo_light.9.png b/core/res/res/drawable-hdpi/dialog_divider_horizontal_holo_light.9.png
new file mode 100644
index 0000000..3fde76e
--- /dev/null
+++ b/core/res/res/drawable-hdpi/dialog_divider_horizontal_holo_light.9.png
Binary files differ
diff --git a/core/res/res/drawable-mdpi/dialog_divider_horizontal_holo_dark.9.png b/core/res/res/drawable-mdpi/dialog_divider_horizontal_holo_dark.9.png
new file mode 100644
index 0000000..77b0999
--- /dev/null
+++ b/core/res/res/drawable-mdpi/dialog_divider_horizontal_holo_dark.9.png
Binary files differ
diff --git a/core/res/res/drawable-mdpi/dialog_divider_horizontal_holo_light.9.png b/core/res/res/drawable-mdpi/dialog_divider_horizontal_holo_light.9.png
new file mode 100644
index 0000000..3fde76e
--- /dev/null
+++ b/core/res/res/drawable-mdpi/dialog_divider_horizontal_holo_light.9.png
Binary files differ
diff --git a/core/res/res/layout-xlarge/alert_dialog.xml b/core/res/res/layout-xlarge/alert_dialog.xml
index 5291e9d..82b4509 100644
--- a/core/res/res/layout-xlarge/alert_dialog.xml
+++ b/core/res/res/layout-xlarge/alert_dialog.xml
@@ -107,7 +107,8 @@
android:layout_height="wrap_content"
android:minHeight="54dip"
android:orientation="vertical" >
- <LinearLayout
+ <ButtonGroup
+ style="?android:attr/alertDialogButtonGroupStyle"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
@@ -145,6 +146,6 @@
android:layout_height="wrap_content"
android:orientation="horizontal"
android:visibility="gone" />
- </LinearLayout>
+ </ButtonGroup>
</LinearLayout>
</com.android.internal.widget.WeightedLinearLayout>
diff --git a/core/res/res/layout/alert_dialog.xml b/core/res/res/layout/alert_dialog.xml
index 541d84d..3982ed9 100644
--- a/core/res/res/layout/alert_dialog.xml
+++ b/core/res/res/layout/alert_dialog.xml
@@ -106,7 +106,8 @@
android:layout_height="wrap_content"
android:minHeight="54dip"
android:orientation="vertical" >
- <LinearLayout
+ <ButtonGroup
+ style="?android:attr/alertDialogButtonGroupStyle"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
@@ -144,6 +145,6 @@
android:layout_height="wrap_content"
android:orientation="horizontal"
android:visibility="gone" />
- </LinearLayout>
+ </ButtonGroup>
</LinearLayout>
</com.android.internal.widget.WeightedLinearLayout>
diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml
index 578191a..b419a91 100755
--- a/core/res/res/values/attrs.xml
+++ b/core/res/res/values/attrs.xml
@@ -347,6 +347,7 @@
<!-- ============ -->
<eat-comment />
<attr name="alertDialogStyle" format="reference" />
+ <attr name="alertDialogButtonGroupStyle" format="reference" />
<!-- ============ -->
<!-- Panel styles -->
diff --git a/core/res/res/values/public.xml b/core/res/res/values/public.xml
index da068dc..2490c0f 100644
--- a/core/res/res/values/public.xml
+++ b/core/res/res/values/public.xml
@@ -1369,6 +1369,7 @@
<public type="attr" name="textLineHeight" />
<public type="attr" name="dividerVertical" />
<public type="attr" name="buttonGroupStyle" />
+ <public type="attr" name="alertDialogButtonGroupStyle" />
<public type="anim" name="animator_fade_in" />
<public type="anim" name="animator_fade_out" />
diff --git a/core/res/res/values/styles.xml b/core/res/res/values/styles.xml
index 4deb97d..2ecb4d0 100644
--- a/core/res/res/values/styles.xml
+++ b/core/res/res/values/styles.xml
@@ -994,9 +994,8 @@
</style>
<style name="Widget.ButtonGroup">
- <item name="divider">?android:attr/dividerVertical</item>
<item name="buttonBackground">?android:attr/groupButtonBackground</item>
- <item name="showDividers">middle</item>
+ <item name="showDividers"></item>
</style>
<!-- Begin Holo theme styles -->
@@ -1275,6 +1274,12 @@
</style>
<style name="Widget.Holo.ButtonGroup" parent="Widget.ButtonGroup">
+ <item name="divider">?android:attr/dividerVertical</item>
+ <item name="showDividers">middle</item>
+ </style>
+
+ <style name="Widget.Holo.ButtonGroup.AlertDialog">
+ <item name="android:background">@android:drawable/dialog_divider_horizontal_holo_dark</item>
</style>
<style name="Widget.Holo.TextView" parent="Widget.TextView">
@@ -1540,6 +1545,10 @@
<style name="Widget.Holo.Light.ButtonGroup" parent="Widget.Holo.ButtonGroup">
</style>
+ <style name="Widget.Holo.Light.ButtonGroup.AlertDialog">
+ <item name="android:background">@android:drawable/dialog_divider_horizontal_holo_light</item>
+ </style>
+
<style name="Widget.Holo.Light.TextView" parent="Widget.TextView">
</style>
diff --git a/core/res/res/values/themes.xml b/core/res/res/values/themes.xml
index 9dbb1de..06c502b 100644
--- a/core/res/res/values/themes.xml
+++ b/core/res/res/values/themes.xml
@@ -89,7 +89,7 @@
<item name="buttonStyleToggle">@android:style/Widget.Button.Toggle</item>
- <item name="groupButtonBackground">?android:attr/listChoiceBackgroundIndicator</item>
+ <item name="groupButtonBackground">@android:drawable/btn_default</item>
<!-- List attributes -->
<item name="listPreferredItemHeight">64dip</item>
@@ -141,6 +141,7 @@
<item name="alertDialogStyle">@android:style/AlertDialog</item>
<item name="dialogTheme">@android:style/Theme.Dialog</item>
<item name="alertDialogTheme">@android:style/Theme.Dialog.Alert</item>
+ <item name="alertDialogButtonGroupStyle">?android:attr/buttonGroupStyle</item>
<!-- Panel attributes -->
<item name="panelBackground">@android:drawable/menu_background</item>
@@ -743,6 +744,7 @@
<item name="alertDialogStyle">@android:style/AlertDialog.Holo</item>
<item name="dialogTheme">@android:style/Theme.Holo.Dialog</item>
<item name="alertDialogTheme">@android:style/Theme.Holo.Dialog.Alert</item>
+ <item name="alertDialogButtonGroupStyle">@android:style/Widget.Holo.ButtonGroup.AlertDialog</item>
<!-- Panel attributes -->
<item name="panelBackground">@android:drawable/menu_background</item>
@@ -972,6 +974,7 @@
<item name="alertDialogStyle">@android:style/AlertDialog.Holo.Light</item>
<item name="dialogTheme">@android:style/Theme.Holo.Light.Dialog</item>
<item name="alertDialogTheme">@android:style/Theme.Holo.Light.Dialog.Alert</item>
+ <item name="alertDialogButtonGroupStyle">@android:style/Widget.Holo.Light.ButtonGroup.AlertDialog</item>
<!-- Panel attributes -->
<item name="panelBackground">@android:drawable/menu_background</item>