MVP解析前言 从Google推出官方MVP架构demo到现在大概有一年多的时间了,半年前大概在所有的Android技术社区都有提到MVP架构,现在关于MVP架构的话题似乎没有以前那么多了,可能是因

来源:互联网 发布:自动生成条形码软件 编辑:程序博客网 时间:2024/06/05 10:38
前言

从Google推出官方MVP架构demo到现在大概有一年多的时间了,半年前大概在所有的Android技术社区都有提到MVP架构,现在关于MVP架构的话题似乎没有以前那么多了,可能是因为大家都已经能够熟练的使用MVP了。在这里先炒碗闲饭,提供了一个快速生成MVP模式的插件。地址


对应的model层

public interface ApiService {    //http://api.expoon.com/AppNews/getNewsList/type/1/p/1    @GET("type/1/p/1")    Observable<News> getHomes();}
//定义接口
public interface IModel {    void getUrl(String url);}
继承接口

public class UserModel implements IModel {    ArrayList<News.DataBean> list;    private OnFinish onFinish;    public interface OnFinish{        void OnFinishListener(ArrayList<News.DataBean> list);    }    public void setOnFinish(OnFinish onFinish){        this.onFinish = onFinish;    }    @Override    public void getUrl(String url) {        list = new ArrayList<>();        Retrofit retrofit = new Retrofit.Builder().baseUrl(url).addConverterFactory(GsonConverterFactory.create()).addCallAdapterFactory(RxJavaCallAdapterFactory.create()).build();        ApiService apiService = retrofit.create(ApiService.class);        Observable<News> homes = apiService.getHomes();        homes.subscribeOn(Schedulers.io())                .observeOn(AndroidSchedulers.mainThread())                .subscribe(new Observer<News>() {                    @Override                    public void onCompleted() {                    }                    @Override                    public void onError(Throwable e) {                    }                    @Override                    public void onNext(News news) {                        list = (ArrayList<News.DataBean>) news.getData();                        onFinish.OnFinishListener(list);                    }                });    }}

对应presenter层的东西

//Api

public class Api {    public static final String HOME_URL="http://api.expoon.com/AppNews/getNewsList/";}

创建类
UserPresenter
public class UserPresenter implements UserModel.OnFinish{    private final IView userView;    private final UserModel userModel;    public UserPresenter(IView userView) {        this.userView = userView;        this.userModel = new UserModel();        userModel.setOnFinish(this);    }    public void getUser(String url){        userModel.getUrl(url);    }    @Override    public void OnFinishListener(ArrayList<News.DataBean> list) {        userView.getNews(list);    }}

view层
public interface IView {    void getNews(ArrayList<News.DataBean> list);}


对应的适配器

public class HomeAdaper extends RecyclerView.Adapter {    Context context;    List<News.DataBean> list;    public HomeAdaper(Context context, List<News.DataBean> list) {        this.context = context;        this.list = list;    }    @Override    public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {        MyViewHolder holder = new MyViewHolder(LayoutInflater.from(                context).inflate(R.layout.listview, parent,                false));        return holder;    }    @Override    public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {        MyViewHolder holder1 = (MyViewHolder) holder;        holder1.tv.setText(list.get(position).getNews_title());        holder1.draweeView1.setImageURI(list.get(position).getPic_url());        //创建DraweeController        DraweeController controller = Fresco.newDraweeControllerBuilder()                //重试之后要加载的图片URI地址                .setUri(list.get(position).getPic_url())                //设置点击重试是否开启                .setTapToRetryEnabled(true)                //动画播放                .setAutoPlayAnimations(true)                //设置旧的Controller                .setOldController(holder1.draweeView1.getController())                //构建                .build();        //设置DraweeController        holder1.draweeView1.setController(controller);    }    @Override    public int getItemCount() {        return list.size();    }    class MyViewHolder extends RecyclerView.ViewHolder {        SimpleDraweeView draweeView1;        TextView tv;        public MyViewHolder(View view) {            super(view);            tv = (TextView) view.findViewById(R.id.tv);            draweeView1 = (SimpleDraweeView) view.findViewById(R.id.img);        }    }}


7. 所谓的mvp,即是(model-处理业务逻辑(主要是数据读写,或者与后台通信(其实也是读写数据)),view-处理ui控件,presenter-主导器,操作model和view)

8. 源码地址

http://download.csdn.net/detail/knxw0001/7983807


对应的主页面

public class MainActivity extends AppCompatActivity implements View.OnClickListener {   ViewPager vp;    ArrayList<Fragment>fragments;       Fragment1 one;        Fragment2 two;    Fragment3 three;    Fragment4 four;    Fragment5 wu;    FragmentManager fm;    Button b1,b2,b3,b4,b5; TextView tvv;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        vp = (ViewPager)findViewById(R.id.vp);        b1 = (Button)findViewById(R.id.b1);        b2= (Button)findViewById(R.id.b2);        b3 = (Button)findViewById(R.id.b3);        b4 = (Button)findViewById(R.id.b4);        b5 = (Button)findViewById(R.id.b5);        tvv= (TextView)findViewById(R.id.tvv);        fm  = getSupportFragmentManager();        fragments = new ArrayList<Fragment>();        one  = new Fragment1();        two = new Fragment2();        three = new Fragment3();        four = new Fragment4();        wu = new Fragment5();        fragments.add(one);        fragments.add(two);        fragments.add(three);        fragments.add(four);        fragments.add(wu);        b1.setOnClickListener(this);        b2.setOnClickListener(this);        b3.setOnClickListener(this);        b4.setOnClickListener(this);        b5.setOnClickListener(this);        vp.setAdapter(new FragmentPagerAdapter(fm) {            @Override            public Fragment getItem(int position) {                return fragments.get(position);            }            @Override            public int getCount() {                return fragments.size();            }        });        vp.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {            @Override            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {            }            @Override            public void onPageSelected(int position) {                switch (position){                    case 0:                        tvv.setText("首页");                        b1.setTextColor(Color.BLUE);                       b2.setTextColor(Color.BLACK);                       b3.setTextColor(Color.BLACK);                       b4.setTextColor(Color.BLACK);                        b5.setTextColor(Color.BLACK);                        break;                    case 1 :                        tvv.setText("自选");                        b1.setTextColor(Color.BLACK);                        b2.setTextColor(Color.BLUE);                        b3.setTextColor(Color.BLACK);                        b4.setTextColor(Color.BLACK);                        b5.setTextColor(Color.BLACK);                        break;                    case 2:                        tvv.setText("行情");                        b1.setTextColor(Color.BLACK);                        b2.setTextColor(Color.BLACK);                        b3.setTextColor(Color.BLUE);                        b4.setTextColor(Color.BLACK);                        b5.setTextColor(Color.BLACK);                        break;                    case 3:                        tvv.setText("资讯");                        b1.setTextColor(Color.BLACK);                        b2.setTextColor(Color.BLACK);                        b3.setTextColor(Color.BLACK);                        b4.setTextColor(Color.BLUE);                        b5.setTextColor(Color.BLACK);                        break;                    case 4:                        tvv.setText("交易");                        b1.setTextColor(Color.BLACK);                        b2.setTextColor(Color.BLACK);                        b3.setTextColor(Color.BLACK);                        b4.setTextColor(Color.BLACK);                        b5.setTextColor(Color.BLUE);                        break;                }            }            @Override            public void onPageScrollStateChanged(int state) {            }        });    }    @Override    public void onClick(View view) {        switch (view.getId())        {            case R.id.b1:                vp.setCurrentItem(0);                break;            case R.id.b2:                vp.setCurrentItem(1);                break;            case R.id.b3:                vp.setCurrentItem(2);                break;            case R.id.b4:                vp.setCurrentItem(3);                break;            case R.id.b5:                vp.setCurrentItem(4);                break;            default:                break;        }    }}


//加载的 图片处理Frofit Myapp

public class Myapp extends Application {    public static Myapp mInstance;    @Override    public void onCreate() {        super.onCreate();        mInstance = this;        Fresco.initialize(this);    }    public static Myapp getInstance() {        return mInstance;    }}

//对应相关的Fragment 解析数据和接口回调
public class Fragment4 extends Fragment implements IView{    RecyclerView recycler;    HomeAdaper homeadper;    List<News.DataBean> list;    UserPresenter userpresenter;    @Nullable    @Override    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {        View view = LayoutInflater.from(getContext()).inflate(R.layout.fragment4,null);        recycler = (RecyclerView)view.findViewById(R.id.recycler);        recycler.setLayoutManager(new LinearLayoutManager(getActivity()));        userpresenter = new UserPresenter(this);        userpresenter.getUser(Api.HOME_URL);        //gethome();        return view;    }//    private  void gethome() {//        //创建Retrofit//        Retrofit retrofit = new Retrofit.Builder().baseUrl(Api.HOME_URL).addConverterFactory(GsonConverterFactory.create()).addCallAdapterFactory(RxJavaCallAdapterFactory.create()).build();//        //通过动态代理得到网络接口对象//        ApiService apiService = retrofit.create(ApiService.class);////        Observable<News> homes = apiService.getHomes();//        homes.subscribeOn(Schedulers.io())//                .observeOn(AndroidSchedulers.mainThread())//                .subscribe(new Observer<News>() {//                    @Override//                    public void onCompleted() {////                    }////                    @Override//                    public void onError(Throwable e) {////                    }////                    @Override//                    public void onNext(News news) {//                        list = news.getData();//                        recycler.setAdapter(homeadper =new HomeAdaper(getActivity(),list));//                    }//////                });////    }    @Override    public void getNews(ArrayList<News.DataBean> list) {        recycler.setAdapter(homeadper =new HomeAdaper(getActivity(),list));    }}

//下面就是相关的布局

<?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:id="@+id/activity_main"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:paddingBottom="@dimen/activity_vertical_margin"    android:paddingLeft="@dimen/activity_horizontal_margin"    android:paddingRight="@dimen/activity_horizontal_margin"    android:paddingTop="@dimen/activity_vertical_margin"    tools:context="com.eightgroup.day114zkx1.MainActivity">    <TextView        android:layout_width="match_parent"        android:layout_height="wrap_content"        android:id="@+id/tvv"        android:textSize="22sp"        android:gravity="center"        android:textStyle="bold"        /><android.support.v4.view.ViewPager    android:id="@+id/vp"    android:layout_width="wrap_content"    android:layout_height="wrap_content"    android:layout_above="@+id/one"></android.support.v4.view.ViewPager>    <LinearLayout        android:drawableTop="@mipmap/ic_launcher"       android:layout_alignParentBottom="true"        android:id="@+id/one"        android:orientation="horizontal"        android:layout_width="match_parent"        android:layout_height="wrap_content">        <Button            android:drawableTop="@mipmap/ic_launcher"            android:id="@+id/b1"           android:layout_weight="1"           android:text="首页"            android:layout_height="wrap_content"            android:layout_width="0dp" />        <Button            android:drawableTop="@mipmap/ic_launcher"            android:id="@+id/b2"            android:layout_weight="1"            android:text="首页2"            android:layout_height="wrap_content"            android:layout_width="0dp" />        <Button            android:id="@+id/b3"            android:layout_weight="1"            android:text="首页3"            android:drawableTop="@mipmap/ic_launcher"            android:layout_height="wrap_content"            android:layout_width="0dp" />        <Button            android:drawableTop="@mipmap/ic_launcher"            android:id="@+id/b4"            android:layout_weight="1"            android:text="首页4"            android:layout_height="wrap_content"            android:layout_width="0dp" />        <Button            android:drawableTop="@mipmap/ic_launcher"            android:id="@+id/b5"            android:layout_weight="1"            android:text="首页5"            android:layout_height="wrap_content"            android:layout_width="0dp" />    </LinearLayout></RelativeLayout>
//对应解析的布局

<?xml version="1.0" encoding="utf-8"?><RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"   android:orientation="horizontal"    android:layout_width="match_parent"    android:layout_height="match_parent">    <HorizontalScrollView        android:id="@+id/hor"        android:layout_width="match_parent"        android:layout_height="wrap_content"        android:scrollbars="horizontal"        >        <LinearLayout            android:layout_width="match_parent"            android:layout_height="wrap_content"            android:orientation="horizontal"            >            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="数据新闻"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/sj"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="快讯"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/kx"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="头条"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/tt"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="精编公告"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/jb"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="美股"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/mg"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="港股"                android:id="@+id/gg"                android:layout_gravity="center"                android:gravity="center"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="基金"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/jj"                />            <Button                android:layout_width="100dp"                android:layout_height="wrap_content"                android:text="理财"                android:layout_gravity="center"                android:gravity="center"                android:id="@+id/lc"                />        </LinearLayout>    </HorizontalScrollView>    <android.support.v7.widget.RecyclerView        android:layout_below="@+id/hor"        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/recycler"        >    </android.support.v7.widget.RecyclerView></RelativeLayout>
对应的listview布局解析的文字和图片 对用的

fresco

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:layout_width="wrap_content"    android:layout_height="wrap_content"    xmlns:fresco="http://schemas.android.com/apk/res-auto">    <com.facebook.drawee.view.SimpleDraweeView        android:id="@+id/img"        android:layout_width="50dp"        android:layout_height="50dp"        fresco:placeholderImage="@mipmap/ic_launcher"        fresco:placeholderImageScaleType="focusCrop"        fresco:roundAsCircle="true"        />    <TextView        android:id="@+id/tv"        android:layout_width="wrap_content"        android:layout_height="wrap_content" /></LinearLayout>


相关权限 重点 name 应用 Myapp
<uses-permission android:name="android.permission.INTERNET"></uses-permission>    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>    <application        android:name=".Myapp"
//通过Xrecyclerview的上拉下拉
  // xrecyclerview的依赖    compile 'com.jcodecraeer:xrecyclerview:1.3.2'


//上拉下拉的监听
public class Fragment4 extends Fragment implements IView{XRecyclerView recycler;    HomeAdaper homeadper;    List<News.DataBean> list;    UserPresenter userpresenter;    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {        View view = LayoutInflater.from(getContext()).inflate(R.layout.fragment4,null);        recycler = (XRecyclerView)view.findViewById(R.id.recycler);        recycler.setLayoutManager(new LinearLayoutManager(getActivity()));        userpresenter = new UserPresenter(this);        userpresenter.getUser(Api.HOME_URL);        recycler.setLoadingListener(new XRecyclerView.LoadingListener() {            @Override            public void onRefresh() {                userpresenter.getUser(Api.HOME_URL);                recycler.refreshComplete();            }            @Override            public void onLoadMore() {                userpresenter.getUser(Api.HOME_URL);                recycler.loadMoreComplete();            }


相关依赖

    compile 'com.android.support:appcompat-v7:26.0.0-alpha1'    testCompile 'junit:junit:4.12'    compile 'com.squareup.retrofit2:retrofit:2.0.1'    compile 'com.squareup.retrofit2:converter-gson:2.0.1'    compile 'com.squareup.retrofit2:adapter-rxjava:2.0.1'    compile 'io.reactivex:rxandroid:1.1.0'    compile 'com.squareup.okhttp3:logging-interceptor:3.4.1'    compile 'com.squareup.okhttp3:logging-interceptor:3.4.1'    compile 'com.google.code.gson:gson:2.8.2'    compile 'com.android.support:recyclerview-v7:24.0.0'    //静态图片    compile 'com.facebook.fresco:fresco:0.12.0'    // 支持 GIF 动图,需要添加    compile 'com.facebook.fresco:animated-gif:0.12.0'    compile 'com.android.support:design:23.4.0'