之前项目部分功能需要重构,其中就包括省市县三级联动的效果,记录下,先上图(gif看不清楚,勉强看看):
1、实现起来也是比较粗暴的,dialog中的listview适配省市县分别对应的Adapter,其实有点low.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="300dp"
android:background="@color/color_white"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingTop="8dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:text="所在地区"
android:textColor="@color/color_black"
android:textSize="14sp"/>
<android.support.design.widget.TabLayout
android:id="@+id/tab_bar"
android:layout_width="match_parent"
android:layout_height="50dip"
android:overScrollMode="never"
app:tabBackground="@color/color_white"
app:tabIndicatorColor="@color/color_black"
app:tabIndicatorHeight="2dip"
app:tabMode="scrollable"
app:tabPaddingStart="13dip"
app:tabSelectedTextColor="@color/color_caselist_select"
app:tabTextAppearance="@style/tab_text"
app:tabTextColor="@color/color_black">
</android.support.design.widget.TabLayout>
<View
style="@style/lineView"/>
<ListView
android:divider="@color/color_transparent"
android:dividerHeight="0dp"
android:scrollbars="none"
android:layout_width="match_parent"
android:id="@+id/lv_base"
android:layout_height="match_parent">
</ListView>
</LinearLayout>
</LinearLayout>
这是dialog布局部分
2.然后是dialog中具体的代码实现部分,为方便自己看代码,差不多都写了注释:
public class AddressDialog extends Dialog implements TabLayout.OnTabSelectedListener {
private final Context mcontext;
@Bind(R.id.tab_bar)
TabLayout mTabBar;
@Bind(R.id.lv_base)
ListView mLvBase;
private ArrayList<AddressProvinceBean> provinceList = new ArrayList<>(); //省份集合
private ArrayList<AddressCityBean> citysList = new ArrayList<>(); //市区集合
private ArrayList<AddressDistrictBean> districtList = new ArrayList<>(); //县区集合
private ArrayList<String> nameList = new ArrayList<>(); //展示的省市区名称
private int provincePosition = -1; //省份选中的位置
private int cityPosition = -1; //市区选中的位置
private int districtPosition = -1; //县区选中的位置
private String provinceName; //选中的省份名称
private String cityName; //选中的市区名称
private String districtName; //选中的县区名称
private AddressProvinceAdapter mProvinceAdapter; //省级adapter
private AddressCityAdapter mCityAdapter; //市级adapter
private AddressDistrictAdapter mDistrictAdapter; //县级adapter
private OnAddressSelectedListener onAddressSelectedListener; //定义的监听,将选中的省市县等数据传给业务层
public AddressDialog(Context context) {
super(context, R.style.dialog_adddata_style);
this.mcontext = context;
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.dialog_address);
ButterKnife.bind(this);
setCanceledOnTouchOutside(true);
init();
}
private void init() {
Window window = getWindow();
WindowManager.LayoutParams lp = window.getAttributes();
lp.width = WindowManager.LayoutParams.MATCH_PARENT;
lp.height = WindowManager.LayoutParams.WRAP_CONTENT;
window.setGravity(Gravity.BOTTOM);
window.setBackgroundDrawable(new BitmapDrawable());
//tablayout设置第一个tab
mTabBar.addTab(mTabBar.newTab().setText("请选择"));
mTabBar.setOnTabSelectedListener(this);
//获取assets下的地址json数据
String addressJson = GsonUtils.getJson(mcontext, "address.json");
//获取到所有的省市区的数据
AddressCountryBean addressCountryBean = GsonUtils.getModel(addressJson, AddressCountryBean.class);
provinceList.addAll(addressCountryBean.getProvinces());
//新建省级adapter
mProvinceAdapter = new AddressProvinceAdapter(mcontext, provinceList);
mLvBase.setAdapter(mProvinceAdapter);
//新建市级adpater
mCityAdapter = new AddressCityAdapter(mcontext, citysList);
//新建县级adapter
mDistrictAdapter = new AddressDistrictAdapter(mcontext, districtList);
//省级adapter回调,拿到选中的省的名称
mProvinceAdapter.setOnAddressSelectedListener(new AddressProvinceAdapter.OnAddressSelectedListener() {
@Override
public void getAddressSelected(String name, int position) {
provinceName = name;
//根据选择的省的来获取到市级的数据
citysList.clear();
citysList.addAll(provinceList.get(position).getCitys());
//将市的adapter设置给listview
mLvBase.setAdapter(mCityAdapter);
//这里可能有点复杂根据tab的数量来显示对应位置的tab显示的文字
if (mTabBar.getTabCount() == 1){
//如果tab只有一个的,那就在给tabayout在新增一个tab
mTabBar.addTab(mTabBar.newTab().setText("请选择"));
}else if (mTabBar.getTabCount() == 3){
//如果tab有三个的话,那就不用新增了
//把第三个tab给删除掉
mTabBar.removeTabAt(2);
//并且把第二个tab的文字改为请选择,表示还没有选择选择市
mTabBar.getTabAt(1).setText("请选择");
}
//手动把第二个tab选中
mTabBar.getTabAt(1).select();
//将选中的省的名称设置给第1个tab
mTabBar.getTabAt(0).setText(provinceName);
}
});
mCityAdapter.setOnAddressSelectedListener(new AddressCityAdapter.OnAddressSelectedListener() {
@Override
public void getAddressSelected(String name, int position) {
cityName = name;
//根据选中的市的名称获取到县的数据
districtList.clear();
districtList.addAll(citysList.get(position).getDistricts());
//设置县的adapter
mLvBase.setAdapter(mDistrictAdapter);
if (mTabBar.getTabCount() == 2){
mTabBar.addTab(mTabBar.newTab().setText("请选择"));
}
mTabBar.getTabAt(2).select();
mTabBar.getTabAt(1).setText(cityName);
}
});
mDistrictAdapter.setOnAddressSelectedListener(new AddressDistrictAdapter.OnAddressSelectedListener() {
@Override
public void getAddressSelected(String name, int position) {
districtName = name;
mTabBar.getTabAt(2).setText(districtName);
//最后将所选择的省市县的相关需要的数据回调给业务层
onAddressSelectedListener.getAddressSelected(provinceName,cityName,districtName,districtList.get(position).getCode());
dismiss();
}
});
}
@Override
public void onTabSelected(TabLayout.Tab tab) {
//tablayout的选中
if (!TextUtils.isEmpty(tab.getText())) {
//点击TAb的时候重新设置对应的adapter
if (tab.getPosition() == 0) {
//设置省份adapter
mLvBase.setAdapter(mProvinceAdapter);
} else if (tab.getPosition() == 1) {
//设置市区adapter
mLvBase.setAdapter(mCityAdapter);
} else {
//设置县区adapter
mLvBase.setAdapter(mDistrictAdapter);
}
}
}
@Override
public void onTabUnselected(TabLayout.Tab tab) {
}
@Override
public void onTabReselected(TabLayout.Tab tab) {
}
public void setOnAddressSelectedListener(OnAddressSelectedListener onAddressSelectedListener) {
this.onAddressSelectedListener = onAddressSelectedListener;
}
public interface OnAddressSelectedListener {
void getAddressSelected(String provinceName, String cityName, String districtName, String code);
}
}
其实看注释很容易就能理解,点击不同的teb的时候就去加载对应的省市县的adapter,这里分别为省市县配了一个adapter.以及一个回调,把需要的信息回调到调用的地方
3,再贴一个省对应的adapter,为了数据好看,把省市县的json数据做了排序
public class AddressProvinceAdapter extends BaseAdapter {
private final Context mcontext;
private final List<AddressProvinceBean> mList;
private OnAddressSelectedListener onAddressSelectedListener;
public AddressProvinceAdapter(Context context, List<AddressProvinceBean> list) {
this.mcontext = context;
this.mList = list;
//按code排序(这个排不排序无所谓)
getSort();
}
private void getSort() {
Collections.sort(mList, new Comparator<AddressProvinceBean>(){
/*
* int compare(Person p1, Person p2) 返回一个基本类型的整型,
* 返回负数表示:p1 小于p2,
* 返回0 表示:p1和p2相等,
* 返回正数表示:p1大于p2
*/
public int compare(AddressProvinceBean a1, AddressProvinceBean a2) {
//按照行政编码升序排列
if(Integer.parseInt(a1.getCode()) > Integer.parseInt(a2.getCode())){
return 1;
}
if(Integer.parseInt(a1.getCode()) == Integer.parseInt(a2.getCode())){
return 0;
}
return -1;
}
});
}
@Override
public int getCount() {
return mList.size();
}
@Override
public AddressProvinceBean getItem(int position) {
return mList.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
final ViewHolder holder;
if (convertView == null) {
convertView = View.inflate(mcontext, R.layout.item_address, null);
holder = new ViewHolder(convertView);
convertView.setTag(holder);
} else {
holder = (ViewHolder) convertView.getTag();
}
if (!TextUtils.isEmpty(mList.get(position).getName())){
holder.mTvAddress.setText(mList.get(position).getName());
}
//根据是否选中设置textview的选中状态
if (mList.get(position).isSelect()){
holder.mTvAddress.setSelected(true);
}else {
holder.mTvAddress.setSelected(false);
}
holder.mRlItem.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
onAddressSelectedListener.getAddressSelected(mList.get(position).getName(),position);
holder.mTvAddress.setSelected(true);
//设置对应的实体类的Select的值,后续根据这个select的值显示是否选中
for (int i = 0; i < mList.size(); i++) {
if (i == position){
mList.get(i).setSelect(true);
}else {
mList.get(i).setSelect(false);
}
}
}
});
return convertView;
}
static class ViewHolder {
@Bind(R.id.tv_address)
TextView mTvAddress;
@Bind(R.id.rl_item)
RelativeLayout mRlItem;
ViewHolder(View view) {
ButterKnife.bind(this, view);
}
}
public void setOnAddressSelectedListener(OnAddressSelectedListener onAddressSelectedListener) {
this.onAddressSelectedListener = onAddressSelectedListener;
}
public interface OnAddressSelectedListener {
void getAddressSelected(String provinceName, int position);
}
}
好了,结束,简单记录一下.