編輯:關於Android編程
**
**
在Android中,我們一般通過RadioGroup來管理一組RadioButton 來達到 單選按鈕的互斥效果。但是,有些需求中,需要完成N行N列這樣的RadioButton組成的矩陣,但是我們的RadioGroup是一個耿直的LinearLayout,無法完成網格布局╮(╯▽╰)╭。所以,下面我就像大家來介紹一種實現網格布局的RadioButton的思路。
無圖無真相, 先上一下效果圖~
**<喎?/kf/ware/vc/" target="_blank" class="keylink">vcD4NCjxoMiBpZD0="思路">思路
**
提到網格布局,最簡單的就是使用系統的GridView來實現,我們需要做的就是 將RadioButton加入GridView中,然後自己來實現RadioButton之間的互斥。
1. 自定義RadioButton:
自定義一個RadioButton ,命名為IconRadioButton
/**
* Created by jk on 2016/1/20.
* 自定義 RadioButton
*/
public class IconRadioButton extends LinearLayout {
private Context mContext;
private Resources mResources;
private boolean mIsCheck;
private View mContentView;
private ImageView mRadio;
private TextView mTextView;
private ColorStateList mTextColor;
public IconRadioButton(Context context) {
this(context, null);
}
public IconRadioButton(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public IconRadioButton(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init(context);
}
private void init(Context context) {
mContext = context;
mResources = context.getResources();
mContentView = LayoutInflater.from(context).inflate(R.layout.btn_icon_radio, this);
mRadio = (ImageView) mContentView.findViewById(R.id.radio);
mTextView = (TextView) mContentView.findViewById(R.id.text);
}
public void setChecked(boolean isChecked) {
mIsCheck = isChecked;
changeUIByChecked(isChecked);
}
public boolean isChecked() {
return mIsCheck;
}
private void changeUIByChecked(boolean isChecked) {
if (mRadio.getVisibility() != GONE) {
mRadio.setImageResource(isChecked ? R.drawable.radio_selected
: R.drawable.radio_unselected);
}
mTextView.setEnabled(isChecked);
}
public void setTextColor(ColorStateList color){
mTextColor = color;
mTextView.setTextColor(color);
}
public void setText(CharSequence text) {
mTextView.setText(text);
}
public void setText(int resId) {
mTextView.setText(resId);
}
public void hiddenRadio(boolean isHidden) {
mRadio.setVisibility(isHidden ? GONE : VISIBLE);
}
}
這個IconRadioButton很簡單 就是一個LinearLayout,內部封裝了根據是否選中來改變文字和按鈕樣式的方法。
btn_icon_radio.xml
<code class=" hljs xml"><!--{cke_protected}{C}%3C!%2D%2D%3Fxml%20version%3D%221.0%22%20encoding%3D%22utf-8%22%3F%2D%2D%3E--> <linearlayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="wrap_content" android:layout_height="wrap_content" android:orientation="horizontal" android:gravity="left" android:paddingbottom="5dp" android:paddingtop="5dp"> <imageview android:id="@+id/radio" android:layout_width="42dp" android:layout_height="match_parent" android:layout_gravity="center_vertical" android:gravity="center" android:src="@drawable/radio_selected" android:textcolor="#FF1CBFA6"> <textview android:id="@+id/text" android:layout_width="wrap_content" android:layout_height="match_parent" android:layout_gravity="center_vertical" android:gravity="center" android:textcolor="#FF999999" android:textsize="14dp"> </textview></imageview></linearlayout></code>
布局文件很簡單 就是一個LinearLayout裡面放了一個ImageView和一個TextView
2 . 定義數據模型
/**
* Created by admin on 2016/1/20.
*/
public class RadioItemModel {
public String text; //RadioButton的文字
public boolean isChecked;//是否選中
public boolean hiddenRadio;//是否需要隱藏radio
public ColorStateList textColor;//文字的不同狀態的顏色
public RadioItemModel(String text, boolean isChecked, boolean hiddenRadio, ColorStateList textColor) {
this.text = text;
this.isChecked = isChecked;
this.hiddenRadio = hiddenRadio;
this.textColor = textColor;
}
public RadioItemModel(String text) {
this.isChecked = false;
this.hiddenRadio = false;
this.textColor = null;
this.text = text;
}
public void setText(String text) {
this.text = text;
}
public String getText() {
return text;
}
public boolean isChecked() {
return isChecked;
}
}
我們定義了一個數據模型來存放RadioButton的各種屬性。其中ColorStateList是用來控制TextView在不同狀態下的顏色的 比如:state_pressed等。
3. 定義Adapter:
既然是使用GridView 那就需要定義我們的Adapter,我們的互斥邏輯也是在Adapter中實現的。
/**
* Created by jk on 2016/1/20.
* function: 單選矩陣的適配器
* purpose: 系統的RadioGroup是個耿直的LinearLayout╮(╯▽╰)╭ 只能線性排列,無法完成
* N行N列的布局。So 為了實現單選按鈕的網格布局 ,重定義
*/
public class GridRadioAdapter extends BaseAdapter {
private List mList;
private Context mContext;
private Resources mResources;
private OnItemCheckedListener mListener;
//RadioButton選中時的回調函數
public interface OnItemCheckedListener {
void onItemChecked(RadioItemModel model, int position);
}
public void setOnItemCheckedListener(OnItemCheckedListener listener) {
this.mListener = listener;
}
public GridRadioAdapter(Context context, List list) {
mContext = context;
mList = list;
check();
}
private void check() {
if (mList.size()>=0 && mList!=null) {
checkDefaultChecked();
checkMutex();
}
}
/**
* 檢查互斥事件 默認只能選中一個 如果有多個選擇,就選中最後一個
*/
private void checkMutex() {
int checkCount = 0;
for (RadioItemModel item : mList) {
if (item.isChecked) {
checkCount++;
}
}
if (checkCount >= 2) {
setOtherUnChecked(checkCount - 1);
}
}
private void setOtherUnChecked(int position) {
for (int i = 0; i < mList.size(); i++) {
if (i != position) {
RadioItemModel item = mList.get(i);
item.isChecked = false;
} else {
mList.get(position).isChecked = true;
}
}
}
public RadioItemModel getItemChecked() {
for (int i = 0; i < mList.size(); i++) {
RadioItemModel item = mList.get(i);
if (item.isChecked)
return item;
}
return null;
}
/**
* 檢查是否有默認選中的按鈕 如果沒有 默認第一個選中
*/
private void checkDefaultChecked() {
for (RadioItemModel item : mList) {
if (item.isChecked)
return;
}
mList.get(0).isChecked = true;
}
@Override
public int getCount() {
return mList == null ? 0 : mList.size();
}
@Override
public Object getItem(int position) {
if (mList != null && mList.size() > position)
return mList.get(position);
return null;
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
IconRadioButton iconBean = null;
iconBean = new IconRadioButton(mContext);
final RadioItemModel model = mList.get(position);
if (!TextUtils.isEmpty(model.text)) {
iconBean.setText(model.text);
}
iconBean.setChecked(model.isChecked);
if (model.textColor != null) {
iconBean.setTextColor(model.textColor);
}
iconBean.hiddenRadio(model.hiddenRadio);
final IconRadioButton finalIconBean = iconBean;
iconBean.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (!finalIconBean.isChecked()) {
setOtherUnChecked(position);
if (mListener != null) {
mListener.onItemChecked(model, position);
}
notifyDataSetChanged();
}
}
});
return iconBean;
}
public void addAll(List list){
mList.clear();
if(list.size()>=0 && list!=null){
mList.addAll(list);
check();
notifyDataSetChanged();
}
}
}
在構造函數中,我們調用了check方法來實現默認選中檢查和 互斥檢查。
(1)checkDefaultChecked函數用來實現默認選中功能,如果傳遞給我們的數據中沒有按鈕是默認選中的 ,那我們就讓第一個按鈕默認選中。
(2)checkMutex函數是用來檢查互斥事件的,如果有多個按鈕同時被選中,我們就設置被選中的最後一個按鈕為選中狀態,其他置為非選中狀態。比如 按鈕1,3,5同時被選中,那麼我們就讓5置為選中狀態,1和3為非選中狀態。
(3)OnItemCheckedListener是當按鈕被選中時的回調方法。
4.使用方式
使用方式就非常簡單粗暴了~
public class MainActivity extends Activity {
private GridView mGridLayout;
private GridRadioAdapter mAdapter;
private List mItemList;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
private void initData() {
mItemList = new ArrayList();
ColorStateList csl = getResources().getColorStateList(R.color.ddt_color_tab_text);
mItemList.add(new RadioItemModel("全部", false, true, csl));
mItemList.add(new RadioItemModel("早餐前", false, true, csl));
mItemList.add(new RadioItemModel("午餐前", false, true, csl));
mItemList.add(new RadioItemModel("晚餐前", false, true, csl));
mItemList.add(new RadioItemModel("早餐後", false, true, csl));
mItemList.add(new RadioItemModel("午餐後", false, true, csl));
mItemList.add(new RadioItemModel("晚餐後", false, true, csl));
mItemList.add(new RadioItemModel("睡前", false, true, csl));
mAdapter.notifyDataSetChanged();
}
}
PS: 如果設置hiddenRadio這個屬性為true,我們就可以實現下面這種效果了。所以這個東西也是可以用來做切換Fragment的選項卡的哦~~~ O(∩_∩)O
以上。
public class EngineerJspActivity extends Activity { private static String Tag = &q
一、獲取屏幕寬高1、android界面簡單介紹要獲取屏幕寬高,我們可以先從android的界面構成了解 android的界面主要由三部分構成:1、狀態欄 2、標
計算機圖形表示的原理 加載大圖出現OOM 縮放加載大的圖片資源 創建一個原圖的副本 圖形處理的常用的API 傻瓜版美圖秀秀 畫畫版計算機圖形表示的原理首先要明確的一點是,
(一)概述上節我們對BroadcastReceiver已經有了一個初步的了解了,知道兩種廣播類型:標准與有序, 動態或靜態注冊廣播接收者,監聽系統廣播,自己發送廣播!已經