Android 购物车页面和逻辑实现

距离上次写第一篇博客已经好久了,今天正好有时间就来写一篇关于最近在做的项目中的一个功能 购物车! 我这个购物车业务逻辑还算可以吧,不算太难,但由于我是第一次做,所以也碰到了很多细节上的问题...所以我想总结下来,方便以后学习和使用..好了先看看效果吧!



目前我做的功能除了结算就这些了...

下面开始来看代码

Activity界面是这样的


首先是Activity 布局xml




    

    


    


    

    

    


        

        
        


        
    

再来看 ListView item的布局



item 布局xml




    

    

    

        

        

            

            

            

            
        


        

        

            

        


        

        

            


            
        
    

    

好了 ,,布局就说完了 现在我们来看看逻辑部分

由于很多操作是在Activity中操作 ListView的item ,所以我这里选择的是接口回调,我感觉方便些..也许你会有更好的方法.

首先我们在 Adapter中定义了几个

    /**
     * 复选框接口
     */
    public interface CheckInterface {
        /**
         * 组选框状态改变触发的事件
         *
         * @param position  元素位置
         * @param isChecked 元素选中与否
         */
        void checkGroup(int position, boolean isChecked);
    }


    /**
     * 改变数量的接口
     */
    public interface ModifyCountInterface {
        /**
         * 增加操作
         *
         * @param position      组元素位置
         * @param showCountView 用于展示变化后数量的View
         * @param isChecked     子元素选中与否
         */
        void doIncrease(int position, View showCountView, boolean isChecked);

        /**
         * 删减操作
         *
         * @param position      组元素位置
         * @param showCountView 用于展示变化后数量的View
         * @param isChecked     子元素选中与否
         */
        void doDecrease(int position, View showCountView, boolean isChecked);

        /**
         * 删除子item
         *
         * @param position
         */
        void childDelete(int position);
    }


再来看看Adapter 没啥可说的.. 注释我在代码写的还算详细 ,相信能看懂

public class ShoppingCartAdapter extends BaseAdapter {

    private boolean isShow = true;//是否显示编辑/完成
    private List shoppingCartBeanList;
    private CheckInterface checkInterface;
    private ModifyCountInterface modifyCountInterface;
    private Context context;

    public ShoppingCartAdapter(Context context) {
        this.context = context;
    }

    public void setShoppingCartBeanList(List shoppingCartBeanList) {
        this.shoppingCartBeanList = shoppingCartBeanList;
        notifyDataSetChanged();
    }

    /**
     * 单选接口
     *
     * @param checkInterface
     */
    public void setCheckInterface(CheckInterface checkInterface) {
        this.checkInterface = checkInterface;
    }

    /**
     * 改变商品数量接口
     *
     * @param modifyCountInterface
     */
    public void setModifyCountInterface(ModifyCountInterface modifyCountInterface) {
        this.modifyCountInterface = modifyCountInterface;
    }

    @Override
    public int getCount() {
        return shoppingCartBeanList == null ? 0 : shoppingCartBeanList.size();
    }

    @Override
    public Object getItem(int position) {
        return shoppingCartBeanList.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }


    /**
     * 是否显示可编辑
     *
     * @param flag
     */
    public void isShow(boolean flag) {
        isShow = flag;
        notifyDataSetChanged();
    }

