二级列表控件:
ExpandableListView一般购物车都是有个表头 有个表位所以要用一个
ScrollView 控件包裹着,一般会出现滑动冲突事件所以需要自定义一个二级列表
public class MyExpandableListView extends ExpandableListView { public MyExpandableListView(Context context, AttributeSet attrs) { super(context, attrs); } //解决滑动事件冲突 @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int height = MeasureSpec.makeMeasureSpec(Integer.MAX_VALUE>>2,MeasureSpec.AT_MOST); super.onMeasure(widthMeasureSpec, height); } }注意这里需要在bean类里写一个自定义的属性为了记录一级列表的checkbox框的状态:
public boolean isGroupChecked() { return isGroupChecked; } public void setGroupChecked(boolean groupChecked) { isGroupChecked = groupChecked; } private boolean isGroupChecked;//首次进入app时isGeoupchecked为false
public class Myadapter extends BaseExpandableListAdapter { private Handler handler; private Context context; private Listgroup_list; private List >child_list; public Myadapter(Handler handler, Context context, List
group_list, List > child_list) { this.handler = handler; this.context = context; this.group_list = group_list; this.child_list = child_list; } @Override public int getGroupCount() { return group_list.size(); } @Override public int getChildrenCount(int groupPosition) { return child_list.get(groupPosition).size(); } @Override public Object getGroup(int groupPosition) { return group_list.get(groupPosition); } @Override public Object getChild(int groupPosition, int childPosition) { return child_list.get(groupPosition).get(childPosition); } @Override public long getGroupId(int groupPosition) { return groupPosition; } @Override public long getChildId(int groupPosition, int childPosition) { return childPosition; } @Override public boolean hasStableIds() { return true; } @Override public View getGroupView(final int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { GroupHolder holder; if(convertView==null){ convertView = View.inflate(context, R.layout.group_item, null); holder = new GroupHolder(); holder.group_checked=convertView.findViewById(R.id.group_checked); holder.group_text=convertView.findViewById(R.id.group_text); convertView.setTag(holder); }else { holder= (GroupHolder) convertView.getTag(); } final Bean.DataBean dataBean = group_list.get(groupPosition); holder.group_checked.setChecked(dataBean.isGroupChecked()); holder.group_text.setText(dataBean.getSellerName()); holder.group_checked.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //改变当前以及列表的状态,不与初始化的相等 dataBean.setGroupChecked(!dataBean.isGroupChecked()); //根据当前一级状态改变二级列表的值 changeChildState(groupPosition,dataBean.isGroupChecked()); //通过判断一级的是否选中,来设置是否为全部选中 changeAllState(isAllGroupChecked()); //发送价格数量 sendPriceAndCount(); notifyDataSetChanged(); } }); return convertView; } @Override public View getChildView(final int groupPosition, int childPosition, boolean isLastChild, View view, ViewGroup parent) { ChildHolder holder; if(view==null){ view = View.inflate(context, R.layout.child_item, null); holder=new ChildHolder(); holder.text_add = view.findViewById(R.id.text_add); holder.text_num = view.findViewById(R.id.text_num); holder.text_jian = view.findViewById(R.id.text_jian); holder.text_title = view.findViewById(R.id.text_title); holder.text_price = view.findViewById(R.id.text_price); holder.image_good = view.findViewById(R.id.image_good); holder.check_child = view.findViewById(R.id.check_child); view.setTag(holder); }else { holder = (ChildHolder) view.getTag(); } final Bean.DataBean.ListBean listBean = child_list.get(groupPosition).get(childPosition); holder.text_num.setText(listBean.getNum()+"");//......注意 holder.text_price.setText("¥"+listBean.getPrice()); holder.text_title.setText(listBean.getTitle()); ImageLoader.getInstance().displayImage(listBean.getImages().split("!")[0],holder.image_good); holder.check_child.setChecked(listBean.getSelected()==0? false:true); holder.check_child.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { listBean.setSelected(listBean.getSelected() ==0? 1:0); sendPriceAndCount(); if(listBean.getSelected()==1){ if(isAllChildSelected(groupPosition)){ //如果全部选中改变当前状态 changeGroupState(groupPosition,true); //.确定是否改变全选 changeAllState(isAllGroupChecked()); } }else { //如果没有选中改变一下当前组的状态 changeGroupState(groupPosition,false); //.确定是否改变全选 changeAllState(isAllGroupChecked()); } //刷新适配器 notifyDataSetChanged(); } }); holder.text_add.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { listBean.setNum(listBean.getNum()+1); if (listBean.getSelected()==1){ sendPriceAndCount(); } notifyDataSetChanged(); } }); holder.text_jian.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { int num = listBean.getNum(); if (num == 1){ return; } listBean.setNum(num-1); if (listBean.getSelected() == 1){ sendPriceAndCount(); } notifyDataSetChanged(); } }); return view; } @Override public boolean isChildSelectable(int groupPosition, int childPosition) { return true; //子条目是否能点击 } //通过二级列表 改变一级列表的状态设置父控件是否选中 private void changeGroupState(int groupPosition, boolean b) { group_list.get(groupPosition).setGroupChecked(b); } //子布局是否选中 //二级列表是否全部选中 private boolean isAllChildSelected(int groupPosition) { List
listBeans = child_list.get(groupPosition); for (int i=0;i if (listBeans.get(i).getSelected() == 0){ return false; } } return true; } //设置总价 private void sendPriceAndCount(){ double price=0; int count=0 ; for (int i = 0; i <group_list.size() ; i++) { List list = group_list.get(i).getList(); for (int j = 0; j if(listBean.getSelected()==1){ //当二级列表选中时计算价格,和物品的个数 price += listBean.getPrice()* listBean.getNum(); //单价*数目 count += listBean.getNum(); } } } CountPriceBean countPriceBean = new CountPriceBean(price, count); //实例化 购物车计算价钱的bean类,把得到的总数总价钱存入 Message msg = Message.obtain(); msg.what = 0; //设置标识符待主类接收 msg.obj = countPriceBean; handler.sendMessage(msg); //把值存入handler值 等待接收 } //设置父控件全选 private boolean isAllGroupChecked(){ for (int i = 0; i <group_list.size() ; i++) { //isGroupChecked 初始值为false当点击的时候为yrue所以 !=isGroupChecked就是false if(!group_list.get(i).isGroupChecked()){ return false; } } return true; } //设置所以元素全选 public void changeAllState(boolean allGroupChecked){ //通过得到一级列表的所有状态设置 全选的值 Message msg = Message.obtain(); msg.what=1; msg.obj=allGroupChecked; handler.sendMessage(msg); //主要就是实现 通过一级二级的状态改变主类里checkbox的值 } public void changeChildState(int groupPosition, boolean groupChecked){ List listBeen = child_list.get(groupPosition); //通过一级列表的状态 设置子二级列表的全部状态 for (int i = 0; i 1:0); } } public void setIfCheckAll(boolean checked) { //本方法是为了通过主类里的checkbox改变一级二级列表的值 for (int i = 0;i<group_list.size();i++){ Bean.DataBean dataBean = group_list.get(i); //设置组上面的checkBox是否选中 dataBean.setGroupChecked(checked); List listBeans = dataBean.getList(); for (int j = 0; j< listBeans.size(); j++){ //改变是否选中的状态...数据应该变的是 listBeans.get(j).setSelected(checked? 1:0); } } //计算价钱和数量并且发送到mainActivity显示 sendPriceAndCount(); //刷新适配器 notifyDataSetChanged(); } private class GroupHolder{ CheckBox group_checked; TextView group_text; } private class ChildHolder{ CheckBox check_child; ImageView image_good; TextView text_title; TextView text_price; TextView text_jian; TextView text_num; TextView text_add; } }
下面是主类使用碎片fragment实现的所以注意上下文的参数:
public class gwc extends Fragment { private MyExpandableListView expandableListView; private CheckBox all_check; private TextView price; private Button buy; //通过Handler接收适配器的值改变主线程的UI private Handler handler =new Handler(){ @Override public void handleMessage(Message msg) { if (msg.what == 0){ CountPriceBean countPriceBean = (CountPriceBean) msg.obj; //设置 price.setText("合计:¥"+countPriceBean.getPrice()); buy.setText("去结算("+countPriceBean.getCount()+")"); }else if (msg.what == 1){//改变全选 boolean flag = (boolean) msg.obj; all_check.setChecked(flag); } } }; private Myadapter myadapter; @Nullable @Override public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { View v = View.inflate(getActivity(), R.layout.gwc, null); expandableListView = (MyExpandableListView)v. findViewById(R.id.expandableListView); all_check = (CheckBox)v. findViewById(R.id.all_check); price = (TextView) v.findViewById(R.id.price); buy = (Button) v.findViewById(R.id.buy); expandableListView.setGroupIndicator(null);//暂时用不到此属性所以为false TextView bt = v.findViewById(R.id.but); bt.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { HashMapmap = new HashMap<>(); map.put("uid","2856"); OkHttp3Utils.doPost("http://120.27.23.105/product/getCarts",map, new GsonObjectCallback () { @Override public void onUi(Bean bean) { if (bean.getData()!=null){ Log.e("**", bean.getMsg()); List data = bean.getData(); List > listChilds = new ArrayList<>(); for (int i = 0; i < data.size(); i++) { listChilds.add(data.get(i).getList()); } myadapter = new Myadapter(handler,getActivity(), data, listChilds); expandableListView.setAdapter(myadapter); for (int i=0;i
//设置一级列表默认展开 expandableListView.expandGroup(i); } all_check.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { myadapter.setIfCheckAll(all_check.isChecked()); } }); } } @Override public void onFailed(Call call, IOException e) { } }); } }); return v; } }
下面是主类的xml文件:
xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical"> <RelativeLayout android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="1" > <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="购物车" android:layout_centerInParent="true" android:textSize="25sp" android:id="@+id/but" /> RelativeLayout> <ScrollView android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="8" > <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" > <com.bwei.ssp.home_work.Fragment.shopcate.view.MyExpandableListView android:id="@+id/expandableListView" android:layout_width="match_parent" android:layout_height="match_parent"/> LinearLayout> ScrollView> <RelativeLayout android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="1" > <CheckBox android:layout_width="wrap_content" android:layout_height="wrap_content" android:id="@+id/all_check" android:layout_centerVertical="true" /> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="全选" android:textSize="19sp" android:layout_marginLeft="40dp" android:layout_centerVertical="true" /> <TextView android:layout_centerInParent="true" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="¥0.0" android:id="@+id/price" android:textColor="#ff9933" /> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" > <Button android:layout_width="70dp" android:layout_height="wrap_content" android:text="删除" android:id="@+id/del" android:background="#cc6600" /> <Button android:layout_width="70dp" android:layout_height="wrap_content" android:text="购买" android:background="#ff0066" android:id="@+id/buy" /> LinearLayout> RelativeLayout> LinearLayout>一级列表的布局:
xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent"> <CheckBox android:layout_width="wrap_content" android:layout_height="wrap_content" android:id="@+id/group_checked" android:layout_marginLeft="10dp" /> <TextView android:layout_marginLeft="10dp" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="天猫运营" android:id="@+id/group_text" android:textSize="20dp" /> LinearLayout>二级列表的努布局:
xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:padding="10dp" android:layout_width="match_parent" android:layout_height="match_parent"> <CheckBox android:layout_centerVertical="true" android:id="@+id/check_child" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <ImageView android:id="@+id/image_good" android:layout_centerVertical="true" android:layout_toRightOf="@+id/check_child" android:layout_marginLeft="10dp" android:layout_width="80dp" android:layout_height="80dp" /> <TextView android:id="@+id/text_title" android:layout_toRightOf="@+id/image_good" android:layout_marginLeft="10dp" android:layout_alignTop="@+id/image_good" android:maxLines="2" android:minLines="2" android:text="我是手机" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <TextView android:id="@+id/text_price" android:layout_toRightOf="@+id/image_good" android:layout_marginLeft="10dp" android:layout_alignBottom="@+id/image_good" android:text="¥99.99" android:textColor="#ff0000" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <LinearLayout android:layout_alignParentRight="true" android:layout_alignBottom="@+id/image_good" android:orientation="horizontal" android:layout_width="wrap_content" android:layout_height="wrap_content"> <TextView android:id="@+id/text_jian" android:text="一" android:padding="5dp" android:background="@drawable/bian_kuang_line" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <TextView android:gravity="center" android:id="@+id/text_num" android:paddingLeft="10dp" android:paddingRight="10dp" android:background="@drawable/bian_kuang_line" android:layout_width="wrap_content" android:layout_height="match_parent" /> <TextView android:id="@+id/text_add" android:text="十" android:padding="5dp" android:background="@drawable/bian_kuang_line" android:layout_width="wrap_content" android:layout_height="wrap_content" /> LinearLayout> RelativeLayout>