欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Android 含有图片和文字的Button的实现

程序员文章站 2022-07-14 08:58:00
...
  要实现一个同时包含图片和文字的按钮,粗糙一点的做法当然是直接画个含有画像和文字的png做button的背景,但是考虑到文字部分的国际化以及灵活性的话,就必须把图片和文字独立开来了。原生的Button控件是做不到的,方法应该有很多,这里介绍我做法,说白了就是一个父View包裹两个子View,父View选用LinearLayout,子View分别是ImageView和TextView。下面看下主要的实现类:
package net.jackie.xxx.view;

import net.jackie.xxx.pickmeupandroid.R;
import android.content.Context;
import android.view.Gravity;
import android.widget.ImageView;
import android.widget.ImageView.ScaleType;
import android.widget.LinearLayout;
import android.widget.TextView;

/**
 * @author jackie
 *
 */
public class MyImageButton extends LinearLayout {

	private ImageView mButtonImage = null; 
	private TextView mButtonText = null;
	private int textSize = 18;
	
	/**
	 * 
	 * @param context
	 * @param intArray intArray[0] : ImageResourceId; 
	 * intArray[1] : textResourceId; intArray[2] : textSize. Other intArray is useless
	 */
	public MyImageButton(Context context, int... intArray) { 
	    super(context); 
	 
	    // Init instance
	    mButtonImage = new ImageView(context);
	    mButtonText = new TextView(context);
	    
	    int len = intArray.length;
	    if (len >= 1) {
	    	// Set Image Resource
	    	setImageResource(intArray[0]);
	    }
	    if (len >= 2) {
	    	// Set Text
		    setText(intArray[1]);
	    }
	    if (len >= 3) {
	    	// Change text size
	    	textSize = intArray[2];
	    }
	    
	    /** Set Child View(ImageView/TextView) properties */
	    // Set Text Size : default 18
	    setTextSize(textSize);
            // Set ImageView ScaleType : default CENTER_INSIDE(located center, without resize)
	    setImgScaleType(ScaleType.CENTER_INSIDE);
	    LayoutParams layoutParams = new LayoutParams(LayoutParams.MATCH_PARENT, 0, 0.5f);
	    // Set ImageView LayoutParams : default half
	    setImgLayoutParams(layoutParams);
	    // Set TextView LayoutParams : default half
	    setTextLayoutParams(layoutParams);
	    // Set Text Gravity : default center
	    setTextGravity(Gravity.CENTER);
	    // Set Text Color : default white
	    setTextColor(0xFFFFFFFF);
	    
	    /** Set Father View(LinearLayout) properties */
	    setClickable(true);
	    setFocusable(true);
		LayoutParams params = new LayoutParams(LayoutParams.MATCH_PARENT,
				LayoutParams.MATCH_PARENT, 1);
//		params.gravity = Gravity.CENTER;
		// Set Father View Orientation : default fulfill
	    setFatherViewLayoutParams(params);
	    // Set Father View Orientation : default my_img_btn_default
	    setFatherViewBgResource(R.drawable.my_img_btn_default);
	    // Set Father View Orientation : default VERTICAL
	    setFatherViewOrientation(LinearLayout.VERTICAL);
	    
	    addView(mButtonImage); 
	    addView(mButtonText); 
	  }

	  /* 
	   * setImageResource
	   */ 
	  public void setImageResource(int resId) { 
	    mButtonImage.setImageResource(resId); 
	  } 
	 
	  /* 
	   * setText
	   */ 
	  public void setText(int resId) { 
	    mButtonText.setText(resId); 
	  } 
	 
	  public void setText(CharSequence buttonText) { 
	    mButtonText.setText(buttonText); 
	  } 
	 
	  /* 
	   * setTextColor
	   */ 
	  public void setTextColor(int color) { 
	    mButtonText.setTextColor(color); 
	  }
	  
	  /* 
	   * setTextSize
	   */ 
	  public void setTextSize(int textSize) { 
	    mButtonText.setTextSize(textSize); 
	  }

	/**
	 * @param layoutParams the layoutParams to set
	 */
	public void setImgLayoutParams(LayoutParams layoutParams) {
		mButtonImage.setLayoutParams(layoutParams);
	}

