一:效果图
二:技术选型
1. 项目框架模式:MVP;注意:分包分层,避免内存泄漏; 2. 自定义View; 3. 图片加载:Fresco图片加载框架; 4. 网络加载框架:Retrofit+rxjava2;Retrofit关联OkhttpClient的日志拦截器(日志库导入Okhttp第三方依赖库; 5. 列表数据展示使用XRecyclerView或RecyclerView; 6. 自定义属性; 7. 二级列表; 8. 自定义Dialog
三:业务逻辑需求
1. 实现首页接口,包括轮播图、京东秒杀和为你推荐等业务模块;
2. 轮播图使用自定义view实现(不允许使用第三方框架),实现轮播图中在不同Android设备中,各图片不变形,不剪切,实现良好的屏幕适配(图片大小比例是:502px*185px),得分点; (此处轮播图使用的第三方框架:Banner)
3. 图片展示使用Fresco图片加载框架;
4. 使用RecyclerView或xRecyclerView实现京东秒杀和为你推荐功能;京东秒杀倒计时功能;京东秒杀产品列表;为你推荐列表;
5. 点击轮播图,跳转到图二界面,图二页面实现一个唱片样式的自定义view
6. 唱片自定义view分为两部分,分别为旋转的唱片,和播放、暂停时改变摆放位置的指针
7. 要求必须添加自定义属性,可以设置该自定义view的唱片中间的图片,和唱片的旋转速度
8. 通过按钮切换唱片状态,当播放时唱片旋转,唱片指针位置在唱片上,暂停时,唱片停止旋转,唱片指针从唱片上移开
9. 点击效果图一上的任意商品,跳转到购物车界面
10. 购物车实现全选功能、选中商品总价功能、选中商品总数功能
11. 点击删除按钮,删除item,底部总数及总价能做出正确修改,接口数据删除
12. 点击数量编辑,弹出自定义Dialog实现加减按钮,每次点击加减,item中的总数及总价要做出相应的改变(如图五所示)
四:接口
1.首页接口:https://www.zhaoapi.cn/ad/getAd
请求参数:无; 响应数据:“data”:[] 轮播图 "tuijian": {} 为你推荐 "miaosha": {} 秒杀;
2.查询购物车:http://120.27.23.105/product/getCarts
返回格式:json; 请求方式:get/post; 接口备注:查询购物车;
请求参数说明:名称 类型 必填 说明
uid string 是 用户id
3.更新数据库:http://120.27.23.105/product/updateCarts?uid=71&sellerid=1&pid=1&selected=0&num=10
返回格式:json;
请求方式:get/post;
接口备注:更新购物车;
请求参数说明:名称 类型 必填 说明
uid string 是 用户id
sellerid string 是 商户id
pid string 是 商品id
num string 是 商品数量
selected string 是 是否选中(可省略);
4.删除购物车:http://120.27.23.105/product/deleteCart?uid=72&pid=1
返回格式:json; 请求方式:get/post ; 接口备注:删除购物车;
请求参数说明:名称 类型 必填 说明
uid string 是 用户id
pid string 是 商品id
一:依赖
//《Fresco图片框架依赖》 implementation 'com.facebook.fresco:fresco:0.14.1' //《Retrofit网络请求依赖》 implementation 'com.squareup.retrofit2:retrofit:2.4.0' implementation 'com.squareup.retrofit2:converter-gson:2.4.0' //《Rxjava2》 implementation 'io.reactivex.rxjava2:rxjava:2.1.7' implementation 'io.reactivex.rxjava2:rxandroid:2.0.1' //《RXjava2的适配器》 implementation 'com.squareup.retrofit2:adapter-rxjava2:2.4.0' //《Okhttp网络请求依赖》 implementation 'com.squareup.okhttp3:okhttp:3.10.0' //《Recyclerview的依赖》 implementation 'com.android.support:recyclerview-v7:27.1.1' //《Butterknife依赖(黄油刀)》 implementation 'com.jakewharton:butterknife:8.8.1' annotationProcessor 'com.jakewharton:butterknife-compiler:8.8.1' //《EventBus的依赖》 implementation 'org.greenrobot:eventbus:3.1.1' //《Banner依赖》 implementation 'com.youth.banner:banner:1.4.9' //日志拦截器 implementation 'com.squareup.okhttp3:logging-interceptor:3.4.1'
二:权限
//《请求网络的权限》 <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" /> <uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" tools:ignore="ProtectedPermissions" />
//App
android:name=".app.FrescoApp"
三:ApiService(定义接口 实现请求数据)
package com.example.dell.luokaiqin20180601.api; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import io.reactivex.Flowable; import retrofit2.http.GET; import retrofit2.http.Query; //定义接口 实现请求数据 public interface ApiService { //首页的数据请求 @GET("ad/getAd") Flowable<HomeDataBean> getHomeData(); //购物车数据请求 @GET("product/getCarts") Flowable<ShoopingDataBean> getShoopingData(@Query("uid") String uid); //购物车数据删除 @GET("product/deleteCart") Flowable<ShoopingDataBean> getShoopingDataDelete(@Query("uid") String uid,@Query("pid") String pid); //更新购物车数据 @GET("product/updateCarts") Flowable<ShoopingDataBean> getShoopingDataUpdata(@Query("uid") String uid,@Query("sellerid")String sellerid,@Query("pid")String pid, @Query("num")String num); }
四:RetrofitUtils(网络请求框架Retrofit+RxJava)
package com.example.dell.luokaiqin20180601.utils; import com.example.dell.luokaiqin20180601.api.ApiService; import okhttp3.OkHttpClient; import okhttp3.logging.HttpLoggingInterceptor; import retrofit2.Retrofit; import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory; import retrofit2.converter.gson.GsonConverterFactory; //网络请求框架Retrofit+RxJava public class RetrofitUtils { //创建单例模式 private static volatile RetrofitUtils instance; private final Retrofit retrofit; private final ApiService apiService; //创建私有的无参构造 private RetrofitUtils(String url){ //创建日志拦截器 HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor(); interceptor.setLevel(HttpLoggingInterceptor.Level.BASIC); OkHttpClient client = new OkHttpClient.Builder() .addInterceptor(interceptor) .build(); //创建Retrofit retrofit = new Retrofit.Builder() .baseUrl(url) .addConverterFactory(GsonConverterFactory.create())//默认使用Gson进行解析 .addCallAdapterFactory(RxJava2CallAdapterFactory.create())//默认使用RxJava2适配器 .client(client)//添加日志拦截器 .build(); //只创建一次 (防止多次调用) apiService = retrofit.create(ApiService.class); } //创建静态方法 得到instance 提供单列实例 public static RetrofitUtils getInstance(String url){ //双向判空 if(instance==null){ //添加同步锁 synchronized (RetrofitUtils.class){ if(null==instance){ //创建instance instance = new RetrofitUtils(url); } } } //返回instance return instance; } //定义方法 便于调用 public ApiService getApiService(){ return apiService; } }
五:初始化Fresco图片
package com.example.dell.luokaiqin20180601.app; import android.app.Application; import com.facebook.drawee.backends.pipeline.Fresco; public class FrescoApp extends Application { @Override public void onCreate() { super.onCreate(); //初始化Fresco图片 Fresco.initialize(this); } }
六:用于Banner轮播图
package com.example.dell.luokaiqin20180601.app; import android.content.Context; import android.net.Uri; import android.widget.ImageView; import com.facebook.drawee.view.SimpleDraweeView; import com.youth.banner.loader.ImageLoader; //用于Banner轮播图 public class HomeImgApp extends ImageLoader{ @Override public void displayImage(Context context, Object path, ImageView imageView) { //用fresco加载图片简单用法,记得要写下面的createImageView方法 Uri uri = Uri.parse((String) path); imageView.setImageURI(uri); } //提供createImageView 方法,如果不用可以不重写这个方法,主要是方便自定义ImageView的创建 @Override public ImageView createImageView(Context context) { //使用fresco,需要创建它提供的ImageView,当然你也可以用自己自定义的具有图片加载功能的ImageView SimpleDraweeView simpleDraweeView=new SimpleDraweeView(context); return simpleDraweeView; } }七:首页的数据Bean
package com.example.dell.luokaiqin20180601.model.Home; import java.util.List; /* 首页的数据Bean */ public class HomeDataBean { private String msg; private String code; private TuijianBean tuijian; private MiaoshaBean miaosha; private List<DataBean> data; public String getMsg() { return msg; } public void setMsg(String msg) { this.msg = msg; } public String getCode() { return code; } public void setCode(String code) { this.code = code; } public TuijianBean getTuijian() { return tuijian; } public void setTuijian(TuijianBean tuijian) { this.tuijian = tuijian; } public MiaoshaBean getMiaosha() { return miaosha; } public void setMiaosha(MiaoshaBean miaosha) { this.miaosha = miaosha; } public List<DataBean> getData() { return data; } public void setData(List<DataBean> data) { this.data = data; } public static class TuijianBean { private String name; private List<ListBean> list; public String getName() { return name; } public void setName(String name) { this.name = name; } public List<ListBean> getList() { return list; } public void setList(List<ListBean> list) { this.list = list; } public static class ListBean { private double bargainPrice; private String createtime; private String detailUrl; private String images; private int itemtype; private int pid; private double price; private int pscid; private int salenum; private int sellerid; private String subhead; private String title; public double getBargainPrice() { return bargainPrice; } public void setBargainPrice(double bargainPrice) { this.bargainPrice = bargainPrice; } public String getCreatetime() { return createtime; } public void setCreatetime(String createtime) { this.createtime = createtime; } public String getDetailUrl() { return detailUrl; } public void setDetailUrl(String detailUrl) { this.detailUrl = detailUrl; } public String getImages() { return images; } public void setImages(String images) { this.images = images; } public int getItemtype() { return itemtype; } public void setItemtype(int itemtype) { this.itemtype = itemtype; } public int getPid() { return pid; } public void setPid(int pid) { this.pid = pid; } public double getPrice() { return price; } public void setPrice(double price) { this.price = price; } public int getPscid() { return pscid; } public void setPscid(int pscid) { this.pscid = pscid; } public int getSalenum() { return salenum; } public void setSalenum(int salenum) { this.salenum = salenum; } public int getSellerid() { return sellerid; } public void setSellerid(int sellerid) { this.sellerid = sellerid; } public String getSubhead() { return subhead; } public void setSubhead(String subhead) { this.subhead = subhead; } public String getTitle() { return title; } public void setTitle(String title) { this.title = title; } } } public static class MiaoshaBean { private String name; private int time; private List<ListBeanX> list; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getTime() { return time; } public void setTime(int time) { this.time = time; } public List<ListBeanX> getList() { return list; } public void setList(List<ListBeanX> list) { this.list = list; } public static class ListBeanX { private double bargainPrice; private String createtime; private String detailUrl; private String images; private int itemtype; private int pid; private double price; private int pscid; private int salenum; private int sellerid; private String subhead; private String title; public double getBargainPrice() { return bargainPrice; } public void setBargainPrice(double bargainPrice) { this.bargainPrice = bargainPrice; } public String getCreatetime() { return createtime; } public void setCreatetime(String createtime) { this.createtime = createtime; } public String getDetailUrl() { return detailUrl; } public void setDetailUrl(String detailUrl) { this.detailUrl = detailUrl; } public String getImages() { return images; } public void setImages(String images) { this.images = images; } public int getItemtype() { return itemtype; } public void setItemtype(int itemtype) { this.itemtype = itemtype; } public int getPid() { return pid; } public void setPid(int pid) { this.pid = pid; } public double getPrice() { return price; } public void setPrice(double price) { this.price = price; } public int getPscid() { return pscid; } public void setPscid(int pscid) { this.pscid = pscid; } public int getSalenum() { return salenum; } public void setSalenum(int salenum) { this.salenum = salenum; } public int getSellerid() { return sellerid; } public void setSellerid(int sellerid) { this.sellerid = sellerid; } public String getSubhead() { return subhead; } public void setSubhead(String subhead) { this.subhead = subhead; } public String getTitle() { return title; } public void setTitle(String title) { this.title = title; } } } public static class DataBean { private int aid; private String createtime; private String icon; private Object productId; private String title; private int type; private String url; public int getAid() { return aid; } public void setAid(int aid) { this.aid = aid; } public String getCreatetime() { return createtime; } public void setCreatetime(String createtime) { this.createtime = createtime; } public String getIcon() { return icon; } public void setIcon(String icon) { this.icon = icon; } public Object getProductId() { return productId; } public void setProductId(Object productId) { this.productId = productId; } public String getTitle() { return title; } public void setTitle(String title) { this.title = title; } public int getType() { return type; } public void setType(int type) { this.type = type; } public String getUrl() { return url; } public void setUrl(String url) { this.url = url; } } }八:首页数据的M层接口
package com.example.dell.luokaiqin20180601.model.Home; import com.example.dell.luokaiqin20180601.prsenter.HomeDataPrsenter; //首页数据的M层接口 public interface HomeDataModel { //首页请求数据 void getHomeData(String url,HomeDataPrsenter prsenter); }九:首页数据的M层实现类
package com.example.dell.luokaiqin20180601.model.Home;
import com.example.dell.luokaiqin20180601.prsenter.HomeDataPrsenter; import com.example.dell.luokaiqin20180601.utils.RetrofitUtils; import io.reactivex.Flowable; //首页数据的M层实现类 public class MyHomeDataModel implements HomeDataModel { @Override public void getHomeData(String url,HomeDataPrsenter prsenter) { Flowable<HomeDataBean> homeData = RetrofitUtils.getInstance(url).getApiService().getHomeData(); //调用P层的方法 prsenter.Success(homeData); } }
十:首页数据的P层接口
package com.example.dell.luokaiqin20180601.prsenter; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; import io.reactivex.Flowable; //首页数据的P层接口 public interface HomeDataPrsenter { //定义成功与失败的方法 void Success(Flowable<HomeDataBean> homeData); void Error(); }十一:
首页数据的P层实现类
package com.example.dell.luokaiqin20180601.prsenter; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; import com.example.dell.luokaiqin20180601.model.Home.MyHomeDataModel; import com.example.dell.luokaiqin20180601.view.Home.HomeDataView; import io.reactivex.Flowable; import io.reactivex.android.schedulers.AndroidSchedulers; import io.reactivex.schedulers.Schedulers; import io.reactivex.subscribers.DisposableSubscriber; //首页数据的P层实现类 public class MyHomeDataPrsenter implements HomeDataPrsenter { HomeDataView dataView; private final MyHomeDataModel model; public MyHomeDataPrsenter(HomeDataView dataView){ this.dataView=dataView; model = new MyHomeDataModel(); } @Override public void Success(Flowable<HomeDataBean> homeData) { homeData.subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new DisposableSubscriber<HomeDataBean>() { @Override public void onNext(HomeDataBean homeDataBean) { if (homeDataBean!=null){ dataView.toBackHome(homeDataBean); } } @Override public void onError(Throwable t) { } @Override public void onComplete() { } }); } @Override public void Error() { } //调用接收url的方法 public void getHomeData(String url){ //进行请求 model.getHomeData(url,this); } //销毁V层 防止内存泄露 public void daadData() { if(dataView!=null){ dataView=null; } }
}
十二:首页数据的V层接口
package com.example.dell.luokaiqin20180601.view.Home; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; //首页数据的V层接口 public interface HomeDataView { //定义接收数据的方法 void toBackHome(HomeDataBean homeDataBean); }十三:首页数据的V层实现(主Activity)
package com.example.dell.luokaiqin20180601.view.Home; import android.content.Intent; import android.os.Bundle; import android.os.Handler; import android.os.Message; import android.support.v7.app.AppCompatActivity; import android.support.v7.widget.DividerItemDecoration; import android.support.v7.widget.GridLayoutManager; import android.support.v7.widget.LinearLayoutManager; import android.support.v7.widget.RecyclerView; import android.util.Log; import android.widget.TextView; import com.example.dell.luokaiqin20180601.R; import com.example.dell.luokaiqin20180601.adapter.MsAdapter; import com.example.dell.luokaiqin20180601.adapter.TjAdapter; import com.example.dell.luokaiqin20180601.app.HomeImgApp; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; import com.example.dell.luokaiqin20180601.prsenter.MyHomeDataPrsenter; import com.example.dell.luokaiqin20180601.view.Play.Main2Activity; import com.example.dell.luokaiqin20180601.view.Shooping.ShoopingActivity; import com.youth.banner.Banner; import com.youth.banner.listener.OnBannerListener; import com.youth.banner.transformer.CubeOutTransformer; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.Calendar; import java.util.Date; import java.util.List; import butterknife.BindView; import butterknife.ButterKnife; //首页数据的V层实现(主Activity) public class MainActivity extends AppCompatActivity implements HomeDataView,TjAdapter.OnClickListener { @BindView(R.id.home_banner) Banner home_Banner; List<String> imglist = new ArrayList<>(); @BindView(R.id.tv_miaosha) TextView tv_Miaosha; @BindView(R.id.tv_miaosha_time) TextView tv_Miaosha_Time; @BindView(R.id.tv_miaosha_shi) TextView tv_Miaosha_Shi; @BindView(R.id.tv_miaosha_minter) TextView tv_Miaosha_Minter; @BindView(R.id.tv_miaosha_second) TextView tv_Miaosha_Second; @BindView(R.id.ms_rcv) RecyclerView ms_Rcv; @BindView(R.id.tj_rcv) RecyclerView tj_Rcv; private List<HomeDataBean.MiaoshaBean.ListBeanX> list; //京东秒杀倒计时Handler private Handler handler = new Handler() { @Override public void handleMessage(Message msg) { super.handleMessage(msg); //秒杀倒计时 setTime(); sendEmptyMessageDelayed(0, 1000); } }; private MsAdapter msAdapter; private List<HomeDataBean.TuijianBean.ListBean> tuijianList; private TjAdapter tjAdapter; private MyHomeDataPrsenter prsenter; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); ButterKnife.bind(this); String url = "https://www.zhaoapi.cn/"; //实例化P层 将所需值传递到P层 prsenter = new MyHomeDataPrsenter(this); prsenter.getHomeData(url); //秒杀倒计时 setTime(); handler.sendEmptyMessageDelayed(0, 1000); //轮播图设置每个页面的点击事件 home_Banner.setOnBannerListener(new OnBannerListener() { @Override public void OnBannerClick(int position) { Intent intent = new Intent(MainActivity.this, Main2Activity.class); startActivity(intent); } }); } //接收数据的方法 @Override public void toBackHome(HomeDataBean homeDataBean) { //获取轮播图的数据 List<HomeDataBean.DataBean> data = homeDataBean.getData(); Log.e("++", "轮播图数量: " + data.size()); for (int i = 0; i < data.size(); i++) { String icon = data.get(i).getIcon(); imglist.add(icon); getBanner(); } //获取秒杀的数据 HomeDataBean.MiaoshaBean miaoshaBean = homeDataBean.getMiaosha(); list = miaoshaBean.getList(); //设置布局管理器 ms_Rcv.setLayoutManager(new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false)); //设置适配器 setMsAdapter(); //获取为你推荐的数据 HomeDataBean.TuijianBean tuijian = homeDataBean.getTuijian(); tuijianList = tuijian.getList(); //设置布局管理器 tj_Rcv.setLayoutManager(new GridLayoutManager(this, 2)); //设置为你推荐的布局添加Android自带的分割线 tj_Rcv.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.VERTICAL)); tj_Rcv.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.HORIZONTAL)); //设置适配器 setTjAdapter(); } //设置为你推荐适配器 private void setTjAdapter() { if (tjAdapter==null){ tjAdapter = new TjAdapter(this,tuijianList); tj_Rcv.setAdapter(tjAdapter); }else{ tjAdapter.notifyDataSetChanged(); } tjAdapter.setOnClick(this); } //设置秒杀适配器 private void setMsAdapter() { if (msAdapter == null) { msAdapter = new MsAdapter(this, list); ms_Rcv.setAdapter(msAdapter); } else { msAdapter.notifyDataSetChanged(); } } //首页的轮播图 private void getBanner() { home_Banner.setImageLoader(new HomeImgApp()); home_Banner.setImages(imglist).setBannerAnimation(CubeOutTransformer.class) .isAutoPlay(true) .setDelayTime(2000) .start(); } //京东秒杀 private void setTime() { SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); Date curDate = new Date(System.currentTimeMillis()); String format = df.format(curDate); StringBuffer buffer = new StringBuffer(); String substring = format.substring(0, 11); buffer.append(substring); Log.d("ccc", substring); Calendar calendar = Calendar.getInstance(); int hour = calendar.get(Calendar.HOUR_OF_DAY); if (hour % 2 == 0) { tv_Miaosha_Time.setText(hour + "点场"); buffer.append((hour + 2)); buffer.append(":00:00"); } else { tv_Miaosha_Time.setText((hour - 1) + "点场"); buffer.append((hour + 1)); buffer.append(":00:00"); } String totime = buffer.toString(); try { Date date = df.parse(totime); Date date1 = df.parse(format); long defferenttime = date.getTime() - date1.getTime(); long days = defferenttime / (1000 * 60 * 60 * 24); long hours = (defferenttime - days * (1000 * 60 * 60 * 24)) / (1000 * 60 * 60); long minute = (defferenttime - days * (1000 * 60 * 60 * 24) - hours * (1000 * 60 * 60)) / (1000 * 60); long seconds = defferenttime % 60000; long second = Math.round((float) seconds / 1000); tv_Miaosha_Shi.setText("0" + hours + ""); if (minute >= 10) { tv_Miaosha_Minter.setText(minute + ""); } else { tv_Miaosha_Minter.setText("0" + minute + ""); } if (second >= 10) { tv_Miaosha_Second.setText(second + ""); } else { tv_Miaosha_Second.setText("0" + second + ""); } } catch (ParseException e) { e.printStackTrace(); } } //为你推荐的条目点击事件 @Override public void OnClickitem(int position) { // Toast.makeText(this,"条目被点击了",Toast.LENGTH_SHORT).show(); Intent intent = new Intent(MainActivity.this, ShoopingActivity.class); startActivity(intent); } //销毁的方法 @Override protected void onDestroy() { super.onDestroy(); prsenter.daadData(); } }
十四:首页秒杀数据的适配器
package com.example.dell.luokaiqin20180601.adapter; import android.content.Context; import android.support.annotation.NonNull; import android.support.v7.widget.RecyclerView; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import com.example.dell.luokaiqin20180601.R; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; import com.facebook.drawee.view.SimpleDraweeView; import java.util.List; //首页秒杀的适配器 public class MsAdapter extends RecyclerView.Adapter { Context context; List<HomeDataBean.MiaoshaBean.ListBeanX> list; public MsAdapter(Context context, List<HomeDataBean.MiaoshaBean.ListBeanX> list) { this.context=context; this.list=list; } @NonNull @Override public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { View view = LayoutInflater.from(context).inflate(R.layout.ms_rcv_item, null); MyViewHolder myViewHolder = new MyViewHolder(view); return myViewHolder; } @Override public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) { MyViewHolder myViewHolder = (MyViewHolder) holder; String images = list.get(position).getImages(); String[] split = images.split("\\|"); myViewHolder.img.setImageURI(split[0]); } @Override public int getItemCount() { return list.size(); } class MyViewHolder extends RecyclerView.ViewHolder{ private final SimpleDraweeView img; public MyViewHolder(View view) { super(view); img = view.findViewById(R.id.ms_rcv_img); } } }
十五:首页为你推荐的数据的适配器
package com.example.dell.luokaiqin20180601.adapter; import android.content.Context; import android.support.annotation.NonNull; import android.support.v7.widget.RecyclerView; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.TextView; import com.example.dell.luokaiqin20180601.R; import com.example.dell.luokaiqin20180601.model.Home.HomeDataBean; import com.facebook.drawee.view.SimpleDraweeView; import java.util.List; //首页为你推荐的适配器 public class TjAdapter extends RecyclerView.Adapter{ Context context; List<HomeDataBean.TuijianBean.ListBean> list; public TjAdapter(Context context, List<HomeDataBean.TuijianBean.ListBean> list) { this.context=context; this.list=list; } @NonNull @Override public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { View view = LayoutInflater.from(context).inflate(R.layout.tj_rcv_item, null); MyViewHolder myViewHolder = new MyViewHolder(view); return myViewHolder; } @Override public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, final int position) { MyViewHolder myViewHolder = (MyViewHolder) holder; String images = list.get(position).getImages(); String[] split = images.split("\\|"); myViewHolder.img.setImageURI(split[0]); myViewHolder.title.setText(list.get(position).getTitle()); //设置条目的点击事件 myViewHolder.itemView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { onClickListener.OnClickitem(position); } }); } @Override public int getItemCount() { return list.size(); } class MyViewHolder extends RecyclerView.ViewHolder{ private final SimpleDraweeView img; private final TextView title; public MyViewHolder(View view) { super(view); img = view.findViewById(R.id.tj_rcv_img); title = view.findViewById(R.id.tj_rcv_title); } } //定义方法 OnClickListener onClickListener; public void setOnClick(OnClickListener onClickListener){ this.onClickListener=onClickListener; } //定义接口 ,实现点击事件 public interface OnClickListener{ void OnClickitem(int position); } }
十六:主布局页面
<?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.Home.MainActivity"> <com.youth.banner.Banner android:id="@+id/home_banner" android:layout_width="match_parent" android:layout_height="200dp"> </com.youth.banner.Banner> <!--京东秒杀布局引入--> <include layout="@layout/home_ms" android:layout_width="match_parent" android:layout_height="50dp"/> <android.support.v7.widget.RecyclerView android:id="@+id/ms_rcv" android:layout_width="match_parent" android:layout_height="100dp"> </android.support.v7.widget.RecyclerView> <TextView android:layout_width="match_parent" android:layout_height="50dp" android:layout_gravity="center" android:gravity="center" android:text="为你推荐"/> <android.support.v7.widget.RecyclerView android:id="@+id/tj_rcv" android:layout_width="match_parent" android:layout_height="match_parent"> </android.support.v7.widget.RecyclerView> </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" android:orientation="vertical"> <LinearLayout android:layout_width="match_parent" android:layout_height="50dp" android:layout_gravity="center_vertical" android:gravity="center_vertical"> <TextView android:id="@+id/tv_miaosha" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="10dp" android:text="京东秒杀" android:textColor="#f00" /> <TextView android:id="@+id/tv_miaosha_time" android:layout_width="wrap_content" android:layout_height="wrap_content" android:padding="5dp" android:text="14点场" /> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content"> <TextView android:id="@+id/tv_miaosha_shi" android:layout_width="15dp" android:layout_height="15dp" android:background="@drawable/shape_miaosha_time" android:gravity="center" android:text="1" android:textColor="#fff" android:textSize="10sp" /> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:padding="3dp" android:text=":" /> <TextView android:id="@+id/tv_miaosha_minter" android:layout_width="15dp" android:layout_height="15dp" android:background="@drawable/shape_miaosha_time" android:gravity="center" android:text="1" android:textColor="#fff" android:textSize="10sp" /> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:padding="3dp" android:text=":" /> <TextView android:id="@+id/tv_miaosha_second" android:layout_width="15dp" android:layout_height="15dp" android:background="@drawable/shape_miaosha_time" android:gravity="center" android:text="1" android:textColor="#fff" android:textSize="10sp" /> </LinearLayout> </LinearLayout> </LinearLayout>十六:秒杀下的rcv子条目布局
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="100dp" android:layout_height="wrap_content"> //秒杀下的rcv子条目布局 <com.facebook.drawee.view.SimpleDraweeView android:id="@+id/ms_rcv_img" android:layout_width="100dp" android:layout_height="100dp" android:padding="10dp" /> </RelativeLayout>十八:首页为你推荐的rcv子条目布局
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content"> //首页为你推荐的rcv子条目布局 <com.facebook.drawee.view.SimpleDraweeView android:id="@+id/tj_rcv_img" android:layout_width="match_parent" android:layout_height="150dp" android:padding="10dp" /> <TextView android:id="@+id/tj_rcv_title" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_below="@id/tj_rcv_img" android:layout_centerHorizontal="true" android:layout_margin="5dp" android:text="全球购 新款Apple MacBook Pro 苹果笔记本电脑" /> </RelativeLayout>十九:自定义唱片的功能
package com.example.dell.luokaiqin20180601.view.Play; import android.content.Context; import android.content.res.TypedArray; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Path; import android.graphics.Rect; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; import android.util.AttributeSet; import android.view.View; import com.example.dell.luokaiqin20180601.R; //自定义唱片的功能 public class GramophoneView extends View{ /** * 尺寸计算设计说明: * 1、唱片有两个主要尺寸:中间图片的半径、黑色圆环的宽度。 * 黑色圆环的宽度 = 图片半径的一半。 * 2、唱针分为“手臂”和“头”,手臂分两段,一段长的一段短的,头也是一段长的一段短的。 * 唱针四个部分的尺寸求和 = 唱片中间图片的半径+黑色圆环的宽度 * 唱针各部分长度 比例——长的手臂:短的手臂:长的头:短的头 = 8:4:2:1 * 3、唱片黑色圆环顶部到唱针顶端的距离 = 唱针长的手臂的长度。 */ private int halfMeasureWidth; // 绘制唱片相关变量 // 中间图片默认半径 private static final int DEFAULT_PICTURE_RADIUS = 400; // 唱片旋转默认速度,其实是通过每次旋转叠加的角度来控制速度 private static final float DEFAULT_DISK_ROTATE_SPEED = 0.3f; private int pictureRadius; // 中间图片的半径 private int ringWidth; // 黑色圆环宽度 private float diskRotateSpeed;// 唱片旋转速度 private Paint discPaint; // 唱片画笔 private Path clipPath; // 裁剪图片的路径 private Bitmap bitmap; // 图片 private Rect srcRect; // 图片被裁减范围 private Rect dstRect; // 图片被绘制范围 // 绘制唱针相关变量 private static final int PLAY_DEGREE = -15; // 播放状态时唱针的旋转角度 private static final int PAUSE_DEGREE = -45; // 暂停状态时唱针的旋转角度 private int smallCircleRadius = 20; // 唱针顶部小圆半径 private int bigCircleRadius; // 唱针顶部大圆半径 private int longArmLength; // 唱针手臂,较长那段的长度 private int shortArmLength; // 唱针手臂,较短那段的长度 private int longHeadLength; // 唱针的头,较长那段的长度 private int shortHeadLength; // 唱针的头,较短那段的长度 private Paint needlePaint; // 唱针画笔 // 状态控制相关变量 private boolean isPlaying; // 是否处于播放状态 private int needleDegreeCounter; // 唱针旋转角度计数器 private float diskDegreeCounter; // 唱片旋转角度计数器 public GramophoneView(Context context) { this(context, null); } public GramophoneView(Context context, AttributeSet attrs) { super(context, attrs); // 读取xml文件属性 TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.GramophoneView); pictureRadius = (int) typedArray.getDimension(R.styleable.GramophoneView_picture_radius, DEFAULT_PICTURE_RADIUS); diskRotateSpeed = typedArray.getFloat(R.styleable.GramophoneView_disk_rotate_speed, DEFAULT_DISK_ROTATE_SPEED); Drawable drawable = typedArray.getDrawable(R.styleable.GramophoneView_src); if (drawable == null) { bitmap = BitmapFactory.decodeResource(getContext().getResources(), R.drawable.tu); } else { bitmap = ((BitmapDrawable) drawable).getBitmap(); } typedArray.recycle(); // 初始化唱片变量 ringWidth = pictureRadius >> 1; discPaint = new Paint(); discPaint.setColor(Color.MAGENTA); discPaint.setStyle(Paint.Style.STROKE); discPaint.setStrokeWidth(ringWidth); srcRect = new Rect(); dstRect = new Rect(); setBitmapRect(srcRect, dstRect); clipPath = new Path(); clipPath.addCircle(0, 0, pictureRadius, Path.Direction.CW); diskDegreeCounter = 0; // 初始化唱针变量 bigCircleRadius = smallCircleRadius << 1; shortHeadLength = (pictureRadius + ringWidth) / 15; longHeadLength = shortHeadLength << 1; shortArmLength = longHeadLength << 1; longArmLength = shortArmLength << 1; needlePaint = new Paint(); needleDegreeCounter = PAUSE_DEGREE; } /** * 根据加载的图片资源尺寸和设置的唱片中间图片直径, * 为canvas.drawBitmap()方法设置源Rect和目标Rect, * 以宽度为例,假设图片资源宽度为width,唱片中间图片直径为diameter * 如果width <= diameter,则截取宽度为整张图片宽度。 * 如果width > diameter,则截取宽度为图片资源横向中间长度为diameter的区域。 * 高度的截取方法与宽度相同。 * * @param src 源矩形 * @param dst 目标矩形 */ private void setBitmapRect(Rect src, Rect dst) { src.set(0, 0, bitmap.getWidth(), bitmap.getHeight()); dst.set(-pictureRadius, -pictureRadius, pictureRadius, pictureRadius); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); /** * wrap_content属性下View的宽高设计: * 宽度:等于唱片直径,即图片半径+圆环宽度求和再乘以2。 * 高度:等于唱片直径+唱针较长的手臂 */ int width = (pictureRadius + ringWidth) * 2; int height = (pictureRadius + ringWidth) * 2 + longArmLength; int measuredWidth = resolveSize(width, widthMeasureSpec); int measuredHeight = resolveSize(height, heightMeasureSpec); setMeasuredDimension(measuredWidth, measuredHeight); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); halfMeasureWidth = getMeasuredWidth() >> 1; drawDisk(canvas); drawNeedle(canvas); if (needleDegreeCounter > PAUSE_DEGREE) { invalidate(); } } // 绘制唱片(胶片) private void drawDisk(Canvas canvas) { diskDegreeCounter = diskDegreeCounter % 360 + diskRotateSpeed; drawDisk(canvas, diskDegreeCounter); } // 绘制旋转了制定角度的唱片 private void drawDisk(Canvas canvas, float degree) { // 绘制圆环,注意理解平移的圆心距离和圆环半径是怎么计算的 canvas.save(); canvas.translate(halfMeasureWidth, pictureRadius + ringWidth + longArmLength); canvas.rotate(degree); canvas.drawCircle(0, 0, pictureRadius + ringWidth / 2, discPaint); // 绘制图片 canvas.clipPath(clipPath); canvas.drawBitmap(bitmap, srcRect, dstRect, discPaint); canvas.restore(); } // 绘制唱针 private void drawNeedle(Canvas canvas) { // 由于PLAY_DEGREE和PAUSE_DEGREE之间的差值是30,所以每次增/减值应当是30的约数即可 if (isPlaying) { if (needleDegreeCounter < PLAY_DEGREE) { needleDegreeCounter += 3; } } else { if (needleDegreeCounter > PAUSE_DEGREE) { needleDegreeCounter -= 3; } } drawNeedle(canvas, needleDegreeCounter); } // 绘制旋转了指定角度的唱针 private void drawNeedle(Canvas canvas, int degree) { // 移动坐标到水平中点 canvas.save(); canvas.translate(halfMeasureWidth, 0); // 绘制唱针手臂 needlePaint.setStrokeWidth(10); needlePaint.setColor(Color.parseColor("#C0C0C0")); // 绘制第一段臂 canvas.rotate(degree); canvas.drawLine(0, 0, 0, longArmLength, needlePaint); // 绘制第二段臂 canvas.translate(0, longArmLength); canvas.rotate(-30); canvas.drawLine(0, 0, 0, shortArmLength, needlePaint); // 绘制唱针头 // 绘制第一段唱针头 canvas.translate(0, shortArmLength); needlePaint.setStrokeWidth(10); canvas.drawLine(0, 0, 0, longHeadLength, needlePaint); // 绘制第二段唱针头 canvas.translate(0, longHeadLength); needlePaint.setStrokeWidth(25); canvas.drawLine(0, 0, 0, shortHeadLength, needlePaint); canvas.restore(); // 两个重叠的圆形 canvas.save(); canvas.translate(halfMeasureWidth, 0); needlePaint.setStyle(Paint.Style.FILL); needlePaint.setColor(Color.parseColor("#C0C0C0")); canvas.drawCircle(0, 0, bigCircleRadius-30, needlePaint); needlePaint.setColor(Color.parseColor("#8A8A8A")); canvas.drawCircle(0, 0, smallCircleRadius-20, needlePaint); canvas.restore(); } /** * 设置是否处于播放状态 * * @param isPlaying true:播放,false:暂停 */ public void setPlaying(boolean isPlaying) { this.isPlaying = isPlaying; invalidate(); } /** * 获取播放状态 * * @return true:播放,false:暂停 */ public boolean getPlaying() { return isPlaying; } /** * 获取图片半径 * * @return 图片半径 */ public int getPictureRadius() { return pictureRadius; } /** * 设置图片半径 * * @param pictureRadius 图片半径 */ public void setPictureRadius(int pictureRadius) { this.pictureRadius = pictureRadius; } /** * 获取唱片旋转速度 * * @return 唱片旋转速度 */ public float getDiskRotateSpeed() { return diskRotateSpeed; } /** * 设置唱片旋转速度 * * @param diskRotateSpeed 旋转速度 */ public void setDiskRotateSpeed(float diskRotateSpeed) { this.diskRotateSpeed = diskRotateSpeed; } /** * 设置图片资源id * * @param resId 图片资源id */ public void setPictureRes(int resId) { bitmap = BitmapFactory.decodeResource(getContext().getResources(), resId); setBitmapRect(srcRect, dstRect); invalidate(); } }二十:唱片播放音乐页面
package com.example.dell.luokaiqin20180601.view.Play; import android.content.res.AssetFileDescriptor; import android.media.MediaPlayer; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.widget.Button; import com.example.dell.luokaiqin20180601.R; import java.io.IOException; import java.util.ArrayList; import java.util.List; import java.util.Random; import butterknife.BindView; import butterknife.ButterKnife; import butterknife.OnClick; //唱片播放音乐的页面 public class Main2Activity extends AppCompatActivity { @BindView(R.id.play_view) GramophoneView play_View; @BindView(R.id.play_btn) Button play_Btn; List<AssetFileDescriptor> muiscList = new ArrayList<>(); private MediaPlayer mediaPlayer; boolean flag; private int index; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main2); ButterKnife.bind(this); //创建音乐播放器 mediaPlayer = new MediaPlayer(); try { //找到音乐文件 AssetFileDescriptor assetFileDescriptor = getAssets().openFd("qfl.mp3"); AssetFileDescriptor assetFileDescriptor1 = getAssets().openFd("zgz.mp3"); //将音乐文件放入集合 muiscList.add(assetFileDescriptor); muiscList.add(assetFileDescriptor1); } catch (IOException e) { e.printStackTrace(); } //设置随机数 随机播放两首音乐 Random random = new Random(); int pick = random.nextInt(2); index = pick; } //点击事件 @OnClick(R.id.play_btn) public void onViewClicked() { if(play_View.getPlaying()){ play_Btn.setText("点击播放"); mediaPlayer.pause(); }else{ play_Btn.setText("点击暂停"); startMusic(); } play_View.setPlaying(!play_View.getPlaying()); } //播放音乐方法 private void startMusic() { if (flag) { //如果判断是暂停了 可以继续接着播放 mediaPlayer.start(); } else { try { //首先需要重置资源...只有重置了之后才能再去设置下一个数据源 mediaPlayer.reset(); //设置播放资源 mediaPlayer.setDataSource(muiscList.get(index).getFileDescriptor(), muiscList.get(index).getStartOffset(), muiscList.get(index).getLength()); mediaPlayer.prepareAsync(); mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() { @Override public void onPrepared(MediaPlayer mp) { // 播放 mediaPlayer.start(); flag = true; } }); } catch (Exception e) { e.printStackTrace(); } } } @Override protected void onDestroy() { super.onDestroy(); //停止播放 并置空 mediaPlayer.stop(); mediaPlayer.release(); mediaPlayer = null; } }二十一:唱片的主布局
<?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.Play.Main2Activity"> //唱片的布局 <com.example.dell.luokaiqin20180601.view.Play.GramophoneView android:id="@+id/play_view" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" app:picture_radius="100dp" app:disk_rotate_speed="0.2" app:src="@drawable/tu"/> <Button android:id="@+id/play_btn" android:text="播放" android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout>二十二:购物车的Bean
package com.example.dell.luokaiqin20180601.model.Shooping; import java.util.List; //购物车数据的Bean public class ShoopingDataBean { private String code; private String msg; private List<DataBean> data; public String getCode() { return code; } public void setCode(String code) { this.code = code; } public String getMsg() { return msg; } public void setMsg(String msg) { this.msg = msg; } public List<DataBean> getData() { return data; } public void setData(List<DataBean> data) { this.data = data; } public static class DataBean { private String sellerName; private String sellerid; boolean groupischeck; public boolean isGroupischeck() { return groupischeck; } public void setGroupischeck(boolean groupischeck) { this.groupischeck = groupischeck; } private List<ListBean> list; public String getSellerName() { return sellerName; } public void setSellerName(String sellerName) { this.sellerName = sellerName; } public String getSellerid() { return sellerid; } public void setSellerid(String sellerid) { this.sellerid = sellerid; } public List<ListBean> getList() { return list; } public void setList(List<ListBean> list) { this.list = list; } public static class ListBean { private double bargainPrice; private String createtime; private String detailUrl; private String images; private int num; private int pid; private double price; private int pscid; private int selected; private int sellerid; private String subhead; private String title; boolean childischeck; public boolean isChildischeck() { return childischeck; } public void setChildischeck(boolean childischeck) { this.childischeck = childischeck; } public double getBargainPrice() { return bargainPrice; } public void setBargainPrice(double bargainPrice) { this.bargainPrice = bargainPrice; } public String getCreatetime() { return createtime; } public void setCreatetime(String createtime) { this.createtime = createtime; } public String getDetailUrl() { return detailUrl; } public void setDetailUrl(String detailUrl) { this.detailUrl = detailUrl; } public String getImages() { return images; } public void setImages(String images) { this.images = images; } public int getNum() { return num; } public void setNum(int num) { this.num = num; } public int getPid() { return pid; } public void setPid(int pid) { this.pid = pid; } public double getPrice() { return price; } public void setPrice(double price) { this.price = price; } public int getPscid() { return pscid; } public void setPscid(int pscid) { this.pscid = pscid; } public int getSelected() { return selected; } public void setSelected(int selected) { this.selected = selected; } public int getSellerid() { return sellerid; } public void setSellerid(int sellerid) { this.sellerid = sellerid; } public String getSubhead() { return subhead; } public void setSubhead(String subhead) { this.subhead = subhead; } public String getTitle() { return title; } public void setTitle(String title) { this.title = title; } } } }二十三: 购物车查询的M层接口
package com.example.dell.luokaiqin20180601.model.Shooping; import com.example.dell.luokaiqin20180601.prsenter.Shooping.ShoopingDataPrsenter; //购物车查询的M层接口 public interface ShoopingDataModel { //请求数据的方法 void getShoopingData(String url, String uid, ShoopingDataPrsenter prsenter); }二十四: 购物车查询的M层实现类
package com.example.dell.luokaiqin20180601.model.Shooping; import com.example.dell.luokaiqin20180601.prsenter.Shooping.ShoopingDataPrsenter; import com.example.dell.luokaiqin20180601.utils.RetrofitUtils; import io.reactivex.Flowable; //购物车查询的M层实现类 public class MyShoopingDataModel implements ShoopingDataModel { @Override public void getShoopingData(String url,String uid, ShoopingDataPrsenter prsenter) { Flowable<ShoopingDataBean> shoopingData = RetrofitUtils.getInstance(url).getApiService().getShoopingData(uid); //调用P层的成功方法 prsenter.Success(shoopingData); } }
二十五:购物车查询的P层接口
package com.example.dell.luokaiqin20180601.prsenter.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import io.reactivex.Flowable; //购物车查询的P层接口 public interface ShoopingDataPrsenter { //定义成功与失败的方法 void Success( Flowable<ShoopingDataBean> shoopingData); void Error(); }
二十六:购物车查询的P层实现类
package com.example.dell.luokaiqin20180601.prsenter.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.MyShoopingDataModel; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import com.example.dell.luokaiqin20180601.view.Shooping.ShoopingDataView; import io.reactivex.Flowable; import io.reactivex.android.schedulers.AndroidSchedulers; import io.reactivex.schedulers.Schedulers; import io.reactivex.subscribers.DisposableSubscriber; //购物车查询的P层实现类 public class MyShoopingDataPrsenter implements ShoopingDataPrsenter { ShoopingDataView dataView; private final MyShoopingDataModel model; public MyShoopingDataPrsenter(ShoopingDataView dataView){ this.dataView=dataView; model = new MyShoopingDataModel(); } @Override public void Success(Flowable<ShoopingDataBean> shoopingData) { shoopingData.subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new DisposableSubscriber<ShoopingDataBean>() { @Override public void onNext(ShoopingDataBean shoopingDataBean) { if (shoopingDataBean!=null){ dataView.toBackHome(shoopingDataBean); } } @Override public void onError(Throwable t) { } @Override public void onComplete() { } }); } @Override public void Error() { } //调用接收url的方法 public void getShoopingData(String url,String uid){ //进行请求 model.getShoopingData(url,uid,this); } //销毁V层 防止内存泄露 public void daadData() { if(dataView!=null){ dataView=null; } } }二十七: 购物车查询的V层接口
package com.example.dell.luokaiqin20180601.view.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; //购物车查询的V层接口 public interface ShoopingDataView { //定义接收数据的方法 void toBackHome(ShoopingDataBean shoopingDataBean); }二十八: 购物车查询的V层实现类 (购物车主Activity)
package com.example.dell.luokaiqin20180601.view.Shooping; import android.os.Bundle; import android.support.v7.app.AlertDialog; import android.support.v7.app.AppCompatActivity; import android.util.Log; import android.view.View; import android.widget.Button; import android.widget.CheckBox; import android.widget.EditText; import android.widget.ExpandableListView; import android.widget.TextView; import android.widget.Toast; import com.example.dell.luokaiqin20180601.R; import com.example.dell.luokaiqin20180601.adapter.ShoopingExpandableAdapter; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import com.example.dell.luokaiqin20180601.prsenter.Shooping.MyShoopingDataDeletePrsenter; import com.example.dell.luokaiqin20180601.prsenter.Shooping.MyShoopingDataPrsenter; import com.example.dell.luokaiqin20180601.prsenter.Shooping.MyShoopingDataUpdataPrsenter; import java.math.BigDecimal; import java.util.ArrayList; import java.util.List; import butterknife.BindView; import butterknife.ButterKnife; //购物车查询的V层实现类 (购物车主Activity) public class ShoopingActivity extends AppCompatActivity implements ShoopingDataView, ShoopingExpandableAdapter.OnClickListener,ShoopingDataDeleteView,ShoopingDataUpdataView{ @BindView(R.id.sp_expandable_lv) ExpandableListView sp_ExpandableLv; @BindView(R.id.sp_box) CheckBox sp_Box; @BindView(R.id.sp_price) TextView sp_Price; @BindView(R.id.sp_btn) Button sp_Btn; String url = "http://120.27.23.105/"; String uid = "10295"; String deleteurl = "http://120.27.23.105/"; String updataurl="http://120.27.23.105/"; private MyShoopingDataPrsenter prsenter; //创建一级列表数据的集合 List<ShoopingDataBean.DataBean> groupList = new ArrayList<>(); //创建二级列表数据的集合 List<List<ShoopingDataBean.DataBean.ListBean>> childList = new ArrayList<>(); private ShoopingExpandableAdapter shoopingExpandableAdapter; private List<ShoopingDataBean.DataBean> data; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_shooping); ButterKnife.bind(this); //实例化P层,将所需值传递给P层 prsenter = new MyShoopingDataPrsenter(this); prsenter.getShoopingData(url,uid); //设置全选与反选的监听 sp_Box.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //若选中 则将一级二级复选框全部设置为选中 if (sp_Box.isChecked()){ for (int i = 0; i <data.size() ; i++) { data.get(i).setGroupischeck(true); List<ShoopingDataBean.DataBean.ListBean> list = data.get(i).getList(); for (int j = 0; j <list.size() ; j++) { list.get(j).setChildischeck(true); } } }else{ //若未选中 则将一级二级复选框全部设置为未选中 for (int i = 0; i <data.size() ; i++) { data.get(i).setGroupischeck(false); List<ShoopingDataBean.DataBean.ListBean> list = data.get(i).getList(); for (int j = 0; j <list.size() ; j++) { list.get(j).setChildischeck(false); } } } //计算总价 setPrices(); //刷新适配器 setExpandableListViewAdapter(); } }); //设置二级列表的条目点击事件 sp_ExpandableLv.setOnChildClickListener(new ExpandableListView.OnChildClickListener() { @Override public boolean onChildClick(ExpandableListView parent, View v, final int groupPosition, final int childPosition, long id) { //Log.e("++该条目被点击了", "onItemClick: "+groupPosition+childPosition ); //弹出弹出框 修改当前条目的数量 List<ShoopingDataBean.DataBean.ListBean> list = data.get(groupPosition).getList(); //获取当前条目的数量 final int num = list.get(childPosition).getNum(); //引入弹出框布局 View view = View.inflate(ShoopingActivity.this, R.layout.dialog_layout, null); //创建AlertDialog final AlertDialog dialog = new AlertDialog.Builder(ShoopingActivity.this).create(); //将弹出框布局赋给dialog dialog.setView(view); dialog.show();//弹出对话框 final EditText dialog_num = view.findViewById(R.id.dialog_num); //将当前条目的数量赋给弹出框 dialog_num.setText(""+num); Button dialog_jian = view.findViewById(R.id.dialog_jian); Button dialog_add = view.findViewById(R.id.dialog_add); Button dialog_no = view.findViewById(R.id.dialog_no); Button dialog_yes = view.findViewById(R.id.dialog_yes); //弹出框实现减数量的功能 dialog_jian.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //获取当前弹出框中的数量 String s = dialog_num.getText().toString(); Integer value = Integer.valueOf(s); if (value>1){ value--; dialog_num.setText(""+value); }else{ Toast.makeText(ShoopingActivity.this,"当前数量不可以再减少",Toast.LENGTH_SHORT).show(); } } }); //弹出框实现加数量的功能 dialog_add.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //获取当前弹出框中的数量 String s = dialog_num.getText().toString(); Integer value = Integer.valueOf(s); value++; dialog_num.setText(""+value); } }); //弹出框实现更改数量的功能 关闭弹出框 dialog_yes.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //获取商户id String s = String.valueOf(data.get(groupPosition).getSellerid()); //获取商品id String s1 = String.valueOf(data.get(groupPosition).getList().get(childPosition).getPid()); //获取修改后的数量 String s2 = dialog_num.getText().toString(); //实例化P层 将所需值传给P层 MyShoopingDataUpdataPrsenter updataPrsenter = new MyShoopingDataUpdataPrsenter(ShoopingActivity.this); updataPrsenter.getShoopingUpdataData(updataurl,uid,s,s1,s2); //关闭弹出框 dialog.dismiss(); } }); //弹出框实现取消更改数量的功能 关闭弹出框 dialog_no.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { dialog.dismiss(); } }); return false; } }); //设置条目的长按删除 } //接收数据的方法 @Override public void toBackHome(ShoopingDataBean shoopingDataBean) { //得到一级列表的数据 并添加入集合 data = shoopingDataBean.getData(); groupList.clear();//因查询请求数据,则需将元集合中数据清空 groupList.addAll(data);//在将查询的所有数据添加入集合 //得到二级列表的数据 并添加集合 childList.clear(); for (int i = 0; i < data.size() ; i++) { List<ShoopingDataBean.DataBean.ListBean> list = data.get(i).getList(); childList.add(list); } //设置二级列表的适配器 setExpandableListViewAdapter(); //设置一二级列表的复选框初始化都为false for (int i = 0; i <data.size() ; i++) { ShoopingDataBean.DataBean dataBean = data.get(i); dataBean.setGroupischeck(false); List<ShoopingDataBean.DataBean.ListBean> list = dataBean.getList(); for (int j = 0; j <list.size() ; j++) { list.get(j).setChildischeck(false); } } } //设置数据库的二级列表的适配器 private void setExpandableListViewAdapter() { if (shoopingExpandableAdapter==null) { shoopingExpandableAdapter = new ShoopingExpandableAdapter(this, groupList, childList); sp_ExpandableLv.setAdapter(shoopingExpandableAdapter); for (int i = 0; i <data.size() ; i++) { //展开一级列表的数据 sp_ExpandableLv.expandGroup(i); } //调用适配器中的点击事件 shoopingExpandableAdapter.SetSpClick(this); }else{ shoopingExpandableAdapter.notifyDataSetChanged(); } } //一级列表复选框选中状态 @Override public void groupCheck(int groupPosition, boolean isCheck) { //选中一级列表的复选框 ShoopingDataBean.DataBean dataBean = data.get(groupPosition); dataBean.setGroupischeck(isCheck); //选中一级列表的复选框时,二级列表的所有复选框也要选中 List<ShoopingDataBean.DataBean.ListBean> list = dataBean.getList(); for (int i = 0; i <list.size() ; i++) { list.get(i).setChildischeck(isCheck); } //计算总价 setPrices(); //刷新适配器 setExpandableListViewAdapter(); } //二级列表复选框选中状态 @Override public void chlidCheck(int groupPosition, int childPosition, boolean isCheck) { ShoopingDataBean.DataBean dataBean = data.get(groupPosition); //设置二级列表的复选框选中 dataBean.getList().get(childPosition).setChildischeck(isCheck); //传入当前二级列表的父列表(一级列表)的下标 boolean b = isAllChlid(groupPosition); //进行比较 若全选中一级列表中的复选框则为true(选中) if (b){ data.get(groupPosition).setGroupischeck(true); }else{ //若未全选中则为false data.get(groupPosition).setGroupischeck(false); } //计算总价 setPrices(); //刷新适配器 setExpandableListViewAdapter(); } //子条目的点击删除事件 @Override public void chlidItemDelete(int groupPosition, int childPosition) { List<ShoopingDataBean.DataBean.ListBean> list = groupList.get(groupPosition).getList(); int pid = list.get(childPosition).getPid(); String s = String.valueOf(pid); Log.e("++下标", "chlidItemDelete: "+pid ); //实例化P层 将所需值传给P层 MyShoopingDataDeletePrsenter prsenter = new MyShoopingDataDeletePrsenter(this); prsenter.getShoopingDeleteData(deleteurl,uid,s); } //判断二级列表复选框是否全部选中 public boolean isAllChlid(int groupPosition){ List<ShoopingDataBean.DataBean.ListBean> list = data.get(groupPosition).getList(); for (int i = 0; i <list.size() ; i++) { //获取某一商家的商品(二级列表)数据 ShoopingDataBean.DataBean.ListBean listBean = list.get(i); //若未选中 则返回false if (!listBean.isChildischeck()){ return false; } } //若选中 则返回true return true; } //设置计算总价的方法 public void setPrices(){ //初始化总价为0 int nums = 0; int prices = 0; for (int i = 0; i <data.size() ; i++) { List<ShoopingDataBean.DataBean.ListBean> list = data.get(i).getList(); for (int j = 0; j <list.size() ; j++) { ShoopingDataBean.DataBean.ListBean listBean = list.get(j); //判断若选中 总价+=数量*单价 if (listBean.isChildischeck()){ prices += listBean.getPrice()*listBean.getNum(); nums+=listBean.getNum(); } } } //将最后的总价进行四舍五入 然后保留小数后2位 BigDecimal bg = new BigDecimal(prices); double f1 = bg.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue(); //为控件赋值 sp_Price.setText("合计:¥"+f1); sp_Btn.setText("去支付("+nums+")"); //适配器 setExpandableListViewAdapter(); } //删除购物车返回的数据 @Override public void toBackHomeDelete(ShoopingDataBean shoopingDataBean) { if (shoopingDataBean.getMsg().equals("删除购物车成功")){ Toast.makeText(ShoopingActivity.this,"删除成功",Toast.LENGTH_SHORT).show(); } //重新请求数据 prsenter.getShoopingData(url,uid); } //修改后返回的数据 @Override public void toBackHomeUpdata(ShoopingDataBean shoopingDataBean) { //重新请求数据 prsenter.getShoopingData(url,uid); } }二十九:购物车的主布局
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout 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" tools:context=".view.Shooping.ShoopingActivity"> //购物车的主布局 <RelativeLayout android:id="@+id/sp_title_layout" android:layout_width="match_parent" android:layout_height="wrap_content" android:padding="10dp" android:background="#d9d3d3"> <ImageView android:layout_width="20dp" android:layout_height="20dp" android:src="@drawable/back" android:layout_marginLeft="10dp" android:layout_centerVertical="true" android:layout_alignParentLeft="true" /> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:text="购物车" android:textSize="18sp" android:textColor="#f00"/> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="编辑" android:layout_marginRight="10dp" android:layout_alignParentRight="true" android:layout_centerVertical="true"/> </RelativeLayout> <!--二级列表--> <ExpandableListView android:id="@+id/sp_expandable_lv" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@id/sp_title_layout"/> <RelativeLayout android:layout_alignParentBottom="true" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="#c0c0c0"> <CheckBox android:id="@+id/sp_box" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerVertical="true" android:textStyle="bold" android:text="全选" /> <TextView android:id="@+id/sp_price" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:textColor="#DD693B" android:textStyle="bold" android:text="合计:¥520.00" /> <Button android:id="@+id/sp_btn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" android:background="#FC7903" android:textColor="#fff" android:text="去支付(0)" /> </RelativeLayout> </RelativeLayout>三十: 购物车一级列表的布局
<?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="vertical"> //购物车一级列表的布局 <RelativeLayout android:layout_width="match_parent" android:layout_height="50dp" android:padding="10dp"> <CheckBox android:id="@+id/sp_group_box" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerVertical="true"/> <TextView android:id="@+id/sp_group_sellerName" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_toRightOf="@id/sp_group_box" android:layout_centerVertical="true" android:layout_marginLeft="20dp" android:text="商家23"/> </RelativeLayout> </LinearLayout>
三十一:购物车二级列表的布局
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent"> //购物车二级列表的布局 <RelativeLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentTop="true" android:padding="10dp"> <CheckBox android:id="@+id/sp_elv_chlid_box" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerVertical="true" android:layout_gravity="center_vertical" /> <com.facebook.drawee.view.SimpleDraweeView android:id="@+id/sp_elv_chlid_img" android:layout_width="100dp" android:layout_height="100dp" android:layout_marginLeft="10dp" android:layout_toRightOf="@id/sp_elv_chlid_box" android:src="@mipmap/ic_launcher" /> <RelativeLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="10dp" android:layout_toRightOf="@id/sp_elv_chlid_img"> <TextView android:id="@+id/sp_elv_chlid_title" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="全球购 新款Apple MacBook Pro 苹果笔记本电脑 银色VP2新13英寸Bar i5/8G/256G" /> <RelativeLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_below="@id/sp_elv_chlid_title" android:layout_marginTop="20dp"> <TextView android:id="@+id/sp_elv_chlid_price" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerVertical="true" android:text="¥888.0" android:textColor="#f00" /> <TextView android:id="@+id/sp_elv_chlid_num" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerHorizontal="true" android:text="X12" /> <TextView android:id="@+id/sp_elv_chlid_delete" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" android:text="删除"/> </RelativeLayout> </RelativeLayout> </RelativeLayout> </RelativeLayout>三十二: 购物车的弹出框 用于修改数量
<?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="vertical"> //购物车的弹出框 用于修改数量 <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:layout_margin="10dp" android:textSize="18sp" android:text="修改购买数量"/> <RelativeLayout android:layout_width="match_parent" android:layout_height="50dp" android:gravity="center" android:layout_margin="10dp"> <Button android:id="@+id/dialog_jian" android:layout_width="80dp" android:layout_height="50dp" android:text=" - "/> <EditText android:id="@+id/dialog_num" android:layout_width="80dp" android:layout_height="50dp" android:layout_toRightOf="@id/dialog_jian" android:gravity="center" android:text=" 0 "/> <Button android:id="@+id/dialog_add" android:layout_width="80dp" android:layout_height="50dp" android:layout_toRightOf="@id/dialog_num" android:text=" + "/> </RelativeLayout> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal" android:layout_margin="10dp"> <Button android:id="@+id/dialog_no" android:layout_width="0dp" android:layout_weight="1" android:layout_height="wrap_content" android:text="取消"/> <Button android:id="@+id/dialog_yes" android:layout_width="0dp" android:layout_weight="1" android:layout_height="wrap_content" android:text="确定"/> </LinearLayout> </LinearLayout>三十三:
购物车删除数据的M层接口
package com.example.dell.luokaiqin20180601.model.Shooping; import com.example.dell.luokaiqin20180601.prsenter.Shooping.ShoopingDataDeletePrsenter; //购物车删除数据的M层接口 public interface ShoopingDataDeleteModel { //定义请求数据的方法 void getShoopingDataDeleteModel(String url, String uid, String pid, ShoopingDataDeletePrsenter prsenter); }
三十四:
购物车删除数据的M层实现类
package com.example.dell.luokaiqin20180601.model.Shooping; import com.example.dell.luokaiqin20180601.prsenter.Shooping.ShoopingDataDeletePrsenter; import com.example.dell.luokaiqin20180601.utils.RetrofitUtils; import io.reactivex.Flowable; //购物车删除数据的M层实现类 public class MyShoopingDataDeleteModel implements ShoopingDataDeleteModel { @Override public void getShoopingDataDeleteModel(String url, String uid, String pid, ShoopingDataDeletePrsenter prsenter) { Flowable<ShoopingDataBean> shoopingDataDelete = RetrofitUtils.getInstance(url).getApiService().getShoopingDataDelete( uid, pid); //调用P层方法 prsenter.Success(shoopingDataDelete); } }
三十五:
购物车删除数据的P层接口
package com.example.dell.luokaiqin20180601.prsenter.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import io.reactivex.Flowable; //购物车删除数据的P层接口 public interface ShoopingDataDeletePrsenter { //定义成功和失败的方法 void Success(Flowable<ShoopingDataBean> shoopingDataDelete); void Error(); }三十六:
购物车删除数据的P层实现类
package com.example.dell.luokaiqin20180601.prsenter.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.MyShoopingDataDeleteModel; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import com.example.dell.luokaiqin20180601.view.Shooping.ShoopingDataDeleteView; import io.reactivex.Flowable; import io.reactivex.android.schedulers.AndroidSchedulers; import io.reactivex.schedulers.Schedulers; import io.reactivex.subscribers.DisposableSubscriber; //购物车删除数据的P层实现类 public class MyShoopingDataDeletePrsenter implements ShoopingDataDeletePrsenter { ShoopingDataDeleteView deleteView; private final MyShoopingDataDeleteModel deleteModel; public MyShoopingDataDeletePrsenter(ShoopingDataDeleteView deleteView){ this.deleteView=deleteView; deleteModel = new MyShoopingDataDeleteModel(); } @Override public void Success(Flowable<ShoopingDataBean> shoopingDataDelete) { shoopingDataDelete.subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new DisposableSubscriber<ShoopingDataBean>() { @Override public void onNext(ShoopingDataBean shoopingDataBean) { if (shoopingDataBean!=null){ deleteView.toBackHomeDelete(shoopingDataBean); } } @Override public void onError(Throwable t) { } @Override public void onComplete() { } }); } @Override public void Error() { } //调用接收url的方法 public void getShoopingDeleteData(String url,String uid,String pid){ //进行请求 deleteModel.getShoopingDataDeleteModel(url,uid,pid,this); } //销毁V层 防止内存泄露 public void daadData() { if(deleteView!=null){ deleteView=null; } } }
三十七:购物车删除数据的V层接口
package com.example.dell.luokaiqin20180601.view.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; //购物车删除数据的V层接口 public interface ShoopingDataDeleteView { //接收数据的方法 void toBackHomeDelete(ShoopingDataBean shoopingDataBean); }
三十八:购物车数据修改的M层接口
package com.example.dell.luokaiqin20180601.model.Shooping; import com.example.dell.luokaiqin20180601.prsenter.Shooping.ShoopingDataUpdataPrsenter; //购物车数据修改的M层接口 public interface ShoopingDataUpdataModel { //定义请求数据的方法 void getShoopingDataUpdataModel(String url,String uid,String sellerid,String pid,String num, ShoopingDataUpdataPrsenter prsenter); }
三十九:购物车数据修改的M层实现类
package com.example.dell.luokaiqin20180601.model.Shooping; import com.example.dell.luokaiqin20180601.prsenter.Shooping.ShoopingDataUpdataPrsenter; import com.example.dell.luokaiqin20180601.utils.RetrofitUtils; import io.reactivex.Flowable; //购物车数据修改的M层实现类 public class MyShoopingDataUpdataModel implements ShoopingDataUpdataModel { @Override public void getShoopingDataUpdataModel(String url,String uid, String sellerid, String pid, String num, ShoopingDataUpdataPrsenter prsenter) { Flowable<ShoopingDataBean> shoopingDataUpdata = RetrofitUtils.getInstance(url).getApiService().getShoopingDataUpdata(uid, sellerid, pid, num); //调用P层的成功方法 prsenter.Success(shoopingDataUpdata); } }
四十:购物车修改数据的P层接口
package com.example.dell.luokaiqin20180601.prsenter.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import io.reactivex.Flowable; //购物车修改数据的P层接口 public interface ShoopingDataUpdataPrsenter { //定义成功和失败的方法 void Success(Flowable<ShoopingDataBean> shoopingDataUpdata); void Error(); }
四十一:购物车修改数据的P层实现类
package com.example.dell.luokaiqin20180601.prsenter.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.MyShoopingDataUpdataModel; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; import com.example.dell.luokaiqin20180601.view.Shooping.ShoopingDataUpdataView; import io.reactivex.Flowable; import io.reactivex.android.schedulers.AndroidSchedulers; import io.reactivex.schedulers.Schedulers; import io.reactivex.subscribers.DisposableSubscriber; //购物车修改数据的P层实现类 public class MyShoopingDataUpdataPrsenter implements ShoopingDataUpdataPrsenter { ShoopingDataUpdataView updataView; private final MyShoopingDataUpdataModel updataModel; public MyShoopingDataUpdataPrsenter(ShoopingDataUpdataView updataView){ this.updataView=updataView; updataModel = new MyShoopingDataUpdataModel(); } @Override public void Success(Flowable<ShoopingDataBean> shoopingDataUpdata) { shoopingDataUpdata.subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new DisposableSubscriber<ShoopingDataBean>() { @Override public void onNext(ShoopingDataBean shoopingDataBean) { if (shoopingDataBean!=null){ updataView.toBackHomeUpdata(shoopingDataBean); } } @Override public void onError(Throwable t) { } @Override public void onComplete() { } }); } @Override public void Error() { } //调用接收url的方法 public void getShoopingUpdataData(String url,String uid,String sellerid,String pid,String num){ //进行请求 updataModel.getShoopingDataUpdataModel(url,uid,sellerid,pid,num,this); } //销毁V层 防止内存泄露 public void daadData() { if(updataView!=null){ updataView=null; } } }四十二: 购物车数据修改的V层接口
package com.example.dell.luokaiqin20180601.view.Shooping; import com.example.dell.luokaiqin20180601.model.Shooping.ShoopingDataBean; //购物车数据修改的V层 public interface ShoopingDataUpdataView { //接收数据的方法 void toBackHomeUpdata(ShoopingDataBean shoopingDataBean); }
注意:购物车删除、修改的V层接口都由购物车查询的V层实现类进行实现