├── .gitignore ├── .idea ├── gradle.xml ├── misc.xml ├── modules.xml ├── runConfigurations.xml └── vcs.xml ├── Readme.md ├── app ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── mvp │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── com │ │ │ └── mvp │ │ │ └── MainActivity.java │ └── res │ │ ├── layout │ │ └── activity_main.xml │ │ └── values │ │ └── strings.xml │ └── test │ └── java │ └── com │ └── mvp │ └── ExampleUnitTest.java ├── build.gradle ├── gradle.properties ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── img ├── app是否引入login.png ├── debug清单文件.png ├── noDebug清单文件.png ├── 依赖关系.png ├── 切换module与library.png ├── 加载不同的资源文件.png └── 更改调试类型.png ├── login ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── login │ │ └── ExampleInstrumentedTest.java │ ├── debug │ └── AndroidManifest.xml │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── com │ │ │ └── login │ │ │ ├── LoginActivity.java │ │ │ ├── di │ │ │ ├── LoginComponent.java │ │ │ └── LoginModule.java │ │ │ ├── loginsuccess │ │ │ └── LoginSuccessActivity.java │ │ │ └── mvp │ │ │ ├── LoginContract.java │ │ │ ├── LoginModel.java │ │ │ └── LoginPresenter.java │ └── res │ │ └── values │ │ └── strings.xml │ └── test │ └── java │ └── com │ └── login │ └── ExampleUnitTest.java ├── module_home ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── home │ │ └── ExampleInstrumentedTest.java │ ├── debug │ └── AndroidManifest.xml │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── com │ │ │ └── home │ │ │ └── HomeActivity.java │ └── res │ │ └── layout │ │ └── activity_home.xml │ └── test │ └── java │ └── com │ └── home │ └── ExampleUnitTest.java ├── resource ├── .gitignore ├── build.gradle ├── libs │ └── mpandroidchartlibrary-2-1-3.jar ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── resource │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── com │ │ │ └── resource │ │ │ ├── base │ │ │ ├── BaseActivity.java │ │ │ ├── BaseApplication.java │ │ │ ├── BaseFragment.java │ │ │ ├── di │ │ │ │ ├── AppModule.java │ │ │ │ ├── component │ │ │ │ │ └── AppComponent.java │ │ │ │ └── scope │ │ │ │ │ └── ActivityScope.java │ │ │ ├── mvp │ │ │ │ ├── BaseModel.java │ │ │ │ ├── BasePresenter.java │ │ │ │ ├── MvpBaseActivity.java │ │ │ │ └── interfaces │ │ │ │ │ ├── IActivity.java │ │ │ │ │ ├── IModel.java │ │ │ │ │ ├── IPresenter.java │ │ │ │ │ └── IView.java │ │ │ └── other │ │ │ │ ├── AppLifecycles.java │ │ │ │ └── AppManager.java │ │ │ ├── bean │ │ │ └── CustomPieChartBean.java │ │ │ ├── common │ │ │ ├── ARouterConstant.java │ │ │ └── Constant.java │ │ │ ├── util │ │ │ ├── ARouterUtil.java │ │ │ ├── AppComponentUtil.java │ │ │ ├── Base64Util.java │ │ │ ├── BitmapUtil.java │ │ │ ├── DestroyActivityUtil.java │ │ │ ├── FileUtil.java │ │ │ ├── GetPathFromUri.java │ │ │ ├── LogUtil.java │ │ │ ├── NetworkUtils.java │ │ │ ├── Preconditions.java │ │ │ ├── RegexUtil.java │ │ │ ├── SoftKeyBoardUtil.java │ │ │ ├── SpUtil.java │ │ │ ├── SurfaceCameraUtil.java │ │ │ ├── ToastUtil.java │ │ │ ├── Utils.java │ │ │ ├── WaitLoadingDialogUtill.java │ │ │ └── statuBar │ │ │ │ ├── Eyes.java │ │ │ │ ├── EyesKitKat.java │ │ │ │ └── EyesLollipop.java │ │ │ └── weight │ │ │ ├── CustomSwipeRefreshLayout.java │ │ │ ├── CustomTabLayout.java │ │ │ ├── CustomToolbar.java │ │ │ ├── EndLessOnScrollListener.java │ │ │ ├── NoScrollViewPager.java │ │ │ ├── photoView │ │ │ ├── Compat.java │ │ │ ├── CustomGestureDetector.java │ │ │ ├── OnGestureListener.java │ │ │ ├── OnMatrixChangedListener.java │ │ │ ├── OnOutsidePhotoTapListener.java │ │ │ ├── OnPhotoTapListener.java │ │ │ ├── OnScaleChangedListener.java │ │ │ ├── OnSingleFlingListener.java │ │ │ ├── OnViewDragListener.java │ │ │ ├── OnViewTapListener.java │ │ │ ├── PhotoView.java │ │ │ ├── PhotoViewAttacher.java │ │ │ └── PhotoViewUtil.java │ │ │ └── recyclerview │ │ │ ├── BaseRecyclerAdapter.java │ │ │ ├── OnRecyclerViewItemClickListener.java │ │ │ ├── OnRecyclerViewItemLongClickListener.java │ │ │ └── RecyclerViewHolder.java │ └── res │ │ ├── anim │ │ └── dialog_wait_loading_rotate.xml │ │ ├── drawable-xxhdpi │ │ ├── icon_back_gray.png │ │ ├── icon_back_white.png │ │ ├── icon_bg_toolbar.png │ │ └── icon_wait_loading.png │ │ ├── drawable │ │ ├── bg_blue_corner_15.xml │ │ ├── bg_blue_corner_3.xml │ │ ├── bg_gray999_corner_3.xml │ │ ├── bg_gray_corner_15.xml │ │ ├── bg_gray_corner_3.xml │ │ ├── bg_orange_corner_3.xml │ │ ├── bg_red_corner_3.xml │ │ ├── bg_white_corner_15.xml │ │ ├── bg_white_corner_3.xml │ │ ├── border_black_corner_3.xml │ │ ├── border_blue_corner_3.xml │ │ ├── border_gray999_corner_3.xml │ │ ├── border_gray_corner_0.xml │ │ ├── border_gray_corner_3.xml │ │ ├── border_orange_corner_3.xml │ │ ├── border_white_corner_3.xml │ │ ├── ic_launcher_background.xml │ │ └── ic_launcher_foreground.xml │ │ ├── layout │ │ ├── activity_layout │ │ │ ├── anim │ │ │ │ └── progressbar_transplate.xml │ │ │ └── layout │ │ │ │ ├── activity_login.xml │ │ │ │ └── activity_login_success.xml │ │ ├── dialog_layout │ │ │ └── layout │ │ │ │ └── dialog_wait_loading.xml │ │ └── layout_custom_toolbar.xml │ │ ├── mipmap-anydpi-v26 │ │ ├── ic_launcher.xml │ │ └── ic_launcher_round.xml │ │ ├── mipmap-hdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-mdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-xhdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-xxhdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-xxxhdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ └── values │ │ ├── attrs.xml │ │ ├── colors.xml │ │ ├── strings.xml │ │ └── styles.xml │ └── test │ └── java │ └── com │ └── resource │ └── ExampleUnitTest.java ├── rthttp ├── .gitignore ├── .idea │ ├── .name │ ├── gradle.xml │ ├── libraries │ │ ├── __local_aars___F__android_code_mvp_Retrofit_Rxjava_resource_libs_mpandroidchartlibrary_2_1_3_jar_unspecified_jar.xml │ │ ├── android_arch_core_common_1_0_0_jar.xml │ │ ├── android_arch_lifecycle_common_1_0_0_jar.xml │ │ ├── android_arch_lifecycle_runtime_1_0_0.xml │ │ ├── com_alibaba_arouter_annotation_1_0_3_jar.xml │ │ ├── com_alibaba_arouter_api_1_2_1_1.xml │ │ ├── com_android_support_animated_vector_drawable_26_1_0.xml │ │ ├── com_android_support_appcompat_v7_26_1_0.xml │ │ ├── com_android_support_constraint_constraint_layout_1_1_3.xml │ │ ├── com_android_support_constraint_constraint_layout_solver_1_1_3_jar.xml │ │ ├── com_android_support_design_26_1_0.xml │ │ ├── com_android_support_multidex_1_0_2.xml │ │ ├── com_android_support_multidex_instrumentation_1_0_2.xml │ │ ├── com_android_support_recyclerview_v7_26_1_0.xml │ │ ├── com_android_support_support_annotations_26_1_0_jar.xml │ │ ├── com_android_support_support_compat_26_1_0.xml │ │ ├── com_android_support_support_core_ui_26_1_0.xml │ │ ├── com_android_support_support_core_utils_26_1_0.xml │ │ ├── com_android_support_support_fragment_26_1_0.xml │ │ ├── com_android_support_support_media_compat_26_1_0.xml │ │ ├── com_android_support_support_v4_26_1_0.xml │ │ ├── com_android_support_support_vector_drawable_26_1_0.xml │ │ ├── com_android_support_transition_26_1_0.xml │ │ ├── com_github_bumptech_glide_annotations_4_5_0_jar.xml │ │ ├── com_github_bumptech_glide_disklrucache_4_5_0_jar.xml │ │ ├── com_github_bumptech_glide_gifdecoder_4_5_0.xml │ │ ├── com_github_bumptech_glide_glide_4_5_0.xml │ │ ├── com_google_code_findbugs_jsr305_3_0_1_jar.xml │ │ ├── com_google_code_gson_gson_2_7_jar.xml │ │ ├── com_google_dagger_dagger_2_9_jar.xml │ │ ├── com_jakewharton_butterknife_8_8_1.xml │ │ ├── com_jakewharton_butterknife_annotations_8_8_1_jar.xml │ │ ├── com_jakewharton_rxbinding_rxbinding_0_4_0.xml │ │ ├── com_squareup_okhttp3_logging_interceptor_3_4_2_jar.xml │ │ ├── com_squareup_okhttp3_okhttp_3_12_0_jar.xml │ │ ├── com_squareup_okio_okio_1_15_0_jar.xml │ │ ├── com_squareup_retrofit2_adapter_rxjava2_2_5_0_jar.xml │ │ ├── com_squareup_retrofit2_converter_gson_2_1_0_jar.xml │ │ ├── com_squareup_retrofit2_retrofit_2_5_0_jar.xml │ │ ├── com_trello_rxlifecycle_1_0_jar.xml │ │ ├── com_trello_rxlifecycle_android_1_0.xml │ │ ├── com_trello_rxlifecycle_components_1_0.xml │ │ ├── io_reactivex_rxandroid_1_1_0.xml │ │ ├── io_reactivex_rxjava2_rxandroid_2_1_2_SNAPSHOT.xml │ │ ├── io_reactivex_rxjava2_rxjava_2_2_7_jar.xml │ │ ├── io_reactivex_rxjava_1_2_1_jar.xml │ │ ├── javax_inject_javax_inject_1_jar.xml │ │ ├── junit_junit_4_12_jar.xml │ │ ├── org_greenrobot_eventbus_3_0_0_jar.xml │ │ ├── org_hamcrest_hamcrest_core_1_3_jar.xml │ │ ├── org_reactivestreams_reactive_streams_1_0_2_jar.xml │ │ └── pub_devrel_easypermissions_1_0_0.xml │ ├── misc.xml │ ├── modules.xml │ ├── runConfigurations.xml │ ├── vcs.xml │ └── workspace.xml ├── build.gradle ├── gradle │ └── wrapper │ │ ├── gradle-wrapper.jar │ │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── local.properties ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── rthttp │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ └── java │ │ └── com │ │ └── rthttp │ │ ├── Mobile.java │ │ ├── RetrofitFactory.java │ │ ├── RxJavaHelper.java │ │ ├── api │ │ └── ApiService.java │ │ ├── base │ │ ├── BaseObserver.java │ │ └── BaseResponse.java │ │ ├── bean │ │ └── LoginBean.java │ │ └── intercept │ │ └── MyIntercept.java │ └── test │ └── java │ └── com │ └── rthttp │ └── ExampleUnitTest.java └── settings.gradle /.gitignore: -------------------------------------------------------------------------------- 1 | *.iml 2 | .gradle 3 | /local.properties 4 | /.idea/workspace.xml 5 | /.idea/libraries 6 | .DS_Store 7 | /build 8 | /captures 9 | .externalNativeBuild 10 | -------------------------------------------------------------------------------- /.idea/gradle.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 21 | 22 | -------------------------------------------------------------------------------- /.idea/misc.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 16 | 26 | 27 | 28 | 29 | 30 | 31 | 33 | 34 | 35 | 36 | 37 | 1.8 38 | 39 | 44 | 45 | 46 | 47 | 48 | 49 | -------------------------------------------------------------------------------- /.idea/modules.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /.idea/runConfigurations.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 11 | 12 | -------------------------------------------------------------------------------- /.idea/vcs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /Readme.md: -------------------------------------------------------------------------------- 1 | # MVP-Retrofit-Rxjava-组件化 2 | **前言: Android框架层出不穷,组件化也被我们广泛运用,现在越来越多的开发者将组件化运用到自己的项目中. 3 | 随着APP版本不断的迭代,新功能的不断增加,业务也会变的越来越复杂,APP业务模块的数量有可能还会继续增加, 4 | 而且每个模块的代码也变的越来越多,这样发展下去单一工程下的APP架构势必会影响开发效率,增加项目的维护成本, 5 | 每个工程师都要熟悉如此之多的代码,将很难进行多人协作开发,而且Android项目在编译代码的时候电脑会非常卡, 6 | 又因为单一工程下代码耦合严重,每修改一处代码后都要重新编译打包测试,导致非常耗时, 7 | 最重要的是这样的代码想要做单元测试根本无从下手,所以必须要有更灵活的架构代替过去单一的工程架构。** 8 | ### 组件化的优点: 9 | + 各个模块分离,多人协作开发,互不影响 10 | + 调试自己所负责模块,不需要将整个项目编译,只需要将自己负责的module编译就可以调试 11 | + 各个组件的可重用性更高,整个app是由各个模块组成的 12 | ### 组件化的缺点 13 | + 增加了学习的成本 14 | + 需要更高更深层的理解 15 | 16 | 17 | ### app 主module 18 | ### login 登录module 19 | ### rthttp 包含所有网络相关 20 | ### resource 包含所有资源文件相关,工具类相关 21 | ## 依赖关系如下 22 | 23 | 24 | ## 单独调试如下 25 | + **login可作为module单独调试** 26 | 27 | 28 | + **切换完之后,app引入的会根据该变量判断是否需要引入login** 29 | 30 | 31 | + **同时我们的login的build文件会根据该变量判断是作为application还是作为library** 32 | 33 | 34 | + **加载不同的资源文件,如果作为module单独运行,则执行debug的资源清单文件,会有默认的启动activity 35 | 如果作为library,则没有默认的启动activity** 36 | 37 | 38 | + **需要单独调试的清单文件,因为是需要单独调试,所以就作为一个app一样,所有该module里所需的权限都要配置, 39 | 还有全局配置类,里面配置了包括ARouter,Dagger等相关,要有默认的启动Activity页面** 40 | 41 | 42 | + **作为依赖包时加载的清单文件,因为他已经作为library包被主module所依赖, 43 | 所有的配置类包括清单文件的权限都在主module类里面有即可** 44 | 45 | 46 | **后续会一直更新,博主QQ : _1271396448_** 47 | -------------------------------------------------------------------------------- /app/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /app/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.application' 2 | apply plugin: 'com.jakewharton.butterknife' 3 | 4 | android { 5 | 6 | compileSdkVersion rootProject.ext.compileSdkVersion 7 | buildToolsVersion rootProject.ext.buildToolsVersion 8 | 9 | defaultConfig { 10 | applicationId rootProject.ext.applicationId 11 | minSdkVersion rootProject.ext.minSdkVersion 12 | targetSdkVersion rootProject.ext.targetSdkVersion 13 | versionCode rootProject.ext.versionCode 14 | versionName rootProject.ext.versionName 15 | 16 | multiDexEnabled true 17 | 18 | javaCompileOptions { 19 | annotationProcessorOptions { 20 | arguments = [moduleName: project.getName()] 21 | } 22 | } 23 | } 24 | 25 | buildTypes { 26 | release { 27 | minifyEnabled false 28 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 29 | } 30 | } 31 | 32 | compileOptions { 33 | sourceCompatibility JavaVersion.VERSION_1_8 34 | targetCompatibility JavaVersion.VERSION_1_8 35 | } 36 | } 37 | 38 | dependencies { 39 | implementation fileTree(dir: 'libs', include: ['*.jar']) 40 | //登录 41 | if (!isLoginNeedDebug.toBoolean()) { 42 | //如果不需要单独调试的话,则作为library引入到此module中 43 | api project(':login') 44 | } 45 | //首页 46 | if (!isHomeNeedDebug.toBoolean()){ 47 | //如果不需要单独调试的话,则作为library引入到此module中 48 | api project(':module_home') 49 | } 50 | 51 | api project(':rthttp') 52 | 53 | annotationProcessor rootProject.ext.arouterCompiler 54 | annotationProcessor rootProject.ext.daggerCompiler 55 | annotationProcessor rootProject.ext.butterknifeCompiler 56 | } 57 | -------------------------------------------------------------------------------- /app/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # You can control the set of applied configuration files using the 3 | # proguardFiles setting in build.gradle. 4 | # 5 | # For more details, see 6 | # http://developer.android.com/guide/developing/tools/proguard.html 7 | 8 | # If your project uses WebView with JS, uncomment the following 9 | # and specify the fully qualified class name to the JavaScript interface 10 | # class: 11 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 12 | # public *; 13 | #} 14 | 15 | # Uncomment this to preserve the line number information for 16 | # debugging stack traces. 17 | #-keepattributes SourceFile,LineNumberTable 18 | 19 | # If you keep the line number information, uncomment this to 20 | # hide the original source file name. 21 | #-renamesourcefileattribute SourceFile 22 | -------------------------------------------------------------------------------- /app/src/androidTest/java/com/mvp/ExampleInstrumentedTest.java: -------------------------------------------------------------------------------- 1 | package com.mvp; 2 | 3 | import android.content.Context; 4 | import android.support.test.InstrumentationRegistry; 5 | import android.support.test.runner.AndroidJUnit4; 6 | 7 | import org.junit.Test; 8 | import org.junit.runner.RunWith; 9 | 10 | import static org.junit.Assert.*; 11 | 12 | /** 13 | * Instrumented test, which will execute on an Android device. 14 | * 15 | * @see Testing documentation 16 | */ 17 | @RunWith(AndroidJUnit4.class) 18 | public class ExampleInstrumentedTest { 19 | @Test 20 | public void useAppContext() throws Exception { 21 | // Context of the app under test. 22 | Context appContext = InstrumentationRegistry.getTargetContext(); 23 | 24 | assertEquals("com.mvp", appContext.getPackageName()); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /app/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | 7 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | -------------------------------------------------------------------------------- /app/src/main/java/com/mvp/MainActivity.java: -------------------------------------------------------------------------------- 1 | package com.mvp; 2 | 3 | import android.view.View; 4 | import android.widget.Button; 5 | 6 | import com.resource.base.BaseActivity; 7 | import com.resource.common.ARouterConstant; 8 | import com.resource.util.ARouterUtil; 9 | 10 | import butterknife.BindView; 11 | import butterknife.OnClick; 12 | 13 | public class MainActivity extends BaseActivity { 14 | 15 | @BindView(R2.id.btn_intent_login) 16 | Button btnIntentLogin; 17 | 18 | @Override 19 | public int initLayout() { 20 | return R.layout.activity_main; 21 | } 22 | 23 | @Override 24 | public void initView() { 25 | } 26 | 27 | @Override 28 | public void initData() { 29 | } 30 | 31 | @OnClick({R2.id.btn_intent_login}) 32 | public void onViewClicked(View view) { 33 | int id = view.getId(); 34 | if (id == R.id.btn_intent_login) 35 | ARouterUtil.start(ARouterConstant.ROUTE_LOGIN_LOGINACTIVITY); 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_main.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 |