        /**
	 * Controls how the image should be resized or moved to match the size of this ImageView
	 * 
	 * @param layoutParams the layoutParams to set
	 */
	public void setImgScaleType(ScaleType scaleType) {
		mButtonImage.setScaleType(scaleType);
	}
	
	/**
	 * @param layoutParams the layoutParams to set
	 */
	public void setTextLayoutParams(LayoutParams layoutParams) {
		mButtonText.setLayoutParams(layoutParams);
	}
	
	/**
	 * @param gravity the gravity to set
	 */
	public void setTextGravity(int gravity) {
		mButtonText.setGravity(gravity);
	}
	
	/**
	 * Set Father View LayoutParams. Notice that this method should not be used generally.
	 * 
	 * @param params
	 */
	public void setFatherViewLayoutParams(LayoutParams params) {
		super.setLayoutParams(params);
	}
	
	public void setFatherViewBgResource(int resId) {
		super.setBackgroundResource(resId);
	}
	
	/**
	 * Set orientation of this Linearlayout. Notice that since the default orientation is vertical, 
	 * when you use this method to modify the orientation to horizontal , make sure that you 
	 * also use {@link #setImgLayoutParams(LayoutParams layoutParams)} and 
	 * {@link #setTextLayoutParams(LayoutParams layoutParams)} together, otherwise, 
	 * the button can not be displayed normally
	 * 
	 * @param orientation
	 */
	public void setFatherViewOrientation(int orientation) {
		super.setOrientation(orientation);
	}
	
}


这个类在构造时会生成一个默认的按钮,图片在上,文字在下,还有一些字体等的默认设置,为了尽量做到共通化,又提供了尽可能多的接口以满足不同的式样需求。具体怎么用呢?

1.布局文件中加一个容器,供我们放置自己的ImageButton对象:
<LinearLayout
            android:id="@+id/pickUpBtnContainer"
        	android:orientation="horizontal"
        	android:layout_width="0dip"
            android:layout_height="match_parent"
            android:layout_weight="0.5"
            android:gravity="center" />


2.在Activity中获取到容器,并将我们的ImageButton放进去:
private void initImageButtons() {
		// Get button container
		pickUpBtnContainer = (LinearLayout) findViewById(R.id.pickUpBtnContainer);
		// Get button instance
		pickUpBtn = new MyImageButton(this, R.drawable.test_img, R.string.pickupCtn, 18);
		// Put button instance into button container
		pickUpBtnContainer.addView(pickUpBtn);
		// Set button OnClickListener
		pickUpBtn.setOnClickListener(new Button.OnClickListener(){
			@Override
			public void onClick(View v) {
				// TODO 这里做什么不用说了
//			}
		});
	}

这样就OK了,至于button的背景啊,点击时的效果,和这篇文章关系不大,不过还是把我自己的xml贴上来吧。
my_img_btn_default.xml
<?xml version="1.0" encoding="UTF-8"?>
<selector  xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="true">
        <shape>
            <gradient android:startColor="@color/my_btn_clicked" android:endColor="@color/my_btn_clicked" android:angle="270" />
            <stroke android:width="1dp" android:color="@color/my_btn_clicked" />
            <padding android:left="10dp" android:top="10dp" android:right="10dp" android:bottom="10dp" />            
        </shape>
    </item>
    <item android:state_focused="true">
        <shape>
            <gradient android:startColor="@color/my_btn_clicked" android:endColor="@color/my_btn_clicked" android:angle="270" />
            <stroke android:width="1dp" android:color="@color/my_btn_clicked" />
            <padding android:left="10dp" android:top="10dp" android:right="10dp" android:bottom="10dp" />            
        </shape>
    </item>
    <item>
        <shape>
            <gradient android:startColor="@color/glb_bg" android:endColor="@color/glb_bg" android:angle="270" />
            <stroke android:width="1dp" android:color="@color/glb_bg" />
            <padding android:left="10dp" android:top="10dp" android:right="10dp" android:bottom="10dp" />            
        </shape>
    </item>
</selector>

如果想要圆角button,在<shape>标签下增加子标签<corners android:radius="5dp" />就可以了,该文件放在drawable下就可使用