Showing preview only (302K chars total). Download the full file or copy to clipboard to get everything.
Repository: salecoding/WanAndroid
Branch: master
Commit: d4d3ed1a4255
Files: 158
Total size: 10.7 MB
Directory structure:
gitextract_ys2tdhgz/
├── .gitignore
├── .idea/
│ ├── compiler.xml
│ ├── copyright/
│ │ └── profiles_settings.xml
│ ├── encodings.xml
│ ├── gradle.xml
│ ├── misc.xml
│ ├── modules.xml
│ ├── runConfigurations.xml
│ └── vcs.xml
├── README.md
├── app/
│ ├── .gitignore
│ ├── build.gradle
│ ├── proguard-rules.pro
│ ├── release/
│ │ ├── app-release.apk
│ │ └── output.json
│ ├── src/
│ │ ├── androidTest/
│ │ │ └── java/
│ │ │ └── com/
│ │ │ └── lw/
│ │ │ └── wanandroid/
│ │ │ └── ExampleInstrumentedTest.java
│ │ ├── main/
│ │ │ ├── AndroidManifest.xml
│ │ │ ├── java/
│ │ │ │ └── com/
│ │ │ │ └── lw/
│ │ │ │ └── wanandroid/
│ │ │ │ ├── MainActivity.java
│ │ │ │ ├── base/
│ │ │ │ │ ├── App.java
│ │ │ │ │ ├── BaseActivity.java
│ │ │ │ │ ├── BaseContract.java
│ │ │ │ │ ├── BaseFragment.java
│ │ │ │ │ └── BasePresenter.java
│ │ │ │ ├── bean/
│ │ │ │ │ ├── Article.java
│ │ │ │ │ ├── Banner.java
│ │ │ │ │ ├── DataResponse.java
│ │ │ │ │ ├── Friend.java
│ │ │ │ │ ├── HotKey.java
│ │ │ │ │ ├── KnowledgeSystem.java
│ │ │ │ │ └── User.java
│ │ │ │ ├── constant/
│ │ │ │ │ ├── Constant.java
│ │ │ │ │ └── LoadType.java
│ │ │ │ ├── db/
│ │ │ │ │ ├── AppDatabase.java
│ │ │ │ │ └── HistoryModel.java
│ │ │ │ ├── di/
│ │ │ │ │ ├── component/
│ │ │ │ │ │ ├── ActivityComponent.java
│ │ │ │ │ │ ├── ApplicationComponent.java
│ │ │ │ │ │ ├── FragmentComponent.java
│ │ │ │ │ │ └── ServiceComponent.java
│ │ │ │ │ ├── module/
│ │ │ │ │ │ ├── ActivityModule.java
│ │ │ │ │ │ ├── ApplicationModule.java
│ │ │ │ │ │ ├── FragmentModule.java
│ │ │ │ │ │ └── ServiceModule.java
│ │ │ │ │ └── scope/
│ │ │ │ │ ├── ContextLife.java
│ │ │ │ │ ├── PerActivity.java
│ │ │ │ │ ├── PerApp.java
│ │ │ │ │ ├── PerFragment.java
│ │ │ │ │ └── PerService.java
│ │ │ │ ├── event/
│ │ │ │ │ └── LoginEvent.java
│ │ │ │ ├── net/
│ │ │ │ │ ├── ApiService.java
│ │ │ │ │ ├── CookiesManager.java
│ │ │ │ │ ├── OkHttpCookies.java
│ │ │ │ │ ├── PersistentCookieStore.java
│ │ │ │ │ └── RetrofitManager.java
│ │ │ │ ├── ui/
│ │ │ │ │ ├── article/
│ │ │ │ │ │ ├── ArticleAdapter.java
│ │ │ │ │ │ ├── ArticleContentActivity.java
│ │ │ │ │ │ ├── ArticleContentContract.java
│ │ │ │ │ │ ├── ArticleContentPresenter.java
│ │ │ │ │ │ ├── ArticleListContract.java
│ │ │ │ │ │ ├── ArticleListFragment.java
│ │ │ │ │ │ ├── ArticleListPresenter.java
│ │ │ │ │ │ ├── ArticleTypeActivity.java
│ │ │ │ │ │ └── ArticleTypeFragmentPagerAdapter.java
│ │ │ │ │ ├── home/
│ │ │ │ │ │ ├── HomeContract.java
│ │ │ │ │ │ ├── HomeFragment.java
│ │ │ │ │ │ └── HomePresenter.java
│ │ │ │ │ ├── hotsearch/
│ │ │ │ │ │ ├── CommonHotAdapter.java
│ │ │ │ │ │ ├── HistoryAdapter.java
│ │ │ │ │ │ ├── HotAdapter.java
│ │ │ │ │ │ ├── HotContract.java
│ │ │ │ │ │ ├── HotFragment.java
│ │ │ │ │ │ ├── HotPresenter.java
│ │ │ │ │ │ ├── SearchActivity.java
│ │ │ │ │ │ ├── SearchContract.java
│ │ │ │ │ │ └── SearchPresenter.java
│ │ │ │ │ ├── knowledgesystem/
│ │ │ │ │ │ ├── KnowledgeSystemAdapter.java
│ │ │ │ │ │ ├── KnowledgeSystemContract.java
│ │ │ │ │ │ ├── KnowledgeSystemFragment.java
│ │ │ │ │ │ └── KnowledgeSystemPresenter.java
│ │ │ │ │ ├── my/
│ │ │ │ │ │ ├── LoginActivity.java
│ │ │ │ │ │ ├── LoginContract.java
│ │ │ │ │ │ ├── LoginPresenter.java
│ │ │ │ │ │ ├── MyBookmarkActivity.java
│ │ │ │ │ │ ├── MyBookmarkContract.java
│ │ │ │ │ │ ├── MyBookmarkPresenter.java
│ │ │ │ │ │ ├── MyCollectionActivity.java
│ │ │ │ │ │ ├── MyCollectionContract.java
│ │ │ │ │ │ ├── MyCollectionPresenter.java
│ │ │ │ │ │ ├── MyContract.java
│ │ │ │ │ │ ├── MyFragment.java
│ │ │ │ │ │ ├── MyPresenter.java
│ │ │ │ │ │ └── RegisterActivity.java
│ │ │ │ │ └── setting/
│ │ │ │ │ ├── SettingActivity.java
│ │ │ │ │ ├── SettingFragment.java
│ │ │ │ │ └── TestPageActivity.java
│ │ │ │ └── utils/
│ │ │ │ ├── ArticleUtils.java
│ │ │ │ ├── GlideImageLoader.java
│ │ │ │ ├── GsonUtils.java
│ │ │ │ ├── RxBus.java
│ │ │ │ └── RxSchedulers.java
│ │ │ └── res/
│ │ │ ├── drawable/
│ │ │ │ ├── ic_action_browser.xml
│ │ │ │ ├── ic_action_hot.xml
│ │ │ │ ├── ic_action_like.xml
│ │ │ │ ├── ic_action_no_like.xml
│ │ │ │ ├── ic_action_search.xml
│ │ │ │ ├── ic_action_share.xml
│ │ │ │ ├── ic_action_white_like.xml
│ │ │ │ ├── ic_chevron_right_black_24dp.xml
│ │ │ │ ├── ic_dashboard_black_24dp.xml
│ │ │ │ ├── ic_home_black_24dp.xml
│ │ │ │ ├── ic_my_black_24dp.xml
│ │ │ │ ├── item_selector.xml
│ │ │ │ └── item_selector_hot.xml
│ │ │ ├── drawable-v21/
│ │ │ │ └── item_selector_hot.xml
│ │ │ ├── layout/
│ │ │ │ ├── activity_article_content.xml
│ │ │ │ ├── activity_article_type.xml
│ │ │ │ ├── activity_login.xml
│ │ │ │ ├── activity_main.xml
│ │ │ │ ├── activity_my_bookmark.xml
│ │ │ │ ├── activity_my_collection.xml
│ │ │ │ ├── activity_register.xml
│ │ │ │ ├── activity_search.xml
│ │ │ │ ├── activity_setting.xml
│ │ │ │ ├── activity_test_page.xml
│ │ │ │ ├── fragment_article_list.xml
│ │ │ │ ├── fragment_home.xml
│ │ │ │ ├── fragment_hot.xml
│ │ │ │ ├── fragment_knowledge_system.xml
│ │ │ │ ├── fragment_my.xml
│ │ │ │ ├── item_article.xml
│ │ │ │ ├── item_history.xml
│ │ │ │ ├── item_hot.xml
│ │ │ │ ├── item_knowledge_system.xml
│ │ │ │ ├── layout_empty_view.xml
│ │ │ │ ├── layout_error_view.xml
│ │ │ │ ├── layout_home_banner_head.xml
│ │ │ │ ├── layout_hot_head.xml
│ │ │ │ └── layout_search_head.xml
│ │ │ ├── menu/
│ │ │ │ ├── menu_content.xml
│ │ │ │ ├── menu_main.xml
│ │ │ │ ├── menu_search.xml
│ │ │ │ ├── menu_type_content.xml
│ │ │ │ └── navigation.xml
│ │ │ ├── values/
│ │ │ │ ├── colors.xml
│ │ │ │ ├── dimens.xml
│ │ │ │ ├── fonts.xml
│ │ │ │ ├── strings.xml
│ │ │ │ └── styles.xml
│ │ │ └── xml/
│ │ │ └── settings_preference_fragment.xml
│ │ └── test/
│ │ └── java/
│ │ └── com/
│ │ └── lw/
│ │ └── wanandroid/
│ │ └── ExampleUnitTest.java
│ └── wanandroid.jks
├── build.gradle
├── config.gradle
├── gradle/
│ └── wrapper/
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradle.properties
├── gradlew
├── gradlew.bat
└── settings.gradle
================================================
FILE CONTENTS
================================================
================================================
FILE: .gitignore
================================================
*.iml
.gradle
/local.properties
/.idea/workspace.xml
/.idea/libraries
.DS_Store
/build
/captures
.externalNativeBuild
================================================
FILE: .idea/compiler.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CompilerConfiguration">
<resourceExtensions />
<wildcardResourcePatterns>
<entry name="!?*.java" />
<entry name="!?*.form" />
<entry name="!?*.class" />
<entry name="!?*.groovy" />
<entry name="!?*.scala" />
<entry name="!?*.flex" />
<entry name="!?*.kt" />
<entry name="!?*.clj" />
<entry name="!?*.aj" />
</wildcardResourcePatterns>
<annotationProcessing>
<profile default="true" name="Default" enabled="false">
<processorPath useClasspath="true" />
</profile>
</annotationProcessing>
</component>
</project>
================================================
FILE: .idea/copyright/profiles_settings.xml
================================================
<component name="CopyrightManager">
<settings default="" />
</component>
================================================
FILE: .idea/encodings.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="Encoding">
<file url="PROJECT" charset="UTF-8" />
</component>
</project>
================================================
FILE: .idea/gradle.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="GradleSettings">
<option name="linkedExternalProjectsSettings">
<GradleProjectSettings>
<option name="distributionType" value="DEFAULT_WRAPPED" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="modules">
<set>
<option value="$PROJECT_DIR$" />
<option value="$PROJECT_DIR$/app" />
</set>
</option>
<option name="resolveModulePerSourceSet" value="false" />
</GradleProjectSettings>
</option>
</component>
</project>
================================================
FILE: .idea/misc.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="NullableNotNullManager">
<option name="myDefaultNullable" value="android.support.annotation.Nullable" />
<option name="myDefaultNotNull" value="android.support.annotation.NonNull" />
<option name="myNullables">
<value>
<list size="4">
<item index="0" class="java.lang.String" itemvalue="org.jetbrains.annotations.Nullable" />
<item index="1" class="java.lang.String" itemvalue="javax.annotation.Nullable" />
<item index="2" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.Nullable" />
<item index="3" class="java.lang.String" itemvalue="android.support.annotation.Nullable" />
</list>
</value>
</option>
<option name="myNotNulls">
<value>
<list size="4">
<item index="0" class="java.lang.String" itemvalue="org.jetbrains.annotations.NotNull" />
<item index="1" class="java.lang.String" itemvalue="javax.annotation.Nonnull" />
<item index="2" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.NonNull" />
<item index="3" class="java.lang.String" itemvalue="android.support.annotation.NonNull" />
</list>
</value>
</option>
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_7" default="true" project-jdk-name="1.8" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" />
</component>
<component name="ProjectType">
<option name="id" value="Android" />
</component>
</project>
================================================
FILE: .idea/modules.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/WanAndroid.iml" filepath="$PROJECT_DIR$/WanAndroid.iml" />
<module fileurl="file://$PROJECT_DIR$/app/app.iml" filepath="$PROJECT_DIR$/app/app.iml" />
</modules>
</component>
</project>
================================================
FILE: .idea/runConfigurations.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="RunConfigurationProducerService">
<option name="ignoredProducers">
<set>
<option value="org.jetbrains.plugins.gradle.execution.test.runner.AllInPackageGradleConfigurationProducer" />
<option value="org.jetbrains.plugins.gradle.execution.test.runner.TestClassGradleConfigurationProducer" />
<option value="org.jetbrains.plugins.gradle.execution.test.runner.TestMethodGradleConfigurationProducer" />
</set>
</option>
</component>
</project>
================================================
FILE: .idea/vcs.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$" vcs="Git" />
</component>
</project>
================================================
FILE: README.md
================================================
#WanAndroid
Try to build a www.wanandroid.com client
# APK
[app-release.apk](https://coding.net/u/salecoding/p/WanAndroid/git/raw/master/app/release/app-release.apk)
# 接口
[玩Android接口](http://www.wanandroid.com/blog/show/2)
# 代码结构
### MVP + RxJava + Retrofit2 + Dagger2 + Glide
* [RxJava2](https://github.com/ReactiveX/RxJava)
* [Dagger2](https://github.com/google/dagger)
* [Retrofit2](https://github.com/square/retrofit)
* [鸿神的Flowlayout](https://github.com/hongyangAndroid/FlowLayout)
* [BRVAH](https://github.com/CymChad/BaseRecyclerViewAdapterHelper)
* [Agentweb](https://github.com/Justson/AgentWeb)
* [Glide](https://github.com/bumptech/glide)
# 项目运行截图
<img src="screenshots/Screenshot_2018-02-23-14-00-13-312_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-00-20-507_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-00-24-498_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-00-32-235_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-00-42-897_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-00-51-177_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-01-29-488_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-01-46-958_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-01-52-929_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-01-57-654_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-02-15-107_com.will.weiyu.png" width="300px"/>
<img src="screenshots/Screenshot_2018-02-23-14-02-27-830_com.will.weiyu.png" width="300px"/>
# 参考项目
WanAndroidClient https://github.com/wangzailfm/WanAndroidClient
微阅 https://github.com/Will-Ls/WeiYue
非常感谢以上开源项目的作者!谢谢!
[Github](https://github.com/salecoding)
================================================
FILE: app/.gitignore
================================================
/build
================================================
FILE: app/build.gradle
================================================
apply plugin: 'com.android.application'
android {
signingConfigs {
config {
keyAlias RELEASE_KEY_ALIAS
keyPassword RELEASE_KEY_PASSWORD
storeFile file(RELEASE_STORE_FILE)
storePassword RELEASE_STORE_PASSWORD
}
}
compileSdkVersion rootProject.ext.android.compileSdkVersion
buildToolsVersion rootProject.ext.android.buildToolsVersion
defaultConfig {
applicationId rootProject.ext.android.applicationId
minSdkVersion rootProject.ext.android.minSdkVersion
targetSdkVersion rootProject.ext.android.targetSdkVersion
versionCode rootProject.ext.android.versionCode
versionName rootProject.ext.android.versionName
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
javaCompileOptions {
annotationProcessorOptions {
arguments = [moduleName: project.getName()]
}
}
multiDexEnabled true
}
buildTypes {
release {
minifyEnabled false
signingConfig signingConfigs.config
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
debug {
buildConfigField "boolean", "LOG_DEBUG", "true"
minifyEnabled false
signingConfig signingConfigs.config
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
buildToolsVersion '26.0.2'
}
dependencies {
compile fileTree(include: ['*.jar'], dir: 'libs')
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
compile rootProject.ext.dependencies["appcompat-v7"]
compile rootProject.ext.dependencies["support-v4"]
compile rootProject.ext.dependencies["cardview"]
compile rootProject.ext.dependencies["design"]
compile rootProject.ext.dependencies["recyclerview"]
compile rootProject.ext.dependencies["preference"]
compile rootProject.ext.dependencies["retrofit2"]
compile rootProject.ext.dependencies["converter-scalars"]
compile rootProject.ext.dependencies["converter-gson"]
compile rootProject.ext.dependencies["adapter-rxjava2"]
compile rootProject.ext.dependencies["rxlifecycle2"]
compile rootProject.ext.dependencies["rxlifecomponents"]
compile rootProject.ext.dependencies["dagger"]
annotationProcessor rootProject.ext.dependencies["dagger-compiler"]
compile rootProject.ext.dependencies["rxjava"]
compile rootProject.ext.dependencies["rxandroid"]
compile rootProject.ext.dependencies["rxbinding2"]
compile rootProject.ext.dependencies["constraint-layout"]
compile rootProject.ext.dependencies["butterknife"]
annotationProcessor rootProject.ext.dependencies["butterknife-compiler"]
compile rootProject.ext.dependencies["BaseAdapterHelper"]
compile rootProject.ext.dependencies["glide"]
compile rootProject.ext.dependencies["banner"]
compile rootProject.ext.dependencies["circleimageview"]
compile rootProject.ext.dependencies["utilcode"]
compile rootProject.ext.dependencies["agentweb"]
compile rootProject.ext.dependencies["flowlayout"]
compile rootProject.ext.dependencies["fragmentation"]
compile rootProject.ext.dependencies["arouter-api"]
annotationProcessor rootProject.ext.dependencies["arouter-compiler"]
annotationProcessor rootProject.ext.dependencies["dbflow-processor"]
compile rootProject.ext.dependencies["dbflow-core"]
compile rootProject.ext.dependencies["dbflow"]
compile rootProject.ext.dependencies["dbflow-sqlcipher"]
testCompile 'junit:junit:4.12'
}
repositories {
mavenCentral()
}
================================================
FILE: app/proguard-rules.pro
================================================
# Add project specific ProGuard rules here.
# By default, the flags in this file are appended to flags specified
# in D:\Android\SDK/tools/proguard/proguard-android.txt
# You can edit the include path and order by changing the proguardFiles
# directive in build.gradle.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html
# Add any project specific keep options here:
# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}
# Uncomment this to preserve the line number information for
# debugging stack traces.
#-keepattributes SourceFile,LineNumberTable
# If you keep the line number information, uncomment this to
# hide the original source file name.
#-renamesourcefileattribute SourceFile
================================================
FILE: app/release/app-release.apk
================================================
[File too large to display: 10.5 MB]
================================================
FILE: app/release/output.json
================================================
[{"outputType":{"type":"APK"},"apkInfo":{"type":"MAIN","splits":[],"versionCode":1},"path":"app-release.apk","properties":{"packageId":"com.will.weiyue","split":"","minSdkVersion":"19"}}]
================================================
FILE: app/src/androidTest/java/com/lw/wanandroid/ExampleInstrumentedTest.java
================================================
package com.lw.wanandroid;
import android.content.Context;
import android.support.test.InstrumentationRegistry;
import android.support.test.runner.AndroidJUnit4;
import org.junit.Test;
import org.junit.runner.RunWith;
import static org.junit.Assert.assertEquals;
/**
* Instrumentation test, which will execute on an Android device.
*
* @see <a href="http://d.android.com/tools/testing">Testing documentation</a>
*/
@RunWith(AndroidJUnit4.class)
public class ExampleInstrumentedTest {
@Test
public void useAppContext() throws Exception {
// Context of the app under test.
Context appContext = InstrumentationRegistry.getTargetContext();
assertEquals("com.lw.wanandroid", appContext.getPackageName());
}
}
================================================
FILE: app/src/main/AndroidManifest.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.lw.wanandroid">
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
<uses-permission android:name="android.permission.DISABLE_KEYGUARD"/>
<uses-permission android:name="android.permission.ACCESS_DOWNLOAD_MANAGER"/>
<uses-permission android:name="android.permission.DOWNLOAD_WITHOUT_NOTIFICATION"/>
<uses-permission android:name="android.permission.EXPAND_STATUS_BAR"/>
<uses-permission android:name="android.permission.GET_ACCOUNTS"/>
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.RESTART_PACKAGES"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<!-- 获取网络状态 -->
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<!-- 获取wifi状态 -->
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE"/>
<!-- 改变wifi状态 -->
<uses-permission android:name="android.permission.READ_LOGS"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<!-- 读取sd卡 -->
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>
<uses-permission android:name="android.permission.BATTERY_STATS"/>
<!-- 获取电池信息 -->
<uses-permission android:name="android.permission.WRITE_SETTINGS"/>
<!-- 设置系统权限 -->
<uses-permission android:name="android.permission.GET_TASKS"/>
<!-- 设置系统权限 -->
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<!-- 电源锁权限 -->
<uses-permission android:name="android.permission.CAMERA"/>
<!-- 允许应用写(非读)用户的日历数据 -->
<uses-permission android:name="android.permission.VIBRATE"/>
<!-- 允许应用访问震动器 -->
<uses-permission android:name="android.permission.RECORD_AUDIO"/>
<application
android:name=".base.App"
android:allowBackup="true"
android:icon="@drawable/logo"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme.NoActionBar">
<activity
android:name=".MainActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:label="@string/app_name"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<activity
android:name=".ui.article.ArticleContentActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.article.ArticleTypeActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.hotsearch.SearchActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.my.LoginActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.my.RegisterActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.my.MyCollectionActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.my.MyBookmarkActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.setting.SettingActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
<activity
android:name=".ui.setting.TestPageActivity"
android:configChanges="screenSize|keyboardHidden|orientation"
android:screenOrientation="portrait"/>
</application>
</manifest>
================================================
FILE: app/src/main/java/com/lw/wanandroid/MainActivity.java
================================================
package com.lw.wanandroid;
import android.support.annotation.NonNull;
import android.support.design.widget.BottomNavigationView;
import android.view.KeyEvent;
import android.view.Menu;
import android.view.MenuItem;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.launcher.ARouter;
import com.blankj.utilcode.util.ToastUtils;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.ui.home.HomeFragment;
import com.lw.wanandroid.ui.hotsearch.HotFragment;
import com.lw.wanandroid.ui.knowledgesystem.KnowledgeSystemFragment;
import com.lw.wanandroid.ui.my.MyFragment;
import butterknife.BindView;
import me.yokeyword.fragmentation.ISupportFragment;
@Route(path = "/wanandroid/MainActivity")
public class MainActivity extends BaseActivity implements BottomNavigationView.OnNavigationItemSelectedListener {
@BindView(R.id.navigation)
BottomNavigationView mNavigation;
private ISupportFragment[] mFragments = new ISupportFragment[4];
private long mExitTime;
private int preIndex;
@Override
protected int getLayoutId() {
return R.layout.activity_main;
}
@Override
protected void initInjector() {
}
@Override
protected void initView() {
mNavigation.setOnNavigationItemSelectedListener(this);
ISupportFragment homeFragment = findFragment(HomeFragment.class);
if (homeFragment == null) {
mFragments[0] = HomeFragment.newInstance();
mFragments[1] = KnowledgeSystemFragment.newInstance();
mFragments[2] = MyFragment.newInstance();
mFragments[3] = HotFragment.newInstance();
loadMultipleRootFragment(R.id.layout_fragment, 0,
mFragments[0],
mFragments[1],
mFragments[2],
mFragments[3]);
} else {
// 这里我们需要拿到mFragments的引用
mFragments[0] = homeFragment;
mFragments[1] = findFragment(KnowledgeSystemFragment.class);
mFragments[2] = findFragment(MyFragment.class);
mFragments[3] = findFragment(HotFragment.class);
}
}
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
switch (item.getItemId()) {
case R.id.navigation_home:
mToolbar.setTitle(R.string.app_name);
showHideFragment(mFragments[0], mFragments[preIndex]);
preIndex = 0;
break;
case R.id.navigation_knowledgesystem:
mToolbar.setTitle(R.string.title_knowledgesystem);
showHideFragment(mFragments[1], mFragments[preIndex]);
preIndex = 1;
break;
case R.id.navigation_my:
mToolbar.setTitle(R.string.title_my);
showHideFragment(mFragments[2], mFragments[preIndex]);
preIndex = 2;
break;
}
return true;
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_main, menu);
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.getItemId() == R.id.menuHot) {
mToolbar.setTitle(R.string.hot_title);
showHideFragment(mFragments[3], mFragments[preIndex]);
preIndex = 3;
} else if (item.getItemId() == R.id.menuSearch) {
ARouter.getInstance().build("/hotsearch/SearchActivity").navigation();
}
return super.onOptionsItemSelected(item);
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
if ((System.currentTimeMillis() - mExitTime) > 2000) {
ToastUtils.showShort(R.string.exit_system);
mExitTime = System.currentTimeMillis();
} else {
System.exit(0);
}
return true;
}
return super.onKeyDown(keyCode, event);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/base/App.java
================================================
package com.lw.wanandroid.base;
import android.app.Application;
import android.content.Context;
import com.alibaba.android.arouter.launcher.ARouter;
import com.blankj.utilcode.util.Utils;
import com.lw.wanandroid.BuildConfig;
import com.lw.wanandroid.di.component.ApplicationComponent;
import com.lw.wanandroid.di.component.DaggerApplicationComponent;
import com.lw.wanandroid.di.module.ApplicationModule;
import com.raizlabs.android.dbflow.config.FlowManager;
import me.yokeyword.fragmentation.Fragmentation;
/**
* Created by lw on 2018/1/18.
*/
public class App extends Application {
private ApplicationComponent mApplicationComponent;
private static App mInstance;
@Override
public void onCreate() {
super.onCreate();
mInstance = this;
initApplicationComponent();
Utils.init(this);
intARouter();
FlowManager.init(this);
Fragmentation.builder()
.stackViewMode(Fragmentation.BUBBLE) // 显示悬浮球 ; 其他Mode:SHAKE: 摇一摇唤出 NONE:隐藏
.debug(BuildConfig.DEBUG)
.install();
}
/**
* 初始化路由
*/
private void intARouter() {
if (BuildConfig.DEBUG) { // 这两行必须写在init之前,否则这些配置在init过程中将无效
ARouter.openLog(); // 打印日志
ARouter.openDebug(); // 开启调试模式(如果在InstantRun模式下运行,必须开启调试模式!线上版本需要关闭,否则有安全风险)
}
ARouter.init(this); // 尽可能早,推荐在Application中初始化
}
/**
* 初始化ApplicationComponent
*/
private void initApplicationComponent() {
mApplicationComponent = DaggerApplicationComponent.builder()
.applicationModule(new ApplicationModule(this))
.build();
}
public ApplicationComponent getApplicationComponent() {
return mApplicationComponent;
}
public static Context getAppContext() {
return mInstance.getApplicationContext();
}
public static App getInstance() {
return mInstance;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/base/BaseActivity.java
================================================
package com.lw.wanandroid.base;
import android.os.Build;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.Toolbar;
import android.view.MenuItem;
import android.view.MotionEvent;
import com.alibaba.android.arouter.launcher.ARouter;
import com.blankj.utilcode.util.NetworkUtils;
import com.blankj.utilcode.util.ToastUtils;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.di.component.ActivityComponent;
import com.lw.wanandroid.di.component.DaggerActivityComponent;
import com.lw.wanandroid.di.module.ActivityModule;
import com.trello.rxlifecycle2.LifecycleTransformer;
import com.trello.rxlifecycle2.components.support.RxAppCompatActivity;
import java.util.List;
import javax.inject.Inject;
import butterknife.ButterKnife;
import butterknife.Unbinder;
import me.yokeyword.fragmentation.ExtraTransaction;
import me.yokeyword.fragmentation.ISupportActivity;
import me.yokeyword.fragmentation.ISupportFragment;
import me.yokeyword.fragmentation.SupportActivityDelegate;
import me.yokeyword.fragmentation.SupportFragment;
import me.yokeyword.fragmentation.SupportHelper;
import me.yokeyword.fragmentation.anim.FragmentAnimator;
/**
* Created by lw on 2018/1/18.
*/
public abstract class BaseActivity<T extends BaseContract.BasePresenter> extends RxAppCompatActivity implements ISupportActivity, BaseContract.BaseView {
@Nullable
@Inject
protected T mPresenter;
protected ActivityComponent mActivityComponent;
@Nullable
protected Toolbar mToolbar;
private Unbinder unbinder;
protected abstract int getLayoutId();
protected abstract void initInjector();
protected abstract void initView();
/**
* 是否显示返回键
*
* @return
*/
protected boolean showHomeAsUp() {
return false;
}
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mDelegate.onCreate(savedInstanceState);
initActivityComponent();
ARouter.getInstance().inject(this);
int layoutId = getLayoutId();
setContentView(layoutId);
initInjector();
unbinder = ButterKnife.bind(this);
initToolBar();
attachView();
initView();
if (!NetworkUtils.isConnected()) showNoNet();
}
@Override
protected void onDestroy() {
super.onDestroy();
mDelegate.onDestroy();
unbinder.unbind();
detachView();
}
@Override
public void showLoading() {
}
@Override
public void hideLoading() {
}
@Override
public void showSuccess(String successMsg) {
ToastUtils.showShort(successMsg);
}
@Override
public void showFaild(String errorMsg) {
ToastUtils.showShort(errorMsg);
}
@Override
public void showNoNet() {
ToastUtils.showShort(R.string.no_network_connection);
}
@Override
public void onRetry() {
}
@Override
public <T> LifecycleTransformer<T> bindToLife() {
return this.bindToLifecycle();
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
switch (id) {
case android.R.id.home:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
finishAfterTransition();
} else {
finish();
}
break;
}
return true;
}
final SupportActivityDelegate mDelegate = new SupportActivityDelegate(this);
@Override
public SupportActivityDelegate getSupportDelegate() {
return mDelegate;
}
/**
* Perform some extra transactions.
* 额外的事务:自定义Tag,添加SharedElement动画,操作非回退栈Fragment
*/
@Override
public ExtraTransaction extraTransaction() {
return mDelegate.extraTransaction();
}
@Override
protected void onPostCreate(@Nullable Bundle savedInstanceState) {
super.onPostCreate(savedInstanceState);
mDelegate.onPostCreate(savedInstanceState);
}
/**
* Note: return mDelegate.dispatchTouchEvent(ev) || super.dispatchTouchEvent(ev);
*/
@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
return mDelegate.dispatchTouchEvent(ev) || super.dispatchTouchEvent(ev);
}
/**
* 不建议复写该方法,请使用 {@link #onBackPressedSupport} 代替
*/
@Override
final public void onBackPressed() {
mDelegate.onBackPressed();
}
/**
* 该方法回调时机为,Activity回退栈内Fragment的数量 小于等于1 时,默认finish Activity
* 请尽量复写该方法,避免复写onBackPress(),以保证SupportFragment内的onBackPressedSupport()回退事件正常执行
*/
@Override
public void onBackPressedSupport() {
mDelegate.onBackPressedSupport();
}
/**
* 获取设置的全局动画 copy
*
* @return FragmentAnimator
*/
@Override
public FragmentAnimator getFragmentAnimator() {
return mDelegate.getFragmentAnimator();
}
/**
* Set all fragments animation.
* 设置Fragment内的全局动画
*/
@Override
public void setFragmentAnimator(FragmentAnimator fragmentAnimator) {
mDelegate.setFragmentAnimator(fragmentAnimator);
}
/**
* Set all fragments animation.
* 构建Fragment转场动画
* <p/>
* 如果是在Activity内实现,则构建的是Activity内所有Fragment的转场动画,
* 如果是在Fragment内实现,则构建的是该Fragment的转场动画,此时优先级 > Activity的onCreateFragmentAnimator()
*
* @return FragmentAnimator对象
*/
@Override
public FragmentAnimator onCreateFragmentAnimator() {
return mDelegate.onCreateFragmentAnimator();
}
/**
* Causes the Runnable r to be added to the action queue.
* <p>
* The runnable will be run after all the previous action has been run.
* <p>
* 前面的事务全部执行后 执行该Action
*/
@Override
public void post(Runnable runnable) {
mDelegate.post(runnable);
}
protected void setToolbarTitle(String title) {
getSupportActionBar().setTitle(title);
}
/**
* 设置加载数据结果
*
* @param baseQuickAdapter
* @param refreshLayout
* @param list
* @param loadType
*/
protected void setLoadDataResult(BaseQuickAdapter baseQuickAdapter, SwipeRefreshLayout refreshLayout, List list, @LoadType.checker int loadType) {
switch (loadType) {
case LoadType.TYPE_REFRESH_SUCCESS:
baseQuickAdapter.setNewData(list);
refreshLayout.setRefreshing(false);
break;
case LoadType.TYPE_REFRESH_ERROR:
refreshLayout.setRefreshing(false);
break;
case LoadType.TYPE_LOAD_MORE_SUCCESS:
if (list != null) baseQuickAdapter.addData(list);
break;
case LoadType.TYPE_LOAD_MORE_ERROR:
baseQuickAdapter.loadMoreFail();
break;
}
if (list == null || list.isEmpty() || list.size() < Constant.PAGE_SIZE) {
baseQuickAdapter.loadMoreEnd(false);
} else {
baseQuickAdapter.loadMoreComplete();
}
}
// 选择性拓展其他方法
public void loadRootFragment(int containerId, @NonNull ISupportFragment toFragment) {
mDelegate.loadRootFragment(containerId, toFragment);
}
public void start(ISupportFragment toFragment) {
mDelegate.start(toFragment);
}
/**
* @param launchMode Same as Activity's LaunchMode.
*/
public void start(ISupportFragment toFragment, @ISupportFragment.LaunchMode int launchMode) {
mDelegate.start(toFragment, launchMode);
}
/**
* It is recommended to use {@link SupportFragment#startWithPopTo(ISupportFragment, Class, boolean)}.
*
* @see #popTo(Class, boolean)
* +
* @see #start(ISupportFragment)
*/
public void startWithPopTo(ISupportFragment toFragment, Class<?> targetFragmentClass, boolean includeTargetFragment) {
mDelegate.startWithPopTo(toFragment, targetFragmentClass, includeTargetFragment);
}
/**
* Pop the fragment.
*/
public void pop() {
mDelegate.pop();
}
/**
* Pop the last fragment transition from the manager's fragment
* back stack.
*/
public void popTo(Class<?> targetFragmentClass, boolean includeTargetFragment) {
mDelegate.popTo(targetFragmentClass, includeTargetFragment);
}
/**
* If you want to begin another FragmentTransaction immediately after popTo(), use this method.
* 如果你想在出栈后, 立刻进行FragmentTransaction操作,请使用该方法
*/
public void popTo(Class<?> targetFragmentClass, boolean includeTargetFragment, Runnable afterPopTransactionRunnable) {
mDelegate.popTo(targetFragmentClass, includeTargetFragment, afterPopTransactionRunnable);
}
public void popTo(Class<?> targetFragmentClass, boolean includeTargetFragment, Runnable afterPopTransactionRunnable, int popAnim) {
mDelegate.popTo(targetFragmentClass, includeTargetFragment, afterPopTransactionRunnable, popAnim);
}
/**
* 得到位于栈顶Fragment
*/
public ISupportFragment getTopFragment() {
return SupportHelper.getTopFragment(getSupportFragmentManager());
}
/**
* 获取栈内的fragment对象
*/
public <T extends ISupportFragment> T findFragment(Class<T> fragmentClass) {
return SupportHelper.findFragment(getSupportFragmentManager(), fragmentClass);
}
/**
* 加载多个同级根Fragment,类似Wechat, QQ主页的场景
*/
public void loadMultipleRootFragment(int containerId, int showPosition, ISupportFragment... toFragments) {
mDelegate.loadMultipleRootFragment(containerId, showPosition, toFragments);
}
/**
* show一个Fragment,hide其他同栈所有Fragment
* 使用该方法时,要确保同级栈内无多余的Fragment,(只有通过loadMultipleRootFragment()载入的Fragment)
* <p>
* 建议使用更明确的{@link #showHideFragment(ISupportFragment, ISupportFragment)}
*
* @param showFragment 需要show的Fragment
*/
public void showHideFragment(ISupportFragment showFragment) {
mDelegate.showHideFragment(showFragment);
}
/**
* show一个Fragment,hide一个Fragment ; 主要用于类似微信主页那种 切换tab的情况
*/
public void showHideFragment(ISupportFragment showFragment, ISupportFragment hideFragment) {
mDelegate.showHideFragment(showFragment, hideFragment);
}
/**
* 初始化ActivityComponent
*/
private void initActivityComponent() {
mActivityComponent = DaggerActivityComponent.builder()
.applicationComponent(((App) getApplication()).getApplicationComponent())
.activityModule(new ActivityModule(this))
.build();
}
/**
* 初始化toolbar
*/
private void initToolBar() {
mToolbar = (Toolbar) findViewById(R.id.toolbar);
if (mToolbar == null) {
throw new NullPointerException("toolbar can not be null");
}
setSupportActionBar(mToolbar);
getSupportActionBar().setDisplayHomeAsUpEnabled(showHomeAsUp());
/**toolbar除掉阴影*/
getSupportActionBar().setElevation(0);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
mToolbar.setElevation(0);
}
}
/**
* 贴上view
*/
private void attachView() {
if (mPresenter != null) {
mPresenter.attachView(this);
}
}
/**
* 分离view
*/
private void detachView() {
if (mPresenter != null) {
mPresenter.detachView();
}
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/base/BaseContract.java
================================================
package com.lw.wanandroid.base;
import com.trello.rxlifecycle2.LifecycleTransformer;
/**
* desc:
* author: Will .
* date: 2017/9/2 .
*/
public interface BaseContract {
interface BasePresenter<T extends BaseContract.BaseView> {
void attachView(T view);
void detachView();
}
interface BaseView {
//显示进度中
void showLoading();
//隐藏进度
void hideLoading();
//显示请求成功
void showSuccess(String message);
//失败重试
void showFaild(String message);
//显示当前网络不可用
void showNoNet();
//重试
void onRetry();
/**
* 绑定生命周期
*
* @param <T>
* @return
*/
<T> LifecycleTransformer<T> bindToLife();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/base/BaseFragment.java
================================================
package com.lw.wanandroid.base;
import android.app.Activity;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentTransaction;
import android.support.v4.widget.SwipeRefreshLayout;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.animation.Animation;
import com.alibaba.android.arouter.launcher.ARouter;
import com.blankj.utilcode.util.NetworkUtils;
import com.blankj.utilcode.util.ToastUtils;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.di.component.DaggerFragmentComponent;
import com.lw.wanandroid.di.component.FragmentComponent;
import com.lw.wanandroid.di.module.FragmentModule;
import com.trello.rxlifecycle2.LifecycleTransformer;
import com.trello.rxlifecycle2.components.support.RxFragment;
import java.util.List;
import javax.inject.Inject;
import butterknife.ButterKnife;
import butterknife.Unbinder;
import me.yokeyword.fragmentation.ExtraTransaction;
import me.yokeyword.fragmentation.ISupportFragment;
import me.yokeyword.fragmentation.SupportFragmentDelegate;
import me.yokeyword.fragmentation.SupportHelper;
import me.yokeyword.fragmentation.anim.FragmentAnimator;
/**
* Created by lw on 2018/1/18.
*/
public abstract class BaseFragment<T extends BaseContract.BasePresenter> extends RxFragment implements ISupportFragment, BaseContract.BaseView {
private static final String STATE_SAVE_IS_HIDDEN = "STATE_SAVE_IS_HIDDEN";
@Nullable
@Inject
protected T mPresenter;
protected FragmentComponent mFragmentComponent;
private Unbinder unbinder;
private View mRootView, mErrorView, mEmptyView;
protected abstract int getLayoutId();
protected abstract void initInjector();
protected abstract void initView(View view);
@Override
public void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mDelegate.onCreate(savedInstanceState);
initFragmentComponent();
ARouter.getInstance().inject(this);
initInjector();
attachView();
if (!NetworkUtils.isConnected()) showNoNet();
if (savedInstanceState != null) {
boolean isSupportHidden = savedInstanceState.getBoolean(STATE_SAVE_IS_HIDDEN);
FragmentTransaction ft = getFragmentManager().beginTransaction();
if (isSupportHidden) {
ft.hide(this);
} else {
ft.show(this);
}
ft.commit();
}
}
@Override
public void onSaveInstanceState(Bundle outState) {
mDelegate.onSaveInstanceState(outState);
outState.putBoolean(STATE_SAVE_IS_HIDDEN, isHidden());
}
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
inflaterView(inflater, container);
unbinder = ButterKnife.bind(this, mRootView);
initView(mRootView);
return mRootView;
}
@Override
public void onDestroy() {
super.onDestroy();
mDelegate.onDestroy();
unbinder.unbind();
detachView();
}
@Override
public void showLoading() {
ToastUtils.showShort("showLoading");
}
@Override
public void hideLoading() {
ToastUtils.showShort("hideLoading");
}
@Override
public void showSuccess(String successMsg) {
ToastUtils.showShort(successMsg);
}
@Override
public void showFaild(String errorMsg) {
ToastUtils.showShort(errorMsg);
}
@Override
public void showNoNet() {
ToastUtils.showShort(R.string.no_network_connection);
}
@Override
public void onRetry() {
ToastUtils.showShort("onRetry");
}
@Override
public <T> LifecycleTransformer<T> bindToLife() {
return this.bindToLifecycle();
}
/**
* 设置加载数据结果
*
* @param baseQuickAdapter
* @param refreshLayout
* @param list
* @param loadType
*/
protected void setLoadDataResult(BaseQuickAdapter baseQuickAdapter, SwipeRefreshLayout refreshLayout, List list, @LoadType.checker int loadType) {
switch (loadType) {
case LoadType.TYPE_REFRESH_SUCCESS:
baseQuickAdapter.setNewData(list);
refreshLayout.setRefreshing(false);
break;
case LoadType.TYPE_REFRESH_ERROR:
refreshLayout.setRefreshing(false);
break;
case LoadType.TYPE_LOAD_MORE_SUCCESS:
if (list != null) baseQuickAdapter.addData(list);
break;
case LoadType.TYPE_LOAD_MORE_ERROR:
baseQuickAdapter.loadMoreFail();
break;
}
if (list == null || list.isEmpty() || list.size() < Constant.PAGE_SIZE) {
baseQuickAdapter.loadMoreEnd(false);
} else {
baseQuickAdapter.loadMoreComplete();
}
}
/**
* 初始化FragmentComponent
*/
private void initFragmentComponent() {
mFragmentComponent = DaggerFragmentComponent.builder()
.applicationComponent(((App) getActivity().getApplication()).getApplicationComponent())
.fragmentModule(new FragmentModule(this))
.build();
}
/**
* 贴上view
*/
private void attachView() {
if (mPresenter != null) {
mPresenter.attachView(this);
}
}
/**
* 分离view
*/
private void detachView() {
if (mPresenter != null) {
mPresenter.detachView();
}
}
/**
* 设置View
*
* @param inflater
* @param container
*/
private void inflaterView(LayoutInflater inflater, @Nullable ViewGroup container) {
if (mRootView == null) {
mRootView = inflater.inflate(getLayoutId(), container, false);
}
}
final SupportFragmentDelegate mDelegate = new SupportFragmentDelegate(this);
protected FragmentActivity _mActivity;
@Override
public SupportFragmentDelegate getSupportDelegate() {
return mDelegate;
}
/**
* Perform some extra transactions.
* 额外的事务:自定义Tag,添加SharedElement动画,操作非回退栈Fragment
*/
@Override
public ExtraTransaction extraTransaction() {
return mDelegate.extraTransaction();
}
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
mDelegate.onAttach(activity);
_mActivity = mDelegate.getActivity();
}
@Override
public Animation onCreateAnimation(int transit, boolean enter, int nextAnim) {
return mDelegate.onCreateAnimation(transit, enter, nextAnim);
}
@Override
public void onActivityCreated(@Nullable Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
mDelegate.onActivityCreated(savedInstanceState);
}
@Override
public void onResume() {
super.onResume();
mDelegate.onResume();
}
@Override
public void onPause() {
super.onPause();
mDelegate.onPause();
}
@Override
public void onDestroyView() {
mDelegate.onDestroyView();
super.onDestroyView();
}
@Override
public void onHiddenChanged(boolean hidden) {
super.onHiddenChanged(hidden);
mDelegate.onHiddenChanged(hidden);
}
@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
super.setUserVisibleHint(isVisibleToUser);
mDelegate.setUserVisibleHint(isVisibleToUser);
}
/**
* Causes the Runnable r to be added to the action queue.
* <p>
* The runnable will be run after all the previous action has been run.
* <p>
* 前面的事务全部执行后 执行该Action
*
* @deprecated Use {@link #post(Runnable)} instead.
*/
@Deprecated
@Override
public void enqueueAction(Runnable runnable) {
mDelegate.enqueueAction(runnable);
}
/**
* Causes the Runnable r to be added to the action queue.
* <p>
* The runnable will be run after all the previous action has been run.
* <p>
* 前面的事务全部执行后 执行该Action
*/
@Override
public void post(Runnable runnable) {
mDelegate.post(runnable);
}
/**
* Called when the enter-animation end.
* 入栈动画 结束时,回调
*/
@Override
public void onEnterAnimationEnd(Bundle savedInstanceState) {
mDelegate.onEnterAnimationEnd(savedInstanceState);
}
/**
* Lazy initial,Called when fragment is first called.
* <p>
* 同级下的 懒加载 + ViewPager下的懒加载 的结合回调方法
*/
@Override
public void onLazyInitView(@Nullable Bundle savedInstanceState) {
mDelegate.onLazyInitView(savedInstanceState);
}
/**
* Called when the fragment is visible.
* 当Fragment对用户可见时回调
* <p>
* Is the combination of [onHiddenChanged() + onResume()/onPause() + setUserVisibleHint()]
*/
@Override
public void onSupportVisible() {
mDelegate.onSupportVisible();
}
/**
* Called when the fragment is invivible.
* <p>
* Is the combination of [onHiddenChanged() + onResume()/onPause() + setUserVisibleHint()]
*/
@Override
public void onSupportInvisible() {
mDelegate.onSupportInvisible();
}
/**
* Return true if the fragment has been supportVisible.
*/
@Override
final public boolean isSupportVisible() {
return mDelegate.isSupportVisible();
}
/**
* Set fragment animation with a higher priority than the ISupportActivity
* 设定当前Fragmemt动画,优先级比在SupportActivity里高
*/
@Override
public FragmentAnimator onCreateFragmentAnimator() {
return mDelegate.onCreateFragmentAnimator();
}
/**
* 获取设置的全局动画 copy
*
* @return FragmentAnimator
*/
@Override
public FragmentAnimator getFragmentAnimator() {
return mDelegate.getFragmentAnimator();
}
/**
* 设置Fragment内的全局动画
*/
@Override
public void setFragmentAnimator(FragmentAnimator fragmentAnimator) {
mDelegate.setFragmentAnimator(fragmentAnimator);
}
/**
* 按返回键触发,前提是SupportActivity的onBackPressed()方法能被调用
*
* @return false则继续向上传递, true则消费掉该事件
*/
@Override
public boolean onBackPressedSupport() {
return mDelegate.onBackPressedSupport();
}
/**
* 类似
* <p>
* Similar to
*
* @see #startForResult(ISupportFragment, int)
*/
@Override
public void setFragmentResult(int resultCode, Bundle bundle) {
mDelegate.setFragmentResult(resultCode, bundle);
}
/**
* 类似
* <p>
* Similar to
*
* @see #startForResult(ISupportFragment, int)
*/
@Override
public void onFragmentResult(int requestCode, int resultCode, Bundle data) {
mDelegate.onFragmentResult(requestCode, resultCode, data);
}
/**
* 在start(TargetFragment,LaunchMode)时,启动模式为SingleTask/SingleTop, 回调TargetFragment的该方法
* 类似
* <p>
* Similar to
*
* @param args putNewBundle(Bundle newBundle)
* @see #start(ISupportFragment, int)
*/
@Override
public void onNewBundle(Bundle args) {
mDelegate.onNewBundle(args);
}
/**
* 添加NewBundle,用于启动模式为SingleTask/SingleTop时
*
* @see #start(ISupportFragment, int)
*/
@Override
public void putNewBundle(Bundle newBundle) {
mDelegate.putNewBundle(newBundle);
}
/****************************************以下为可选方法(Optional methods)******************************************************/
// 自定制Support时,可移除不必要的方法
/**
* 隐藏软键盘
*/
protected void hideSoftInput() {
mDelegate.hideSoftInput();
}
/**
* 显示软键盘,调用该方法后,会在onPause时自动隐藏软键盘
*/
protected void showSoftInput(final View view) {
mDelegate.showSoftInput(view);
}
/**
* 加载根Fragment, 即Activity内的第一个Fragment 或 Fragment内的第一个子Fragment
*
* @param containerId 容器id
* @param toFragment 目标Fragment
*/
public void loadRootFragment(int containerId, ISupportFragment toFragment) {
mDelegate.loadRootFragment(containerId, toFragment);
}
public void loadRootFragment(int containerId, ISupportFragment toFragment, boolean addToBackStack, boolean allowAnim) {
mDelegate.loadRootFragment(containerId, toFragment, addToBackStack, allowAnim);
}
public void start(ISupportFragment toFragment) {
mDelegate.start(toFragment);
}
/**
* @param launchMode Similar to Activity's LaunchMode.
*/
public void start(final ISupportFragment toFragment, @LaunchMode int launchMode) {
mDelegate.start(toFragment, launchMode);
}
/**
* Launch an fragment for which you would like a result when it poped.
*/
public void startForResult(ISupportFragment toFragment, int requestCode) {
mDelegate.startForResult(toFragment, requestCode);
}
/**
* Start the target Fragment and pop itself
*/
public void startWithPop(ISupportFragment toFragment) {
mDelegate.startWithPop(toFragment);
}
/**
* @see #popTo(Class, boolean)
* +
* @see #start(ISupportFragment)
*/
public void startWithPopTo(ISupportFragment toFragment, Class<?> targetFragmentClass, boolean includeTargetFragment) {
mDelegate.startWithPopTo(toFragment, targetFragmentClass, includeTargetFragment);
}
public void replaceFragment(ISupportFragment toFragment, boolean addToBackStack) {
mDelegate.replaceFragment(toFragment, addToBackStack);
}
public void pop() {
mDelegate.pop();
}
/**
* Pop the last fragment transition from the manager's fragment
* back stack.
* <p>
* 出栈到目标fragment
*
* @param targetFragmentClass 目标fragment
* @param includeTargetFragment 是否包含该fragment
*/
public void popTo(Class<?> targetFragmentClass, boolean includeTargetFragment) {
mDelegate.popTo(targetFragmentClass, includeTargetFragment);
}
/**
* 获取栈内的fragment对象
*/
public <T extends ISupportFragment> T findChildFragment(Class<T> fragmentClass) {
return SupportHelper.findFragment(getChildFragmentManager(), fragmentClass);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/base/BasePresenter.java
================================================
package com.lw.wanandroid.base;
/**
* desc:
* author: Will .
* date: 2017/9/2 .
*/
public class BasePresenter<T extends BaseContract.BaseView> implements BaseContract.BasePresenter<T> {
protected T mView;
@Override
public void attachView(T view) {
this.mView = view;
}
@Override
public void detachView() {
if (mView != null) {
mView = null;
}
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/Article.java
================================================
package com.lw.wanandroid.bean;
import java.util.List;
/**
* Created by lw on 2018/1/18.
*/
public class Article {
private int offset;
private int size;
private int total;
private int pageCount;
private int curPage;
private boolean over;
private List<DatasBean> datas;
public int getOffset() {
return offset;
}
public void setOffset(int offset) {
this.offset = offset;
}
public int getSize() {
return size;
}
public void setSize(int size) {
this.size = size;
}
public int getTotal() {
return total;
}
public void setTotal(int total) {
this.total = total;
}
public int getPageCount() {
return pageCount;
}
public void setPageCount(int pageCount) {
this.pageCount = pageCount;
}
public int getCurPage() {
return curPage;
}
public void setCurPage(int curPage) {
this.curPage = curPage;
}
public boolean isOver() {
return over;
}
public void setOver(boolean over) {
this.over = over;
}
public List<DatasBean> getDatas() {
return datas;
}
public void setDatas(List<DatasBean> datas) {
this.datas = datas;
}
public static class DatasBean {
/**
* id : 1578
* title : 这些 Drawable 的小技巧,你都了解吗?
* chapterId : 168
* chapterName : Drawable
* envelopePic : null
* link : https://juejin.im/post/5a28b2d0f265da431c703153
* author : 承香墨影
* origin : null
* publishTime : 1512660849000
* zan : null
* desc : null
* visible : 1
* niceDate : 2017-12-07
* courseId : 13
* collect : false
*/
private int id;
private String title;
private int chapterId;
private String chapterName;
private String envelopePic;
private String link;
private String author;
private String origin;
private long publishTime;
private String zan;
private String desc;
private int visible;
private String niceDate;
private int courseId;
private boolean collect;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public int getChapterId() {
return chapterId;
}
public void setChapterId(int chapterId) {
this.chapterId = chapterId;
}
public String getChapterName() {
return chapterName;
}
public void setChapterName(String chapterName) {
this.chapterName = chapterName;
}
public String getEnvelopePic() {
return envelopePic;
}
public void setEnvelopePic(String envelopePic) {
this.envelopePic = envelopePic;
}
public String getLink() {
return link;
}
public void setLink(String link) {
this.link = link;
}
public String getAuthor() {
return author;
}
public void setAuthor(String author) {
this.author = author;
}
public String getOrigin() {
return origin;
}
public void setOrigin(String origin) {
this.origin = origin;
}
public long getPublishTime() {
return publishTime;
}
public void setPublishTime(long publishTime) {
this.publishTime = publishTime;
}
public String getZan() {
return zan;
}
public void setZan(String zan) {
this.zan = zan;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public int getVisible() {
return visible;
}
public void setVisible(int visible) {
this.visible = visible;
}
public String getNiceDate() {
return niceDate;
}
public void setNiceDate(String niceDate) {
this.niceDate = niceDate;
}
public int getCourseId() {
return courseId;
}
public void setCourseId(int courseId) {
this.courseId = courseId;
}
public boolean isCollect() {
return collect;
}
public void setCollect(boolean collect) {
this.collect = collect;
}
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/Banner.java
================================================
package com.lw.wanandroid.bean;
/**
* Created by lw on 2018/1/19.
*/
public class Banner {
private int id;
private String url;
private String imagePath;
private String title;
private String desc;
private int isVisible;
private int order;
private int type;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public String getImagePath() {
return imagePath;
}
public void setImagePath(String imagePath) {
this.imagePath = imagePath;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public int getIsVisible() {
return isVisible;
}
public void setIsVisible(int isVisible) {
this.isVisible = isVisible;
}
public int getOrder() {
return order;
}
public void setOrder(int order) {
this.order = order;
}
public int getType() {
return type;
}
public void setType(int type) {
this.type = type;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/DataResponse.java
================================================
package com.lw.wanandroid.bean;
/**
* Created by lw on 2018/1/19.
*/
public class DataResponse<T> {
private int errorCode;
private Object errorMsg;
private T data;
public int getErrorCode() {
return errorCode;
}
public void setErrorCode(int errorCode) {
this.errorCode = errorCode;
}
public Object getErrorMsg() {
return errorMsg;
}
public void setErrorMsg(Object errorMsg) {
this.errorMsg = errorMsg;
}
public T getData() {
return data;
}
public void setData(T data) {
this.data = data;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/Friend.java
================================================
package com.lw.wanandroid.bean;
/**
* Created by lw on 2018/1/23.
*/
public class Friend {
private int id;
private String name;
private String link;
private int visible;
private int order;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getLink() {
return link;
}
public void setLink(String link) {
this.link = link;
}
public int getVisible() {
return visible;
}
public void setVisible(int visible) {
this.visible = visible;
}
public int getOrder() {
return order;
}
public void setOrder(int order) {
this.order = order;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/HotKey.java
================================================
package com.lw.wanandroid.bean;
/**
* Created by lw on 2018/1/23.
*/
public class HotKey {
private int id;
private String name;
private String link;
private int visible;
private int order;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getLink() {
return link;
}
public void setLink(String link) {
this.link = link;
}
public int getVisible() {
return visible;
}
public void setVisible(int visible) {
this.visible = visible;
}
public int getOrder() {
return order;
}
public void setOrder(int order) {
this.order = order;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/KnowledgeSystem.java
================================================
package com.lw.wanandroid.bean;
import android.content.Context;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.facade.service.SerializationService;
import com.lw.wanandroid.utils.GsonUtils;
import java.lang.reflect.Type;
import java.util.List;
/**
* Created by lw on 2018/1/22.
*/
@Route(path = "/service/json")
public class KnowledgeSystem implements SerializationService {
private int id;
private String name;
private int courseId;
private int parentChapterId;
private int order;
private int visible;
private List<ChildrenBean> children;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getCourseId() {
return courseId;
}
public void setCourseId(int courseId) {
this.courseId = courseId;
}
public int getParentChapterId() {
return parentChapterId;
}
public void setParentChapterId(int parentChapterId) {
this.parentChapterId = parentChapterId;
}
public int getOrder() {
return order;
}
public void setOrder(int order) {
this.order = order;
}
public int getVisible() {
return visible;
}
public void setVisible(int visible) {
this.visible = visible;
}
public List<ChildrenBean> getChildren() {
return children;
}
public void setChildren(List<ChildrenBean> children) {
this.children = children;
}
@Override
public <T> T json2Object(String input, Class<T> clazz) {
return GsonUtils.convertObj(input, clazz);
}
@Override
public String object2Json(Object instance) {
return GsonUtils.toJson(instance);
}
@Override
public <T> T parseObject(String input, Type clazz) {
return GsonUtils.convertObj(input, clazz);
}
@Override
public void init(Context context) {
}
public static class ChildrenBean implements SerializationService {
/**
* id : 60
* name : Android Studio相关
* courseId : 13
* parentChapterId : 150
* order : 1000
* visible : 1
* children : []
*/
private int id;
private String name;
private int courseId;
private int parentChapterId;
private int order;
private int visible;
private List<ChildrenBean> children;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getCourseId() {
return courseId;
}
public void setCourseId(int courseId) {
this.courseId = courseId;
}
public int getParentChapterId() {
return parentChapterId;
}
public void setParentChapterId(int parentChapterId) {
this.parentChapterId = parentChapterId;
}
public int getOrder() {
return order;
}
public void setOrder(int order) {
this.order = order;
}
public int getVisible() {
return visible;
}
public void setVisible(int visible) {
this.visible = visible;
}
public List<?> getChildren() {
return children;
}
public void setChildren(List<ChildrenBean> children) {
this.children = children;
}
@Override
public <T> T json2Object(String input, Class<T> clazz) {
return GsonUtils.convertObj(input, clazz);
}
@Override
public String object2Json(Object instance) {
return GsonUtils.toJson(instance);
}
@Override
public <T> T parseObject(String input, Type clazz) {
return GsonUtils.convertObj(input, clazz);
}
@Override
public void init(Context context) {
}
public ChildrenBean(int id, String name) {
this.id = id;
this.name = name;
}
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/bean/User.java
================================================
package com.lw.wanandroid.bean;
import java.util.List;
/**
* Created by lw on 2018/1/24.
*/
public class User {
private int id;
private String username;
private String password;
private String icon;
private int type;
private List<Integer> collectIds;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getIcon() {
return icon;
}
public void setIcon(String icon) {
this.icon = icon;
}
public int getType() {
return type;
}
public void setType(int type) {
this.type = type;
}
public List<Integer> getCollectIds() {
return collectIds;
}
public void setCollectIds(List<Integer> collectIds) {
this.collectIds = collectIds;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/constant/Constant.java
================================================
package com.lw.wanandroid.constant;
/**
* Created by lw on 2018/1/19.
*/
public class Constant {
public static final String REQUEST_BASE_URL = "http://wanandroid.com/";
/**
* 每页数量
*/
public static final int PAGE_SIZE = 20;
/**
* url key
*/
public static final String CONTENT_URL_KEY = "url";
/**
* title key
*/
public static final String CONTENT_TITLE_KEY = "title";
/**
* id key
*/
public static final String CONTENT_ID_KEY = "id";
/**
* cid key
*/
public static final String CONTENT_CID_KEY = "cid";
public static final String CONTENT_AUTHOR_KEY = "author";
/**
* childrenData key
*/
public static final String CONTENT_CHILDREN_DATA_KEY = "childrenData";
/**
* hotFriend key
*/
public static final String CONTENT_HOT_FRIEND_KEY = "hotFriend";
/**
* hot key
*/
public static final String CONTENT_HOT_KEY = "hotKey";
/**
* hot key
*/
public static final String CONTENT_HOT_NAME_KEY = "hotNameKey";
public static final String SAVE_USER_LOGIN_KEY = "user/login";
public static final String SAVE_USER_REGISTER_KEY = "user/register";
public static final String SET_COOKIE_KEY = "set-cookie";
public static final String SHARED_NAME = "_preferences";
public static final String USERNAME_KEY = "username";
public static final String PASSWORD_KEY = "password";
public static final String LOGIN_KEY = "login";
public static final String USER_KEY = "user";
public static final String BANNER_KEY = "banner";
public static final String ARTICLE_KEY = "article";
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/constant/LoadType.java
================================================
package com.lw.wanandroid.constant;
import android.support.annotation.IntDef;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
/**
* Created by lw on 2017-04-06.
*/
public class LoadType {
public static final int TYPE_REFRESH_SUCCESS = 1;
public static final int TYPE_REFRESH_ERROR = 2;
public static final int TYPE_LOAD_MORE_SUCCESS = 3;
public static final int TYPE_LOAD_MORE_ERROR = 4;
@IntDef({TYPE_REFRESH_SUCCESS, TYPE_REFRESH_ERROR, TYPE_LOAD_MORE_SUCCESS, TYPE_LOAD_MORE_ERROR})
@Retention(RetentionPolicy.SOURCE)
public @interface checker {
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/db/AppDatabase.java
================================================
package com.lw.wanandroid.db;
import com.raizlabs.android.dbflow.annotation.Database;
/**
* Created by lw on 2018/2/2.
*/
@Database(name = AppDatabase.NAME, version = AppDatabase.VERSION)
public class AppDatabase {
public static final String NAME = "WanAndroid-db";
public static final int VERSION = 1;
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/db/HistoryModel.java
================================================
package com.lw.wanandroid.db;
import com.raizlabs.android.dbflow.annotation.Column;
import com.raizlabs.android.dbflow.annotation.PrimaryKey;
import com.raizlabs.android.dbflow.annotation.Table;
import com.raizlabs.android.dbflow.structure.BaseModel;
import java.util.Date;
/**
* Created by lw on 2018/2/2.
*/
@Table(database = AppDatabase.class)
public class HistoryModel extends BaseModel {
@PrimaryKey(autoincrement = true)
private long id;
@Column
private String name;
@Column
private Date date;
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Date getDate() {
return date;
}
public void setDate(Date date) {
this.date = date;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/component/ActivityComponent.java
================================================
package com.lw.wanandroid.di.component;
import android.app.Activity;
import android.content.Context;
import com.lw.wanandroid.di.module.ActivityModule;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerActivity;
import com.lw.wanandroid.ui.article.ArticleContentActivity;
import com.lw.wanandroid.ui.hotsearch.SearchActivity;
import com.lw.wanandroid.ui.my.LoginActivity;
import com.lw.wanandroid.ui.my.MyBookmarkActivity;
import com.lw.wanandroid.ui.my.MyCollectionActivity;
import dagger.Component;
/**
* Created by lw on 2017/1/19.
*/
@PerActivity
@Component(dependencies = ApplicationComponent.class, modules = ActivityModule.class)
public interface ActivityComponent {
@ContextLife("Activity")
Context getActivityContext();
@ContextLife("Application")
Context getApplicationContext();
Activity getActivity();
void inject(SearchActivity activity);
void inject(LoginActivity activity);
void inject(ArticleContentActivity activity);
void inject(MyCollectionActivity activity);
void inject(MyBookmarkActivity activity);
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/component/ApplicationComponent.java
================================================
package com.lw.wanandroid.di.component;
import android.content.Context;
import com.lw.wanandroid.di.module.ApplicationModule;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerApp;
import dagger.Component;
/**
* Created by lw on 2017/1/19.
*/
@PerApp
@Component(modules = ApplicationModule.class)
public interface ApplicationComponent {
@ContextLife("Application")
Context getApplication();
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/component/FragmentComponent.java
================================================
package com.lw.wanandroid.di.component;
import android.app.Activity;
import android.content.Context;
import com.lw.wanandroid.di.module.FragmentModule;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerFragment;
import com.lw.wanandroid.ui.article.ArticleListFragment;
import com.lw.wanandroid.ui.home.HomeFragment;
import com.lw.wanandroid.ui.hotsearch.HotFragment;
import com.lw.wanandroid.ui.knowledgesystem.KnowledgeSystemFragment;
import com.lw.wanandroid.ui.my.MyFragment;
import dagger.Component;
/**
* Created by lw on 2017/1/19.
*/
@PerFragment
@Component(dependencies = ApplicationComponent.class, modules = FragmentModule.class)
public interface FragmentComponent {
@ContextLife("Activity")
Context getActivityContext();
@ContextLife("Application")
Context getApplicationContext();
Activity getActivity();
void inject(HomeFragment fragment);
void inject(KnowledgeSystemFragment fragment);
void inject(MyFragment fragment);
void inject(ArticleListFragment fragment);
void inject(HotFragment fragment);
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/component/ServiceComponent.java
================================================
package com.lw.wanandroid.di.component;
import android.content.Context;
import com.lw.wanandroid.di.module.ServiceModule;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerService;
import dagger.Component;
/**
* Created by lw on 2017/1/19.
*/
@PerService
@Component(dependencies = ApplicationComponent.class, modules = ServiceModule.class)
public interface ServiceComponent {
@ContextLife("Service")
Context getServiceContext();
@ContextLife("Application")
Context getApplicationContext();
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/module/ActivityModule.java
================================================
package com.lw.wanandroid.di.module;
import android.app.Activity;
import android.content.Context;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerActivity;
import dagger.Module;
import dagger.Provides;
/**
* Created by lw on 2017/1/19.
*/
@Module
public class ActivityModule {
private Activity mActivity;
public ActivityModule(Activity activity) {
mActivity = activity;
}
@Provides
@PerActivity
@ContextLife("Activity")
public Context provideActivityContext() {
return mActivity;
}
@Provides
@PerActivity
public Activity provideActivity() {
return mActivity;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/module/ApplicationModule.java
================================================
package com.lw.wanandroid.di.module;
import android.content.Context;
import com.lw.wanandroid.base.App;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerApp;
import dagger.Module;
import dagger.Provides;
/**
* Created by lw on 2017/1/19.
*/
@Module
public class ApplicationModule {
private App mApplication;
public ApplicationModule(App application) {
mApplication = application;
}
@Provides
@PerApp
@ContextLife("Application")
public Context provideApplicationContext() {
return mApplication.getApplicationContext();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/module/FragmentModule.java
================================================
package com.lw.wanandroid.di.module;
import android.app.Activity;
import android.content.Context;
import android.support.v4.app.Fragment;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerFragment;
import dagger.Module;
import dagger.Provides;
/**
* Created by lw on 2017/1/19.
*/
@Module
public class FragmentModule {
private Fragment mFragment;
public FragmentModule(Fragment fragment) {
mFragment = fragment;
}
@Provides
@PerFragment
@ContextLife("Activity")
public Context provideActivityContext() {
return mFragment.getActivity();
}
@Provides
@PerFragment
public Activity provideActivity() {
return mFragment.getActivity();
}
@Provides
@PerFragment
public Fragment provideFragment() {
return mFragment;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/module/ServiceModule.java
================================================
package com.lw.wanandroid.di.module;
import android.app.Service;
import android.content.Context;
import com.lw.wanandroid.di.scope.ContextLife;
import com.lw.wanandroid.di.scope.PerService;
import dagger.Module;
import dagger.Provides;
/**
* Created by lw on 2017/1/19.
*/
@Module
public class ServiceModule {
private Service mService;
public ServiceModule(Service service) {
mService = service;
}
@Provides
@PerService
@ContextLife("Service")
public Context ProvideServiceContext() {
return mService;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/scope/ContextLife.java
================================================
package com.lw.wanandroid.di.scope;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import javax.inject.Qualifier;
/**
* Created by lw on 2017/1/19.
*/
@Qualifier
@Documented
@Retention(RetentionPolicy.RUNTIME)
public @interface ContextLife {
String value() default "Application";
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/scope/PerActivity.java
================================================
package com.lw.wanandroid.di.scope;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import javax.inject.Scope;
/**
* Created by lw on 2017/1/19.
*/
@Scope
@Documented
@Retention(RetentionPolicy.RUNTIME)
public @interface PerActivity {
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/scope/PerApp.java
================================================
package com.lw.wanandroid.di.scope;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import javax.inject.Scope;
/**
* Created by lw on 2017/1/19.
*/
@Scope
@Documented
@Retention(RetentionPolicy.RUNTIME)
public @interface PerApp {
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/scope/PerFragment.java
================================================
package com.lw.wanandroid.di.scope;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import javax.inject.Scope;
/**
* Created by lw on 2017/1/19.
*/
@Scope
@Documented
@Retention(RetentionPolicy.RUNTIME)
public @interface PerFragment {
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/di/scope/PerService.java
================================================
package com.lw.wanandroid.di.scope;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import javax.inject.Scope;
/**
* Created by lw on 2017/1/19.
*/
@Scope
@Documented
@Retention(RetentionPolicy.RUNTIME)
public @interface PerService {
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/event/LoginEvent.java
================================================
package com.lw.wanandroid.event;
/**
* Created by lw on 2018/1/25.
*/
public class LoginEvent {
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/net/ApiService.java
================================================
package com.lw.wanandroid.net;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.Banner;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.bean.Friend;
import com.lw.wanandroid.bean.HotKey;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.bean.User;
import java.util.List;
import io.reactivex.Observable;
import retrofit2.http.Field;
import retrofit2.http.FormUrlEncoded;
import retrofit2.http.GET;
import retrofit2.http.POST;
import retrofit2.http.Path;
import retrofit2.http.Query;
/**
* Created by lw on 2018/1/23.
*/
public interface ApiService {
/**
* 首页数据
* http://www.wanandroid.com/article/list/0/json
*
* @param page page
*/
@GET("/article/list/{page}/json")
Observable<DataResponse<Article>> getHomeArticles(@Path("page") int page);
/**
* 首页Banner
*
* @return BannerResponse
*/
@GET("/banner/json")
Observable<DataResponse<List<Banner>>> getHomeBanners();
/**
* 知识体系
* http://www.wanandroid.com/tree/json
*
* @return BannerResponse
*/
@GET("/tree/json")
Observable<DataResponse<List<KnowledgeSystem>>> getKnowledgeSystems();
/**
* 知识体系下的文章
* http://www.wanandroid.com/article/list/0/json?cid=168
*
* @param page page
* @param cid cid
*/
@GET("/article/list/{page}/json")
Observable<DataResponse<Article>> getKnowledgeSystemArticles(@Path("page") int page, @Query("cid") int cid);
/**
* 常用网站
* http://www.wanandroid.com/friend/json
*/
@GET("/friend/json")
Observable<DataResponse<List<Friend>>> getHotFriends();
/**
* 大家都在搜
* http://www.wanandroid.com/hotkey/json
*/
@GET("/hotkey/json")
Observable<DataResponse<List<HotKey>>> getHotKeys();
/**
* 搜索
* http://www.wanandroid.com/article/query/0/json
*
* @param page page
* @param k POST search key
*/
@POST("/article/query/{page}/json")
@FormUrlEncoded
Observable<DataResponse<Article>> getSearchArticles(@Path("page") int page, @Field("k") String k);
/**
* 登录
*
* @param username username
* @param password password
* @return Deferred<User>
*/
@POST("/user/login")
@FormUrlEncoded
Observable<DataResponse<User>> login(@Field("username") String username, @Field("password") String password);
/**
* 注册
*
* @param username username
* @param password password
* @param repassword repassword
* @return Deferred<User>
*/
@POST("/user/register")
@FormUrlEncoded
Observable<DataResponse<User>> register(@Field("username") String username, @Field("password") String password, @Field("repassword") String repassword);
/**
* 收藏文章
*
* @param id id
* @return Deferred<DataResponse>
*/
@POST("/lg/collect/{id}/json")
Observable<DataResponse> addCollectArticle(@Path("id") int id);
/**
* 收藏站外文章
*
* @param title title
* @param author author
* @param link link
* @return Deferred<DataResponse>
*/
@POST("/lg/collect/add/json")
@FormUrlEncoded
Observable<DataResponse> addCollectOutsideArticle(@Field("title") String title, @Field("author") String author, @Field("link") String link);
/**
* 删除收藏文章
*
* @param id id
* @param originId -1
* @return Deferred<DataResponse>
*/
@POST("/lg/uncollect/{id}/json")
@FormUrlEncoded
Observable<DataResponse> removeCollectArticle(@Path("id") int id, @Field("originId") int originId);
/**
* 获取自己收藏的文章列表
*
* @param page page
* @return Deferred<Article>
*/
@GET("/lg/collect/list/{page}/json")
Observable<DataResponse<Article>> getCollectArticles(@Path("page") int page);
/**
* 我的书签
* http://www.wanandroid.com/lg/collect/usertools/json
*/
@GET("/lg/collect/usertools/json")
Observable<DataResponse<List<Friend>>> getBookmarks();
/**
* 编辑书签
* http://www.wanandroid.com/lg/collect/updatetool/json
*/
@POST("/lg/collect/usertools/json")
@FormUrlEncoded
Observable<DataResponse> editBookmark(@Field("id") int id, @Field("name") String name, @Field("link") String link);
/**
* 删除书签
* http://www.wanandroid.com/lg/collect/deletetool/json
*/
@POST("/lg/collect/usertools/json")
@FormUrlEncoded
Observable<DataResponse> delBookmark(@Field("id") int id);
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/net/CookiesManager.java
================================================
package com.lw.wanandroid.net;
import java.util.List;
import okhttp3.Cookie;
import okhttp3.CookieJar;
import okhttp3.HttpUrl;
/**
* Created by lw on 2018/1/25.
*/
public class CookiesManager implements CookieJar {
private static final PersistentCookieStore cookieStore = new PersistentCookieStore();
@Override
public void saveFromResponse(HttpUrl url, List<Cookie> cookies) {
if (cookies != null && cookies.size() > 0) {
for (Cookie item : cookies) {
cookieStore.add(url, item);
}
}
}
@Override
public List<Cookie> loadForRequest(HttpUrl url) {
List<Cookie> cookies = cookieStore.get(url);
return cookies;
}
/**
* 清除所有cookie
*/
public static void clearAllCookies() {
cookieStore.removeAll();
}
/**
* 清除指定cookie
*
* @param url
* @param cookie
* @return
*/
public static boolean clearCookies(HttpUrl url, Cookie cookie) {
return cookieStore.remove(url, cookie);
}
/**
* 获取cookies
*
* @return
*/
public static List<Cookie> getCookies() {
return cookieStore.getCookies();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/net/OkHttpCookies.java
================================================
package com.lw.wanandroid.net;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import okhttp3.Cookie;
/**
* Created by lw on 2018/1/25.
*/
public class OkHttpCookies implements Serializable {
private transient final Cookie cookies;
private transient Cookie clientCookies;
public OkHttpCookies(Cookie cookies) {
this.cookies = cookies;
}
public Cookie getCookies() {
Cookie bestCookies = cookies;
if (clientCookies != null) {
bestCookies = clientCookies;
}
return bestCookies;
}
private void writeObject(ObjectOutputStream out) throws IOException {
out.writeObject(cookies.name());
out.writeObject(cookies.value());
out.writeLong(cookies.expiresAt());
out.writeObject(cookies.domain());
out.writeObject(cookies.path());
out.writeBoolean(cookies.secure());
out.writeBoolean(cookies.httpOnly());
out.writeBoolean(cookies.hostOnly());
out.writeBoolean(cookies.persistent());
}
private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException {
String name = (String) in.readObject();
String value = (String) in.readObject();
long expiresAt = in.readLong();
String domain = (String) in.readObject();
String path = (String) in.readObject();
boolean secure = in.readBoolean();
boolean httpOnly = in.readBoolean();
boolean hostOnly = in.readBoolean();
boolean persistent = in.readBoolean();
Cookie.Builder builder = new Cookie.Builder();
builder = builder.name(name);
builder = builder.value(value);
builder = builder.expiresAt(expiresAt);
builder = hostOnly ? builder.hostOnlyDomain(domain) : builder.domain(domain);
builder = builder.path(path);
builder = secure ? builder.secure() : builder;
builder = httpOnly ? builder.httpOnly() : builder;
clientCookies = builder.build();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/net/PersistentCookieStore.java
================================================
package com.lw.wanandroid.net;
import android.content.SharedPreferences;
import android.text.TextUtils;
import android.util.Log;
import com.lw.wanandroid.base.App;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import okhttp3.Cookie;
import okhttp3.HttpUrl;
/**
* Created by lw on 2018/1/25.
*/
public class PersistentCookieStore {
private static final String LOG_TAG = "PersistentCookieStore";
private static final String COOKIE_PREFS = "Cookies_Prefs";
private final Map<String, ConcurrentHashMap<String, Cookie>> cookies;
private final SharedPreferences cookiePrefs;
public PersistentCookieStore() {
cookiePrefs = App.getAppContext().getSharedPreferences(COOKIE_PREFS, 0);
cookies = new HashMap<>();
//将持久化的cookies缓存到内存中 即map cookies
Map<String, ?> prefsMap = cookiePrefs.getAll();
for (Map.Entry<String, ?> entry : prefsMap.entrySet()) {
String[] cookieNames = TextUtils.split((String) entry.getValue(), ",");
for (String name : cookieNames) {
String encodedCookie = cookiePrefs.getString(name, null);
if (encodedCookie != null) {
Cookie decodedCookie = decodeCookie(encodedCookie);
if (decodedCookie != null) {
if (!cookies.containsKey(entry.getKey())) {
cookies.put(entry.getKey(), new ConcurrentHashMap<String, Cookie>());
}
cookies.get(entry.getKey()).put(name, decodedCookie);
}
}
}
}
}
protected String getCookieToken(Cookie cookie) {
return cookie.name() + "@" + cookie.domain();
}
public void add(HttpUrl url, Cookie cookie) {
String name = getCookieToken(cookie);
//将cookies缓存到内存中 如果缓存过期 就重置此cookie
if (!cookie.persistent()) {
if (!cookies.containsKey(url.host())) {
cookies.put(url.host(), new ConcurrentHashMap<String, Cookie>());
}
cookies.get(url.host()).put(name, cookie);
} else {
if (cookies.containsKey(url.host())) {
cookies.get(url.host()).remove(name);
}
}
//讲cookies持久化到本地
SharedPreferences.Editor prefsWriter = cookiePrefs.edit();
prefsWriter.putString(url.host(), TextUtils.join(",", cookies.get(url.host()).keySet()));
prefsWriter.putString(name, encodeCookie(new OkHttpCookies(cookie)));
prefsWriter.apply();
}
public List<Cookie> get(HttpUrl url) {
ArrayList<Cookie> ret = new ArrayList<>();
if (cookies.containsKey(url.host()))
ret.addAll(cookies.get(url.host()).values());
return ret;
}
public boolean removeAll() {
SharedPreferences.Editor prefsWriter = cookiePrefs.edit();
prefsWriter.clear();
prefsWriter.apply();
cookies.clear();
return true;
}
public boolean remove(HttpUrl url, Cookie cookie) {
String name = getCookieToken(cookie);
if (cookies.containsKey(url.host()) && cookies.get(url.host()).containsKey(name)) {
cookies.get(url.host()).remove(name);
SharedPreferences.Editor prefsWriter = cookiePrefs.edit();
if (cookiePrefs.contains(name)) {
prefsWriter.remove(name);
}
prefsWriter.putString(url.host(), TextUtils.join(",", cookies.get(url.host()).keySet()));
prefsWriter.apply();
return true;
} else {
return false;
}
}
public List<Cookie> getCookies() {
ArrayList<Cookie> ret = new ArrayList<>();
for (String key : cookies.keySet())
ret.addAll(cookies.get(key).values());
return ret;
}
/**
* cookies 序列化成 string
*
* @param cookie 要序列化的cookie
* @return 序列化之后的string
*/
protected String encodeCookie(OkHttpCookies cookie) {
if (cookie == null)
return null;
ByteArrayOutputStream os = new ByteArrayOutputStream();
try {
ObjectOutputStream outputStream = new ObjectOutputStream(os);
outputStream.writeObject(cookie);
} catch (IOException e) {
Log.d(LOG_TAG, "IOException in encodeCookie", e);
return null;
}
return byteArrayToHexString(os.toByteArray());
}
/**
* 将字符串反序列化成cookies
*
* @param cookieString cookies string
* @return cookie object
*/
protected Cookie decodeCookie(String cookieString) {
byte[] bytes = hexStringToByteArray(cookieString);
ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(bytes);
Cookie cookie = null;
try {
ObjectInputStream objectInputStream = new ObjectInputStream(byteArrayInputStream);
cookie = ((OkHttpCookies) objectInputStream.readObject()).getCookies();
} catch (IOException e) {
Log.d(LOG_TAG, "IOException in decodeCookie", e);
} catch (ClassNotFoundException e) {
Log.d(LOG_TAG, "ClassNotFoundException in decodeCookie", e);
}
return cookie;
}
/**
* 二进制数组转十六进制字符串
*
* @param bytes byte array to be converted
* @return string containing hex values
*/
protected String byteArrayToHexString(byte[] bytes) {
StringBuilder sb = new StringBuilder(bytes.length * 2);
for (byte element : bytes) {
int v = element & 0xff;
if (v < 16) {
sb.append('0');
}
sb.append(Integer.toHexString(v));
}
return sb.toString().toUpperCase(Locale.US);
}
/**
* 十六进制字符串转二进制数组
*
* @param hexString string of hex-encoded values
* @return decoded byte array
*/
protected byte[] hexStringToByteArray(String hexString) {
int len = hexString.length();
byte[] data = new byte[len / 2];
for (int i = 0; i < len; i += 2) {
data[i / 2] = (byte) ((Character.digit(hexString.charAt(i), 16) << 4) + Character.digit(hexString.charAt(i + 1), 16));
}
return data;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/net/RetrofitManager.java
================================================
package com.lw.wanandroid.net;
import com.blankj.utilcode.util.NetworkUtils;
import com.lw.wanandroid.base.App;
import com.lw.wanandroid.constant.Constant;
import java.io.File;
import java.io.IOException;
import java.util.concurrent.TimeUnit;
import okhttp3.Cache;
import okhttp3.CacheControl;
import okhttp3.Interceptor;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import retrofit2.Retrofit;
import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory;
import retrofit2.converter.gson.GsonConverterFactory;
/**
* Created by lw on 2017-04-01.
*/
public class RetrofitManager {
private static long CONNECT_TIMEOUT = 60L;
private static long READ_TIMEOUT = 10L;
private static long WRITE_TIMEOUT = 10L;
//设缓存有效期为1天
private static final long CACHE_STALE_SEC = 60 * 60 * 24 * 1;
//查询缓存的Cache-Control设置,为if-only-cache时只查询缓存而不会请求服务器,max-stale可以配合设置缓存失效时间
public static final String CACHE_CONTROL_CACHE = "only-if-cached, max-stale=" + CACHE_STALE_SEC;
//查询网络的Cache-Control设置
//(假如请求了服务器并在a时刻返回响应结果,则在max-age规定的秒数内,浏览器将不会发送对应的请求到服务器,数据由缓存直接返回)
public static final String CACHE_CONTROL_NETWORK = "Cache-Control: public, max-age=10";
// 避免出现 HTTP 403 Forbidden,参考:http://stackoverflow.com/questions/13670692/403-forbidden-with-java-but-not-web-browser
private static final String AVOID_HTTP403_FORBIDDEN = "User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.95 Safari/537.11";
private static volatile OkHttpClient mOkHttpClient;
/**
* 云端响应头拦截器,用来配置缓存策略
* Dangerous interceptor that rewrites the server's cache-control header.
*/
private static final Interceptor mRewriteCacheControlInterceptor = new Interceptor() {
@Override
public Response intercept(Chain chain) throws IOException {
Request request = chain.request();
if (!NetworkUtils.isConnected()) {
request = request.newBuilder()
.cacheControl(CacheControl.FORCE_CACHE)
.build();
}
Response originalResponse = chain.proceed(request);
if (NetworkUtils.isConnected()) {
//有网的时候读接口上的@Headers里的配置,可以在这里进行统一的设置
String cacheControl = request.cacheControl().toString();
return originalResponse.newBuilder()
.header("Cache-Control", cacheControl)
.removeHeader("Pragma")
.build();
} else {
return originalResponse.newBuilder()
.header("Cache-Control", "public, only-if-cached, max-stale=" + CACHE_CONTROL_CACHE)
.removeHeader("Pragma")
.build();
}
}
};
/**
* 日志拦截器
*/
private static final Interceptor mLoggingInterceptor = new Interceptor() {
@Override
public Response intercept(Chain chain) throws IOException {
Request request = chain.request();
Response response = chain.proceed(request);
return response;
}
};
/**
* 获取OkHttpClient实例
*
* @return
*/
private static OkHttpClient getOkHttpClient() {
if (mOkHttpClient == null) {
synchronized (RetrofitManager.class) {
Cache cache = new Cache(new File(App.getAppContext().getCacheDir(), "HttpCache"), 1024 * 1024 * 100);
if (mOkHttpClient == null) {
mOkHttpClient = new OkHttpClient.Builder().cache(cache)
.connectTimeout(CONNECT_TIMEOUT, TimeUnit.SECONDS)
.readTimeout(READ_TIMEOUT, TimeUnit.SECONDS)
.writeTimeout(WRITE_TIMEOUT, TimeUnit.SECONDS)
.addInterceptor(mRewriteCacheControlInterceptor)
.addInterceptor(mLoggingInterceptor)
.cookieJar(new CookiesManager())
.build();
}
}
}
return mOkHttpClient;
}
/**
* 获取Service
*
* @param clazz
* @param <T>
* @return
*/
public static <T> T create(Class<T> clazz) {
Retrofit retrofit = new Retrofit.Builder().baseUrl(Constant.REQUEST_BASE_URL)
.client(getOkHttpClient())
.addConverterFactory(GsonConverterFactory.create())
.addCallAdapterFactory(RxJava2CallAdapterFactory.create()).build();
return retrofit.create(clazz);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleAdapter.java
================================================
package com.lw.wanandroid.ui.article;
import android.text.Html;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.lw.wanandroid.R;
import com.lw.wanandroid.bean.Article;
import javax.inject.Inject;
/**
* Created by lw on 2018/1/19.
*/
public class ArticleAdapter extends BaseQuickAdapter<Article.DatasBean, BaseViewHolder> {
private boolean mChapterNameVisible = true;
private boolean mIsMyColection = false;
@Inject
public ArticleAdapter() {
super(R.layout.item_article, null);
}
@Override
protected void convert(BaseViewHolder helper, Article.DatasBean item) {
helper.setText(R.id.tvAuthor, item.getAuthor());
helper.setText(R.id.tvNiceDate, item.getNiceDate());
helper.setText(R.id.tvTitle, Html.fromHtml(item.getTitle()));
helper.setText(R.id.tvChapterName, item.getChapterName());
if (mIsMyColection) item.setCollect(mIsMyColection);
helper.setImageResource(R.id.ivCollect, item.isCollect()
? R.drawable.ic_action_like : R.drawable.ic_action_no_like);
helper.addOnClickListener(R.id.tvChapterName);
helper.addOnClickListener(R.id.ivCollect);
helper.setVisible(R.id.tvChapterName, mChapterNameVisible);
}
public void setChapterNameVisible(boolean chapterNameVisible) {
this.mChapterNameVisible = chapterNameVisible;
}
public void isMyColection(boolean isMyColection) {
this.mIsMyColection = isMyColection;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentActivity.java
================================================
package com.lw.wanandroid.ui.article;
import android.content.Intent;
import android.net.Uri;
import android.view.Menu;
import android.view.MenuItem;
import android.webkit.WebView;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import com.alibaba.android.arouter.facade.annotation.Autowired;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.launcher.ARouter;
import com.just.agentweb.AgentWeb;
import com.just.agentweb.ChromeClientCallbackManager;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.constant.Constant;
import butterknife.BindView;
/**
* Created by lw on 2018/1/22.
*/
@Route(path = "/article/ArticleContentActivity")
public class ArticleContentActivity extends BaseActivity<ArticleContentPresenter> implements ArticleContentContract.View {
@Autowired
public int id;
@Autowired
public String url;
@Autowired
public String title;
@Autowired
public String author;
@BindView(R.id.webContent)
FrameLayout mWebContent;
@Override
protected int getLayoutId() {
return R.layout.activity_article_content;
}
@Override
protected void initInjector() {
mActivityComponent.inject(this);
}
@Override
protected void initView() {
AgentWeb.with(this)//传入Activity or Fragment
.setAgentWebParent(mWebContent, new LinearLayout.LayoutParams(-1, -1))//传入AgentWeb 的父控件 ,如果父控件为 RelativeLayout , 那么第二参数需要传入 RelativeLayout.LayoutParams ,第一个参数和第二个参数应该对应。
.useDefaultIndicator()// 使用默认进度条
.defaultProgressBarColor() // 使用默认进度条颜色
.setReceivedTitleCallback(mReceivedTitleCallback) //设置 Web 页面的 title 回调
.createAgentWeb()//
.ready()
.go(url);
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_content, menu);
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.getItemId() == R.id.menuShare) {
Intent intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_TEXT, getString(R.string.share_article_url, getString(R.string.app_name), title, url));
intent.setType("text/plain");
startActivity(intent);
} else if (item.getItemId() == R.id.menuLike) {
if (id == 0) mPresenter.collectOutsideArticle(title, author, url);
else mPresenter.collectArticle(id);
} else if (item.getItemId() == R.id.menuBrowser) {
Intent intent = new Intent("android.intent.action.VIEW");
intent.setData(Uri.parse(url));
startActivity(intent);
}
return super.onOptionsItemSelected(item);
}
public static void start(int id, String url, String title, String author) {
ARouter.getInstance().build("/article/ArticleContentActivity")
.withInt(Constant.CONTENT_ID_KEY, id)
.withString(Constant.CONTENT_URL_KEY, url)
.withString(Constant.CONTENT_TITLE_KEY, title)
.withString(Constant.CONTENT_AUTHOR_KEY, author)
.navigation();
}
private ChromeClientCallbackManager.ReceivedTitleCallback mReceivedTitleCallback = new ChromeClientCallbackManager.ReceivedTitleCallback() {
@Override
public void onReceivedTitle(WebView view, String title) {
setToolbarTitle(title);
}
};
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentContract.java
================================================
package com.lw.wanandroid.ui.article;
import com.lw.wanandroid.base.BaseContract;
import retrofit2.http.Field;
/**
* Created by lw on 2018/1/25.
*/
public interface ArticleContentContract {
interface View extends BaseContract.BaseView {
}
interface Presenter extends BaseContract.BasePresenter<ArticleContentContract.View> {
void collectArticle(int id);
void collectOutsideArticle(String title, String author, String link);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentPresenter.java
================================================
package com.lw.wanandroid.ui.article;
import com.blankj.utilcode.util.SPUtils;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.App;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.ui.my.LoginActivity;
import com.lw.wanandroid.utils.RxSchedulers;
import javax.inject.Inject;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/25.
*/
public class ArticleContentPresenter extends BasePresenter<ArticleContentContract.View> implements ArticleContentContract.Presenter {
@Inject
public ArticleContentPresenter() {
}
@Override
public void collectArticle(int id) {
if (SPUtils.getInstance(Constant.SHARED_NAME).getBoolean(Constant.LOGIN_KEY)) {
RetrofitManager.create(ApiService.class)
.addCollectArticle(id)
.compose(RxSchedulers.<DataResponse>applySchedulers())
.compose(mView.<DataResponse>bindToLife())
.subscribe(new Consumer<DataResponse>() {
@Override
public void accept(DataResponse response) throws Exception {
if (response.getErrorCode() == 0) {
mView.showSuccess(App.getAppContext().getString(R.string.collection_success));
} else {
mView.showFaild(App.getAppContext().getString(R.string.collection_failed, response.getErrorMsg()));
}
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
} else {
LoginActivity.start();
}
}
@Override
public void collectOutsideArticle(String title, String author, String link) {
if (SPUtils.getInstance(Constant.SHARED_NAME).getBoolean(Constant.LOGIN_KEY)) {
RetrofitManager.create(ApiService.class)
.addCollectOutsideArticle(title, author, link)
.compose(RxSchedulers.<DataResponse>applySchedulers())
.compose(mView.<DataResponse>bindToLife())
.subscribe(new Consumer<DataResponse>() {
@Override
public void accept(DataResponse response) throws Exception {
if (response.getErrorCode() == 0) {
mView.showSuccess(App.getAppContext().getString(R.string.collection_success));
} else {
mView.showFaild(App.getAppContext().getString(R.string.collection_failed, response.getErrorMsg()));
}
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
} else {
LoginActivity.start();
}
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleListContract.java
================================================
package com.lw.wanandroid.ui.article;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.constant.LoadType;
/**
* Created by lw on 2018/1/23.
*/
public interface ArticleListContract {
interface View extends BaseContract.BaseView {
void setKnowledgeSystemArticles(Article article, @LoadType.checker int loadType);
void collectArticleSuccess(int position, Article.DatasBean bean);
}
interface Presenter extends BaseContract.BasePresenter<ArticleListContract.View> {
void loadKnowledgeSystemArticles(int cid);
void refresh();
void loadMore();
void collectArticle(int position, Article.DatasBean bean);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleListFragment.java
================================================
package com.lw.wanandroid.ui.article;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.View;
import com.alibaba.android.arouter.facade.annotation.Autowired;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseFragment;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.event.LoginEvent;
import com.lw.wanandroid.utils.RxBus;
import javax.inject.Inject;
import butterknife.BindView;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/22.
*/
@Route(path = "/article/ArticleListFragment")
public class ArticleListFragment extends BaseFragment<ArticleListPresenter> implements ArticleListContract.View, ArticleAdapter.OnItemClickListener, ArticleAdapter.OnItemChildClickListener,
SwipeRefreshLayout.OnRefreshListener, ArticleAdapter.RequestLoadMoreListener {
@BindView(R.id.rvArticleList)
RecyclerView mRvArticleList;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
@Autowired
public int cid;
@Inject
ArticleAdapter mArticleAdapter;
@Override
protected int getLayoutId() {
return R.layout.fragment_article_list;
}
@Override
protected void initInjector() {
mFragmentComponent.inject(this);
}
@Override
protected void initView(View view) {
/**隐藏文章类型*/
mArticleAdapter.setChapterNameVisible(false);
/**设置RecyclerView*/
mRvArticleList.setLayoutManager(new LinearLayoutManager(getContext()));
mRvArticleList.setAdapter(mArticleAdapter);
/**设置事件监听*/
mArticleAdapter.setOnItemClickListener(this);
mArticleAdapter.setOnItemChildClickListener(this);
mSwipeRefreshLayout.setOnRefreshListener(this);
mArticleAdapter.setOnLoadMoreListener(this);
/**请求数据*/
mPresenter.loadKnowledgeSystemArticles(cid);
/**登陆成功刷新*/
RxBus.getInstance().toFlowable(LoginEvent.class)
.subscribe(new Consumer<LoginEvent>() {
@Override
public void accept(LoginEvent event) throws Exception {
mPresenter.refresh();
}
});
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
@Override
public void onItemChildClick(BaseQuickAdapter adapter, View view, int position) {
if (view.getId() == R.id.ivCollect) {
mPresenter.collectArticle(position, mArticleAdapter.getItem(position));
}
}
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
ArticleContentActivity.start(mArticleAdapter.getItem(position).getId(),
mArticleAdapter.getItem(position).getLink(), mArticleAdapter.getItem(position).getTitle(),
mArticleAdapter.getItem(position).getAuthor());
}
@Override
public void onLoadMoreRequested() {
mPresenter.loadMore();
}
@Override
public void setKnowledgeSystemArticles(Article article, int loadType) {
setLoadDataResult(mArticleAdapter, mSwipeRefreshLayout, article.getDatas(), loadType);
}
@Override
public void collectArticleSuccess(int position, Article.DatasBean bean) {
mArticleAdapter.setData(position, bean);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleListPresenter.java
================================================
package com.lw.wanandroid.ui.article;
import com.blankj.utilcode.util.SPUtils;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.App;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.RxSchedulers;
import com.lw.wanandroid.ui.my.LoginActivity;
import javax.inject.Inject;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/23.
*/
public class ArticleListPresenter extends BasePresenter<ArticleListContract.View> implements ArticleListContract.Presenter {
private boolean mIsRefresh;
private int mPage, mCid;
@Inject
public ArticleListPresenter() {
this.mIsRefresh = true;
}
@Override
public void loadKnowledgeSystemArticles(int cid) {
this.mCid = cid;
RetrofitManager.create(ApiService.class).getKnowledgeSystemArticles(mPage, mCid)
.compose(RxSchedulers.<DataResponse<Article>>applySchedulers())
.compose(mView.<DataResponse<Article>>bindToLife())
.subscribe(new Consumer<DataResponse<Article>>() {
@Override
public void accept(DataResponse<Article> dataResponse) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_SUCCESS : LoadType.TYPE_LOAD_MORE_SUCCESS;
mView.setKnowledgeSystemArticles(dataResponse.getData(), loadType);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_ERROR : LoadType.TYPE_LOAD_MORE_ERROR;
mView.setKnowledgeSystemArticles(new Article(), loadType);
}
});
}
@Override
public void refresh() {
mPage = 0;
mIsRefresh = true;
loadKnowledgeSystemArticles(mCid);
}
@Override
public void loadMore() {
mPage++;
mIsRefresh = false;
loadKnowledgeSystemArticles(mCid);
}
@Override
public void collectArticle(final int position, final Article.DatasBean bean) {
if (SPUtils.getInstance(Constant.SHARED_NAME).getBoolean(Constant.LOGIN_KEY)) {
if (bean.isCollect()) {
RetrofitManager.create(ApiService.class).removeCollectArticle(bean.getId(), -1)
.compose(RxSchedulers.<DataResponse>applySchedulers())
.compose(mView.<DataResponse>bindToLife())
.subscribe(new Consumer<DataResponse>() {
@Override
public void accept(DataResponse response) throws Exception {
if (response.getErrorCode() == 0) {
bean.setCollect(!bean.isCollect());
mView.collectArticleSuccess(position, bean);
mView.showSuccess(App.getAppContext().getString(R.string.collection_cancel_success));
} else {
mView.showFaild(App.getAppContext().getString(R.string.collection_cancel_failed, response.getData()));
}
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
} else {
RetrofitManager.create(ApiService.class).addCollectArticle(bean.getId())
.compose(RxSchedulers.<DataResponse>applySchedulers())
.compose(mView.<DataResponse>bindToLife())
.subscribe(new Consumer<DataResponse>() {
@Override
public void accept(DataResponse response) throws Exception {
if (response.getErrorCode() == 0) {
bean.setCollect(!bean.isCollect());
mView.collectArticleSuccess(position, bean);
mView.showSuccess(App.getAppContext().getString(R.string.collection_success));
} else {
mView.showFaild(App.getAppContext().getString(R.string.collection_failed, response.getErrorMsg()));
}
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
} else {
LoginActivity.start();
}
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleTypeActivity.java
================================================
package com.lw.wanandroid.ui.article;
import android.content.Intent;
import android.support.design.widget.TabLayout;
import android.support.v4.view.ViewPager;
import android.view.Menu;
import android.view.MenuItem;
import com.alibaba.android.arouter.facade.annotation.Autowired;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.launcher.ARouter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.bean.KnowledgeSystem;
import java.util.List;
import butterknife.BindView;
/**
* Created by lw on 2018/1/22.
*/
@Route(path = "/article/ArticleTypeActivity")
public class ArticleTypeActivity extends BaseActivity {
@Autowired
public String title;
@Autowired
public List<KnowledgeSystem.ChildrenBean> childrenData;
@BindView(R.id.tabArticleTypes)
TabLayout mTabArticleTypes;
@BindView(R.id.vpArticleTypes)
ViewPager mVpArticleTypes;
ArticleTypeFragmentPagerAdapter mArticleTypeFragmentPagerAdapter;
@Override
protected int getLayoutId() {
return R.layout.activity_article_type;
}
@Override
protected void initInjector() {
}
@Override
protected void initView() {
setToolbarTitle(title);
mArticleTypeFragmentPagerAdapter = new ArticleTypeFragmentPagerAdapter(getSupportFragmentManager(), childrenData);
mVpArticleTypes.setAdapter(mArticleTypeFragmentPagerAdapter);
mTabArticleTypes.setupWithViewPager(mVpArticleTypes);
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_type_content, menu);
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.getItemId() == R.id.menuShare) {
Intent intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_TEXT, getString(R.string.share_type_url, getString(R.string.app_name),
childrenData.get(mTabArticleTypes.getSelectedTabPosition()).getName(), childrenData.get(mTabArticleTypes.getSelectedTabPosition()).getId()));
intent.setType("text/plain");
startActivity(Intent.createChooser(intent, getString(R.string.share_title)));
} else if (item.getItemId() == R.id.menuSearch) {
ARouter.getInstance().build("/hotsearch/SearchActivity").navigation();
}
return super.onOptionsItemSelected(item);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleTypeFragmentPagerAdapter.java
================================================
package com.lw.wanandroid.ui.article;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;
import com.alibaba.android.arouter.launcher.ARouter;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.constant.Constant;
import java.util.ArrayList;
import java.util.List;
import javax.inject.Inject;
/**
* Created by lw on 2018/1/22.
*/
public class ArticleTypeFragmentPagerAdapter extends FragmentPagerAdapter {
@Nullable
private List<KnowledgeSystem.ChildrenBean> mChildrenData;
private List<ArticleListFragment> mArticleTypeFragments;
@Inject
public ArticleTypeFragmentPagerAdapter(FragmentManager fm, List<KnowledgeSystem.ChildrenBean> childrenData) {
super(fm);
this.mChildrenData = childrenData;
mArticleTypeFragments = new ArrayList<>();
if (mChildrenData == null) return;
for (KnowledgeSystem.ChildrenBean childrenBean : mChildrenData) {
ArticleListFragment articleListFragment = (ArticleListFragment) ARouter.getInstance()
.build("/article/ArticleListFragment")
.withInt(Constant.CONTENT_CID_KEY, childrenBean.getId())
.navigation();
mArticleTypeFragments.add(articleListFragment);
}
}
@Override
public Fragment getItem(int position) {
return mArticleTypeFragments.get(position);
}
@Override
public int getCount() {
return mArticleTypeFragments.size();
}
@Override
public CharSequence getPageTitle(int position) {
return mChildrenData.get(position).getName();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/home/HomeContract.java
================================================
package com.lw.wanandroid.ui.home;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.Banner;
import com.lw.wanandroid.constant.LoadType;
import java.util.List;
/**
* Created by lw on 2018/1/18.
*/
public interface HomeContract {
interface View extends BaseContract.BaseView {
void setHomeBanners(List<Banner> banners);
void setHomeArticles(Article article, @LoadType.checker int loadType);
void collectArticleSuccess(int position, Article.DatasBean bean);
}
interface Presenter extends BaseContract.BasePresenter<View> {
void loadHomeBanners();
void loadHomeArticles();
void refresh();
void loadMore();
void collectArticle(int position, Article.DatasBean bean);
void loadHomeData();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/home/HomeFragment.java
================================================
package com.lw.wanandroid.ui.home;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import com.alibaba.android.arouter.launcher.ARouter;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseFragment;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.Banner;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.event.LoginEvent;
import com.lw.wanandroid.ui.article.ArticleAdapter;
import com.lw.wanandroid.ui.article.ArticleContentActivity;
import com.lw.wanandroid.utils.GlideImageLoader;
import com.lw.wanandroid.utils.RxBus;
import com.youth.banner.BannerConfig;
import com.youth.banner.listener.OnBannerListener;
import java.util.ArrayList;
import java.util.List;
import javax.inject.Inject;
import butterknife.BindView;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/18.
*/
public class HomeFragment extends BaseFragment<HomePresenter> implements HomeContract.View, ArticleAdapter.OnItemClickListener, ArticleAdapter.OnItemChildClickListener,
SwipeRefreshLayout.OnRefreshListener, ArticleAdapter.RequestLoadMoreListener {
@BindView(R.id.rvHomeArticles)
RecyclerView mRvHomeArticles;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
@Inject
ArticleAdapter mArticleAdapter;
private com.youth.banner.Banner mBannerAds;
private View mHomeBannerHeadView;
@Override
protected int getLayoutId() {
return R.layout.fragment_home;
}
@Override
protected void initInjector() {
mFragmentComponent.inject(this);
}
@Override
protected void initView(View view) {
/**设置RecyclerView*/
mRvHomeArticles.setLayoutManager(new LinearLayoutManager(getContext()));
mRvHomeArticles.setAdapter(mArticleAdapter);
/**设置BannerHeadView*/
mHomeBannerHeadView = LayoutInflater.from(getContext()).inflate(R.layout.layout_home_banner_head, null);
mBannerAds = (com.youth.banner.Banner) mHomeBannerHeadView.findViewById(R.id.banner_ads);
mArticleAdapter.addHeaderView(mHomeBannerHeadView);
/**设置事件监听*/
mArticleAdapter.setOnItemClickListener(this);
mArticleAdapter.setOnItemChildClickListener(this);
mSwipeRefreshLayout.setOnRefreshListener(this);
mArticleAdapter.setOnLoadMoreListener(this);
/**请求数据*/
mPresenter.loadHomeData();
/**登陆成功刷新*/
RxBus.getInstance().toFlowable(LoginEvent.class)
.subscribe(new Consumer<LoginEvent>() {
@Override
public void accept(LoginEvent event) throws Exception {
mPresenter.refresh();
}
});
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
public void showFaild(String errorMsg) {
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void setHomeBanners(final List<Banner> banners) {
List<String> images = new ArrayList();
List<String> titles = new ArrayList();
for (Banner banner : banners) {
images.add(banner.getImagePath());
titles.add(banner.getTitle());
}
mBannerAds.setImages(images)
.setBannerTitles(titles)
.setBannerStyle(BannerConfig.CIRCLE_INDICATOR_TITLE_INSIDE)
.setImageLoader(new GlideImageLoader())
.start();
mBannerAds.setOnBannerListener(new OnBannerListener() {
@Override
public void OnBannerClick(int position) {
ArticleContentActivity.start(banners.get(position).getId(), banners.get(position).getUrl(),
banners.get(position).getTitle(), null);
}
});
}
@Override
public void setHomeArticles(Article article, @LoadType.checker int loadType) {
setLoadDataResult(mArticleAdapter, mSwipeRefreshLayout, article.getDatas(), loadType);
}
@Override
public void collectArticleSuccess(int position, Article.DatasBean bean) {
mArticleAdapter.setData(position, bean);
}
@Override
public void onItemChildClick(BaseQuickAdapter adapter, View view, int position) {
if (view.getId() == R.id.tvChapterName) {
List<KnowledgeSystem.ChildrenBean> childrenBeans = new ArrayList<>();
childrenBeans.add(new KnowledgeSystem.ChildrenBean(mArticleAdapter.getItem(position).getChapterId(),
mArticleAdapter.getItem(position).getChapterName()));
ARouter.getInstance().build("/article/ArticleTypeActivity")
.withString(Constant.CONTENT_TITLE_KEY, mArticleAdapter.getItem(position).getChapterName())
.withObject(Constant.CONTENT_CHILDREN_DATA_KEY, childrenBeans)
.navigation();
} else if (view.getId() == R.id.ivCollect) {
mPresenter.collectArticle(position, mArticleAdapter.getItem(position));
}
}
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
ArticleContentActivity.start(mArticleAdapter.getItem(position).getId(),
mArticleAdapter.getItem(position).getLink(), mArticleAdapter.getItem(position).getTitle(),
mArticleAdapter.getItem(position).getAuthor());
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
@Override
public void onLoadMoreRequested() {
mPresenter.loadMore();
}
public static HomeFragment newInstance() {
return new HomeFragment();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/home/HomePresenter.java
================================================
package com.lw.wanandroid.ui.home;
import com.blankj.utilcode.util.SPUtils;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.App;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.Banner;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.bean.User;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.ArticleUtils;
import com.lw.wanandroid.utils.RxSchedulers;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.inject.Inject;
import io.reactivex.Observable;
import io.reactivex.functions.Consumer;
import io.reactivex.functions.Function3;
/**
* Created by lw on 2018/1/18.
*/
public class HomePresenter extends BasePresenter<HomeContract.View> implements HomeContract.Presenter {
private int mPage;
private boolean mIsRefresh;
@Inject
public HomePresenter() {
this.mIsRefresh = true;
}
@Override
public void loadHomeBanners() {
RetrofitManager.create(ApiService.class)
.getHomeBanners()
.compose(RxSchedulers.<DataResponse<List<Banner>>>applySchedulers())
.compose(mView.<DataResponse<List<Banner>>>bindToLife())
.subscribe(new Consumer<DataResponse<List<Banner>>>() {
@Override
public void accept(DataResponse<List<Banner>> dataResponse) throws Exception {
mView.setHomeBanners(dataResponse.getData());
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
@Override
public void loadHomeArticles() {
RetrofitManager.create(ApiService.class)
.getHomeArticles(mPage)
.compose(RxSchedulers.<DataResponse<Article>>applySchedulers())
.compose(mView.<DataResponse<Article>>bindToLife())
.subscribe(new Consumer<DataResponse<Article>>() {
@Override
public void accept(DataResponse<Article> dataResponse) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_SUCCESS : LoadType.TYPE_LOAD_MORE_SUCCESS;
mView.setHomeArticles(dataResponse.getData(), loadType);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_ERROR : LoadType.TYPE_LOAD_MORE_ERROR;
mView.setHomeArticles(new Article(), loadType);
}
});
}
@Override
public void refresh() {
mPage = 0;
mIsRefresh = true;
loadHomeBanners();
loadHomeArticles();
}
@Override
public void loadMore() {
mPage++;
mIsRefresh = false;
loadHomeArticles();
}
@Override
public void collectArticle(final int position, final Article.DatasBean bean) {
ArticleUtils.collectArticle(mView, position, bean);
}
@Override
public void loadHomeData() {
mView.showLoading();
String username = SPUtils.getInstance(Constant.SHARED_NAME).getString(Constant.USERNAME_KEY);
String password = SPUtils.getInstance(Constant.SHARED_NAME).getString(Constant.PASSWORD_KEY);
Observable<DataResponse<User>> observableUser = RetrofitManager.create(ApiService.class).login(username, password);
Observable<DataResponse<List<Banner>>> observableBanner = RetrofitManager.create(ApiService.class).getHomeBanners();
Observable<DataResponse<Article>> observableArticle = RetrofitManager.create(ApiService.class).getHomeArticles(mPage);
Observable.zip(observableUser, observableBanner, observableArticle, new Function3<DataResponse<User>, DataResponse<List<Banner>>, DataResponse<Article>, Map<String, Object>>() {
@Override
public Map<String, Object> apply(DataResponse<User> response, DataResponse<List<Banner>> dataResponse, DataResponse<Article> dataResponse2) throws Exception {
Map<String, Object> objMap = new HashMap<>();
objMap.put(Constant.USER_KEY, response);
objMap.put(Constant.BANNER_KEY, dataResponse.getData());
objMap.put(Constant.ARTICLE_KEY, dataResponse2.getData());
return objMap;
}
}).compose(RxSchedulers.<Map<String, Object>>applySchedulers()).compose(mView.<Map<String, Object>>bindToLife()).subscribe(new Consumer<Map<String, Object>>() {
@Override
public void accept(Map<String, Object> map) throws Exception {
DataResponse<User> dataResponse = (DataResponse<User>) map.get(Constant.USER_KEY);
if (dataResponse.getErrorCode() == 0) {
mView.showSuccess(App.getAppContext().getString(R.string.auto_login_success));
} else {
mView.showFaild(String.valueOf(dataResponse.getErrorMsg()));
}
List<Banner> banners = (List<Banner>) map.get(Constant.BANNER_KEY);
Article article = (Article) map.get(Constant.ARTICLE_KEY);
mView.setHomeBanners(banners);
mView.setHomeArticles(article, LoadType.TYPE_REFRESH_SUCCESS);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/CommonHotAdapter.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.lw.wanandroid.R;
import com.lw.wanandroid.bean.Friend;
import javax.inject.Inject;
/**
* Created by lw on 2018/1/23.
*/
public class CommonHotAdapter extends BaseQuickAdapter<Friend, BaseViewHolder> {
@Inject
public CommonHotAdapter() {
super(R.layout.item_hot, null);
}
@Override
protected void convert(BaseViewHolder helper, Friend item) {
helper.setText(R.id.tvTitle, item.getName());
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HistoryAdapter.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import android.content.Context;
import android.graphics.Color;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.TextView;
import com.lw.wanandroid.R;
import com.lw.wanandroid.db.HistoryModel;
import com.zhy.view.flowlayout.FlowLayout;
import com.zhy.view.flowlayout.TagAdapter;
import java.util.List;
/**
* Created by lw on 2018/2/2.
*/
public class HistoryAdapter extends TagAdapter<HistoryModel> {
private Context mContext;
private LayoutInflater mInflater;
public HistoryAdapter(Context context, List<HistoryModel> datas) {
super(datas);
this.mContext = context;
this.mInflater = LayoutInflater.from(mContext);
}
@Override
public View getView(FlowLayout parent, int position, HistoryModel model) {
View view = mInflater.inflate(R.layout.item_history, parent, false);
TextView tvTitle = (TextView) view.findViewById(R.id.tvTitle);
int parseColor = 0;
try {
tvTitle.setText(model.getName());
String str = Integer.toHexString((int) (Math.random() * 16777215));
parseColor = Color.parseColor("#".concat(str));
tvTitle.setTextColor(parseColor);
} catch (Exception e) {
e.printStackTrace();
parseColor = mContext.getResources().getColor(R.color.colorAccent);
}
tvTitle.setTextColor(parseColor);
return view;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotAdapter.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import android.content.Context;
import android.graphics.Color;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.TextView;
import com.lw.wanandroid.R;
import com.zhy.view.flowlayout.FlowLayout;
import com.zhy.view.flowlayout.TagAdapter;
import java.lang.reflect.Field;
import java.util.List;
/**
* Created by lw on 2018/1/23.
*/
public class HotAdapter<T> extends TagAdapter<T> {
private Context mContext;
private LayoutInflater mInflater;
public HotAdapter(Context context, List<T> datas) {
super(datas);
this.mContext = context;
this.mInflater = LayoutInflater.from(mContext);
}
@Override
public View getView(FlowLayout parent, int position, T item) {
View view = mInflater.inflate(R.layout.item_hot, parent, false);
TextView tvTitle = (TextView) view.findViewById(R.id.tvTitle);
int parseColor = 0;
try {
String name = "";
Field[] fields = item.getClass().getDeclaredFields();
for (Field field : fields) {
field.setAccessible(true);
if (field.getName().equals("name")) {
name = (String) field.get(item);
break;
}
}
tvTitle.setText(name);
String str = Integer.toHexString((int) (Math.random() * 16777215));
parseColor = Color.parseColor("#".concat(str));
tvTitle.setTextColor(parseColor);
} catch (Exception e) {
e.printStackTrace();
parseColor = mContext.getResources().getColor(R.color.colorAccent);
}
tvTitle.setTextColor(parseColor);
return view;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotContract.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.Friend;
import com.lw.wanandroid.bean.HotKey;
import java.util.List;
/**
* Created by lw on 2018/1/23.
*/
public interface HotContract {
interface View extends BaseContract.BaseView {
void setHotData(List<HotKey> hotKeys, List<Friend> friends);
}
interface Presenter extends BaseContract.BasePresenter<View> {
void loadHotData();
void refresh();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotFragment.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import com.alibaba.android.arouter.launcher.ARouter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseFragment;
import com.lw.wanandroid.bean.Friend;
import com.lw.wanandroid.bean.HotKey;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.ui.article.ArticleContentActivity;
import com.zhy.view.flowlayout.FlowLayout;
import com.zhy.view.flowlayout.TagFlowLayout;
import java.util.List;
import javax.inject.Inject;
import butterknife.BindView;
/**
* Created by lw on 2018/1/23.
*/
public class HotFragment extends BaseFragment<HotPresenter> implements HotContract.View, SwipeRefreshLayout.OnRefreshListener {
@BindView(R.id.rvHots)
RecyclerView mRvHots;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
@Inject
public CommonHotAdapter mCommonHotAdapter;
private TagFlowLayout mTtlBookMarks, mTflHotKeys, mTflHotFriends;
private HotAdapter<HotKey> mHotKeyAdapter;
private HotAdapter<Friend> mHotFriendAdapter, mBookMarkAdapter;
private View mHotHeadView;
@Override
protected int getLayoutId() {
return R.layout.fragment_hot;
}
@Override
protected void initInjector() {
mFragmentComponent.inject(this);
}
@Override
protected void initView(View view) {
/**设置RecyclerView*/
mRvHots.setLayoutManager(new LinearLayoutManager(getContext()));
mRvHots.setAdapter(mCommonHotAdapter);
/**设置HotHeadView*/
mHotHeadView = LayoutInflater.from(getContext()).inflate(R.layout.layout_hot_head, null);
mTtlBookMarks = (TagFlowLayout) mHotHeadView.findViewById(R.id.tflBookMarks);
mTflHotKeys = (TagFlowLayout) mHotHeadView.findViewById(R.id.tflHotKeys);
mTflHotFriends = (TagFlowLayout) mHotHeadView.findViewById(R.id.tflHotFriends);
mCommonHotAdapter.addHeaderView(mHotHeadView);
/**设置监听*/
setListener();
/**请求数据*/
mPresenter.loadHotData();
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
public void showFaild(String errorMsg) {
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void setHotData(List<HotKey> hotKeys, List<Friend> friends) {
mHotKeyAdapter = new HotAdapter(getContext(), hotKeys);
mTflHotKeys.setAdapter(mHotKeyAdapter);
mHotFriendAdapter = new HotAdapter<>(getContext(), friends);
mTflHotFriends.setAdapter(mHotFriendAdapter);
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
public static HotFragment newInstance() {
return new HotFragment();
}
private void setListener() {
mSwipeRefreshLayout.setOnRefreshListener(this);
mTflHotKeys.setOnTagClickListener(new TagFlowLayout.OnTagClickListener() {
@Override
public boolean onTagClick(View view, int position, FlowLayout parent) {
String name = mHotKeyAdapter.getItem(position).getName();
ARouter.getInstance().build("/hotsearch/SearchActivity")
.withString(Constant.CONTENT_HOT_NAME_KEY, name)
.navigation();
return false;
}
});
mTflHotFriends.setOnTagClickListener(new TagFlowLayout.OnTagClickListener() {
@Override
public boolean onTagClick(View view, int position, FlowLayout parent) {
ArticleContentActivity.start(mHotFriendAdapter.getItem(position).getId(),
mHotFriendAdapter.getItem(position).getLink(), mHotFriendAdapter.getItem(position).getName(),
null);
return false;
}
});
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotPresenter.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.bean.Friend;
import com.lw.wanandroid.bean.HotKey;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.RxSchedulers;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.inject.Inject;
import io.reactivex.Observable;
import io.reactivex.functions.BiFunction;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/23.
*/
public class HotPresenter extends BasePresenter<HotContract.View> implements HotContract.Presenter {
@Inject
public HotPresenter() {
}
@Override
public void loadHotData() {
mView.showLoading();
Observable<DataResponse<List<Friend>>> observableFriend = RetrofitManager.create(ApiService.class).getHotFriends();
Observable<DataResponse<List<HotKey>>> observableHotKey = RetrofitManager.create(ApiService.class).getHotKeys();
Observable.zip(observableFriend, observableHotKey, new BiFunction<DataResponse<List<Friend>>, DataResponse<List<HotKey>>, Map<String, Object>>() {
@Override
public Map<String, Object> apply(DataResponse<List<Friend>> response, DataResponse<List<HotKey>> response2) throws Exception {
Map<String, Object> objMap = new HashMap<>();
objMap.put(Constant.CONTENT_HOT_KEY, response2.getData());
objMap.put(Constant.CONTENT_HOT_FRIEND_KEY, response.getData());
return objMap;
}
}).compose(RxSchedulers.<Map<String, Object>>applySchedulers()).compose(mView.<Map<String, Object>>bindToLife()).subscribe(new Consumer<Map<String, Object>>() {
@Override
public void accept(Map<String, Object> map) throws Exception {
List<HotKey> hotKeys = (List<HotKey>) map.get(Constant.CONTENT_HOT_KEY);
List<Friend> friends = (List<Friend>) map.get(Constant.CONTENT_HOT_FRIEND_KEY);
mView.setHotData(hotKeys, friends);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
@Override
public void refresh() {
loadHotData();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchActivity.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.support.v7.widget.SearchView;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.View;
import com.alibaba.android.arouter.facade.annotation.Autowired;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.launcher.ARouter;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.db.HistoryModel;
import com.lw.wanandroid.event.LoginEvent;
import com.lw.wanandroid.ui.article.ArticleAdapter;
import com.lw.wanandroid.ui.article.ArticleContentActivity;
import com.lw.wanandroid.utils.RxBus;
import com.zhy.view.flowlayout.FlowLayout;
import com.zhy.view.flowlayout.TagFlowLayout;
import java.util.ArrayList;
import java.util.List;
import javax.inject.Inject;
import butterknife.BindView;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/23.
*/
@Route(path = "/hotsearch/SearchActivity")
public class SearchActivity extends BaseActivity<SearchPresenter> implements SearchContract.View, ArticleAdapter.OnItemClickListener, ArticleAdapter.OnItemChildClickListener,
SwipeRefreshLayout.OnRefreshListener, ArticleAdapter.RequestLoadMoreListener {
@BindView(R.id.rvArticleList)
RecyclerView mRvArticleList;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
@Inject
ArticleAdapter mArticleAdapter;
@Autowired
public String hotNameKey;
private HistoryAdapter mHistoryAdapter;
private SearchView mSearchView;
private List<HistoryModel> mHistoryModels;
private View mSearchHeadView;
private TagFlowLayout mTflHistorys;
@Override
protected int getLayoutId() {
return R.layout.activity_search;
}
@Override
protected void initInjector() {
mActivityComponent.inject(this);
}
@Override
protected void initView() {
/**设置RecyclerView*/
mRvArticleList.setLayoutManager(new LinearLayoutManager(this));
mRvArticleList.setAdapter(mArticleAdapter);
/**设置SearchHeadView*/
mSearchHeadView = LayoutInflater.from(this).inflate(R.layout.layout_search_head, null);
mTflHistorys = (TagFlowLayout) mSearchHeadView.findViewById(R.id.tflHistorys);
mArticleAdapter.addHeaderView(mSearchHeadView);
/**设置事件监听*/
mArticleAdapter.setOnItemClickListener(this);
mArticleAdapter.setOnItemChildClickListener(this);
mSwipeRefreshLayout.setOnRefreshListener(this);
mArticleAdapter.setOnLoadMoreListener(this);
/**加载历史搜索记录*/
mPresenter.loadHistory();
/**登陆成功刷新*/
RxBus.getInstance().toFlowable(LoginEvent.class)
.subscribe(new Consumer<LoginEvent>() {
@Override
public void accept(LoginEvent event) throws Exception {
mPresenter.refresh();
}
});
mTflHistorys.setOnTagClickListener(new TagFlowLayout.OnTagClickListener() {
@Override
public boolean onTagClick(View view, int position, FlowLayout parent) {
String name = mHistoryAdapter.getItem(position).getName();
mSearchView.setQuery(name, false);
mPresenter.loadSearchArtcles(name);
return false;
}
});
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_search, menu);
mSearchView = (SearchView) menu.findItem(R.id.menuSearch).getActionView();
mSearchView.setMaxWidth(1920);
mSearchView.setIconified(false);
mSearchView.setOnCloseListener(new SearchView.OnCloseListener() {
@Override
public boolean onClose() {
SearchActivity.this.finish();
return true;
}
});
mSearchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
@Override
public boolean onQueryTextSubmit(String query) {
mPresenter.addHistory(query);
mPresenter.loadSearchArtcles(query);
return true;
}
@Override
public boolean onQueryTextChange(String newText) {
return false;
}
});
/**是否是从hot页面过来的*/
mSearchView.setQuery(hotNameKey, true);
return super.onCreateOptionsMenu(menu);
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
@Override
public void onItemChildClick(BaseQuickAdapter adapter, View view, int position) {
if (view.getId() == R.id.tvChapterName) {
List<KnowledgeSystem.ChildrenBean> childrenBeans = new ArrayList<>();
childrenBeans.add(new KnowledgeSystem.ChildrenBean(mArticleAdapter.getItem(position).getChapterId(),
mArticleAdapter.getItem(position).getChapterName()));
ARouter.getInstance().build("/article/ArticleTypeActivity")
.withString(Constant.CONTENT_TITLE_KEY, mArticleAdapter.getItem(position).getChapterName())
.withObject(Constant.CONTENT_CHILDREN_DATA_KEY, childrenBeans)
.navigation();
} else if (view.getId() == R.id.ivCollect) {
mPresenter.collectArticle(position, mArticleAdapter.getItem(position));
}
}
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
ArticleContentActivity.start(mArticleAdapter.getItem(position).getId(),
mArticleAdapter.getItem(position).getLink(), mArticleAdapter.getItem(position).getTitle(),
mArticleAdapter.getItem(position).getAuthor());
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
public void onLoadMoreRequested() {
mPresenter.loadMore();
}
@Override
public void setSearchArtcles(Article article, int loadType) {
setLoadDataResult(mArticleAdapter, mSwipeRefreshLayout, article.getDatas(), loadType);
}
@Override
public void collectArticleSuccess(int position, Article.DatasBean bean) {
mArticleAdapter.setData(position, bean);
}
@Override
public void setHistory(List<HistoryModel> historyModels) {
this.mHistoryModels = historyModels;
mHistoryAdapter = new HistoryAdapter(this, mHistoryModels);
mTflHistorys.setAdapter(mHistoryAdapter);
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void addHistorySuccess(HistoryModel historyModel) {
if (mHistoryModels != null) mHistoryModels.add(0, historyModel);
mHistoryAdapter.notifyDataChanged();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchContract.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.db.HistoryModel;
import java.util.List;
/**
* Created by lw on 2018/1/23.
*/
public interface SearchContract {
interface View extends BaseContract.BaseView {
void setSearchArtcles(Article article, @LoadType.checker int loadType);
void collectArticleSuccess(int position, Article.DatasBean bean);
void setHistory(List<HistoryModel> historyModels);
void addHistorySuccess(HistoryModel historyModel);
}
interface Presenter extends BaseContract.BasePresenter<SearchContract.View> {
void loadSearchArtcles(String k);
void refresh();
void loadMore();
void collectArticle(int position, Article.DatasBean bean);
void loadHistory();
void addHistory(String name);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchPresenter.java
================================================
package com.lw.wanandroid.ui.hotsearch;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.db.HistoryModel;
import com.lw.wanandroid.db.HistoryModel_Table;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.ArticleUtils;
import com.lw.wanandroid.utils.RxSchedulers;
import com.raizlabs.android.dbflow.sql.language.SQLite;
import java.util.Date;
import java.util.List;
import javax.inject.Inject;
import io.reactivex.Observable;
import io.reactivex.ObservableEmitter;
import io.reactivex.ObservableOnSubscribe;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/23.
*/
public class SearchPresenter extends BasePresenter<SearchContract.View> implements SearchContract.Presenter {
private int mPage;
private boolean mIsRefresh;
private String mK;
@Inject
public SearchPresenter() {
this.mIsRefresh = true;
}
@Override
public void loadSearchArtcles(String k) {
this.mK = k;
RetrofitManager.create(ApiService.class)
.getSearchArticles(mPage, mK)
.compose(RxSchedulers.<DataResponse<Article>>applySchedulers())
.compose(mView.<DataResponse<Article>>bindToLife())
.subscribe(new Consumer<DataResponse<Article>>() {
@Override
public void accept(DataResponse<Article> dataResponse) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_SUCCESS : LoadType.TYPE_LOAD_MORE_SUCCESS;
mView.setSearchArtcles(dataResponse.getData(), loadType);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_ERROR : LoadType.TYPE_LOAD_MORE_ERROR;
mView.setSearchArtcles(new Article(), loadType);
}
});
}
@Override
public void refresh() {
mPage = 0;
mIsRefresh = true;
loadSearchArtcles(mK);
}
@Override
public void loadMore() {
mPage++;
mIsRefresh = false;
loadSearchArtcles(mK);
}
@Override
public void collectArticle(final int position, final Article.DatasBean bean) {
ArticleUtils.collectArticle(mView, position, bean);
}
@Override
public void loadHistory() {
mView.showLoading();
Observable.create(new ObservableOnSubscribe<List<HistoryModel>>() {
@Override
public void subscribe(ObservableEmitter<List<HistoryModel>> e) throws Exception {
List<HistoryModel> historyModels = SQLite.select().from(HistoryModel.class)
.orderBy(HistoryModel_Table.date, false)
.limit(10).offset(0)
.queryList();
e.onNext(historyModels);
}
}).compose(RxSchedulers.<List<HistoryModel>>applySchedulers()).compose(mView.<List<HistoryModel>>bindToLife()).subscribe(new Consumer<List<HistoryModel>>() {
@Override
public void accept(List<HistoryModel> historyModels) throws Exception {
mView.setHistory(historyModels);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
@Override
public void addHistory(String name) {
HistoryModel historyModel = new HistoryModel();
historyModel.setName(name);
historyModel.setDate(new Date());
long id = historyModel.insert();
if (id > 0) mView.addHistorySuccess(historyModel);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemAdapter.java
================================================
package com.lw.wanandroid.ui.knowledgesystem;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.lw.wanandroid.R;
import com.lw.wanandroid.bean.KnowledgeSystem;
import javax.inject.Inject;
/**
* Created by lw on 2018/1/22.
*/
public class KnowledgeSystemAdapter extends BaseQuickAdapter<KnowledgeSystem, BaseViewHolder> {
@Inject
public KnowledgeSystemAdapter() {
super(R.layout.item_knowledge_system, null);
}
@Override
protected void convert(BaseViewHolder helper, KnowledgeSystem item) {
helper.setText(R.id.typeItemFirst, item.getName());
StringBuffer sb = new StringBuffer();
for (KnowledgeSystem.ChildrenBean childrenBean : item.getChildren()) {
sb.append(childrenBean.getName() + " ");
}
helper.setText(R.id.typeItemSecond, sb.toString());
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemContract.java
================================================
package com.lw.wanandroid.ui.knowledgesystem;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.KnowledgeSystem;
import java.util.List;
/**
* Created by lw on 2018/1/19.
*/
public interface KnowledgeSystemContract {
interface View extends BaseContract.BaseView {
void setKnowledgeSystems(List<KnowledgeSystem> knowledgeSystems);
}
interface Presenter extends BaseContract.BasePresenter<KnowledgeSystemContract.View> {
void loadKnowledgeSystems();
void refresh();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemFragment.java
================================================
package com.lw.wanandroid.ui.knowledgesystem;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.View;
import com.alibaba.android.arouter.launcher.ARouter;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseFragment;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.constant.Constant;
import java.util.List;
import javax.inject.Inject;
import butterknife.BindView;
/**
* Created by lw on 2018/1/18.
*/
public class KnowledgeSystemFragment extends BaseFragment<KnowledgeSystemPresenter> implements KnowledgeSystemContract.View,
KnowledgeSystemAdapter.OnItemClickListener, SwipeRefreshLayout.OnRefreshListener {
@BindView(R.id.rvKnowledgeSystems)
RecyclerView mRvKnowledgeSystems;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
@Inject
KnowledgeSystemAdapter mKnowledgeSystemAdapter;
@Override
protected int getLayoutId() {
return R.layout.fragment_knowledge_system;
}
@Override
protected void initInjector() {
mFragmentComponent.inject(this);
}
@Override
protected void initView(View view) {
/**设置RecyclerView*/
mRvKnowledgeSystems.setLayoutManager(new LinearLayoutManager(getContext()));
mRvKnowledgeSystems.setAdapter(mKnowledgeSystemAdapter);
/**设置事件监听*/
mKnowledgeSystemAdapter.setOnItemClickListener(this);
mSwipeRefreshLayout.setOnRefreshListener(this);
/**请求数据*/
mPresenter.loadKnowledgeSystems();
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
public void showFaild(String errorMsg) {
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void setKnowledgeSystems(List<KnowledgeSystem> knowledgeSystems) {
mKnowledgeSystemAdapter.setNewData(knowledgeSystems);
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
ARouter.getInstance().build("/article/ArticleTypeActivity")
.withString(Constant.CONTENT_TITLE_KEY, mKnowledgeSystemAdapter.getItem(position).getName())
.withObject(Constant.CONTENT_CHILDREN_DATA_KEY, mKnowledgeSystemAdapter.getItem(position).getChildren())
.navigation();
}
public static KnowledgeSystemFragment newInstance() {
return new KnowledgeSystemFragment();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemPresenter.java
================================================
package com.lw.wanandroid.ui.knowledgesystem;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.RxSchedulers;
import java.util.List;
import javax.inject.Inject;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/19.
*/
public class KnowledgeSystemPresenter extends BasePresenter<KnowledgeSystemContract.View> implements KnowledgeSystemContract.Presenter {
@Inject
public KnowledgeSystemPresenter() {
}
@Override
public void loadKnowledgeSystems() {
mView.showLoading();
RetrofitManager.create(ApiService.class)
.getKnowledgeSystems()
.compose(RxSchedulers.<DataResponse<List<KnowledgeSystem>>>applySchedulers())
.compose(mView.<DataResponse<List<KnowledgeSystem>>>bindToLife())
.subscribe(new Consumer<DataResponse<List<KnowledgeSystem>>>() {
@Override
public void accept(DataResponse<List<KnowledgeSystem>> dataResponse) throws Exception {
mView.setKnowledgeSystems(dataResponse.getData());
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
@Override
public void refresh() {
loadKnowledgeSystems();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/LoginActivity.java
================================================
package com.lw.wanandroid.ui.my;
import android.support.design.widget.TextInputEditText;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.launcher.ARouter;
import com.blankj.utilcode.util.SPUtils;
import com.blankj.utilcode.util.StringUtils;
import com.blankj.utilcode.util.ToastUtils;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.bean.User;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.event.LoginEvent;
import com.lw.wanandroid.utils.RxBus;
import butterknife.BindView;
import butterknife.OnClick;
/**
* Created by lw on 2018/1/24.
*/
@Route(path = "/my/LoginActivity")
public class LoginActivity extends BaseActivity<LoginPresenter> implements LoginContract.View {
@BindView(R.id.etUsername)
TextInputEditText mEtUsername;
@BindView(R.id.etPassword)
TextInputEditText mEtPassword;
@Override
protected int getLayoutId() {
return R.layout.activity_login;
}
@Override
protected void initInjector() {
mActivityComponent.inject(this);
}
@Override
protected void initView() {
mEtUsername.setText(SPUtils.getInstance(Constant.SHARED_NAME).getString(Constant.USERNAME_KEY));
mEtPassword.setText(SPUtils.getInstance(Constant.SHARED_NAME).getString(Constant.PASSWORD_KEY));
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@OnClick(R.id.btnLogin)
public void login() {
String username = mEtUsername.getText().toString();
String password = mEtPassword.getText().toString();
if (StringUtils.isEmpty(username) || StringUtils.isEmpty(password)) {
ToastUtils.showShort(R.string.the_username_or_password_can_not_be_empty);
return;
}
mPresenter.login(username, password);
}
@Override
public void loginSuccess(User user) {
SPUtils.getInstance(Constant.SHARED_NAME).put(Constant.LOGIN_KEY, true);
SPUtils.getInstance(Constant.SHARED_NAME).put(Constant.USERNAME_KEY, user.getUsername());
SPUtils.getInstance(Constant.SHARED_NAME).put(Constant.PASSWORD_KEY, user.getPassword());
/**登陆成功通知其他界面刷新*/
RxBus.getInstance().post(new LoginEvent());
this.finish();
}
public static void start() {
ARouter.getInstance().build("/my/LoginActivity").navigation();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/LoginContract.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.User;
/**
* Created by lw on 2018/1/24.
*/
public interface LoginContract {
interface View extends BaseContract.BaseView {
void loginSuccess(User user);
}
interface Presenter extends BaseContract.BasePresenter<LoginContract.View> {
void login(String username, String password);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/LoginPresenter.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.bean.User;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.RxSchedulers;
import javax.inject.Inject;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/24.
*/
public class LoginPresenter extends BasePresenter<LoginContract.View> implements LoginContract.Presenter {
@Inject
public LoginPresenter() {
}
@Override
public void login(String username, String password) {
RetrofitManager.create(ApiService.class)
.login(username, password)
.compose(RxSchedulers.<DataResponse<User>>applySchedulers())
.compose(mView.<DataResponse<User>>bindToLife())
.subscribe(new Consumer<DataResponse<User>>() {
@Override
public void accept(DataResponse<User> response) throws Exception {
if (response.getErrorCode() == 0) {
mView.loginSuccess(response.getData());
} else {
mView.showFaild(String.valueOf(response.getErrorMsg()));
}
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkActivity.java
================================================
package com.lw.wanandroid.ui.my;
import android.support.v4.widget.SwipeRefreshLayout;
import android.util.Log;
import android.view.View;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.blankj.utilcode.util.ToastUtils;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.bean.Friend;
import com.lw.wanandroid.ui.article.ArticleContentActivity;
import com.lw.wanandroid.ui.hotsearch.HotAdapter;
import com.zhy.view.flowlayout.FlowLayout;
import com.zhy.view.flowlayout.TagFlowLayout;
import java.util.List;
import java.util.Set;
import butterknife.BindView;
/**
* Created by lw on 2018/1/25.
*/
@Route(path = "/my/MyBookmarkActivity")
public class MyBookmarkActivity extends BaseActivity<MyBookmarkPresenter> implements MyBookmarkContract.View, SwipeRefreshLayout.OnRefreshListener {
@BindView(R.id.tflMyBookmarks)
TagFlowLayout mTflMyBookmarks;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
private HotAdapter<Friend> mBookmarkAdapter;
@Override
protected int getLayoutId() {
return R.layout.activity_my_bookmark;
}
@Override
protected void initInjector() {
mActivityComponent.inject(this);
}
@Override
protected void initView() {
mSwipeRefreshLayout.setOnRefreshListener(this);
mPresenter.loadMyBookmarks();
mTflMyBookmarks.setOnTagClickListener(new TagFlowLayout.OnTagClickListener() {
@Override
public boolean onTagClick(View view, int position, FlowLayout parent) {
ArticleContentActivity.start(mBookmarkAdapter.getItem(position).getId(),
mBookmarkAdapter.getItem(position).getLink(), mBookmarkAdapter.getItem(position).getName(),
null);
return false;
}
});
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@Override
public void setMyBookmarks(List<Friend> bookmarks) {
mBookmarkAdapter = new HotAdapter(this, bookmarks);
mTflMyBookmarks.setAdapter(mBookmarkAdapter);
mSwipeRefreshLayout.setRefreshing(false);
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkContract.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.Friend;
import java.util.List;
/**
* Created by lw on 2018/2/2.
*/
public interface MyBookmarkContract {
interface View extends BaseContract.BaseView {
void setMyBookmarks(List<Friend> bookmarks);
}
interface Presenter extends BaseContract.BasePresenter<MyBookmarkContract.View> {
void loadMyBookmarks();
void editBookmark(int id, String name, String link);
void delBookmark(int id);
void refresh();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkPresenter.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.bean.Friend;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.RxSchedulers;
import java.util.List;
import javax.inject.Inject;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/2/2.
*/
public class MyBookmarkPresenter extends BasePresenter<MyBookmarkContract.View> implements MyBookmarkContract.Presenter {
private boolean mIsRefresh;
@Inject
public MyBookmarkPresenter() {
this.mIsRefresh = true;
}
@Override
public void loadMyBookmarks() {
mView.showLoading();
RetrofitManager.create(ApiService.class)
.getBookmarks()
.compose(RxSchedulers.<DataResponse<List<Friend>>>applySchedulers())
.compose(mView.<DataResponse<List<Friend>>>bindToLife())
.subscribe(new Consumer<DataResponse<List<Friend>>>() {
@Override
public void accept(DataResponse<List<Friend>> response) throws Exception {
mView.setMyBookmarks(response.getData());
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
mView.showFaild(throwable.getMessage());
}
});
}
@Override
public void editBookmark(int id, String name, String link) {
}
@Override
public void delBookmark(int id) {
}
@Override
public void refresh() {
mIsRefresh = true;
loadMyBookmarks();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionActivity.java
================================================
package com.lw.wanandroid.ui.my;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.View;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.alibaba.android.arouter.launcher.ARouter;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.KnowledgeSystem;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.ui.article.ArticleAdapter;
import com.lw.wanandroid.ui.article.ArticleContentActivity;
import java.util.ArrayList;
import java.util.List;
import javax.inject.Inject;
import butterknife.BindView;
/**
* Created by lw on 2018/1/25.
*/
@Route(path = "/my/MyCollectionActivity")
public class MyCollectionActivity extends BaseActivity<MyCollectionPresenter> implements MyCollectionContract.View,
ArticleAdapter.OnItemClickListener, ArticleAdapter.OnItemChildClickListener, SwipeRefreshLayout.OnRefreshListener, ArticleAdapter.RequestLoadMoreListener {
@BindView(R.id.rvMyCollectionArticles)
RecyclerView mRvMyCollectionArticles;
@BindView(R.id.swipeRefreshLayout)
SwipeRefreshLayout mSwipeRefreshLayout;
@Inject
ArticleAdapter mArticleAdapter;
@Override
protected int getLayoutId() {
return R.layout.activity_my_collection;
}
@Override
protected void initInjector() {
mActivityComponent.inject(this);
}
@Override
protected void initView() {
/**设置RecyclerView*/
mRvMyCollectionArticles.setLayoutManager(new LinearLayoutManager(this));
mRvMyCollectionArticles.setAdapter(mArticleAdapter);
/**设置事件监听*/
mArticleAdapter.setOnItemClickListener(this);
mArticleAdapter.setOnItemChildClickListener(this);
mSwipeRefreshLayout.setOnRefreshListener(this);
mArticleAdapter.setOnLoadMoreListener(this);
mArticleAdapter.isMyColection(true);
/**请求数据*/
mPresenter.loadMyCollectArticles();
}
@Override
public void showLoading() {
mSwipeRefreshLayout.setRefreshing(true);
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@Override
public void setMyCollectArticles(Article article, int loadType) {
setLoadDataResult(mArticleAdapter, mSwipeRefreshLayout, article.getDatas(), loadType);
}
@Override
public void unCollectArticleSuccess(int position) {
mArticleAdapter.remove(position);
}
@Override
public void onRefresh() {
mPresenter.refresh();
}
@Override
public void onItemChildClick(BaseQuickAdapter adapter, View view, int position) {
if (view.getId() == R.id.tvChapterName) {
List<KnowledgeSystem.ChildrenBean> childrenBeans = new ArrayList<>();
childrenBeans.add(new KnowledgeSystem.ChildrenBean(mArticleAdapter.getItem(position).getChapterId(),
mArticleAdapter.getItem(position).getChapterName()));
ARouter.getInstance().build("/article/ArticleTypeActivity")
.withString(Constant.CONTENT_TITLE_KEY, mArticleAdapter.getItem(position).getChapterName())
.withObject(Constant.CONTENT_CHILDREN_DATA_KEY, childrenBeans)
.navigation();
} else if (view.getId() == R.id.ivCollect) {
mPresenter.unCollectArticle(position, mArticleAdapter.getItem(position));
}
}
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
ArticleContentActivity.start(mArticleAdapter.getItem(position).getId(),
mArticleAdapter.getItem(position).getLink(), mArticleAdapter.getItem(position).getTitle(),
mArticleAdapter.getItem(position).getAuthor());
}
@Override
public void onLoadMoreRequested() {
mPresenter.loadMore();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionContract.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BaseContract;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.constant.LoadType;
/**
* Created by lw on 2018/2/2.
*/
public interface MyCollectionContract {
interface View extends BaseContract.BaseView {
void setMyCollectArticles(Article article, @LoadType.checker int loadType);
void unCollectArticleSuccess(int position);
}
interface Presenter extends BaseContract.BasePresenter<MyCollectionContract.View> {
void loadMyCollectArticles();
void refresh();
void loadMore();
void unCollectArticle(int position, Article.DatasBean bean);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionPresenter.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BasePresenter;
import com.lw.wanandroid.bean.Article;
import com.lw.wanandroid.bean.DataResponse;
import com.lw.wanandroid.constant.LoadType;
import com.lw.wanandroid.net.ApiService;
import com.lw.wanandroid.net.RetrofitManager;
import com.lw.wanandroid.utils.ArticleUtils;
import com.lw.wanandroid.utils.RxSchedulers;
import javax.inject.Inject;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/2/2.
*/
public class MyCollectionPresenter extends BasePresenter<MyCollectionContract.View> implements MyCollectionContract.Presenter {
private int mPage;
private boolean mIsRefresh;
@Inject
public MyCollectionPresenter() {
this.mIsRefresh = true;
}
@Override
public void loadMyCollectArticles() {
if (mIsRefresh) mView.showLoading();
RetrofitManager.create(ApiService.class)
.getCollectArticles(mPage)
.compose(RxSchedulers.<DataResponse<Article>>applySchedulers())
.compose(mView.<DataResponse<Article>>bindToLife())
.subscribe(new Consumer<DataResponse<Article>>() {
@Override
public void accept(DataResponse<Article> dataResponse) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_SUCCESS : LoadType.TYPE_LOAD_MORE_SUCCESS;
mView.setMyCollectArticles(dataResponse.getData(), loadType);
}
}, new Consumer<Throwable>() {
@Override
public void accept(Throwable throwable) throws Exception {
int loadType = mIsRefresh ? LoadType.TYPE_REFRESH_ERROR : LoadType.TYPE_LOAD_MORE_ERROR;
mView.setMyCollectArticles(new Article(), loadType);
}
});
}
@Override
public void refresh() {
mPage = 0;
mIsRefresh = true;
loadMyCollectArticles();
}
@Override
public void loadMore() {
mPage++;
mIsRefresh = false;
loadMyCollectArticles();
}
@Override
public void unCollectArticle(final int position, final Article.DatasBean bean) {
ArticleUtils.collectArticle(mView, position, bean);
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyContract.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BaseContract;
/**
* Created by lw on 2018/1/19.
*/
public interface MyContract {
interface View extends BaseContract.BaseView {
}
interface Presenter extends BaseContract.BasePresenter<MyContract.View> {
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyFragment.java
================================================
package com.lw.wanandroid.ui.my;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.TextView;
import com.alibaba.android.arouter.launcher.ARouter;
import com.blankj.utilcode.util.SPUtils;
import com.blankj.utilcode.util.ToastUtils;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseFragment;
import com.lw.wanandroid.constant.Constant;
import com.lw.wanandroid.event.LoginEvent;
import com.lw.wanandroid.net.CookiesManager;
import com.lw.wanandroid.utils.RxBus;
import butterknife.BindView;
import butterknife.OnClick;
import de.hdodenhof.circleimageview.CircleImageView;
import io.reactivex.functions.Consumer;
/**
* Created by lw on 2018/1/18.
*/
public class MyFragment extends BaseFragment<MyPresenter> implements MyContract.View {
@BindView(R.id.civAvatar)
CircleImageView mCivAvatar;
@BindView(R.id.tvNick)
TextView mTvNick;
@BindView(R.id.llLogout)
LinearLayout mLlLogout;
private boolean mIsLogin;
@Override
protected int getLayoutId() {
return R.layout.fragment_my;
}
@Override
protected void initInjector() {
mFragmentComponent.inject(this);
}
@Override
protected void initView(View view) {
setUserStatusInfo();
/**登陆成功重新设置用户新*/
RxBus.getInstance().toFlowable(LoginEvent.class).subscribe(new Consumer<LoginEvent>() {
@Override
public void accept(LoginEvent event) throws Exception {
setUserStatusInfo();
}
});
}
@OnClick({R.id.civAvatar, R.id.tvMyCollection, R.id.tvMyBookmark, R.id.tvSetting, R.id.llLogout})
public void onViewClicked(View view) {
switch (view.getId()) {
case R.id.civAvatar:
if (!mIsLogin) LoginActivity.start();
break;
case R.id.tvMyCollection:
if (mIsLogin) ARouter.getInstance().build("/my/MyCollectionActivity").navigation();
else ToastUtils.showShort(R.string.not_login);
break;
case R.id.tvMyBookmark:
if (mIsLogin) ARouter.getInstance().build("/my/MyBookmarkActivity").navigation();
else ToastUtils.showShort(R.string.not_login);
break;
case R.id.tvSetting:
ARouter.getInstance().build("/setting/SettingActivity").navigation();
break;
case R.id.llLogout:
logout();
break;
}
}
/**
* 退出登陆
*/
private void logout() {
/**设置退出登陆*/
SPUtils.getInstance(Constant.SHARED_NAME).clear();
setUserStatusInfo();
/**清除cookies*/
CookiesManager.clearAllCookies();
/**发送退出登陆的消息*/
RxBus.getInstance().post(new LoginEvent());
}
/**
* 设置用户状态信息
*/
private void setUserStatusInfo() {
mIsLogin = SPUtils.getInstance(Constant.SHARED_NAME).getBoolean(Constant.LOGIN_KEY);
if (mIsLogin) {
mCivAvatar.setImageResource(R.drawable.ic_head_portrait);
mTvNick.setText(SPUtils.getInstance(Constant.SHARED_NAME).getString(Constant.USERNAME_KEY));
mLlLogout.setVisibility(View.VISIBLE);
} else {
mCivAvatar.setImageResource(R.drawable.ic_avatar);
mTvNick.setText(R.string.click_avatar_login);
mLlLogout.setVisibility(View.GONE);
}
}
public static MyFragment newInstance() {
return new MyFragment();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyPresenter.java
================================================
package com.lw.wanandroid.ui.my;
import com.lw.wanandroid.base.BasePresenter;
import javax.inject.Inject;
/**
* Created by lw on 2018/1/19.
*/
public class MyPresenter extends BasePresenter<MyContract.View> implements MyContract.Presenter {
@Inject
public MyPresenter() {
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/my/RegisterActivity.java
================================================
package com.lw.wanandroid.ui.my;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
/**
* Created by lw on 2018/1/24.
*/
@Route(path = "/my/RegisterActivity")
public class RegisterActivity extends BaseActivity {
@Override
protected int getLayoutId() {
return R.layout.activity_register;
}
@Override
protected void initInjector() {
}
@Override
protected void initView() {
}
@Override
protected boolean showHomeAsUp() {
return true;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/setting/SettingActivity.java
================================================
package com.lw.wanandroid.ui.setting;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
/**
* Created by lw on 2018/1/25.
*/
@Route(path = "/setting/SettingActivity")
public class SettingActivity extends BaseActivity {
@Override
protected int getLayoutId() {
return R.layout.activity_setting;
}
@Override
protected void initInjector() {
}
@Override
protected void initView() {
getSupportFragmentManager().beginTransaction()
.replace(R.id.layout_fragment, SettingFragment.newInstance())
.commit();
}
@Override
protected boolean showHomeAsUp() {
return true;
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/setting/SettingFragment.java
================================================
package com.lw.wanandroid.ui.setting;
import android.os.Bundle;
import android.support.v7.preference.Preference;
import android.support.v7.preference.PreferenceFragmentCompat;
import com.alibaba.android.arouter.launcher.ARouter;
import com.lw.wanandroid.R;
/**
* Created by lw on 2017-09-05.
*/
public class SettingFragment extends PreferenceFragmentCompat {
private Preference mSettingAutoUpdate, mCheckUpdate, mAbout, mTestPage;
@Override
public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
addPreferencesFromResource(R.xml.settings_preference_fragment);
mSettingAutoUpdate = findPreference("settingAutoUpdate");
mCheckUpdate = findPreference("checkUpdate");
mAbout = findPreference("about");
mTestPage = findPreference("testPage");
mTestPage.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() {
@Override
public boolean onPreferenceClick(Preference preference) {
ARouter.getInstance().build("/setting/TestPageActivity").navigation();
return false;
}
});
}
public static SettingFragment newInstance() {
return new SettingFragment();
}
}
================================================
FILE: app/src/main/java/com/lw/wanandroid/ui/setting/TestPageActivity.java
================================================
package com.lw.wanandroid.ui.setting;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import com.alibaba.android.arouter.facade.annotation.Route;
import com.lw.wanandroid.R;
import com.lw.wanandroid.base.BaseActivity;
import java.io.IOException;
import java.util.concurrent.TimeUnit;
import butterknife.BindView;
import butterknife.OnClick;
import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
/**
* Created by lw on 2018/2/12.
*/
@Route(path = "/setting/TestPageActivity")
public class TestPageActivity extends BaseActivity {
private static final String TAG = "TestPageActivity";
@BindView(R.id.btnTest1)
Button mBtnTest1;
@BindView(R.id.btnTest2)
Button mBtnTest2;
@BindView(R.id.btnTest3)
Button mBtnTest3;
OkHttpClient mOkHttpClient = new OkHttpClient.Builder().readTimeout(5, TimeUnit.SECONDS).build();
@Override
protected int getLayoutId() {
return R.layout.activity_test_page;
}
@Override
protected void initInjector() {
}
@Override
protected void initView() {
}
@Override
protected boolean showHomeAsUp() {
return true;
}
@OnClick({R.id.btnTest1, R.id.btnTest2, R.id.btnTest3})
public void onViewClicked(View view) {
switch (view.getId()) {
case R.id.btnTest1:
test1();
break;
case R.id.btnTest2:
break;
case R.id.btnTest3:
break;
}
}
private void test1() {
Request request = new Request.Builder().url("http://www.baidu.com").build();
Call call = mOkHttpClient.newCall(request);
try {
//Response response = call.execute();
//L
gitextract_ys2tdhgz/ ├── .gitignore ├── .idea/ │ ├── compiler.xml │ ├── copyright/ │ │ └── profiles_settings.xml │ ├── encodings.xml │ ├── gradle.xml │ ├── misc.xml │ ├── modules.xml │ ├── runConfigurations.xml │ └── vcs.xml ├── README.md ├── app/ │ ├── .gitignore │ ├── build.gradle │ ├── proguard-rules.pro │ ├── release/ │ │ ├── app-release.apk │ │ └── output.json │ ├── src/ │ │ ├── androidTest/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── lw/ │ │ │ └── wanandroid/ │ │ │ └── ExampleInstrumentedTest.java │ │ ├── main/ │ │ │ ├── AndroidManifest.xml │ │ │ ├── java/ │ │ │ │ └── com/ │ │ │ │ └── lw/ │ │ │ │ └── wanandroid/ │ │ │ │ ├── MainActivity.java │ │ │ │ ├── base/ │ │ │ │ │ ├── App.java │ │ │ │ │ ├── BaseActivity.java │ │ │ │ │ ├── BaseContract.java │ │ │ │ │ ├── BaseFragment.java │ │ │ │ │ └── BasePresenter.java │ │ │ │ ├── bean/ │ │ │ │ │ ├── Article.java │ │ │ │ │ ├── Banner.java │ │ │ │ │ ├── DataResponse.java │ │ │ │ │ ├── Friend.java │ │ │ │ │ ├── HotKey.java │ │ │ │ │ ├── KnowledgeSystem.java │ │ │ │ │ └── User.java │ │ │ │ ├── constant/ │ │ │ │ │ ├── Constant.java │ │ │ │ │ └── LoadType.java │ │ │ │ ├── db/ │ │ │ │ │ ├── AppDatabase.java │ │ │ │ │ └── HistoryModel.java │ │ │ │ ├── di/ │ │ │ │ │ ├── component/ │ │ │ │ │ │ ├── ActivityComponent.java │ │ │ │ │ │ ├── ApplicationComponent.java │ │ │ │ │ │ ├── FragmentComponent.java │ │ │ │ │ │ └── ServiceComponent.java │ │ │ │ │ ├── module/ │ │ │ │ │ │ ├── ActivityModule.java │ │ │ │ │ │ ├── ApplicationModule.java │ │ │ │ │ │ ├── FragmentModule.java │ │ │ │ │ │ └── ServiceModule.java │ │ │ │ │ └── scope/ │ │ │ │ │ ├── ContextLife.java │ │ │ │ │ ├── PerActivity.java │ │ │ │ │ ├── PerApp.java │ │ │ │ │ ├── PerFragment.java │ │ │ │ │ └── PerService.java │ │ │ │ ├── event/ │ │ │ │ │ └── LoginEvent.java │ │ │ │ ├── net/ │ │ │ │ │ ├── ApiService.java │ │ │ │ │ ├── CookiesManager.java │ │ │ │ │ ├── OkHttpCookies.java │ │ │ │ │ ├── PersistentCookieStore.java │ │ │ │ │ └── RetrofitManager.java │ │ │ │ ├── ui/ │ │ │ │ │ ├── article/ │ │ │ │ │ │ ├── ArticleAdapter.java │ │ │ │ │ │ ├── ArticleContentActivity.java │ │ │ │ │ │ ├── ArticleContentContract.java │ │ │ │ │ │ ├── ArticleContentPresenter.java │ │ │ │ │ │ ├── ArticleListContract.java │ │ │ │ │ │ ├── ArticleListFragment.java │ │ │ │ │ │ ├── ArticleListPresenter.java │ │ │ │ │ │ ├── ArticleTypeActivity.java │ │ │ │ │ │ └── ArticleTypeFragmentPagerAdapter.java │ │ │ │ │ ├── home/ │ │ │ │ │ │ ├── HomeContract.java │ │ │ │ │ │ ├── HomeFragment.java │ │ │ │ │ │ └── HomePresenter.java │ │ │ │ │ ├── hotsearch/ │ │ │ │ │ │ ├── CommonHotAdapter.java │ │ │ │ │ │ ├── HistoryAdapter.java │ │ │ │ │ │ ├── HotAdapter.java │ │ │ │ │ │ ├── HotContract.java │ │ │ │ │ │ ├── HotFragment.java │ │ │ │ │ │ ├── HotPresenter.java │ │ │ │ │ │ ├── SearchActivity.java │ │ │ │ │ │ ├── SearchContract.java │ │ │ │ │ │ └── SearchPresenter.java │ │ │ │ │ ├── knowledgesystem/ │ │ │ │ │ │ ├── KnowledgeSystemAdapter.java │ │ │ │ │ │ ├── KnowledgeSystemContract.java │ │ │ │ │ │ ├── KnowledgeSystemFragment.java │ │ │ │ │ │ └── KnowledgeSystemPresenter.java │ │ │ │ │ ├── my/ │ │ │ │ │ │ ├── LoginActivity.java │ │ │ │ │ │ ├── LoginContract.java │ │ │ │ │ │ ├── LoginPresenter.java │ │ │ │ │ │ ├── MyBookmarkActivity.java │ │ │ │ │ │ ├── MyBookmarkContract.java │ │ │ │ │ │ ├── MyBookmarkPresenter.java │ │ │ │ │ │ ├── MyCollectionActivity.java │ │ │ │ │ │ ├── MyCollectionContract.java │ │ │ │ │ │ ├── MyCollectionPresenter.java │ │ │ │ │ │ ├── MyContract.java │ │ │ │ │ │ ├── MyFragment.java │ │ │ │ │ │ ├── MyPresenter.java │ │ │ │ │ │ └── RegisterActivity.java │ │ │ │ │ └── setting/ │ │ │ │ │ ├── SettingActivity.java │ │ │ │ │ ├── SettingFragment.java │ │ │ │ │ └── TestPageActivity.java │ │ │ │ └── utils/ │ │ │ │ ├── ArticleUtils.java │ │ │ │ ├── GlideImageLoader.java │ │ │ │ ├── GsonUtils.java │ │ │ │ ├── RxBus.java │ │ │ │ └── RxSchedulers.java │ │ │ └── res/ │ │ │ ├── drawable/ │ │ │ │ ├── ic_action_browser.xml │ │ │ │ ├── ic_action_hot.xml │ │ │ │ ├── ic_action_like.xml │ │ │ │ ├── ic_action_no_like.xml │ │ │ │ ├── ic_action_search.xml │ │ │ │ ├── ic_action_share.xml │ │ │ │ ├── ic_action_white_like.xml │ │ │ │ ├── ic_chevron_right_black_24dp.xml │ │ │ │ ├── ic_dashboard_black_24dp.xml │ │ │ │ ├── ic_home_black_24dp.xml │ │ │ │ ├── ic_my_black_24dp.xml │ │ │ │ ├── item_selector.xml │ │ │ │ └── item_selector_hot.xml │ │ │ ├── drawable-v21/ │ │ │ │ └── item_selector_hot.xml │ │ │ ├── layout/ │ │ │ │ ├── activity_article_content.xml │ │ │ │ ├── activity_article_type.xml │ │ │ │ ├── activity_login.xml │ │ │ │ ├── activity_main.xml │ │ │ │ ├── activity_my_bookmark.xml │ │ │ │ ├── activity_my_collection.xml │ │ │ │ ├── activity_register.xml │ │ │ │ ├── activity_search.xml │ │ │ │ ├── activity_setting.xml │ │ │ │ ├── activity_test_page.xml │ │ │ │ ├── fragment_article_list.xml │ │ │ │ ├── fragment_home.xml │ │ │ │ ├── fragment_hot.xml │ │ │ │ ├── fragment_knowledge_system.xml │ │ │ │ ├── fragment_my.xml │ │ │ │ ├── item_article.xml │ │ │ │ ├── item_history.xml │ │ │ │ ├── item_hot.xml │ │ │ │ ├── item_knowledge_system.xml │ │ │ │ ├── layout_empty_view.xml │ │ │ │ ├── layout_error_view.xml │ │ │ │ ├── layout_home_banner_head.xml │ │ │ │ ├── layout_hot_head.xml │ │ │ │ └── layout_search_head.xml │ │ │ ├── menu/ │ │ │ │ ├── menu_content.xml │ │ │ │ ├── menu_main.xml │ │ │ │ ├── menu_search.xml │ │ │ │ ├── menu_type_content.xml │ │ │ │ └── navigation.xml │ │ │ ├── values/ │ │ │ │ ├── colors.xml │ │ │ │ ├── dimens.xml │ │ │ │ ├── fonts.xml │ │ │ │ ├── strings.xml │ │ │ │ └── styles.xml │ │ │ └── xml/ │ │ │ └── settings_preference_fragment.xml │ │ └── test/ │ │ └── java/ │ │ └── com/ │ │ └── lw/ │ │ └── wanandroid/ │ │ └── ExampleUnitTest.java │ └── wanandroid.jks ├── build.gradle ├── config.gradle ├── gradle/ │ └── wrapper/ │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradle.properties ├── gradlew ├── gradlew.bat └── settings.gradle
SYMBOL INDEX (675 symbols across 79 files)
FILE: app/src/androidTest/java/com/lw/wanandroid/ExampleInstrumentedTest.java
class ExampleInstrumentedTest (line 17) | @RunWith(AndroidJUnit4.class)
method useAppContext (line 19) | @Test
FILE: app/src/main/java/com/lw/wanandroid/MainActivity.java
class MainActivity (line 21) | @Route(path = "/wanandroid/MainActivity")
method getLayoutId (line 29) | @Override
method initInjector (line 34) | @Override
method initView (line 38) | @Override
method onNavigationItemSelected (line 61) | @Override
method onCreateOptionsMenu (line 83) | @Override
method onOptionsItemSelected (line 89) | @Override
method onKeyDown (line 101) | @Override
FILE: app/src/main/java/com/lw/wanandroid/base/App.java
class App (line 20) | public class App extends Application {
method onCreate (line 24) | @Override
method intARouter (line 41) | private void intARouter() {
method initApplicationComponent (line 52) | private void initApplicationComponent() {
method getApplicationComponent (line 58) | public ApplicationComponent getApplicationComponent() {
method getAppContext (line 62) | public static Context getAppContext() {
method getInstance (line 66) | public static App getInstance() {
FILE: app/src/main/java/com/lw/wanandroid/base/BaseActivity.java
class BaseActivity (line 43) | public abstract class BaseActivity<T extends BaseContract.BasePresenter>...
method getLayoutId (line 52) | protected abstract int getLayoutId();
method initInjector (line 54) | protected abstract void initInjector();
method initView (line 56) | protected abstract void initView();
method showHomeAsUp (line 63) | protected boolean showHomeAsUp() {
method onCreate (line 67) | @Override
method onDestroy (line 83) | @Override
method showLoading (line 91) | @Override
method hideLoading (line 96) | @Override
method showSuccess (line 101) | @Override
method showFaild (line 106) | @Override
method showNoNet (line 111) | @Override
method onRetry (line 116) | @Override
method bindToLife (line 121) | @Override
method onOptionsItemSelected (line 126) | @Override
method getSupportDelegate (line 143) | @Override
method extraTransaction (line 152) | @Override
method onPostCreate (line 158) | @Override
method dispatchTouchEvent (line 168) | @Override
method onBackPressed (line 176) | @Override
method onBackPressedSupport (line 185) | @Override
method getFragmentAnimator (line 195) | @Override
method setFragmentAnimator (line 204) | @Override
method onCreateFragmentAnimator (line 218) | @Override
method post (line 230) | @Override
method setToolbarTitle (line 235) | protected void setToolbarTitle(String title) {
method setLoadDataResult (line 247) | protected void setLoadDataResult(BaseQuickAdapter baseQuickAdapter, Sw...
method loadRootFragment (line 272) | public void loadRootFragment(int containerId, @NonNull ISupportFragmen...
method start (line 276) | public void start(ISupportFragment toFragment) {
method start (line 283) | public void start(ISupportFragment toFragment, @ISupportFragment.Launc...
method startWithPopTo (line 294) | public void startWithPopTo(ISupportFragment toFragment, Class<?> targe...
method pop (line 301) | public void pop() {
method popTo (line 309) | public void popTo(Class<?> targetFragmentClass, boolean includeTargetF...
method popTo (line 317) | public void popTo(Class<?> targetFragmentClass, boolean includeTargetF...
method popTo (line 321) | public void popTo(Class<?> targetFragmentClass, boolean includeTargetF...
method getTopFragment (line 328) | public ISupportFragment getTopFragment() {
method findFragment (line 335) | public <T extends ISupportFragment> T findFragment(Class<T> fragmentCl...
method loadMultipleRootFragment (line 342) | public void loadMultipleRootFragment(int containerId, int showPosition...
method showHideFragment (line 354) | public void showHideFragment(ISupportFragment showFragment) {
method showHideFragment (line 361) | public void showHideFragment(ISupportFragment showFragment, ISupportFr...
method initActivityComponent (line 368) | private void initActivityComponent() {
method initToolBar (line 378) | private void initToolBar() {
method attachView (line 395) | private void attachView() {
method detachView (line 404) | private void detachView() {
FILE: app/src/main/java/com/lw/wanandroid/base/BaseContract.java
type BaseContract (line 10) | public interface BaseContract {
type BasePresenter (line 12) | interface BasePresenter<T extends BaseContract.BaseView> {
method attachView (line 14) | void attachView(T view);
method detachView (line 16) | void detachView();
type BaseView (line 20) | interface BaseView {
method showLoading (line 23) | void showLoading();
method hideLoading (line 26) | void hideLoading();
method showSuccess (line 29) | void showSuccess(String message);
method showFaild (line 32) | void showFaild(String message);
method showNoNet (line 35) | void showNoNet();
method onRetry (line 38) | void onRetry();
method bindToLife (line 46) | <T> LifecycleTransformer<T> bindToLife();
FILE: app/src/main/java/com/lw/wanandroid/base/BaseFragment.java
class BaseFragment (line 43) | public abstract class BaseFragment<T extends BaseContract.BasePresenter>...
method getLayoutId (line 52) | protected abstract int getLayoutId();
method initInjector (line 54) | protected abstract void initInjector();
method initView (line 56) | protected abstract void initView(View view);
method onCreate (line 58) | @Override
method onSaveInstanceState (line 79) | @Override
method onCreateView (line 85) | @Nullable
method onDestroy (line 94) | @Override
method showLoading (line 102) | @Override
method hideLoading (line 107) | @Override
method showSuccess (line 112) | @Override
method showFaild (line 117) | @Override
method showNoNet (line 122) | @Override
method onRetry (line 127) | @Override
method bindToLife (line 132) | @Override
method setLoadDataResult (line 145) | protected void setLoadDataResult(BaseQuickAdapter baseQuickAdapter, Sw...
method initFragmentComponent (line 171) | private void initFragmentComponent() {
method attachView (line 181) | private void attachView() {
method detachView (line 190) | private void detachView() {
method inflaterView (line 203) | private void inflaterView(LayoutInflater inflater, @Nullable ViewGroup...
method getSupportDelegate (line 212) | @Override
method extraTransaction (line 221) | @Override
method onAttach (line 226) | @Override
method onCreateAnimation (line 233) | @Override
method onActivityCreated (line 238) | @Override
method onResume (line 244) | @Override
method onPause (line 250) | @Override
method onDestroyView (line 256) | @Override
method onHiddenChanged (line 263) | @Override
method setUserVisibleHint (line 269) | @Override
method enqueueAction (line 284) | @Deprecated
method post (line 297) | @Override
method onEnterAnimationEnd (line 306) | @Override
method onLazyInitView (line 317) | @Override
method onSupportVisible (line 328) | @Override
method onSupportInvisible (line 338) | @Override
method isSupportVisible (line 346) | @Override
method onCreateFragmentAnimator (line 355) | @Override
method getFragmentAnimator (line 365) | @Override
method setFragmentAnimator (line 373) | @Override
method onBackPressedSupport (line 383) | @Override
method setFragmentResult (line 395) | @Override
method onFragmentResult (line 407) | @Override
method onNewBundle (line 421) | @Override
method putNewBundle (line 431) | @Override
method hideSoftInput (line 443) | protected void hideSoftInput() {
method showSoftInput (line 450) | protected void showSoftInput(final View view) {
method loadRootFragment (line 460) | public void loadRootFragment(int containerId, ISupportFragment toFragm...
method loadRootFragment (line 464) | public void loadRootFragment(int containerId, ISupportFragment toFragm...
method start (line 468) | public void start(ISupportFragment toFragment) {
method start (line 475) | public void start(final ISupportFragment toFragment, @LaunchMode int l...
method startForResult (line 482) | public void startForResult(ISupportFragment toFragment, int requestCod...
method startWithPop (line 489) | public void startWithPop(ISupportFragment toFragment) {
method startWithPopTo (line 498) | public void startWithPopTo(ISupportFragment toFragment, Class<?> targe...
method replaceFragment (line 502) | public void replaceFragment(ISupportFragment toFragment, boolean addTo...
method pop (line 506) | public void pop() {
method popTo (line 519) | public void popTo(Class<?> targetFragmentClass, boolean includeTargetF...
method findChildFragment (line 526) | public <T extends ISupportFragment> T findChildFragment(Class<T> fragm...
FILE: app/src/main/java/com/lw/wanandroid/base/BasePresenter.java
class BasePresenter (line 9) | public class BasePresenter<T extends BaseContract.BaseView> implements B...
method attachView (line 13) | @Override
method detachView (line 18) | @Override
FILE: app/src/main/java/com/lw/wanandroid/bean/Article.java
class Article (line 9) | public class Article {
method getOffset (line 19) | public int getOffset() {
method setOffset (line 23) | public void setOffset(int offset) {
method getSize (line 27) | public int getSize() {
method setSize (line 31) | public void setSize(int size) {
method getTotal (line 35) | public int getTotal() {
method setTotal (line 39) | public void setTotal(int total) {
method getPageCount (line 43) | public int getPageCount() {
method setPageCount (line 47) | public void setPageCount(int pageCount) {
method getCurPage (line 51) | public int getCurPage() {
method setCurPage (line 55) | public void setCurPage(int curPage) {
method isOver (line 59) | public boolean isOver() {
method setOver (line 63) | public void setOver(boolean over) {
method getDatas (line 67) | public List<DatasBean> getDatas() {
method setDatas (line 71) | public void setDatas(List<DatasBean> datas) {
class DatasBean (line 75) | public static class DatasBean {
method getId (line 110) | public int getId() {
method setId (line 114) | public void setId(int id) {
method getTitle (line 118) | public String getTitle() {
method setTitle (line 122) | public void setTitle(String title) {
method getChapterId (line 126) | public int getChapterId() {
method setChapterId (line 130) | public void setChapterId(int chapterId) {
method getChapterName (line 134) | public String getChapterName() {
method setChapterName (line 138) | public void setChapterName(String chapterName) {
method getEnvelopePic (line 142) | public String getEnvelopePic() {
method setEnvelopePic (line 146) | public void setEnvelopePic(String envelopePic) {
method getLink (line 150) | public String getLink() {
method setLink (line 154) | public void setLink(String link) {
method getAuthor (line 158) | public String getAuthor() {
method setAuthor (line 162) | public void setAuthor(String author) {
method getOrigin (line 166) | public String getOrigin() {
method setOrigin (line 170) | public void setOrigin(String origin) {
method getPublishTime (line 174) | public long getPublishTime() {
method setPublishTime (line 178) | public void setPublishTime(long publishTime) {
method getZan (line 182) | public String getZan() {
method setZan (line 186) | public void setZan(String zan) {
method getDesc (line 190) | public String getDesc() {
method setDesc (line 194) | public void setDesc(String desc) {
method getVisible (line 198) | public int getVisible() {
method setVisible (line 202) | public void setVisible(int visible) {
method getNiceDate (line 206) | public String getNiceDate() {
method setNiceDate (line 210) | public void setNiceDate(String niceDate) {
method getCourseId (line 214) | public int getCourseId() {
method setCourseId (line 218) | public void setCourseId(int courseId) {
method isCollect (line 222) | public boolean isCollect() {
method setCollect (line 226) | public void setCollect(boolean collect) {
FILE: app/src/main/java/com/lw/wanandroid/bean/Banner.java
class Banner (line 7) | public class Banner {
method getId (line 17) | public int getId() {
method setId (line 21) | public void setId(int id) {
method getUrl (line 25) | public String getUrl() {
method setUrl (line 29) | public void setUrl(String url) {
method getImagePath (line 33) | public String getImagePath() {
method setImagePath (line 37) | public void setImagePath(String imagePath) {
method getTitle (line 41) | public String getTitle() {
method setTitle (line 45) | public void setTitle(String title) {
method getDesc (line 49) | public String getDesc() {
method setDesc (line 53) | public void setDesc(String desc) {
method getIsVisible (line 57) | public int getIsVisible() {
method setIsVisible (line 61) | public void setIsVisible(int isVisible) {
method getOrder (line 65) | public int getOrder() {
method setOrder (line 69) | public void setOrder(int order) {
method getType (line 73) | public int getType() {
method setType (line 77) | public void setType(int type) {
FILE: app/src/main/java/com/lw/wanandroid/bean/DataResponse.java
class DataResponse (line 7) | public class DataResponse<T> {
method getErrorCode (line 12) | public int getErrorCode() {
method setErrorCode (line 16) | public void setErrorCode(int errorCode) {
method getErrorMsg (line 20) | public Object getErrorMsg() {
method setErrorMsg (line 24) | public void setErrorMsg(Object errorMsg) {
method getData (line 28) | public T getData() {
method setData (line 32) | public void setData(T data) {
FILE: app/src/main/java/com/lw/wanandroid/bean/Friend.java
class Friend (line 7) | public class Friend {
method getId (line 14) | public int getId() {
method setId (line 18) | public void setId(int id) {
method getName (line 22) | public String getName() {
method setName (line 26) | public void setName(String name) {
method getLink (line 30) | public String getLink() {
method setLink (line 34) | public void setLink(String link) {
method getVisible (line 38) | public int getVisible() {
method setVisible (line 42) | public void setVisible(int visible) {
method getOrder (line 46) | public int getOrder() {
method setOrder (line 50) | public void setOrder(int order) {
FILE: app/src/main/java/com/lw/wanandroid/bean/HotKey.java
class HotKey (line 7) | public class HotKey {
method getId (line 14) | public int getId() {
method setId (line 18) | public void setId(int id) {
method getName (line 22) | public String getName() {
method setName (line 26) | public void setName(String name) {
method getLink (line 30) | public String getLink() {
method setLink (line 34) | public void setLink(String link) {
method getVisible (line 38) | public int getVisible() {
method setVisible (line 42) | public void setVisible(int visible) {
method getOrder (line 46) | public int getOrder() {
method setOrder (line 50) | public void setOrder(int order) {
FILE: app/src/main/java/com/lw/wanandroid/bean/KnowledgeSystem.java
class KnowledgeSystem (line 15) | @Route(path = "/service/json")
method getId (line 26) | public int getId() {
method setId (line 30) | public void setId(int id) {
method getName (line 34) | public String getName() {
method setName (line 38) | public void setName(String name) {
method getCourseId (line 42) | public int getCourseId() {
method setCourseId (line 46) | public void setCourseId(int courseId) {
method getParentChapterId (line 50) | public int getParentChapterId() {
method setParentChapterId (line 54) | public void setParentChapterId(int parentChapterId) {
method getOrder (line 58) | public int getOrder() {
method setOrder (line 62) | public void setOrder(int order) {
method getVisible (line 66) | public int getVisible() {
method setVisible (line 70) | public void setVisible(int visible) {
method getChildren (line 74) | public List<ChildrenBean> getChildren() {
method setChildren (line 78) | public void setChildren(List<ChildrenBean> children) {
method json2Object (line 82) | @Override
method object2Json (line 87) | @Override
method parseObject (line 92) | @Override
method init (line 97) | @Override
class ChildrenBean (line 102) | public static class ChildrenBean implements SerializationService {
method getId (line 121) | public int getId() {
method setId (line 125) | public void setId(int id) {
method getName (line 129) | public String getName() {
method setName (line 133) | public void setName(String name) {
method getCourseId (line 137) | public int getCourseId() {
method setCourseId (line 141) | public void setCourseId(int courseId) {
method getParentChapterId (line 145) | public int getParentChapterId() {
method setParentChapterId (line 149) | public void setParentChapterId(int parentChapterId) {
method getOrder (line 153) | public int getOrder() {
method setOrder (line 157) | public void setOrder(int order) {
method getVisible (line 161) | public int getVisible() {
method setVisible (line 165) | public void setVisible(int visible) {
method getChildren (line 169) | public List<?> getChildren() {
method setChildren (line 173) | public void setChildren(List<ChildrenBean> children) {
method json2Object (line 177) | @Override
method object2Json (line 182) | @Override
method parseObject (line 187) | @Override
method init (line 192) | @Override
method ChildrenBean (line 197) | public ChildrenBean(int id, String name) {
FILE: app/src/main/java/com/lw/wanandroid/bean/User.java
class User (line 9) | public class User {
method getId (line 17) | public int getId() {
method setId (line 21) | public void setId(int id) {
method getUsername (line 25) | public String getUsername() {
method setUsername (line 29) | public void setUsername(String username) {
method getPassword (line 33) | public String getPassword() {
method setPassword (line 37) | public void setPassword(String password) {
method getIcon (line 41) | public String getIcon() {
method setIcon (line 45) | public void setIcon(String icon) {
method getType (line 49) | public int getType() {
method setType (line 53) | public void setType(int type) {
method getCollectIds (line 57) | public List<Integer> getCollectIds() {
method setCollectIds (line 61) | public void setCollectIds(List<Integer> collectIds) {
FILE: app/src/main/java/com/lw/wanandroid/constant/Constant.java
class Constant (line 7) | public class Constant {
FILE: app/src/main/java/com/lw/wanandroid/constant/LoadType.java
class LoadType (line 12) | public class LoadType {
FILE: app/src/main/java/com/lw/wanandroid/db/AppDatabase.java
class AppDatabase (line 8) | @Database(name = AppDatabase.NAME, version = AppDatabase.VERSION)
FILE: app/src/main/java/com/lw/wanandroid/db/HistoryModel.java
class HistoryModel (line 13) | @Table(database = AppDatabase.class)
method getId (line 22) | public long getId() {
method setId (line 26) | public void setId(long id) {
method getName (line 30) | public String getName() {
method setName (line 34) | public void setName(String name) {
method getDate (line 38) | public Date getDate() {
method setDate (line 42) | public void setDate(Date date) {
FILE: app/src/main/java/com/lw/wanandroid/di/component/ActivityComponent.java
type ActivityComponent (line 20) | @PerActivity
method getActivityContext (line 24) | @ContextLife("Activity")
method getApplicationContext (line 27) | @ContextLife("Application")
method getActivity (line 30) | Activity getActivity();
method inject (line 32) | void inject(SearchActivity activity);
method inject (line 34) | void inject(LoginActivity activity);
method inject (line 36) | void inject(ArticleContentActivity activity);
method inject (line 38) | void inject(MyCollectionActivity activity);
method inject (line 40) | void inject(MyBookmarkActivity activity);
FILE: app/src/main/java/com/lw/wanandroid/di/component/ApplicationComponent.java
type ApplicationComponent (line 15) | @PerApp
method getApplication (line 18) | @ContextLife("Application")
FILE: app/src/main/java/com/lw/wanandroid/di/component/FragmentComponent.java
type FragmentComponent (line 20) | @PerFragment
method getActivityContext (line 23) | @ContextLife("Activity")
method getApplicationContext (line 26) | @ContextLife("Application")
method getActivity (line 29) | Activity getActivity();
method inject (line 31) | void inject(HomeFragment fragment);
method inject (line 33) | void inject(KnowledgeSystemFragment fragment);
method inject (line 35) | void inject(MyFragment fragment);
method inject (line 37) | void inject(ArticleListFragment fragment);
method inject (line 39) | void inject(HotFragment fragment);
FILE: app/src/main/java/com/lw/wanandroid/di/component/ServiceComponent.java
type ServiceComponent (line 15) | @PerService
method getServiceContext (line 18) | @ContextLife("Service")
method getApplicationContext (line 21) | @ContextLife("Application")
FILE: app/src/main/java/com/lw/wanandroid/di/module/ActivityModule.java
class ActivityModule (line 15) | @Module
method ActivityModule (line 19) | public ActivityModule(Activity activity) {
method provideActivityContext (line 23) | @Provides
method provideActivity (line 30) | @Provides
FILE: app/src/main/java/com/lw/wanandroid/di/module/ApplicationModule.java
class ApplicationModule (line 16) | @Module
method ApplicationModule (line 20) | public ApplicationModule(App application) {
method provideApplicationContext (line 24) | @Provides
FILE: app/src/main/java/com/lw/wanandroid/di/module/FragmentModule.java
class FragmentModule (line 16) | @Module
method FragmentModule (line 20) | public FragmentModule(Fragment fragment) {
method provideActivityContext (line 24) | @Provides
method provideActivity (line 31) | @Provides
method provideFragment (line 37) | @Provides
FILE: app/src/main/java/com/lw/wanandroid/di/module/ServiceModule.java
class ServiceModule (line 15) | @Module
method ServiceModule (line 19) | public ServiceModule(Service service) {
method ProvideServiceContext (line 23) | @Provides
FILE: app/src/main/java/com/lw/wanandroid/event/LoginEvent.java
class LoginEvent (line 7) | public class LoginEvent {
FILE: app/src/main/java/com/lw/wanandroid/net/ApiService.java
type ApiService (line 25) | public interface ApiService {
method getHomeArticles (line 32) | @GET("/article/list/{page}/json")
method getHomeBanners (line 40) | @GET("/banner/json")
method getKnowledgeSystems (line 49) | @GET("/tree/json")
method getKnowledgeSystemArticles (line 59) | @GET("/article/list/{page}/json")
method getHotFriends (line 67) | @GET("/friend/json")
method getHotKeys (line 74) | @GET("/hotkey/json")
method getSearchArticles (line 84) | @POST("/article/query/{page}/json")
method login (line 96) | @POST("/user/login")
method register (line 108) | @POST("/user/register")
method addCollectArticle (line 118) | @POST("/lg/collect/{id}/json")
method addCollectOutsideArticle (line 129) | @POST("/lg/collect/add/json")
method removeCollectArticle (line 140) | @POST("/lg/uncollect/{id}/json")
method getCollectArticles (line 151) | @GET("/lg/collect/list/{page}/json")
method getBookmarks (line 158) | @GET("/lg/collect/usertools/json")
method editBookmark (line 165) | @POST("/lg/collect/usertools/json")
method delBookmark (line 173) | @POST("/lg/collect/usertools/json")
FILE: app/src/main/java/com/lw/wanandroid/net/CookiesManager.java
class CookiesManager (line 13) | public class CookiesManager implements CookieJar {
method saveFromResponse (line 17) | @Override
method loadForRequest (line 26) | @Override
method clearAllCookies (line 35) | public static void clearAllCookies() {
method clearCookies (line 46) | public static boolean clearCookies(HttpUrl url, Cookie cookie) {
method getCookies (line 55) | public static List<Cookie> getCookies() {
FILE: app/src/main/java/com/lw/wanandroid/net/OkHttpCookies.java
class OkHttpCookies (line 14) | public class OkHttpCookies implements Serializable {
method OkHttpCookies (line 18) | public OkHttpCookies(Cookie cookies) {
method getCookies (line 22) | public Cookie getCookies() {
method writeObject (line 30) | private void writeObject(ObjectOutputStream out) throws IOException {
method readObject (line 42) | private void readObject(ObjectInputStream in) throws IOException, Clas...
FILE: app/src/main/java/com/lw/wanandroid/net/PersistentCookieStore.java
class PersistentCookieStore (line 28) | public class PersistentCookieStore {
method PersistentCookieStore (line 34) | public PersistentCookieStore() {
method getCookieToken (line 57) | protected String getCookieToken(Cookie cookie) {
method add (line 61) | public void add(HttpUrl url, Cookie cookie) {
method get (line 83) | public List<Cookie> get(HttpUrl url) {
method removeAll (line 90) | public boolean removeAll() {
method remove (line 98) | public boolean remove(HttpUrl url, Cookie cookie) {
method getCookies (line 117) | public List<Cookie> getCookies() {
method encodeCookie (line 131) | protected String encodeCookie(OkHttpCookies cookie) {
method decodeCookie (line 152) | protected Cookie decodeCookie(String cookieString) {
method byteArrayToHexString (line 174) | protected String byteArrayToHexString(byte[] bytes) {
method hexStringToByteArray (line 192) | protected byte[] hexStringToByteArray(String hexString) {
FILE: app/src/main/java/com/lw/wanandroid/net/RetrofitManager.java
class RetrofitManager (line 25) | public class RetrofitManager {
method intercept (line 45) | @Override
method intercept (line 74) | @Override
method getOkHttpClient (line 87) | private static OkHttpClient getOkHttpClient() {
method create (line 114) | public static <T> T create(Class<T> clazz) {
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleAdapter.java
class ArticleAdapter (line 16) | public class ArticleAdapter extends BaseQuickAdapter<Article.DatasBean, ...
method ArticleAdapter (line 20) | @Inject
method convert (line 25) | @Override
method setChapterNameVisible (line 39) | public void setChapterNameVisible(boolean chapterNameVisible) {
method isMyColection (line 43) | public void isMyColection(boolean isMyColection) {
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentActivity.java
class ArticleContentActivity (line 25) | @Route(path = "/article/ArticleContentActivity")
method getLayoutId (line 38) | @Override
method initInjector (line 43) | @Override
method initView (line 48) | @Override
method showHomeAsUp (line 60) | @Override
method onCreateOptionsMenu (line 65) | @Override
method onOptionsItemSelected (line 71) | @Override
method start (line 89) | public static void start(int id, String url, String title, String auth...
method onReceivedTitle (line 99) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentContract.java
type ArticleContentContract (line 11) | public interface ArticleContentContract {
type View (line 12) | interface View extends BaseContract.BaseView {
type Presenter (line 16) | interface Presenter extends BaseContract.BasePresenter<ArticleContentC...
method collectArticle (line 17) | void collectArticle(int id);
method collectOutsideArticle (line 19) | void collectOutsideArticle(String title, String author, String link);
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentPresenter.java
class ArticleContentPresenter (line 22) | public class ArticleContentPresenter extends BasePresenter<ArticleConten...
method ArticleContentPresenter (line 23) | @Inject
method collectArticle (line 27) | @Override
method collectOutsideArticle (line 54) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleListContract.java
type ArticleListContract (line 11) | public interface ArticleListContract {
type View (line 12) | interface View extends BaseContract.BaseView {
method setKnowledgeSystemArticles (line 14) | void setKnowledgeSystemArticles(Article article, @LoadType.checker i...
method collectArticleSuccess (line 16) | void collectArticleSuccess(int position, Article.DatasBean bean);
type Presenter (line 20) | interface Presenter extends BaseContract.BasePresenter<ArticleListCont...
method loadKnowledgeSystemArticles (line 21) | void loadKnowledgeSystemArticles(int cid);
method refresh (line 23) | void refresh();
method loadMore (line 25) | void loadMore();
method collectArticle (line 27) | void collectArticle(int position, Article.DatasBean bean);
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleListFragment.java
class ArticleListFragment (line 25) | @Route(path = "/article/ArticleListFragment")
method getLayoutId (line 37) | @Override
method initInjector (line 42) | @Override
method initView (line 47) | @Override
method showLoading (line 75) | @Override
method onRefresh (line 80) | @Override
method onItemChildClick (line 85) | @Override
method onItemClick (line 92) | @Override
method onLoadMoreRequested (line 99) | @Override
method setKnowledgeSystemArticles (line 104) | @Override
method collectArticleSuccess (line 109) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleListPresenter.java
class ArticleListPresenter (line 24) | public class ArticleListPresenter extends BasePresenter<ArticleListContr...
method ArticleListPresenter (line 29) | @Inject
method loadKnowledgeSystemArticles (line 34) | @Override
method refresh (line 55) | @Override
method loadMore (line 62) | @Override
method collectArticle (line 69) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleTypeActivity.java
class ArticleTypeActivity (line 23) | @Route(path = "/article/ArticleTypeActivity")
method getLayoutId (line 36) | @Override
method initInjector (line 41) | @Override
method initView (line 46) | @Override
method showHomeAsUp (line 54) | @Override
method onCreateOptionsMenu (line 59) | @Override
method onOptionsItemSelected (line 65) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/article/ArticleTypeFragmentPagerAdapter.java
class ArticleTypeFragmentPagerAdapter (line 21) | public class ArticleTypeFragmentPagerAdapter extends FragmentPagerAdapter {
method ArticleTypeFragmentPagerAdapter (line 27) | @Inject
method getItem (line 42) | @Override
method getCount (line 47) | @Override
method getPageTitle (line 52) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/home/HomeContract.java
type HomeContract (line 14) | public interface HomeContract {
type View (line 16) | interface View extends BaseContract.BaseView {
method setHomeBanners (line 17) | void setHomeBanners(List<Banner> banners);
method setHomeArticles (line 19) | void setHomeArticles(Article article, @LoadType.checker int loadType);
method collectArticleSuccess (line 21) | void collectArticleSuccess(int position, Article.DatasBean bean);
type Presenter (line 25) | interface Presenter extends BaseContract.BasePresenter<View> {
method loadHomeBanners (line 26) | void loadHomeBanners();
method loadHomeArticles (line 28) | void loadHomeArticles();
method refresh (line 30) | void refresh();
method loadMore (line 32) | void loadMore();
method collectArticle (line 34) | void collectArticle(int position, Article.DatasBean bean);
method loadHomeData (line 36) | void loadHomeData();
FILE: app/src/main/java/com/lw/wanandroid/ui/home/HomeFragment.java
class HomeFragment (line 38) | public class HomeFragment extends BaseFragment<HomePresenter> implements...
method getLayoutId (line 49) | @Override
method initInjector (line 54) | @Override
method initView (line 59) | @Override
method showLoading (line 89) | @Override
method showFaild (line 94) | @Override
method setHomeBanners (line 99) | @Override
method setHomeArticles (line 121) | @Override
method collectArticleSuccess (line 126) | @Override
method onItemChildClick (line 131) | @Override
method onItemClick (line 146) | @Override
method onRefresh (line 153) | @Override
method onLoadMoreRequested (line 158) | @Override
method newInstance (line 163) | public static HomeFragment newInstance() {
FILE: app/src/main/java/com/lw/wanandroid/ui/home/HomePresenter.java
class HomePresenter (line 32) | public class HomePresenter extends BasePresenter<HomeContract.View> impl...
method HomePresenter (line 36) | @Inject
method loadHomeBanners (line 41) | @Override
method loadHomeArticles (line 60) | @Override
method refresh (line 81) | @Override
method loadMore (line 89) | @Override
method collectArticle (line 96) | @Override
method loadHomeData (line 101) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/CommonHotAdapter.java
class CommonHotAdapter (line 14) | public class CommonHotAdapter extends BaseQuickAdapter<Friend, BaseViewH...
method CommonHotAdapter (line 15) | @Inject
method convert (line 20) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HistoryAdapter.java
class HistoryAdapter (line 20) | public class HistoryAdapter extends TagAdapter<HistoryModel> {
method HistoryAdapter (line 24) | public HistoryAdapter(Context context, List<HistoryModel> datas) {
method getView (line 30) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotAdapter.java
class HotAdapter (line 20) | public class HotAdapter<T> extends TagAdapter<T> {
method HotAdapter (line 24) | public HotAdapter(Context context, List<T> datas) {
method getView (line 30) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotContract.java
type HotContract (line 13) | public interface HotContract {
type View (line 14) | interface View extends BaseContract.BaseView {
method setHotData (line 15) | void setHotData(List<HotKey> hotKeys, List<Friend> friends);
type Presenter (line 18) | interface Presenter extends BaseContract.BasePresenter<View> {
method loadHotData (line 19) | void loadHotData();
method refresh (line 21) | void refresh();
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotFragment.java
class HotFragment (line 29) | public class HotFragment extends BaseFragment<HotPresenter> implements H...
method getLayoutId (line 41) | @Override
method initInjector (line 46) | @Override
method initView (line 51) | @Override
method showLoading (line 71) | @Override
method showFaild (line 76) | @Override
method setHotData (line 81) | @Override
method onRefresh (line 92) | @Override
method newInstance (line 97) | public static HotFragment newInstance() {
method setListener (line 101) | private void setListener() {
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotPresenter.java
class HotPresenter (line 26) | public class HotPresenter extends BasePresenter<HotContract.View> implem...
method HotPresenter (line 27) | @Inject
method loadHotData (line 31) | @Override
method refresh (line 59) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchActivity.java
class SearchActivity (line 39) | @Route(path = "/hotsearch/SearchActivity")
method getLayoutId (line 56) | @Override
method initInjector (line 61) | @Override
method initView (line 66) | @Override
method showHomeAsUp (line 105) | @Override
method onCreateOptionsMenu (line 110) | @Override
method onRefresh (line 141) | @Override
method onItemChildClick (line 146) | @Override
method onItemClick (line 161) | @Override
method showLoading (line 168) | @Override
method onLoadMoreRequested (line 173) | @Override
method setSearchArtcles (line 178) | @Override
method collectArticleSuccess (line 183) | @Override
method setHistory (line 188) | @Override
method addHistorySuccess (line 196) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchContract.java
type SearchContract (line 14) | public interface SearchContract {
type View (line 15) | interface View extends BaseContract.BaseView {
method setSearchArtcles (line 16) | void setSearchArtcles(Article article, @LoadType.checker int loadType);
method collectArticleSuccess (line 18) | void collectArticleSuccess(int position, Article.DatasBean bean);
method setHistory (line 20) | void setHistory(List<HistoryModel> historyModels);
method addHistorySuccess (line 22) | void addHistorySuccess(HistoryModel historyModel);
type Presenter (line 25) | interface Presenter extends BaseContract.BasePresenter<SearchContract....
method loadSearchArtcles (line 26) | void loadSearchArtcles(String k);
method refresh (line 28) | void refresh();
method loadMore (line 30) | void loadMore();
method collectArticle (line 32) | void collectArticle(int position, Article.DatasBean bean);
method loadHistory (line 34) | void loadHistory();
method addHistory (line 36) | void addHistory(String name);
FILE: app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchPresenter.java
class SearchPresenter (line 29) | public class SearchPresenter extends BasePresenter<SearchContract.View> ...
method SearchPresenter (line 34) | @Inject
method loadSearchArtcles (line 39) | @Override
method refresh (line 62) | @Override
method loadMore (line 69) | @Override
method collectArticle (line 76) | @Override
method loadHistory (line 81) | @Override
method addHistory (line 107) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemAdapter.java
class KnowledgeSystemAdapter (line 14) | public class KnowledgeSystemAdapter extends BaseQuickAdapter<KnowledgeSy...
method KnowledgeSystemAdapter (line 15) | @Inject
method convert (line 20) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemContract.java
type KnowledgeSystemContract (line 12) | public interface KnowledgeSystemContract {
type View (line 13) | interface View extends BaseContract.BaseView {
method setKnowledgeSystems (line 14) | void setKnowledgeSystems(List<KnowledgeSystem> knowledgeSystems);
type Presenter (line 17) | interface Presenter extends BaseContract.BasePresenter<KnowledgeSystem...
method loadKnowledgeSystems (line 18) | void loadKnowledgeSystems();
method refresh (line 20) | void refresh();
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemFragment.java
class KnowledgeSystemFragment (line 25) | public class KnowledgeSystemFragment extends BaseFragment<KnowledgeSyste...
method getLayoutId (line 34) | @Override
method initInjector (line 39) | @Override
method initView (line 44) | @Override
method showLoading (line 58) | @Override
method showFaild (line 63) | @Override
method setKnowledgeSystems (line 68) | @Override
method onRefresh (line 74) | @Override
method onItemClick (line 79) | @Override
method newInstance (line 87) | public static KnowledgeSystemFragment newInstance() {
FILE: app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemPresenter.java
class KnowledgeSystemPresenter (line 20) | public class KnowledgeSystemPresenter extends BasePresenter<KnowledgeSys...
method KnowledgeSystemPresenter (line 21) | @Inject
method loadKnowledgeSystems (line 26) | @Override
method refresh (line 46) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/my/LoginActivity.java
class LoginActivity (line 23) | @Route(path = "/my/LoginActivity")
method getLayoutId (line 30) | @Override
method initInjector (line 35) | @Override
method initView (line 40) | @Override
method showHomeAsUp (line 46) | @Override
method login (line 51) | @OnClick(R.id.btnLogin)
method loginSuccess (line 62) | @Override
method start (line 72) | public static void start() {
FILE: app/src/main/java/com/lw/wanandroid/ui/my/LoginContract.java
type LoginContract (line 10) | public interface LoginContract {
type View (line 11) | interface View extends BaseContract.BaseView {
method loginSuccess (line 12) | void loginSuccess(User user);
type Presenter (line 15) | interface Presenter extends BaseContract.BasePresenter<LoginContract.V...
method login (line 16) | void login(String username, String password);
FILE: app/src/main/java/com/lw/wanandroid/ui/my/LoginPresenter.java
class LoginPresenter (line 18) | public class LoginPresenter extends BasePresenter<LoginContract.View> im...
method LoginPresenter (line 19) | @Inject
method login (line 23) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkActivity.java
class MyBookmarkActivity (line 25) | @Route(path = "/my/MyBookmarkActivity")
method getLayoutId (line 33) | @Override
method initInjector (line 38) | @Override
method initView (line 43) | @Override
method showHomeAsUp (line 60) | @Override
method setMyBookmarks (line 65) | @Override
method showLoading (line 72) | @Override
method onRefresh (line 77) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkContract.java
type MyBookmarkContract (line 12) | public interface MyBookmarkContract {
type View (line 13) | interface View extends BaseContract.BaseView {
method setMyBookmarks (line 14) | void setMyBookmarks(List<Friend> bookmarks);
type Presenter (line 17) | interface Presenter extends BaseContract.BasePresenter<MyBookmarkContr...
method loadMyBookmarks (line 18) | void loadMyBookmarks();
method editBookmark (line 20) | void editBookmark(int id, String name, String link);
method delBookmark (line 22) | void delBookmark(int id);
method refresh (line 24) | void refresh();
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkPresenter.java
class MyBookmarkPresenter (line 20) | public class MyBookmarkPresenter extends BasePresenter<MyBookmarkContrac...
method MyBookmarkPresenter (line 23) | @Inject
method loadMyBookmarks (line 28) | @Override
method editBookmark (line 48) | @Override
method delBookmark (line 53) | @Override
method refresh (line 58) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionActivity.java
class MyCollectionActivity (line 29) | @Route(path = "/my/MyCollectionActivity")
method getLayoutId (line 39) | @Override
method initInjector (line 44) | @Override
method initView (line 49) | @Override
method showLoading (line 66) | @Override
method showHomeAsUp (line 71) | @Override
method setMyCollectArticles (line 76) | @Override
method unCollectArticleSuccess (line 81) | @Override
method onRefresh (line 86) | @Override
method onItemChildClick (line 91) | @Override
method onItemClick (line 106) | @Override
method onLoadMoreRequested (line 113) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionContract.java
type MyCollectionContract (line 11) | public interface MyCollectionContract {
type View (line 12) | interface View extends BaseContract.BaseView {
method setMyCollectArticles (line 13) | void setMyCollectArticles(Article article, @LoadType.checker int loa...
method unCollectArticleSuccess (line 15) | void unCollectArticleSuccess(int position);
type Presenter (line 18) | interface Presenter extends BaseContract.BasePresenter<MyCollectionCon...
method loadMyCollectArticles (line 19) | void loadMyCollectArticles();
method refresh (line 21) | void refresh();
method loadMore (line 23) | void loadMore();
method unCollectArticle (line 25) | void unCollectArticle(int position, Article.DatasBean bean);
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionPresenter.java
class MyCollectionPresenter (line 20) | public class MyCollectionPresenter extends BasePresenter<MyCollectionCon...
method MyCollectionPresenter (line 24) | @Inject
method loadMyCollectArticles (line 29) | @Override
method refresh (line 51) | @Override
method loadMore (line 58) | @Override
method unCollectArticle (line 65) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyContract.java
type MyContract (line 9) | public interface MyContract {
type View (line 10) | interface View extends BaseContract.BaseView {
type Presenter (line 13) | interface Presenter extends BaseContract.BasePresenter<MyContract.View> {
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyFragment.java
class MyFragment (line 26) | public class MyFragment extends BaseFragment<MyPresenter> implements MyC...
method getLayoutId (line 35) | @Override
method initInjector (line 40) | @Override
method initView (line 45) | @Override
method onViewClicked (line 57) | @OnClick({R.id.civAvatar, R.id.tvMyCollection, R.id.tvMyBookmark, R.id...
method logout (line 83) | private void logout() {
method setUserStatusInfo (line 96) | private void setUserStatusInfo() {
method newInstance (line 109) | public static MyFragment newInstance() {
FILE: app/src/main/java/com/lw/wanandroid/ui/my/MyPresenter.java
class MyPresenter (line 11) | public class MyPresenter extends BasePresenter<MyContract.View> implemen...
method MyPresenter (line 12) | @Inject
FILE: app/src/main/java/com/lw/wanandroid/ui/my/RegisterActivity.java
class RegisterActivity (line 10) | @Route(path = "/my/RegisterActivity")
method getLayoutId (line 12) | @Override
method initInjector (line 17) | @Override
method initView (line 22) | @Override
method showHomeAsUp (line 27) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/setting/SettingActivity.java
class SettingActivity (line 10) | @Route(path = "/setting/SettingActivity")
method getLayoutId (line 12) | @Override
method initInjector (line 17) | @Override
method initView (line 22) | @Override
method showHomeAsUp (line 29) | @Override
FILE: app/src/main/java/com/lw/wanandroid/ui/setting/SettingFragment.java
class SettingFragment (line 15) | public class SettingFragment extends PreferenceFragmentCompat {
method onCreatePreferences (line 18) | @Override
method newInstance (line 34) | public static SettingFragment newInstance() {
FILE: app/src/main/java/com/lw/wanandroid/ui/setting/TestPageActivity.java
class TestPageActivity (line 25) | @Route(path = "/setting/TestPageActivity")
method getLayoutId (line 36) | @Override
method initInjector (line 41) | @Override
method initView (line 46) | @Override
method showHomeAsUp (line 51) | @Override
method onViewClicked (line 56) | @OnClick({R.id.btnTest1, R.id.btnTest2, R.id.btnTest3})
method test1 (line 69) | private void test1() {
FILE: app/src/main/java/com/lw/wanandroid/utils/ArticleUtils.java
class ArticleUtils (line 24) | public class ArticleUtils {
method collectArticle (line 32) | public static void collectArticle(final BaseContract.BaseView view, fi...
FILE: app/src/main/java/com/lw/wanandroid/utils/GlideImageLoader.java
class GlideImageLoader (line 13) | public class GlideImageLoader extends ImageLoader {
method displayImage (line 14) | @Override
FILE: app/src/main/java/com/lw/wanandroid/utils/GsonUtils.java
class GsonUtils (line 18) | public class GsonUtils {
method convertList (line 34) | public static <T> List<T> convertList(String json, TypeToken<List<T>> ...
method convertObj (line 51) | public static <T> T convertObj(String json, Class<T> cls) {
method convertObj (line 68) | public static <T> T convertObj(String json, Type cls) {
method toJson (line 83) | public static String toJson(Object obj) {
method getJsonObjectAsString (line 90) | public static String getJsonObjectAsString(JsonObject jsonObject, Stri...
method getJsonObjectChild (line 98) | public static JsonObject getJsonObjectChild(JsonObject jsonObject, Str...
method getJsonObjectAsBoolean (line 106) | public static boolean getJsonObjectAsBoolean(JsonObject jsonObject, St...
FILE: app/src/main/java/com/lw/wanandroid/utils/RxBus.java
class RxBus (line 11) | public class RxBus {
method RxBus (line 17) | public RxBus() {
method getInstance (line 22) | public static RxBus getInstance() {
method post (line 34) | public void post(Object o) {
method toFlowable (line 39) | public <T> Flowable<T> toFlowable(Class<T> eventType) {
FILE: app/src/main/java/com/lw/wanandroid/utils/RxSchedulers.java
class RxSchedulers (line 14) | public class RxSchedulers {
method apply (line 18) | @Override
method applySchedulers (line 26) | public static <T> ObservableTransformer<T, T> applySchedulers() {
FILE: app/src/test/java/com/lw/wanandroid/ExampleUnitTest.java
class ExampleUnitTest (line 12) | public class ExampleUnitTest {
method addition_isCorrect (line 13) | @Test
Condensed preview — 158 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (289K chars).
[
{
"path": ".gitignore",
"chars": 118,
"preview": "*.iml\n.gradle\n/local.properties\n/.idea/workspace.xml\n/.idea/libraries\n.DS_Store\n/build\n/captures\n.externalNativeBuild\n"
},
{
"path": ".idea/compiler.xml",
"chars": 686,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"CompilerConfiguration\">\n <resourceExt"
},
{
"path": ".idea/copyright/profiles_settings.xml",
"chars": 74,
"preview": "<component name=\"CopyrightManager\">\n <settings default=\"\" />\n</component>"
},
{
"path": ".idea/encodings.xml",
"chars": 159,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"Encoding\">\n <file url=\"PROJECT\" chars"
},
{
"path": ".idea/gradle.xml",
"chars": 626,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"GradleSettings\">\n <option name=\"linke"
},
{
"path": ".idea/misc.xml",
"chars": 1626,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"NullableNotNullManager\">\n <option nam"
},
{
"path": ".idea/modules.xml",
"chars": 357,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"ProjectModuleManager\">\n <modules>\n "
},
{
"path": ".idea/runConfigurations.xml",
"chars": 564,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"RunConfigurationProducerService\">\n <o"
},
{
"path": ".idea/vcs.xml",
"chars": 180,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"VcsDirectoryMappings\">\n <mapping dire"
},
{
"path": "README.md",
"chars": 1991,
"preview": "#WanAndroid\r\nTry to build a www.wanandroid.com client\r\n\r\n# APK\r\n[app-release.apk](https://coding.net/u/salecoding/p/WanA"
},
{
"path": "app/.gitignore",
"chars": 7,
"preview": "/build\n"
},
{
"path": "app/build.gradle",
"chars": 3807,
"preview": "apply plugin: 'com.android.application'\n\nandroid {\n signingConfigs {\n config {\n keyAlias RELEASE_KE"
},
{
"path": "app/proguard-rules.pro",
"chars": 916,
"preview": "# Add project specific ProGuard rules here.\n# By default, the flags in this file are appended to flags specified\n# in D:"
},
{
"path": "app/release/output.json",
"chars": 187,
"preview": "[{\"outputType\":{\"type\":\"APK\"},\"apkInfo\":{\"type\":\"MAIN\",\"splits\":[],\"versionCode\":1},\"path\":\"app-release.apk\",\"properties"
},
{
"path": "app/src/androidTest/java/com/lw/wanandroid/ExampleInstrumentedTest.java",
"chars": 749,
"preview": "package com.lw.wanandroid;\n\nimport android.content.Context;\nimport android.support.test.InstrumentationRegistry;\nimport "
},
{
"path": "app/src/main/AndroidManifest.xml",
"chars": 4548,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"\n pa"
},
{
"path": "app/src/main/java/com/lw/wanandroid/MainActivity.java",
"chars": 4118,
"preview": "package com.lw.wanandroid;\n\nimport android.support.annotation.NonNull;\nimport android.support.design.widget.BottomNaviga"
},
{
"path": "app/src/main/java/com/lw/wanandroid/base/App.java",
"chars": 1995,
"preview": "package com.lw.wanandroid.base;\n\nimport android.app.Application;\nimport android.content.Context;\n\nimport com.alibaba.and"
},
{
"path": "app/src/main/java/com/lw/wanandroid/base/BaseActivity.java",
"chars": 11780,
"preview": "package com.lw.wanandroid.base;\n\nimport android.os.Build;\nimport android.os.Bundle;\nimport android.support.annotation.No"
},
{
"path": "app/src/main/java/com/lw/wanandroid/base/BaseContract.java",
"chars": 777,
"preview": "package com.lw.wanandroid.base;\n\nimport com.trello.rxlifecycle2.LifecycleTransformer;\n\n/**\n * desc:\n * author: Will .\n *"
},
{
"path": "app/src/main/java/com/lw/wanandroid/base/BaseFragment.java",
"chars": 14614,
"preview": "package com.lw.wanandroid.base;\n\nimport android.app.Activity;\nimport android.os.Bundle;\nimport android.support.annotatio"
},
{
"path": "app/src/main/java/com/lw/wanandroid/base/BasePresenter.java",
"chars": 419,
"preview": "package com.lw.wanandroid.base;\n\n/**\n * desc:\n * author: Will .\n * date: 2017/9/2 .\n */\n\npublic class BasePresenter<T ex"
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/Article.java",
"chars": 4807,
"preview": "package com.lw.wanandroid.bean;\n\nimport java.util.List;\n\n/**\n * Created by lw on 2018/1/18.\n */\n\npublic class Article {\n"
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/Banner.java",
"chars": 1364,
"preview": "package com.lw.wanandroid.bean;\n\n/**\n * Created by lw on 2018/1/19.\n */\n\npublic class Banner {\n private int id;\n p"
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/DataResponse.java",
"chars": 610,
"preview": "package com.lw.wanandroid.bean;\n\n/**\n * Created by lw on 2018/1/19.\n */\n\npublic class DataResponse<T> {\n private int "
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/Friend.java",
"chars": 859,
"preview": "package com.lw.wanandroid.bean;\n\n/**\n * Created by lw on 2018/1/23.\n */\n\npublic class Friend {\n private int id;\n p"
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/HotKey.java",
"chars": 859,
"preview": "package com.lw.wanandroid.bean;\n\n/**\n * Created by lw on 2018/1/23.\n */\n\npublic class HotKey {\n private int id;\n p"
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/KnowledgeSystem.java",
"chars": 4404,
"preview": "package com.lw.wanandroid.bean;\n\nimport android.content.Context;\n\nimport com.alibaba.android.arouter.facade.annotation.R"
},
{
"path": "app/src/main/java/com/lw/wanandroid/bean/User.java",
"chars": 1136,
"preview": "package com.lw.wanandroid.bean;\n\nimport java.util.List;\n\n/**\n * Created by lw on 2018/1/24.\n */\n\npublic class User {\n "
},
{
"path": "app/src/main/java/com/lw/wanandroid/constant/Constant.java",
"chars": 1668,
"preview": "package com.lw.wanandroid.constant;\n\n/**\n * Created by lw on 2018/1/19.\n */\n\npublic class Constant {\n public static f"
},
{
"path": "app/src/main/java/com/lw/wanandroid/constant/LoadType.java",
"chars": 628,
"preview": "package com.lw.wanandroid.constant;\n\nimport android.support.annotation.IntDef;\n\nimport java.lang.annotation.Retention;\ni"
},
{
"path": "app/src/main/java/com/lw/wanandroid/db/AppDatabase.java",
"chars": 318,
"preview": "package com.lw.wanandroid.db;\n\nimport com.raizlabs.android.dbflow.annotation.Database;\n\n/**\n * Created by lw on 2018/2/2"
},
{
"path": "app/src/main/java/com/lw/wanandroid/db/HistoryModel.java",
"chars": 901,
"preview": "package com.lw.wanandroid.db;\n\nimport com.raizlabs.android.dbflow.annotation.Column;\nimport com.raizlabs.android.dbflow."
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/component/ActivityComponent.java",
"chars": 1111,
"preview": "package com.lw.wanandroid.di.component;\n\nimport android.app.Activity;\nimport android.content.Context;\n\nimport com.lw.wan"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/component/ApplicationComponent.java",
"chars": 441,
"preview": "package com.lw.wanandroid.di.component;\n\nimport android.content.Context;\n\nimport com.lw.wanandroid.di.module.Application"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/component/FragmentComponent.java",
"chars": 1101,
"preview": "package com.lw.wanandroid.di.component;\n\nimport android.app.Activity;\nimport android.content.Context;\n\nimport com.lw.wan"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/component/ServiceComponent.java",
"chars": 550,
"preview": "package com.lw.wanandroid.di.component;\n\nimport android.content.Context;\n\nimport com.lw.wanandroid.di.module.ServiceModu"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/module/ActivityModule.java",
"chars": 680,
"preview": "package com.lw.wanandroid.di.module;\n\nimport android.app.Activity;\nimport android.content.Context;\n\nimport com.lw.wanand"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/module/ApplicationModule.java",
"chars": 614,
"preview": "package com.lw.wanandroid.di.module;\n\nimport android.content.Context;\n\nimport com.lw.wanandroid.base.App;\nimport com.lw."
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/module/FragmentModule.java",
"chars": 852,
"preview": "package com.lw.wanandroid.di.module;\n\nimport android.app.Activity;\nimport android.content.Context;\nimport android.suppor"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/module/ServiceModule.java",
"chars": 562,
"preview": "package com.lw.wanandroid.di.module;\n\nimport android.app.Service;\nimport android.content.Context;\n\nimport com.lw.wanandr"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/scope/ContextLife.java",
"chars": 368,
"preview": "package com.lw.wanandroid.di.scope;\n\nimport java.lang.annotation.Documented;\nimport java.lang.annotation.Retention;\nimpo"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/scope/PerActivity.java",
"chars": 318,
"preview": "package com.lw.wanandroid.di.scope;\n\nimport java.lang.annotation.Documented;\nimport java.lang.annotation.Retention;\nimpo"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/scope/PerApp.java",
"chars": 313,
"preview": "package com.lw.wanandroid.di.scope;\n\nimport java.lang.annotation.Documented;\nimport java.lang.annotation.Retention;\nimpo"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/scope/PerFragment.java",
"chars": 318,
"preview": "package com.lw.wanandroid.di.scope;\n\nimport java.lang.annotation.Documented;\nimport java.lang.annotation.Retention;\nimpo"
},
{
"path": "app/src/main/java/com/lw/wanandroid/di/scope/PerService.java",
"chars": 317,
"preview": "package com.lw.wanandroid.di.scope;\n\nimport java.lang.annotation.Documented;\nimport java.lang.annotation.Retention;\nimpo"
},
{
"path": "app/src/main/java/com/lw/wanandroid/event/LoginEvent.java",
"chars": 102,
"preview": "package com.lw.wanandroid.event;\n\n/**\n * Created by lw on 2018/1/25.\n */\n\npublic class LoginEvent {\n}\n"
},
{
"path": "app/src/main/java/com/lw/wanandroid/net/ApiService.java",
"chars": 4533,
"preview": "package com.lw.wanandroid.net;\n\nimport com.lw.wanandroid.bean.Article;\nimport com.lw.wanandroid.bean.Banner;\nimport com."
},
{
"path": "app/src/main/java/com/lw/wanandroid/net/CookiesManager.java",
"chars": 1205,
"preview": "package com.lw.wanandroid.net;\n\nimport java.util.List;\n\nimport okhttp3.Cookie;\nimport okhttp3.CookieJar;\nimport okhttp3."
},
{
"path": "app/src/main/java/com/lw/wanandroid/net/OkHttpCookies.java",
"chars": 2095,
"preview": "package com.lw.wanandroid.net;\n\nimport java.io.IOException;\nimport java.io.ObjectInputStream;\nimport java.io.ObjectOutpu"
},
{
"path": "app/src/main/java/com/lw/wanandroid/net/PersistentCookieStore.java",
"chars": 6566,
"preview": "package com.lw.wanandroid.net;\n\nimport android.content.SharedPreferences;\nimport android.text.TextUtils;\nimport android."
},
{
"path": "app/src/main/java/com/lw/wanandroid/net/RetrofitManager.java",
"chars": 4650,
"preview": "package com.lw.wanandroid.net;\n\nimport com.blankj.utilcode.util.NetworkUtils;\nimport com.lw.wanandroid.base.App;\nimport "
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleAdapter.java",
"chars": 1554,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport android.text.Html;\n\nimport com.chad.library.adapter.base.BaseQuickAdapter;"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentActivity.java",
"chars": 3689,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport android.content.Intent;\nimport android.net.Uri;\nimport android.view.Menu;\n"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentContract.java",
"chars": 469,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport com.lw.wanandroid.base.BaseContract;\n\nimport retrofit2.http.Field;\n\n/**\n *"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleContentPresenter.java",
"chars": 3451,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport com.blankj.utilcode.util.SPUtils;\nimport com.lw.wanandroid.R;\nimport com.l"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleListContract.java",
"chars": 737,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.Article"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleListFragment.java",
"chars": 3643,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.support.v7.wi"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleListPresenter.java",
"chars": 5328,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport com.blankj.utilcode.util.SPUtils;\nimport com.lw.wanandroid.R;\nimport com.l"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleTypeActivity.java",
"chars": 2596,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport android.content.Intent;\nimport android.support.design.widget.TabLayout;\nim"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/article/ArticleTypeFragmentPagerAdapter.java",
"chars": 1746,
"preview": "package com.lw.wanandroid.ui.article;\n\nimport android.support.annotation.Nullable;\nimport android.support.v4.app.Fragmen"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/home/HomeContract.java",
"chars": 854,
"preview": "package com.lw.wanandroid.ui.home;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.Article;\ni"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/home/HomeFragment.java",
"chars": 6001,
"preview": "package com.lw.wanandroid.ui.home;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.support.v7.widge"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/home/HomePresenter.java",
"chars": 5996,
"preview": "package com.lw.wanandroid.ui.home;\n\nimport com.blankj.utilcode.util.SPUtils;\nimport com.lw.wanandroid.R;\nimport com.lw.w"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/CommonHotAdapter.java",
"chars": 598,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport com.chad.library.adapter.base.BaseQuickAdapter;\nimport com.chad.library."
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/HistoryAdapter.java",
"chars": 1481,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport android.content.Context;\nimport android.graphics.Color;\nimport android.v"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotAdapter.java",
"chars": 1764,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport android.content.Context;\nimport android.graphics.Color;\nimport android.v"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotContract.java",
"chars": 512,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.Frien"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotFragment.java",
"chars": 4104,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.support.v7."
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/HotPresenter.java",
"chars": 2498,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport com.lw.wanandroid.base.BasePresenter;\nimport com.lw.wanandroid.bean.Data"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchActivity.java",
"chars": 7267,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.support.v7."
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchContract.java",
"chars": 961,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.Artic"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/hotsearch/SearchPresenter.java",
"chars": 4041,
"preview": "package com.lw.wanandroid.ui.hotsearch;\n\nimport com.lw.wanandroid.base.BasePresenter;\nimport com.lw.wanandroid.bean.Arti"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemAdapter.java",
"chars": 914,
"preview": "package com.lw.wanandroid.ui.knowledgesystem;\n\nimport com.chad.library.adapter.base.BaseQuickAdapter;\nimport com.chad.li"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemContract.java",
"chars": 539,
"preview": "package com.lw.wanandroid.ui.knowledgesystem;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemFragment.java",
"chars": 2763,
"preview": "package com.lw.wanandroid.ui.knowledgesystem;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.suppo"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/knowledgesystem/KnowledgeSystemPresenter.java",
"chars": 1663,
"preview": "package com.lw.wanandroid.ui.knowledgesystem;\n\nimport com.lw.wanandroid.base.BasePresenter;\nimport com.lw.wanandroid.bea"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/LoginActivity.java",
"chars": 2441,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport android.support.design.widget.TextInputEditText;\n\nimport com.alibaba.android.ar"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/LoginContract.java",
"chars": 427,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.User;\n\n/**\n "
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/LoginPresenter.java",
"chars": 1610,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BasePresenter;\nimport com.lw.wanandroid.bean.DataRespons"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkActivity.java",
"chars": 2400,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.util.Log;\nimport a"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkContract.java",
"chars": 577,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.Friend;\n\nimp"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyBookmarkPresenter.java",
"chars": 1792,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BasePresenter;\nimport com.lw.wanandroid.bean.DataRespons"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionActivity.java",
"chars": 4055,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport android.support.v4.widget.SwipeRefreshLayout;\nimport android.support.v7.widget."
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionContract.java",
"chars": 691,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BaseContract;\nimport com.lw.wanandroid.bean.Article;\nimp"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyCollectionPresenter.java",
"chars": 2340,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BasePresenter;\nimport com.lw.wanandroid.bean.Article;\nim"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyContract.java",
"chars": 293,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BaseContract;\n\n/**\n * Created by lw on 2018/1/19.\n */\n\np"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyFragment.java",
"chars": 3528,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport android.view.View;\nimport android.widget.LinearLayout;\nimport android.widget.Te"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/MyPresenter.java",
"chars": 295,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.lw.wanandroid.base.BasePresenter;\n\nimport javax.inject.Inject;\n\n/**\n * Crea"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/my/RegisterActivity.java",
"chars": 589,
"preview": "package com.lw.wanandroid.ui.my;\n\nimport com.alibaba.android.arouter.facade.annotation.Route;\nimport com.lw.wanandroid.R"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/setting/SettingActivity.java",
"chars": 755,
"preview": "package com.lw.wanandroid.ui.setting;\n\nimport com.alibaba.android.arouter.facade.annotation.Route;\nimport com.lw.wanandr"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/setting/SettingFragment.java",
"chars": 1250,
"preview": "package com.lw.wanandroid.ui.setting;\n\nimport android.os.Bundle;\nimport android.support.v7.preference.Preference;\nimport"
},
{
"path": "app/src/main/java/com/lw/wanandroid/ui/setting/TestPageActivity.java",
"chars": 2394,
"preview": "package com.lw.wanandroid.ui.setting;\n\nimport android.util.Log;\nimport android.view.View;\nimport android.widget.Button;\n"
},
{
"path": "app/src/main/java/com/lw/wanandroid/utils/ArticleUtils.java",
"chars": 5333,
"preview": "package com.lw.wanandroid.utils;\n\nimport com.blankj.utilcode.util.SPUtils;\nimport com.lw.wanandroid.R;\nimport com.lw.wan"
},
{
"path": "app/src/main/java/com/lw/wanandroid/utils/GlideImageLoader.java",
"chars": 552,
"preview": "package com.lw.wanandroid.utils;\n\nimport android.content.Context;\nimport android.widget.ImageView;\n\nimport com.bumptech."
},
{
"path": "app/src/main/java/com/lw/wanandroid/utils/GsonUtils.java",
"chars": 2837,
"preview": "package com.lw.wanandroid.utils;\n\nimport com.blankj.utilcode.util.StringUtils;\nimport com.google.gson.Gson;\nimport com.g"
},
{
"path": "app/src/main/java/com/lw/wanandroid/utils/RxBus.java",
"chars": 987,
"preview": "package com.lw.wanandroid.utils;\n\nimport io.reactivex.Flowable;\nimport io.reactivex.processors.FlowableProcessor;\nimport"
},
{
"path": "app/src/main/java/com/lw/wanandroid/utils/RxSchedulers.java",
"chars": 842,
"preview": "package com.lw.wanandroid.utils;\n\n\nimport io.reactivex.Observable;\nimport io.reactivex.ObservableSource;\nimport io.react"
},
{
"path": "app/src/main/res/drawable/ic_action_browser.xml",
"chars": 3386,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_action_hot.xml",
"chars": 1719,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_action_like.xml",
"chars": 497,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_action_no_like.xml",
"chars": 497,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_action_search.xml",
"chars": 865,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_action_share.xml",
"chars": 783,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_action_white_like.xml",
"chars": 497,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_chevron_right_black_24dp.xml",
"chars": 477,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_dashboard_black_24dp.xml",
"chars": 367,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_home_black_24dp.xml",
"chars": 325,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/ic_my_black_24dp.xml",
"chars": 415,
"preview": "<vector xmlns:android=\"http://schemas.android.com/apk/res/android\"\n android:width=\"24dp\"\n android:height=\""
},
{
"path": "app/src/main/res/drawable/item_selector.xml",
"chars": 274,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<selector xmlns:android=\"http://schemas.android.com/apk/res/android\">\n <item a"
},
{
"path": "app/src/main/res/drawable/item_selector_hot.xml",
"chars": 347,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<selector xmlns:android=\"http://schemas.android.com/apk/res/android\">\n <item a"
},
{
"path": "app/src/main/res/drawable-v21/item_selector_hot.xml",
"chars": 564,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<ripple xmlns:android=\"http://schemas.android.com/apk/res/android\"\n androi"
},
{
"path": "app/src/main/res/layout/activity_article_content.xml",
"chars": 978,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_article_type.xml",
"chars": 1407,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_login.xml",
"chars": 2196,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_main.xml",
"chars": 1935,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.design.widget.CoordinatorLayout xmlns:android=\"http://schemas.an"
},
{
"path": "app/src/main/res/layout/activity_my_bookmark.xml",
"chars": 1416,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_my_collection.xml",
"chars": 1234,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_register.xml",
"chars": 796,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_search.xml",
"chars": 1180,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_setting.xml",
"chars": 964,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/activity_test_page.xml",
"chars": 1289,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/fragment_article_list.xml",
"chars": 495,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.v4.widget.SwipeRefreshLayout\n xmlns:android=\"http://schemas.a"
},
{
"path": "app/src/main/res/layout/fragment_home.xml",
"chars": 496,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.v4.widget.SwipeRefreshLayout\n xmlns:android=\"http://schemas.a"
},
{
"path": "app/src/main/res/layout/fragment_hot.xml",
"chars": 571,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.v4.widget.SwipeRefreshLayout\n xmlns:android=\"http://schemas.a"
},
{
"path": "app/src/main/res/layout/fragment_knowledge_system.xml",
"chars": 500,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.v4.widget.SwipeRefreshLayout\n xmlns:android=\"http://schemas.a"
},
{
"path": "app/src/main/res/layout/fragment_my.xml",
"chars": 3551,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout\n xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/item_article.xml",
"chars": 2947,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.v7.widget.CardView xmlns:android=\"http://schemas.android.com/apk"
},
{
"path": "app/src/main/res/layout/item_history.xml",
"chars": 532,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<TextView\n xmlns:android=\"http://schemas.android.com/apk/res/android\"\n xmln"
},
{
"path": "app/src/main/res/layout/item_hot.xml",
"chars": 533,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<TextView\n xmlns:android=\"http://schemas.android.com/apk/res/android\"\n xmln"
},
{
"path": "app/src/main/res/layout/item_knowledge_system.xml",
"chars": 1631,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.v7.widget.CardView xmlns:android=\"http://schemas.android.com/apk"
},
{
"path": "app/src/main/res/layout/layout_empty_view.xml",
"chars": 572,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/layout_error_view.xml",
"chars": 664,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/layout_home_banner_head.xml",
"chars": 380,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/layout_hot_head.xml",
"chars": 2495,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/layout/layout_search_head.xml",
"chars": 857,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n "
},
{
"path": "app/src/main/res/menu/menu_content.xml",
"chars": 821,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n xmlns:app="
},
{
"path": "app/src/main/res/menu/menu_main.xml",
"chars": 517,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n xmlns:app="
},
{
"path": "app/src/main/res/menu/menu_search.xml",
"chars": 365,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n xmlns:app="
},
{
"path": "app/src/main/res/menu/menu_type_content.xml",
"chars": 567,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n xmlns:app="
},
{
"path": "app/src/main/res/menu/navigation.xml",
"chars": 585,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\">\n\n <item\n "
},
{
"path": "app/src/main/res/values/colors.xml",
"chars": 861,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n <color name=\"colorPrimary\">#03A9F4</color>\n <color name=\"color"
},
{
"path": "app/src/main/res/values/dimens.xml",
"chars": 1385,
"preview": "<resources>\n <!-- Default screen margins, per the Android Design guidelines. -->\n <dimen name=\"nav_header_vertical"
},
{
"path": "app/src/main/res/values/fonts.xml",
"chars": 336,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n <dimen name=\"big_large\">24sp</dimen>\n <dimen name=\"large\">22sp"
},
{
"path": "app/src/main/res/values/strings.xml",
"chars": 2365,
"preview": "<resources>\n <string name=\"app_name\">玩Android</string>\n <string name=\"title_home\">首页</string>\n <string name=\"ti"
},
{
"path": "app/src/main/res/values/styles.xml",
"chars": 2864,
"preview": "<resources>\n\n <!-- Base application theme. -->\n <style name=\"AppTheme\" parent=\"Theme.AppCompat.Light.NoActionBar\">"
},
{
"path": "app/src/main/res/xml/settings_preference_fragment.xml",
"chars": 1578,
"preview": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n ~ Copyright 2017 lizhaotailang\n ~\n ~ Licensed under the Apache License, V"
},
{
"path": "app/src/test/java/com/lw/wanandroid/ExampleUnitTest.java",
"chars": 406,
"preview": "package com.lw.wanandroid;\n\nimport org.junit.Test;\n\nimport static org.junit.Assert.assertEquals;\n\n/**\n * Example local u"
},
{
"path": "build.gradle",
"chars": 648,
"preview": "// Top-level build file where you can add configuration options common to all sub-projects/modules.\napply from: \"config."
},
{
"path": "config.gradle",
"chars": 3614,
"preview": "ext {\n\n android = [\n compileSdkVersion: 25,\n buildToolsVersion: \"25.0.2\",\n applicati"
},
{
"path": "gradle/wrapper/gradle-wrapper.properties",
"chars": 230,
"preview": "#Thu Oct 26 09:51:01 CST 2017\ndistributionBase=GRADLE_USER_HOME\ndistributionPath=wrapper/dists\nzipStoreBase=GRADLE_USER_"
},
{
"path": "gradle.properties",
"chars": 857,
"preview": "# Project-wide Gradle settings.\n# IDE (e.g. Android Studio) users:\n# Gradle settings configured through the IDE *will ov"
},
{
"path": "gradlew",
"chars": 4971,
"preview": "#!/usr/bin/env bash\n\n##############################################################################\n##\n## Gradle start "
},
{
"path": "gradlew.bat",
"chars": 2314,
"preview": "@if \"%DEBUG%\" == \"\" @echo off\n@rem ##########################################################################\n@rem\n@rem "
},
{
"path": "settings.gradle",
"chars": 15,
"preview": "include ':app'\n"
}
]
// ... and 3 more files (download for full content)
About this extraction
This page contains the full source code of the salecoding/WanAndroid GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 158 files (10.7 MB), approximately 68.2k tokens, and a symbol index with 675 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.