    @Override
    public View getView(final int position, View convertView, ViewGroup parent) {

        final ViewHolder holder;
        if (convertView == null) {
            convertView = LayoutInflater.from(context).inflate(R.layout.item_shopping_cart_layout, parent, false);
            holder = new ViewHolder(convertView);
            convertView.setTag(holder);
        } else {
            holder = (ViewHolder) convertView.getTag();
        }
        final ShoppingCartBean shoppingCartBean = shoppingCartBeanList.get(position);
        holder.tv_commodity_name.setText(shoppingCartBean.getShoppingName());
        holder.tv_fabric.setText("面料:" + shoppingCartBean.getFabric());
        holder.tv_dress.setText("西服尺寸:" + shoppingCartBean.getDressSize());
        holder.tv_pants.setText("西裤尺寸:" + shoppingCartBean.getPantsSize());
        holder.tv_price.setText("¥:" + shoppingCartBean.getPrice());
        holder.ck_chose.setChecked(shoppingCartBean.isChoosed());
        holder.tv_show_num.setText(shoppingCartBean.getCount() + "");
        holder.tv_num.setText("X" + shoppingCartBean.getCount());

        //单选框按钮
        holder.ck_chose.setOnClickListener(
                new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        shoppingCartBean.setChoosed(((CheckBox) v).isChecked());
                        checkInterface.checkGroup(position, ((CheckBox) v).isChecked());//向外暴露接口
                    }
                }
        );

        //增加按钮
        holder.iv_add.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                modifyCountInterface.doIncrease(position, holder.tv_show_num, holder.ck_chose.isChecked());//暴露增加接口
            }
        });

        //删减按钮
        holder.iv_sub.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                modifyCountInterface.doDecrease(position, holder.tv_show_num, holder.ck_chose.isChecked());//暴露删减接口
            }
        });


        //删除弹窗
        holder.tv_delete.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                AlertDialog alert = new AlertDialog.Builder(context).create();
                alert.setTitle("操作提示");
                alert.setMessage("您确定要将这些商品从购物车中移除吗?");
                alert.setButton(DialogInterface.BUTTON_NEGATIVE, "取消",
                        new DialogInterface.OnClickListener() {
                            @Override
                            public void onClick(DialogInterface dialog, int which) {
                                return;
                            }
                        });
                alert.setButton(DialogInterface.BUTTON_POSITIVE, "确定",
                        new DialogInterface.OnClickListener() {
                            @Override
                            public void onClick(DialogInterface dialog, int which) {
                                modifyCountInterface.childDelete(position);//删除 目前只是从item中移除

                            }
                        });
                alert.show();
            }
        });

        //判断是否在编辑状态下
        if (isShow) {
            holder.tv_commodity_name.setVisibility(View.VISIBLE);
            holder.tv_fabric.setVisibility(View.VISIBLE);
            holder.rl_edit.setVisibility(View.GONE);
            holder.tv_delete.setVisibility(View.GONE);
        } else {
            holder.tv_commodity_name.setVisibility(View.GONE);
            holder.tv_fabric.setVisibility(View.GONE);
            holder.rl_edit.setVisibility(View.VISIBLE);
            holder.tv_delete.setVisibility(View.VISIBLE);
        }

        return convertView;
    }


    //初始化控件
    class ViewHolder {
        ImageView iv_chose;
        ImageView iv_show_pic, iv_sub, iv_add;
        TextView tv_commodity_name, tv_fabric, tv_dress, tv_pants, tv_price, tv_num, tv_delete, tv_show_num;
        CheckBox ck_chose;
        RelativeLayout rl_edit;

        public ViewHolder(View itemView) {
            ck_chose = (CheckBox) itemView.findViewById(R.id.ck_chose);
            iv_show_pic = (ImageView) itemView.findViewById(R.id.iv_show_pic);
            iv_sub = (ImageView) itemView.findViewById(R.id.iv_sub);
            iv_add = (ImageView) itemView.findViewById(R.id.iv_add);

            tv_commodity_name = (TextView) itemView.findViewById(R.id.tv_commodity_name);
            tv_fabric = (TextView) itemView.findViewById(R.id.tv_fabric);
            tv_dress = (TextView) itemView.findViewById(R.id.tv_dress);
            tv_pants = (TextView) itemView.findViewById(R.id.tv_pants);
            tv_price = (TextView) itemView.findViewById(R.id.tv_price);
            tv_num = (TextView) itemView.findViewById(R.id.tv_num);
            tv_delete = (TextView) itemView.findViewById(R.id.tv_delete);
            tv_show_num = (TextView) itemView.findViewById(R.id.tv_show_num);
            rl_edit = (RelativeLayout) itemView.findViewById(R.id.rl_edit);

        }

    }

现在我们在来看看Activity 代码, 同样注释写的很详细

