MainActivity
package com.zjh.administrat.shoppcarexpandablelistview.view;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.ExpandableListView;
import android.widget.TextView;
import com.zjh.administrat.shoppcarexpandablelistview.R;
import com.zjh.administrat.shoppcarexpandablelistview.adapter.MyAdapter;
import com.zjh.administrat.shoppcarexpandablelistview.bean.ShoppingBean;
import com.zjh.administrat.shoppcarexpandablelistview.presenter.IPresenterImpl;
import java.util.HashMap;
import java.util.Map;
public class MainActivity extends AppCompatActivity implements IView {
private String urlStr = "http://www.zhaoapi.cn/product/getCarts";
private IPresenterImpl iPresenter;
private ExpandableListView mListView;
private CheckBox selectAll;
private TextView priceAll;
private Button numberAll;
private MyAdapter mAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();
initData();
//创建我的适配器
mAdapter = new MyAdapter(this);
mListView.setAdapter(mAdapter);
}
private void initView() {
mListView = findViewById(R.id.listView);
selectAll = findViewById(R.id.selectAll);
priceAll = findViewById(R.id.priceAll);
numberAll = findViewById(R.id.numberAll);
//全选按钮
selectAll.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//底部全选按钮选中的时候所有得商品都被选中
boolean allSelected = mAdapter.isAllSelected();
mAdapter.changeAllStatus(!allSelected);
mAdapter.notifyDataSetChanged();
//刷新底部数据
refreshData();
}
});
}
//刷新的方法 checkBox, 总价, 总数量
private void refreshData(){
//判断所有商品是否被选中
boolean allSelected = mAdapter.isAllSelected();
//设置给全选
selectAll.setSelected(allSelected);
//计算总价
float totalPrice = mAdapter.totalPrice();
priceAll.setText("总价:¥"+totalPrice);
//计算总数量
int totalNumber = mAdapter.totalNumber();
numberAll.setText("去结算("+totalNumber+")");
}
//处理数据
private void initData() {
iPresenter = new IPresenterImpl(this);
Map<String, String> map = new HashMap<>();
map.put("uid", "71");
iPresenter.pRequestData(urlStr, map, ShoppingBean.class);
}
//返回数据i
@Override
public void viewData(Object object) {
ShoppingBean shoppingBean = (ShoppingBean) object;
mAdapter.setDataAll(shoppingBean.getData());
//展开二级列表
for (int p = 0; p < shoppingBean.getData().size(); p++) {
mListView.expandGroup(p);
}
//回调处理
mAdapter.setOnCartListChangeListener(new MyAdapter.OnCartListChangeListener() {
@Override
public void onParentCheckedChange(int i) {
//点击商家复选框
boolean parentSelected = mAdapter.isParentSelected(i);
mAdapter.changeParentAllStatus(i, !parentSelected);
mAdapter.notifyDataSetChanged();
//刷新底部数据
refreshData();
}
@Override
public void onChildCheckedChange(int i, int i1) {
//点击商品复选框
mAdapter.changeChildAllStatus(i, i1);
mAdapter.notifyDataSetChanged();
//刷新底部数据
refreshData();
}
@Override
public void onNumberChange(int i, int i1, int number) {
//点击加减器
mAdapter.changeNumber(i, i1, number);
mAdapter.notifyDataSetChanged();
//刷新底部数据
refreshData();
}
});
}
//处理内存
@Override
protected void onDestroy() {
super.onDestroy();
iPresenter.onDetch();
}
}
MyAdapter
package com.zjh.administrat.shoppcarexpandablelistview.adapter;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.CheckBox;
import android.widget.ImageView;
import android.widget.TextView;
import com.bumptech.glide.Glide;
import com.zjh.administrat.shoppcarexpandablelistview.R;
import com.zjh.administrat.shoppcarexpandablelistview.bean.ShoppingBean;
import com.zjh.administrat.shoppcarexpandablelistview.view.AddSubView;
import java.util.ArrayList;
import java.util.List;
public class MyAdapter extends BaseExpandableListAdapter {
private List<ShoppingBean.DataBean> list;
private Context mContext;
public MyAdapter(Context mContext) {
this.mContext = mContext;
list = new ArrayList<>();
}
//数据料理
public void setDataAll(List<ShoppingBean.DataBean> data) {
if (data != null) {
list.addAll(data);
}
notifyDataSetChanged();
}
@Override
public int getGroupCount() {
return list.size();
}
@Override
public int getChildrenCount(int groupPosition) {
return list.get(groupPosition).getList().size();
}
//商家------------
@Override
public View getGroupView(final int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) {
ParentHolder parentHolder;
if (convertView == null) {
convertView = LayoutInflater.from(mContext).inflate(R.layout.item_cart_parent, parent, false);
parentHolder = new ParentHolder(convertView);
} else {
parentHolder = (ParentHolder) convertView.getTag();
}
parentHolder.parent_title.setText(list.get(groupPosition).getSellerName());
boolean parentSelected = isParentSelected(groupPosition);
parentHolder.parent_checkBox.setChecked(parentSelected);
//设置点击商家的checkBox,
parentHolder.parent_checkBox.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (mOnCartListChangeListener != null){
mOnCartListChangeListener.onParentCheckedChange(groupPosition);
}
}
});
return convertView;
}
//商品-----------------------
@Override
public View getChildView(final int groupPosition, final int childPosition, boolean isLastChild, View convertView, ViewGroup parent) {
ChildHolder childHolder;
if (convertView == null) {
convertView = LayoutInflater.from(mContext).inflate(R.layout.item_cart_child, parent, false);
childHolder = new ChildHolder(convertView);
} else {
childHolder = (ChildHolder) convertView.getTag();
}
//设置商品图片***
String str = "";
int length = list.get(groupPosition).getList().get(childPosition).getImages().length();
for (int j = 0; j < length; j++) {
if (list.get(groupPosition).getList().get(childPosition).getImages().substring(j, j + 1).equals("|")) {
str = list.get(groupPosition).getList().get(childPosition).getImages().substring(j + 1, length).trim();
}
}
Glide.with(mContext).load(str).into(childHolder.child_icon);
// 设置商品名称***
childHolder.child_title.setText(list.get(groupPosition).getList().get(childPosition).getTitle());
// 设置商品价格***
childHolder.child_price.setText("¥"+list.get(groupPosition).getList().get(childPosition).getPrice() + "");
//设置chebox复选框是否选中
childHolder.child_checkBox.setChecked(list.get(groupPosition).getList().get(childPosition).getSelected() == 1);
//设置自定义控件中的数量
childHolder.add_remove_view.setNumber(list.get(groupPosition).getList().get(childPosition).getNum());
//设置商品checkBox点击事件, 通过接口回调,暴露给外面
childHolder.child_checkBox.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (mOnCartListChangeListener != null){
mOnCartListChangeListener.onChildCheckedChange(groupPosition, childPosition);
}
}
});
//设置数量点击事件, 通过接口回调,暴露给外面
childHolder.add_remove_view.setNumberChangeListener(new AddSubView.OnNumberChangeListener() {
@Override
public void OnNumberChange(int number) {
if (mOnCartListChangeListener != null){
mOnCartListChangeListener.onNumberChange(groupPosition, childPosition, number);
}
}
});
return convertView;
}
//定义判断复选框的boolean状态--------------------------------------
//创建商家的复选框方法 //遍历所有商品复选框 //判断商家选中状态
public boolean isParentSelected(int i) {
List<ShoppingBean.DataBean.ListBean> getList = this.list.get(i).getList();
for (ShoppingBean.DataBean.ListBean bean : getList) {
if (bean.getSelected() == 0) {
return false;
}
}
return true;
}
//下方的全选/全不选按钮的状态 //遍历所有的框
public boolean isAllSelected(){
for(int s = 0; s < list.size(); s++){
List<ShoppingBean.DataBean.ListBean> listAll = this.list.get(s).getList();
for (int j = 0; j < listAll.size(); j++){
if (listAll.get(j).getSelected() == 0){
return false;
}
}
}
return true;
}
//计算总数量 遍历 求所有商品数量的和
public int totalNumber(){
int totalNumber = 0;
for (int i = 0; i < list.size(); i++) {
List<ShoppingBean.DataBean.ListBean> list2 = this.list.get(i).getList();
for (int j = 0; j < list2.size(); j++) {
if (list2.get(j).getSelected() == 1){
int num = list2.get(j).getNum();
totalNumber += num;
}
}
}
return totalNumber;
}
//计算总价格 遍历 求所有商品价格的和
public float totalPrice(){
int totalPrice = 0;
for (int i = 0; i < list.size(); i++) {
List<ShoppingBean.DataBean.ListBean> list3 = this.list.get(i).getList();
for (int j = 0; j < list3.size(); j++) {
if (list3.get(j).getSelected() == 1){
double price = list3.get(j).getPrice();
int num = list3.get(j).getNum();
totalPrice += num * price;
}
}
}
return totalPrice;
}
//商家选中时 更新checkBox的状态
public void changeParentAllStatus(int i, boolean isSelected){
List<ShoppingBean.DataBean.ListBean> beans = this.list.get(i).getList();
for (int j = 0; j < beans.size(); j++) {
ShoppingBean.DataBean.ListBean bean = beans.get(j);
bean.setSelected(isSelected ? 1 : 0);
}
}
//当商品选中时 更新checkbox状态
public void changeChildAllStatus(int i, int i1){
ShoppingBean.DataBean.ListBean beans = list.get(i).getList().get(i1);
beans.setSelected(beans.getSelected()==0 ? 1 : 0);
}
//*设置所有的checkBox的状态
public void changeAllStatus(boolean isSelected){
for (int i = 0; i < list.size(); i++) {
List<ShoppingBean.DataBean.ListBean> beans = this.list.get(i).getList();
for (int j = 0; j < beans.size() ; j++) {
beans.get(j).setSelected(isSelected ? 1 : 0);
}
}
}
//*当加减器被点击
public void changeNumber(int i, int i1, int number){
ShoppingBean.DataBean.ListBean beans = list.get(i).getList().get(i1);
beans.setNum(number);
}
//*************商家的ViewHolder----------------------------------------------------
class ParentHolder {
CheckBox parent_checkBox;
TextView parent_title;
public ParentHolder(View itemView) {
parent_checkBox = itemView.findViewById(R.id.parent_checkBox);
parent_title = itemView.findViewById(R.id.parent_title);
itemView.setTag(this);
}
//绑定数据写在holder中。
}
//商品------------------------------
class ChildHolder {
CheckBox child_checkBox;
ImageView child_icon;
TextView child_title, child_price;
AddSubView add_remove_view;
private ChildHolder(View itemView) {
child_checkBox = itemView.findViewById(R.id.child_checkBox);
child_icon = itemView.findViewById(R.id.child_icon);
child_title = itemView.findViewById(R.id.child_title);
child_price = itemView.findViewById(R.id.child_price);
add_remove_view = itemView.findViewById(R.id.add_remove_view);
itemView.setTag(this);
}
//绑定数据写在holder中。
}
//向activity暴露数据的接口
//成员变量
OnCartListChangeListener mOnCartListChangeListener;
//方法的set方法
public void setOnCartListChangeListener(OnCartListChangeListener onCartListChangeListener) {
mOnCartListChangeListener = onCartListChangeListener;
}
public interface OnCartListChangeListener {
//当商家的checkBox点击时回调 **
void onParentCheckedChange(int i);
//当商品的CheckBox点击时回调 **
void onChildCheckedChange(int i, int i1);
//当点击加减按钮的回调 ***
void onNumberChange(int i, int i1, int number);
}
//以下的 不需要使用============================
@Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return false;
}
@Override
public Object getGroup(int groupPosition) {
return null;
}
@Override
public Object getChild(int groupPosition, int childPosition) {
return null;
}
@Override
public long getGroupId(int groupPosition) {
return 0;
}
@Override
public long getChildId(int groupPosition, int childPosition) {
return 0;
}
@Override
public boolean hasStableIds() {
return false;
}
}
AddSubView自定义(加减)
package com.zjh.administrat.shoppcarexpandablelistview.view;
import android.content.Context;
import android.util.AttributeSet;
import android.view.View;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;
import com.zjh.administrat.shoppcarexpandablelistview.R;
public class AddSubView extends LinearLayout implements View.OnClickListener {
private int number = 1;
private TextView number_jian,number_number, number_add;
public AddSubView(Context context) {
this(context, null);
}
public AddSubView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public AddSubView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
View view = inflate(context, R.layout.add_remove_number, this);
number_jian = view.findViewById(R.id.number_jian);
number_number = view.findViewById(R.id.number_number);
number_add = view.findViewById(R.id.number_add);
number_jian.setOnClickListener(this);
number_add.setOnClickListener(this);
}
//点击事件
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.number_jian:
if (number > 1) {
-- number;
number_number.setText(number + "");
if (mNumberChangeListener != null) {
mNumberChangeListener.OnNumberChange(number);
}
} else {
Toast.makeText(getContext(), "我是有底线的!", Toast.LENGTH_SHORT).show();
}
break;
case R.id.number_add:
if (number < 9) {
++ number;
number_number.setText(number+"");
if (mNumberChangeListener != null) {
mNumberChangeListener.OnNumberChange(number);
}
} else {
Toast.makeText(getContext(), "每人限购9件!", Toast.LENGTH_SHORT).show();
}
default:
break;
}
}
public int getNumber() {
return number;
}
public void setNumber(int number) {
this.number = number;
number_number.setText(number+"");
}
//成员变量
OnNumberChangeListener mNumberChangeListener;
//set方法
public void setNumberChangeListener(OnNumberChangeListener onNumberChangeListener) {
this.mNumberChangeListener = onNumberChangeListener;
}
//定义个接口
public interface OnNumberChangeListener{
void OnNumberChange(int number);
}
}
以下的布局
activity_main.xml主布局
<?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"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".view.MainActivity">
<TextView
android:layout_width="match_parent"
android:layout_height="50dp"
android:background="#fffc"
android:gravity="center"
android:text="购 物 车"
android:textColor="#f00"
android:textSize="30sp"
android:textStyle="bold" />
<ExpandableListView
android:id="@+id/listView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="9" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="60dp"
android:layout_alignParentBottom="true"
android:layout_weight="1"
android:background="#94cc"
android:gravity="center_vertical">
<CheckBox
android:id="@+id/selectAll"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="全选"
android:textSize="25sp" />
<TextView
android:id="@+id/priceAll"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:paddingLeft="20dp"
android:text="合计:¥0.00"
android:textColor="#f00"
android:textSize="30sp" />
<Button
android:id="@+id/numberAll"
android:layout_width="120dp"
android:layout_height="match_parent"
android:background="#cc4"
android:text="去结算[0]"
android:textSize="20sp"
android:textStyle="bold" />
</LinearLayout>
</LinearLayout>
item_cart_parent.xml商家
<?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"
android:orientation="horizontal">
<CheckBox
android:id="@+id/parent_checkBox"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"/>
<TextView
android:id="@+id/parent_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="30sp"
android:textStyle="bold"
android:gravity="center"
/>
</LinearLayout>
item_cart_child.xml商品
<?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="wrap_content"
android:orientation="horizontal">
<CheckBox
android:id="@+id/child_checkBox"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
/>
<ImageView
android:id="@+id/child_icon"
android:layout_width="80dp"
android:layout_height="80dp"
android:scaleType="centerCrop"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="8"
android:orientation="vertical">
<TextView
android:id="@+id/child_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="数据"
android:textSize="25sp"
android:maxLines="2"
/>
<TextView
android:id="@+id/child_price"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="¥0.0"
android:textSize="25sp"
android:textStyle="bold"
android:textColor="#f00"
/>
</LinearLayout>
<com.zjh.administrat.shoppcarexpandablelistview.view.AddSubView
android:id="@+id/add_remove_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"/>
</LinearLayout>
add_remove_number.xml加减器
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="70dp"
android:layout_height="30dp"
android:background="#99fff0"
android:padding="3dp"
android:orientation="horizontal">
<TextView
android:id="@+id/number_jian"
android:layout_width="0dp"
android:layout_height="match_parent"
android:background="#fcf4ff"
android:layout_weight="1"
android:textSize="25sp"
android:gravity="center"
android:text="-"
/>
<TextView
android:id="@+id/number_number"
android:layout_width="0dp"
android:layout_height="match_parent"
android:background="#44cc"
android:layout_weight="2"
android:text="1"
android:padding="1dp"
android:textSize="20sp"
android:gravity="center"
/>
<TextView
android:id="@+id/number_add"
android:layout_width="0dp"
android:layout_height="match_parent"
android:background="#fcf4ff"
android:layout_weight="1"
android:textSize="25sp"
android:gravity="center"
android:text="+"
/>
</LinearLayout>
![购物车1](https://i-blog.csdnimg.cn/blog_migrate/a14599588fe348313d8c6fe421c4a8d3.png)