비슷한 문제가 있었지만 텍스트가없고 래핑 된 레이아웃이없는 가운데 드로어 블을 원했습니다. 해결책은 사용자 정의 버튼을 만들고 LEFT, RIGHT, TOP, BOTTOM 외에도 드로어 블을 하나 더 추가하는 것이 었습니다. 드로어 블 배치를 쉽게 수정할 수 있으며 텍스트를 기준으로 원하는 위치에 배치 할 수 있습니다.
CenterDrawableButton.java
public class CenterDrawableButton extends Button {
private Drawable mDrawableCenter;
public CenterDrawableButton(Context context) {
super(context);
init(context, null);
}
public CenterDrawableButton(Context context, AttributeSet attrs) {
super(context, attrs);
init(context, attrs);
}
public CenterDrawableButton(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init(context, attrs);
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
public CenterDrawableButton(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
init(context, attrs);
}
private void init(Context context, AttributeSet attrs){
//if (isInEditMode()) return;
if(attrs!=null){
TypedArray a = context.getTheme().obtainStyledAttributes(
attrs, R.styleable.CenterDrawableButton, 0, 0);
try {
setCenterDrawable(a.getDrawable(R.styleable.CenterDrawableButton_drawableCenter));
} finally {
a.recycle();
}
}
}
public void setCenterDrawable(int center) {
if(center==0){
setCenterDrawable(null);
}else
setCenterDrawable(getContext().getResources().getDrawable(center));
}
public void setCenterDrawable(@Nullable Drawable center) {
int[] state;
state = getDrawableState();
if (center != null) {
center.setState(state);
center.setBounds(0, 0, center.getIntrinsicWidth(), center.getIntrinsicHeight());
center.setCallback(this);
}
mDrawableCenter = center;
invalidate();
requestLayout();
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
if(mDrawableCenter!=null) {
setMeasuredDimension(Math.max(getMeasuredWidth(), mDrawableCenter.getIntrinsicWidth()),
Math.max(getMeasuredHeight(), mDrawableCenter.getIntrinsicHeight()));
}
}
@Override
protected void drawableStateChanged() {
super.drawableStateChanged();
if (mDrawableCenter != null) {
int[] state = getDrawableState();
mDrawableCenter.setState(state);
mDrawableCenter.setBounds(0, 0, mDrawableCenter.getIntrinsicWidth(),
mDrawableCenter.getIntrinsicHeight());
}
invalidate();
}
@Override
protected void onDraw(@NonNull Canvas canvas) {
super.onDraw(canvas);
if (mDrawableCenter != null) {
Rect rect = mDrawableCenter.getBounds();
canvas.save();
canvas.translate(getWidth() / 2 - rect.right / 2, getHeight() / 2 - rect.bottom / 2);
mDrawableCenter.draw(canvas);
canvas.restore();
}
}
}
attrs.xml
<resources>
<attr name="drawableCenter" format="reference"/>
<declare-styleable name="CenterDrawableButton">
<attr name="drawableCenter"/>
</declare-styleable>
</resources>
용법
<com.virtoos.android.view.custom.CenterDrawableButton
android:id="@id/centerDrawableButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:drawableCenter="@android:drawable/ic_menu_info_details"/>