MainActivity:
public class MainActivity extends AppCompatActivity implements IMainView {
@BindView(R.id.recycle)
RecyclerView recycle;
private MainPresenter mainPresenter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ButterKnife.bind(this);
mainPresenter = new MainPresenter(this);
mainPresenter.getDate("笔记本",1);
}
@Override
public void onSuccess(MainBean mainBean) {
Log.i("zxc",mainBean.getMsg());
}
@Override
public void onFailure(Throwable throwable) {
Log.i("zxc",throwable.getMessage());
}
@Override
protected void onDestroy() {
super.onDestroy();
if (mainPresenter != null) {
mainPresenter.onDestroy();
}
}
}
MainActivity布局:
<RelativeLayout 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"
tools:context="com.example.xiangmu2_dome01.view.MainActivity">
<android.support.v7.widget.RecyclerView
android:id="@+id/recycle"
android:layout_width="match_parent"
android:layout_height="match_parent">android.support.v7.widget.RecyclerView>
RelativeLayout>
P层:
MainPresenter:
public class MainPresenter implements IMainPresenter {
private MainMolde mainMolde;
private IMainView iMainView;
public MainPresenter(IMainView iMainView) {
this.iMainView=iMainView;
mainMolde = new MainMolde(this);
}
public void getDate(String keywords, int page) {
mainMolde.getDate(keywords,page);
}
@Override
public void onSuccess(MainBean mainBean) {
iMainView.onSuccess(mainBean);
}
@Override
public void onFailure(Throwable throwable) {
iMainView.onFailure(throwable);
}
public void onDestroy() {
if (iMainView != null) {
iMainView = null;
}
}
}
M层:
public class MainMolde {
private IMainPresenter iMainPresenter;
public MainMolde(IMainPresenter iMainPresenter) {
this.iMainPresenter=iMainPresenter;
}
public void getDate(String keywords, int page) {
// //基本使用
// //1.拿到retrofit对象
// Retrofit retrofit = new Retrofit.Builder()
// .baseUrl("https://www.zhaoapi.cn/")
// .addConverterFactory(GsonConverterFactory.create())
// .build();
//
// //2.创建一个网络请求的接口
// ApiService apiService = retrofit.create(ApiService.class);
// //3.调用
// Call call = apiService.getData(keywords, page);
//
// call.enqueue(new Callback() {
// @Override
// public void onResponse(Call call, Response response) {
// iMainPresenter.onSuccess(response.body());
//
// }
//
// @Override
// public void onFailure(Call call, Throwable t) {
// iMainPresenter.onFailure(t);
// }
// });
Map map=new HashMap<>();
map.put("keywords",keywords);
map.put("page", String.valueOf(page));
RetrofitUtil.getInstance("https://www.zhaoapi.cn/")
.createService(ApiService.class)
.postData(map)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer() {
@Override
public void onSubscribe(Disposable d) {
}
@Override
public void onNext(MainBean mainBean) {
iMainPresenter.onSuccess(mainBean);
}
@Override
public void onError(Throwable e) {
iMainPresenter.onFailure(e);
}
@Override
public void onComplete() {
}
});
}
}
util:
ApiService:
public interface ApiService {
//https://www.zhaoapi.cn/product/searchProducts?keywords=笔记本&page=1
//1.calll泛型 可以是string...表示的是返回的json字符串...还可以是bean对象,,已经给解析过的bean...responseBody响应实体,,,通用的
//2.方法中可以有参数 也可以没有参数...给get方式的参数进行注解的@QueryMap集合形式的多个参数 @Query单个参数
//3.retrofit在使用的时候 把路径拆成两部分baseUrl+相对路径....https://www.zhaoapi.cn/ baseUrl一定带着"/"
@GET("product/searchProducts")
Call getData(@Query("keywords") String keywords,@Query("page") int page);
@GET("{url}")
Call getDataWithUrl(@Path("url") String url,@Query("keywords") String keywords,@Query("page") int page);
//post
//1.post方式 参数需要注解 单个参数 @field @fieldMap
@FormUrlEncoded
@POST("product/searchProducts")
Observable postData(@FieldMap Map map);
}
RetrofitUtil:
public class RetrofitUtil {
private static RetrofitUtil retrofitUtil = null;
private Retrofit retrofit;
private RetrofitUtil() {
}
private RetrofitUtil(String baseUrl) {
OkHttpClient okHttpClient = new OkHttpClient.Builder()
//.addNetworkInterceptor()//网络拦截器
.addInterceptor(new CommonParamsInterceptor())//拦截器
//.connectTimeout()//连接超时
.build();
//创建retrofit
retrofit = new Retrofit.Builder()
.baseUrl(baseUrl)
.client(okHttpClient)//指定网络请求的客户端对象
.addConverterFactory(GsonConverterFactory.create())//添加转换器
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())//设置支持rxjava 注意是2
.build();
}
/**
* 单例模式
* @return
*/
public static RetrofitUtil getInstance(String baseUrl) {
if (retrofitUtil == null) {
synchronized (RetrofitUtil.class) {
if (retrofitUtil == null) {
retrofitUtil = new RetrofitUtil(baseUrl);
}
}
}
return retrofitUtil;
}
public <T> T createService(Class<T> service) {
return retrofit.create(service);
}
/**
* 公共参数的拦截器
*/
private static class CommonParamsInterceptor implements Interceptor {
//intercept方法就是拦截的意思....拦截的是一个请求,,,一旦拦截之后可以对请求的参数进行处理
//Chain chain 链条的意思
@Override
public Response intercept(Chain chain) throws IOException {
//调用request()方法得到拦截的请求
Request request = chain.request();
//获取请求的方式
String method = request.method();//GET POST
//拦截的请求的路径
String oldUrl = request.url().toString();
Log.e("----oldUrl",oldUrl);
//要添加的公共参数...map
Map map = new HashMap<>();
map.put("source","android");
if ("GET".equals(method)){
StringBuilder stringBuilder = new StringBuilder();//创建一个stringBuilder...字符串缓冲区
stringBuilder.append(oldUrl);
if (oldUrl.contains("?")){
//?在最后面....2类型
if (oldUrl.indexOf("?") == oldUrl.length()-1){
}else {
//3类型...拼接上&
stringBuilder.append("&");
}
}else {
//不包含? 属于1类型,,,先拼接上?号
stringBuilder.append("?");
}
//添加公共参数....source=android&appVersion=100&
for (Map.Entry entry: map.entrySet()) {
//拼接
stringBuilder.append(entry.getKey())
.append("=")
.append(entry.getValue())
.append("&");
}
//删掉最后一个&符号
if (stringBuilder.indexOf("&") != -1){
stringBuilder.deleteCharAt(stringBuilder.lastIndexOf("&"));
}
//得到含有公共参数的新路径.....使用新路径去请求
String newUrl = stringBuilder.toString();
Log.e("----newUrl",newUrl);
//新的路径构建一个新的请求
request = request.newBuilder().url(newUrl).build();
}else if ("POST".equals(method)){
//参数在请求的实体内容上....拿到以前的参数,把以前的参数和公共参数全都添加到请求实体上
RequestBody requestBody = request.body();
if (requestBody instanceof FormBody){//前边是不是后边的子类/实例对象
FormBody oldBody = (FormBody) requestBody;//keywords...page
FormBody.Builder builder = new FormBody.Builder();
//先添加之前的参数
for (int i = 0;i//键值对的形式添加
builder.add(oldBody.name(i),oldBody.value(i));
}
//添加公共参数
for (Map.Entry entry: map.entrySet()) {
builder.add(entry.getKey(),entry.getValue());
}
//构建一个新的请求
request = request.newBuilder().url(oldUrl).post(builder.build()).build();
}
}
//执行请求 获取到响应
Response response = chain.proceed(request);
return response;
}
}
/**
* 接口地址:http://www.bwstudent.com/kjbd/user/modifyImg
接口交互:POST
接口描述:上传用户的头像
FormParam入参
Parameter 类型 描述 例子
img String 图片 需要上传的图片路径
head入参
Parameter 类型 描述 例子
ak string 版本号 001002003
userId int 用户id 1
sessionId string 用户状态 201801301
------------封装header的拦截器....注意封装的是不变的head头信息
*/
}
IPresenter:
public interface IMainPresenter {
void onSuccess(MainBean mainBean);
void onFailure(Throwable throwable);
}
IView:
public interface IMainView {
void onSuccess(MainBean mainBean);
void onFailure(Throwable throwable);
}
依赖:
//butterknife
implementation 'com.jakewharton:butterknife:8.8.1'
annotationProcessor 'com.jakewharton:butterknife-compiler:8.8.1'
//添加retrofit依赖
compile 'com.squareup.retrofit2:retrofit:2.3.0'
//添加gson转换器的依赖
compile 'com.squareup.retrofit2:converter-gson:2.3.0'
//注意 rxjava2是2.0的 不加2表示的是1.0
compile 'com.squareup.retrofit2:adapter-rxjava2:2.3.0'
compile "io.reactivex.rxjava2:rxjava:2.1.10"
compile 'io.reactivex.rxjava2:rxandroid:2.0.2'
compile 'com.facebook.fresco:fresco:1.3.0'
//glide
compile 'com.github.bumptech.glide:glide:3.7.0'
//ok的依赖
compile 'com.squareup.okhttp3:okhttp:3.6.0'
compile 'com.squareup.okio:okio:1.11.0'
//glide
compile 'com.github.bumptech.glide:glide:3.7.0'