public class ShoppingCartActivity extends BaseActivity implements View.OnClickListener
        , ShoppingCartAdapter.CheckInterface, ShoppingCartAdapter.ModifyCountInterface {
    public TextView tv_title, tv_settlement, tv_show_price;
    private TextView tv_all_check;
    private CheckBox ck_all;
    private ListView list_shopping_cart;
    private ShoppingCartAdapter shoppingCartAdapter;
    private TextView tv_edit;
    private boolean flag = false;
    private List shoppingCartBeanList = new ArrayList<>();
    private boolean mSelect;
    private double totalPrice = 0.00;// 购买的商品总价
    private int totalCount = 0;// 购买的商品总数量
    /**
     * 批量模式下,用来记录当前选中状态
     */
    private SparseArray mSelectState = new SparseArray();


    @Override
    protected int getLayout() {
        return R.layout.layout_shopping_cart_activity;
    }

    @Override
    protected void initView() {
        tv_title = bindView(R.id.tv_title);
        tv_title.setText("购物车");
        list_shopping_cart = bindView(R.id.list_shopping_cart);
//        list_shopping_cart.setOnItemClickListener(this);
        ck_all = bindView(R.id.ck_all);
        ck_all.setOnClickListener(this);
//        ck_all.setOnCheckedChangeListener(this);
        tv_show_price = bindView(R.id.tv_show_price);
        tv_settlement = bindView(R.id.tv_settlement);
        tv_settlement.setOnClickListener(this);
        tv_edit = bindView(R.id.tv_edit);
        tv_edit.setOnClickListener(this);
        shoppingCartAdapter = new ShoppingCartAdapter(this);
        shoppingCartAdapter.setCheckInterface(this);
        shoppingCartAdapter.setModifyCountInterface(this);
        list_shopping_cart.setAdapter(shoppingCartAdapter);
        shoppingCartAdapter.setShoppingCartBeanList(shoppingCartBeanList);

    }

    @Override
    protected void initData() {

        for (int i = 0; i < 6; i++) {
            ShoppingCartBean shoppingCartBean = new ShoppingCartBean();
            shoppingCartBean.setShoppingName("高端大气上档次的T桖");
            shoppingCartBean.setFabric("纯棉");
            shoppingCartBean.setDressSize(48);
            shoppingCartBean.setPantsSize(65);
            shoppingCartBean.setPrice(60);
            shoppingCartBean.setCount(2);
            shoppingCartBeanList.add(shoppingCartBean);
        }

    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            //全选按钮  
            case R.id.ck_all:
                if (shoppingCartBeanList.size() != 0) {
                    if (ck_all.isChecked()) {
                        for (int i = 0; i < shoppingCartBeanList.size(); i++) {
                            shoppingCartBeanList.get(i).setChoosed(true);
                        }
                        shoppingCartAdapter.notifyDataSetChanged();
                    } else {
                        for (int i = 0; i < shoppingCartBeanList.size(); i++) {
                            shoppingCartBeanList.get(i).setChoosed(false);
                        }
                        shoppingCartAdapter.notifyDataSetChanged();
                    }
                }
                statistics();
                break;
            case R.id.tv_edit:
                flag = !flag;
                if (flag) {
                    tv_edit.setText("完成");
                    shoppingCartAdapter.isShow(false);
                } else {
                    tv_edit.setText("编辑");
                    shoppingCartAdapter.isShow(true);
                }
                break;
        }
    }

    /**
     * 单选
     *
     * @param position  组元素位置
     * @param isChecked 组元素选中与否
     */
    @Override
    public void checkGroup(int position, boolean isChecked) {

        shoppingCartBeanList.get(position).setChoosed(isChecked);

        if (isAllCheck())
            ck_all.setChecked(true);
        else
            ck_all.setChecked(false);

        shoppingCartAdapter.notifyDataSetChanged();
        statistics();
    }


    /**
     * 遍历list集合
     *
     * @return
     */
    private boolean isAllCheck() {

        for (ShoppingCartBean group : shoppingCartBeanList) {
            if (!group.isChoosed())
                return false;
        }
        return true;
    }

    /**
     * 统计操作
     * 1.先清空全局计数器
* 2.遍历所有子元素,只要是被选中状态的,就进行相关的计算操作 * 3.给底部的textView进行数据填充 */ public void statistics() { totalCount = 0; totalPrice = 0.00; for (int i = 0; i < shoppingCartBeanList.size(); i++) { ShoppingCartBean shoppingCartBean = shoppingCartBeanList.get(i); if (shoppingCartBean.isChoosed()) { totalCount++; totalPrice += shoppingCartBean.getPrice() * shoppingCartBean.getCount(); } } tv_show_price.setText("合计:" + totalPrice); tv_settlement.setText("结算(" + totalCount + ")"); } /** * 增加 * * @param position 组元素位置 * @param showCountView 用于展示变化后数量的View * @param isChecked 子元素选中与否 */ @Override public void doIncrease(int position, View showCountView, boolean isChecked) { ShoppingCartBean shoppingCartBean = shoppingCartBeanList.get(position); int currentCount = shoppingCartBean.getCount(); currentCount++; shoppingCartBean.setCount(currentCount); ((TextView) showCountView).setText(currentCount + ""); shoppingCartAdapter.notifyDataSetChanged(); statistics(); } /** * 删减 * * @param position 组元素位置 * @param showCountView 用于展示变化后数量的View * @param isChecked 子元素选中与否 */ @Override public void doDecrease(int position, View showCountView, boolean isChecked) { ShoppingCartBean shoppingCartBean = shoppingCartBeanList.get(position); int currentCount = shoppingCartBean.getCount(); if (currentCount == 1) { return; } currentCount--; shoppingCartBean.setCount(currentCount); ((TextView) showCountView).setText(currentCount + ""); shoppingCartAdapter.notifyDataSetChanged(); statistics(); } /** * 删除 * * @param position */ @Override public void childDelete(int position) { shoppingCartBeanList.remove(position); shoppingCartAdapter.notifyDataSetChanged(); statistics(); } }

整体的就是这样,,我说一下 我做的时候遇到的问题和解决办法

1.

问题:当我单选一个一个选中后,全选按钮也会自动选中 ,但是当我取消一个item后 全选按钮没有自动取消 (正常是只有有一个item没有选中 全选按钮是不会选中的)

解决:首先解决问题要找到原因所在 ,造成这个Bug的原因是我CheckBox的点击事件用的是setOnCheckedChangeListener 后来换成了setOnClickListener 就好了 .

两者都能实现对CheckBox的状态改变的监听,但一般情况下,用的更多的是setOnCheckedChangeListener。因为,当CheckBox的状态不是通过点击事件改变,而是通过其他的方式改变时,比如setCheck(),setOnClickListener无法完成此种情况下的监听。OnCheckChangedListener监听CheckBox的状态,无论来自你的onClick事件还是其他。

2.

问题: 就是在改变物品个数的是时候会出现复用!

解决: 原因就是我没有保存当前 改变后是值, 保存一下就OK了..


总体上就是这些了.......感兴趣的同学可以下载demo看看



Demo在这里----->http://download.csdn.net/detail/u011011744/9706870





你可能感兴趣的:(Android 购物车页面和逻辑实现)