├── .gitignore ├── LICENSE ├── README.md ├── README_EN.md ├── app ├── .gitignore ├── build.gradle ├── debug.keystore ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── scwang │ │ └── refreshlayout │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ ├── ic_launcher-web.png │ ├── java │ │ └── com │ │ │ └── scwang │ │ │ └── refreshlayout │ │ │ ├── App.java │ │ │ ├── activity │ │ │ ├── ExperimentActivity.java │ │ │ ├── IndexMainActivity.java │ │ │ ├── practice │ │ │ │ ├── BannerPracticeActivity.java │ │ │ │ ├── FeedlistPracticeActivity.java │ │ │ │ ├── ProfilePracticeActivity.java │ │ │ │ ├── QQBrowserPracticeActivity.java │ │ │ │ ├── RepastPracticeActivity.java │ │ │ │ ├── WebviewPracticeActivity.java │ │ │ │ └── WeiboPracticeActivity.java │ │ │ ├── style │ │ │ │ ├── BezierStyleActivity.java │ │ │ │ ├── CircleStyleActivity.java │ │ │ │ ├── ClassicsStyleActivity.java │ │ │ │ ├── DeliveryStyleActivity.java │ │ │ │ ├── DropboxStyleActivity.java │ │ │ │ ├── FlyRefreshStyleActivity.java │ │ │ │ ├── FunGameBattleCityStyleActivity.java │ │ │ │ ├── FunGameHitBlockStyleActivity.java │ │ │ │ ├── MaterialStyleActivity.java │ │ │ │ ├── PhoenixStyleActivity.java │ │ │ │ ├── StoreHouseStyleActivity.java │ │ │ │ ├── TaurusStyleActivity.java │ │ │ │ ├── WaterDropStyleActivity.java │ │ │ │ └── WaveSwipStyleActivity.java │ │ │ └── using │ │ │ │ ├── AssignCodeUsingActivity.java │ │ │ │ ├── AssignDefaultUsingActivity.java │ │ │ │ ├── AssignXmlUsingActivity.java │ │ │ │ ├── BasicUsingActivity.java │ │ │ │ ├── CustomUsingActivity.java │ │ │ │ ├── ListenerUsingActivity.java │ │ │ │ ├── NestLayoutUsingActivity.java │ │ │ │ ├── OverScrollUsingActivity.java │ │ │ │ └── SnapHelperUsingActivity.java │ │ │ ├── adapter │ │ │ ├── BaseRecyclerAdapter.java │ │ │ └── SmartViewHolder.java │ │ │ ├── fragment │ │ │ ├── RefreshPractiveFragment.java │ │ │ ├── RefreshStylesFragment.java │ │ │ └── RefreshUsingFragment.java │ │ │ ├── util │ │ │ ├── DynamicTimeFormat.java │ │ │ └── StatusBarUtil.java │ │ │ └── widget │ │ │ └── RefreshLayout.java │ └── res │ │ ├── drawable │ │ ├── bc_background_panel.xml │ │ ├── ic_arrow_back_dark_24dp.xml │ │ ├── ic_arrow_back_gray_24dp.xml │ │ ├── ic_arrow_back_white_24dp.xml │ │ ├── ic_chevron_right.xml │ │ ├── ic_chevron_right_gray.xml │ │ ├── ic_feed_list_favorite.xml │ │ ├── ic_feed_list_mail.xml │ │ ├── ic_feed_list_photo.xml │ │ ├── ic_fly_refresh_folder.xml │ │ ├── ic_fly_refresh_info.xml │ │ ├── ic_fly_refresh_poll.xml │ │ ├── ic_fly_refresh_send.xml │ │ ├── ic_fly_refresh_smartphone.xml │ │ ├── ic_index_dashboard.xml │ │ ├── ic_index_home.xml │ │ ├── ic_index_notifications.xml │ │ ├── ic_list_divider.xml │ │ └── ic_progress_hojder.xml │ │ ├── layout │ │ ├── activity_experiment.xml │ │ ├── activity_fly_refresh.xml │ │ ├── activity_fly_refresh_item.xml │ │ ├── activity_index_main.xml │ │ ├── activity_practice_banner.xml │ │ ├── activity_practice_feedlist.xml │ │ ├── activity_practice_profile.xml │ │ ├── activity_practice_qqbrowser.xml │ │ ├── activity_practice_repast.xml │ │ ├── activity_practice_webview.xml │ │ ├── activity_practice_weibo.xml │ │ ├── activity_style_bezier.xml │ │ ├── activity_style_circle.xml │ │ ├── activity_style_classics.xml │ │ ├── activity_style_delivery.xml │ │ ├── activity_style_dropbox.xml │ │ ├── activity_style_fungame_battlecity.xml │ │ ├── activity_style_fungame_hitblock.xml │ │ ├── activity_style_material.xml │ │ ├── activity_style_phoenix.xml │ │ ├── activity_style_storehouse.xml │ │ ├── activity_style_taurus.xml │ │ ├── activity_style_water_drop.xml │ │ ├── activity_style_wave_swip.xml │ │ ├── activity_using_assign_code.xml │ │ ├── activity_using_assign_default.xml │ │ ├── activity_using_assign_xml.xml │ │ ├── activity_using_basic.xml │ │ ├── activity_using_custom.xml │ │ ├── activity_using_listener.xml │ │ ├── activity_using_overscroll.xml │ │ ├── activity_using_region.xml │ │ ├── activity_using_snaphelper.xml │ │ ├── fragment_refresh_practive.xml │ │ ├── fragment_refresh_styles.xml │ │ ├── fragment_refresh_using.xml │ │ ├── listitem_movie_banner.xml │ │ ├── listitem_movie_header.xml │ │ ├── listitem_movie_item.xml │ │ ├── listitem_practive_repast.xml │ │ ├── listitem_style_delivery.xml │ │ └── listitem_using_snaphelper.xml │ │ ├── menu │ │ └── navigation.xml │ │ ├── mipmap-hdpi │ │ ├── gif_header_repast.gif │ │ ├── ic_item1.jpg │ │ ├── ic_item2.jpg │ │ ├── ic_item3.jpg │ │ ├── ic_launcher.png │ │ ├── ic_launcher_round.png │ │ ├── image_avatar_1.jpg │ │ ├── image_avatar_2.jpg │ │ ├── image_avatar_3.jpg │ │ ├── image_avatar_4.jpg │ │ ├── image_avatar_5.jpg │ │ ├── image_avatar_6.jpg │ │ ├── image_movie_header_12231501221682438.jpg │ │ ├── image_movie_header_12981501221820220.jpg │ │ ├── image_movie_header_48621499931969370.jpg │ │ ├── image_practice_repast_1.jpg │ │ ├── image_practice_repast_2.jpg │ │ ├── image_practice_repast_3.jpg │ │ ├── image_practice_repast_4.jpg │ │ ├── image_practice_repast_5.jpg │ │ ├── image_practice_repast_6.jpg │ │ ├── image_weibo_home_1.png │ │ └── image_weibo_home_2.png │ │ ├── mipmap-mdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-xhdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-xxhdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── mipmap-xxxhdpi │ │ ├── ic_launcher.png │ │ └── ic_launcher_round.png │ │ ├── values-v19 │ │ └── styles.xml │ │ ├── values-v21 │ │ └── styles.xml │ │ └── values │ │ ├── colors.xml │ │ ├── dimens.xml │ │ ├── strings.xml │ │ └── styles.xml │ └── test │ └── java │ └── com │ └── scwang │ └── refreshlayout │ └── ExampleUnitTest.java ├── art ├── UMLRefreshLayout.classdiagram ├── app-debug.apk ├── gif_BattleCity.gif ├── gif_BezierRadar.gif ├── gif_Circle.gif ├── gif_Classics.gif ├── gif_Delivery.gif ├── gif_Dropbox.gif ├── gif_FlyRefresh.gif ├── gif_HitBlock.gif ├── gif_Material.gif ├── gif_Phoenix.gif ├── gif_StoreHouse.gif ├── gif_Taurus.gif ├── gif_WaterDrop.gif ├── gif_WaveSwipe.gif ├── gif_demo_multitouch_1.gif ├── gif_demo_multitouch_2.gif ├── gif_practive_feedlist.gif ├── gif_practive_profile.gif ├── gif_practive_repast.gif ├── gif_practive_smart.gif ├── gif_practive_weibo.gif ├── gif_preview_textheader.gif ├── jpg_preview_gifheader.jpg ├── jpg_preview_textheader.jpg ├── jpg_preview_xml_define.jpg ├── jpg_uml.jpg ├── md_custom.md ├── md_donationlist.md ├── md_multitouch.md ├── md_property.md ├── md_smart.md ├── md_update.md ├── pay_alipay.jpg ├── pay_tencent.jpg ├── pay_wxpay.jpg ├── png_apk_rqcode.png ├── png_ptr_elema.png ├── png_ptr_meituan.png ├── png_ptr_tianmao.png └── svg_minsdkapi.svg ├── bintrayUpload.bat ├── build.gradle ├── refresh-footer ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── scwang │ │ └── smartrefresh │ │ └── footer │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ └── res │ │ └── values │ │ ├── attrs.xml │ │ └── strings.xml │ └── test │ └── java │ └── com │ └── scwang │ └── smartrefresh │ └── footer │ └── ExampleUnitTest.java ├── refresh-header ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── scwang │ │ └── smartrefresh │ │ └── header │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── com │ │ │ └── scwang │ │ │ └── smartrefresh │ │ │ └── header │ │ │ ├── CircleHeader.java │ │ │ ├── DeliveryHeader.java │ │ │ ├── DropboxHeader.java │ │ │ ├── FlyRefreshHeader.java │ │ │ ├── FunGameBattleCityHeader.java │ │ │ ├── FunGameHitBlockHeader.java │ │ │ ├── MaterialHeader.java │ │ │ ├── PhoenixHeader.java │ │ │ ├── StoreHouseHeader.java │ │ │ ├── TaurusHeader.java │ │ │ ├── WaterDropHeader.java │ │ │ ├── WaveSwipeHeader.java │ │ │ ├── flyrefresh │ │ │ ├── FlyView.java │ │ │ ├── MountanScenceView.java │ │ │ ├── PathInterpolatorCompat.java │ │ │ ├── PathInterpolatorCompatApi21.java │ │ │ ├── PathInterpolatorCompatBase.java │ │ │ └── PathInterpolatorGingerbread.java │ │ │ ├── fungame │ │ │ ├── FunGameBase.java │ │ │ ├── FunGameHeader.java │ │ │ └── FunGameView.java │ │ │ ├── internal │ │ │ ├── FastOutSlowInInterpolator.java │ │ │ ├── LookupTableInterpolator.java │ │ │ └── MaterialProgressDrawable.java │ │ │ ├── material │ │ │ └── CircleImageView.java │ │ │ ├── storehouse │ │ │ ├── StoreHouseBarItem.java │ │ │ └── StoreHousePath.java │ │ │ ├── waterdrop │ │ │ ├── Circle.java │ │ │ └── WaterDropView.java │ │ │ └── waveswipe │ │ │ ├── AnimationImageView.java │ │ │ ├── DisplayUtil.java │ │ │ ├── DropBounceInterpolator.java │ │ │ └── WaveView.java │ └── res │ │ └── values │ │ ├── attrs.xml │ │ └── strings.xml │ └── test │ └── java │ └── com │ └── scwang │ └── smartrefresh │ └── header │ └── ExampleUnitTest.java ├── refresh-layout ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── scwang │ │ └── smartrefresh │ │ └── layout │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ ├── android │ │ │ └── support │ │ │ │ └── v4 │ │ │ │ └── view │ │ │ │ └── PagerAdapterWrapper.java │ │ └── com │ │ │ └── scwang │ │ │ └── smartrefresh │ │ │ └── layout │ │ │ ├── SmartRefreshLayout.java │ │ │ ├── api │ │ │ ├── DefaultRefreshFooterCreater.java │ │ │ ├── DefaultRefreshHeaderCreater.java │ │ │ ├── RefreshContent.java │ │ │ ├── RefreshFooter.java │ │ │ ├── RefreshHeader.java │ │ │ ├── RefreshInternal.java │ │ │ ├── RefreshKernel.java │ │ │ ├── RefreshLayout.java │ │ │ └── ScrollBoundaryDecider.java │ │ │ ├── constant │ │ │ ├── DimensionStatus.java │ │ │ ├── RefreshState.java │ │ │ └── SpinnerStyle.java │ │ │ ├── footer │ │ │ ├── BallPulseFooter.java │ │ │ ├── ClassicsFooter.java │ │ │ ├── FalsifyFooter.java │ │ │ └── ballpulse │ │ │ │ └── BallPulseView.java │ │ │ ├── header │ │ │ ├── BezierRadarHeader.java │ │ │ ├── ClassicsHeader.java │ │ │ ├── FalsifyHeader.java │ │ │ └── bezierradar │ │ │ │ ├── RippleView.java │ │ │ │ ├── RoundDotView.java │ │ │ │ ├── RoundProgressView.java │ │ │ │ └── WaveView.java │ │ │ ├── impl │ │ │ ├── RefreshContentWrapper.java │ │ │ ├── RefreshFooterWrapper.java │ │ │ ├── RefreshHeaderWrapper.java │ │ │ └── ScrollBoundaryDeciderAdapter.java │ │ │ ├── internal │ │ │ ├── ProgressDrawable.java │ │ │ └── pathview │ │ │ │ ├── PathParser.java │ │ │ │ ├── PathsDrawable.java │ │ │ │ └── PathsView.java │ │ │ ├── listener │ │ │ ├── AnimationEndListener.java │ │ │ ├── OnLoadmoreListener.java │ │ │ ├── OnMultiPurposeListener.java │ │ │ ├── OnRefreshListener.java │ │ │ ├── OnRefreshLoadmoreListener.java │ │ │ ├── OnStateChangedListener.java │ │ │ └── SimpleMultiPurposeListener.java │ │ │ └── util │ │ │ ├── ColorUtils.java │ │ │ ├── DelayedRunable.java │ │ │ ├── DensityUtil.java │ │ │ ├── ScrollBoundaryUtil.java │ │ │ └── ViscousFluidInterpolator.java │ └── res │ │ └── values │ │ ├── attrs.xml │ │ └── strings.xml │ └── test │ └── java │ └── com │ └── scwang │ └── smartrefresh │ └── layout │ └── ExampleUnitTest.java └── settings.gradle /.gitignore: -------------------------------------------------------------------------------- 1 | *.iml 2 | .gradle 3 | gradle 4 | /local.properties 5 | /.idea 6 | /build 7 | /gradlew 8 | /gradlew.bat -------------------------------------------------------------------------------- /app/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /app/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.application' 2 | 3 | android { 4 | compileSdkVersion 26 5 | buildToolsVersion "26.0.1" 6 | defaultConfig { 7 | applicationId "com.scwang.refreshlayout" 8 | minSdkVersion 15 9 | targetSdkVersion 26 10 | versionCode 1 11 | versionName "1.0" 12 | testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" 13 | vectorDrawables.useSupportLibrary = true 14 | 15 | renderscriptTargetApi 25 16 | renderscriptSupportModeEnabled true // Enable RS support 17 | 18 | } 19 | signingConfigs { 20 | debug { 21 | storeFile file('debug.keystore') 22 | storePassword "android" 23 | keyAlias "androiddebugkey" 24 | keyPassword "android" 25 | } 26 | } 27 | buildTypes { 28 | release { 29 | minifyEnabled true 30 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 31 | signingConfig = signingConfigs.debug 32 | } 33 | } 34 | lintOptions { 35 | abortOnError false 36 | } 37 | } 38 | 39 | 40 | repositories { 41 | maven { url "https://jitpack.io" } 42 | } 43 | 44 | dependencies { 45 | compile fileTree(include: ['*.jar'], dir: 'libs') 46 | androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { 47 | exclude group: 'com.android.support', module: 'support-annotations' 48 | }) 49 | 50 | debugCompile 'com.squareup.leakcanary:leakcanary-android:1.5.1' 51 | releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5.1' 52 | testCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5.1' 53 | 54 | compile project(':refresh-footer') 55 | compile project(':refresh-header') 56 | compile project(':refresh-layout') 57 | 58 | compile 'com.android.support:cardview-v7:26.0.0-alpha1' 59 | compile 'com.android.support.constraint:constraint-layout:1.0.2' 60 | compile 'com.android.support:design:26.0.0-alpha1' 61 | compile 'com.flyco.roundview:FlycoRoundView_Lib:1.1.4@aar' 62 | compile 'com.github.CymChad:BaseRecyclerViewAdapterHelper:2.9.22' 63 | compile 'com.github.mmin18:realtimeblurview:1.0.6' 64 | compile 'com.google.code.gson:gson:2.7' 65 | compile 'com.youth.banner:banner:1.4.9' //最新版本 66 | compile 'de.hdodenhof:circleimageview:2.1.0' 67 | compile 'jp.wasabeef:recyclerview-animators:2.2.6' 68 | compile 'pl.droidsonroids.gif:android-gif-drawable:1.2.3' 69 | // compile 'com.scwang.smartrefresh:SmartRefreshLayout:1.0.3' 70 | // compile 'com.scwang.smartrefresh:SmartRefreshHeader:1.0.3' 71 | testCompile 'junit:junit:4.12' 72 | 73 | compile 'com.github.bumptech.glide:glide:4.0.0-RC1' 74 | annotationProcessor 'com.github.bumptech.glide:compiler:4.0.0-RC1' 75 | } 76 | -------------------------------------------------------------------------------- /app/debug.keystore: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/debug.keystore -------------------------------------------------------------------------------- /app/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # By default, the flags in this file are appended to flags specified 3 | # in E:\Android\android-sdk/tools/proguard/proguard-android.txt 4 | # You can edit the include path and order by changing the proguardFiles 5 | # directive in build.gradle. 6 | # 7 | # For more details, see 8 | # http://developer.android.com/guide/developing/tools/proguard.html 9 | 10 | # Add any project specific keep options here: 11 | 12 | # If your project uses WebView with JS, uncomment the following 13 | # and specify the fully qualified class name to the JavaScript interface 14 | # class: 15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 16 | # public *; 17 | #} 18 | 19 | # Uncomment this to preserve the line number information for 20 | # debugging stack traces. 21 | #-keepattributes SourceFile,LineNumberTable 22 | 23 | # If you keep the line number information, uncomment this to 24 | # hide the original source file name. 25 | #-renamesourcefileattribute SourceFile 26 | 27 | #app混淆标记 28 | -keep class com.github.mmin18.** {*;} 29 | 30 | -dontwarn android.support.v8.renderscript.* 31 | -keepclassmembers class android.support.v8.renderscript.RenderScript { 32 | native *** rsn*(...); 33 | native *** n*(...); 34 | } 35 | 36 | -keep enum com.scwang.smartrefresh.layout.impl.** {*;} 37 | -------------------------------------------------------------------------------- /app/src/androidTest/java/com/scwang/refreshlayout/ExampleInstrumentedTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout; 2 | 3 | import android.content.Context; 4 | import android.support.test.InstrumentationRegistry; 5 | import android.support.test.runner.AndroidJUnit4; 6 | 7 | import org.junit.Test; 8 | import org.junit.runner.RunWith; 9 | 10 | import static org.junit.Assert.*; 11 | 12 | /** 13 | * Instrumentation test, which will execute on an Android device. 14 | * 15 | * @see Testing documentation 16 | */ 17 | @RunWith(AndroidJUnit4.class) 18 | public class ExampleInstrumentedTest { 19 | @Test 20 | public void useAppContext() throws Exception { 21 | // Context of the app under test. 22 | Context appContext = InstrumentationRegistry.getTargetContext(); 23 | 24 | assertEquals("com.scwang.refreshlayout", appContext.getPackageName()); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /app/src/main/ic_launcher-web.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/ic_launcher-web.png -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/App.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout; 2 | 3 | import android.app.Application; 4 | import android.content.Context; 5 | import android.support.annotation.NonNull; 6 | import android.support.v7.app.AppCompatDelegate; 7 | 8 | import com.scwang.smartrefresh.layout.SmartRefreshLayout; 9 | import com.scwang.smartrefresh.layout.api.DefaultRefreshHeaderCreater; 10 | import com.scwang.smartrefresh.layout.api.RefreshHeader; 11 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 12 | import com.scwang.smartrefresh.layout.constant.SpinnerStyle; 13 | import com.scwang.smartrefresh.layout.header.ClassicsHeader; 14 | import com.squareup.leakcanary.LeakCanary; 15 | 16 | /** 17 | * 18 | * Created by SCWANG on 2017/6/11. 19 | */ 20 | 21 | public class App extends Application { 22 | 23 | static { 24 | AppCompatDelegate.setCompatVectorFromResourcesEnabled(true); 25 | SmartRefreshLayout.setDefaultRefreshHeaderCreater(new DefaultRefreshHeaderCreater() { 26 | @NonNull 27 | @Override 28 | public RefreshHeader createRefreshHeader(Context context, RefreshLayout layout) { 29 | layout.setPrimaryColorsId(R.color.colorPrimary, android.R.color.white);//全局设置主题颜色 30 | return new ClassicsHeader(context).setSpinnerStyle(SpinnerStyle.Translate); 31 | } 32 | }); 33 | } 34 | 35 | @Override 36 | public void onCreate() { 37 | super.onCreate(); 38 | if (LeakCanary.isInAnalyzerProcess(this)) { 39 | // This process is dedicated to LeakCanary for heap analysis. 40 | // You should not init your app in this process. 41 | return; 42 | } 43 | LeakCanary.install(this); 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/ExperimentActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.DividerItemDecoration; 6 | import android.support.v7.widget.LinearLayoutManager; 7 | import android.support.v7.widget.RecyclerView; 8 | 9 | import com.scwang.refreshlayout.R; 10 | import com.scwang.refreshlayout.adapter.BaseRecyclerAdapter; 11 | import com.scwang.refreshlayout.adapter.SmartViewHolder; 12 | 13 | import java.util.Arrays; 14 | import java.util.Collection; 15 | import java.util.Locale; 16 | 17 | import static android.R.layout.simple_list_item_2; 18 | import static android.support.v7.widget.DividerItemDecoration.VERTICAL; 19 | 20 | public class ExperimentActivity extends AppCompatActivity { 21 | 22 | @Override 23 | protected void onCreate(Bundle savedInstanceState) { 24 | super.onCreate(savedInstanceState); 25 | setContentView(R.layout.activity_experiment); 26 | 27 | 28 | final RecyclerView recyclerView = (RecyclerView) findViewById(R.id.recyclerView); 29 | recyclerView.addItemDecoration(new DividerItemDecoration(this, VERTICAL)); 30 | recyclerView.setLayoutManager(new LinearLayoutManager(this)); 31 | recyclerView.setAdapter(new BaseRecyclerAdapter(buildData(),simple_list_item_2) { 32 | @Override 33 | protected void onBindViewHolder(SmartViewHolder holder, Void model, int position) { 34 | holder.text(android.R.id.text1, String.format(Locale.CHINA, "第%02d条数据", position)); 35 | holder.text(android.R.id.text2, String.format(Locale.CHINA, "这是测试的第%02d条数据", position)); 36 | holder.textColorId(android.R.id.text2, R.color.colorTextAssistant); 37 | } 38 | }); 39 | 40 | } 41 | 42 | protected Collection buildData() { 43 | return Arrays.asList(null,null,null,null,null,null,null,null,null,null,null,null,null,null,null,null); 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/practice/FeedlistPracticeActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.practice; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.Toolbar; 6 | import android.view.View; 7 | 8 | import com.scwang.refreshlayout.R; 9 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 10 | 11 | /** 12 | * 微博列表 13 | */ 14 | public class FeedlistPracticeActivity extends AppCompatActivity { 15 | 16 | private static boolean isFirstEnter = true; 17 | 18 | @Override 19 | protected void onCreate(Bundle savedInstanceState) { 20 | super.onCreate(savedInstanceState); 21 | setContentView(R.layout.activity_practice_feedlist); 22 | 23 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 24 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 25 | @Override 26 | public void onClick(View v) { 27 | finish(); 28 | } 29 | }); 30 | 31 | final RefreshLayout refreshLayout = (RefreshLayout) findViewById(R.id.refreshLayout); 32 | if (isFirstEnter) { 33 | isFirstEnter = false; 34 | refreshLayout.autoRefresh(); 35 | } 36 | 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/practice/ProfilePracticeActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.practice; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.Toolbar; 6 | import android.view.View; 7 | 8 | import com.scwang.refreshlayout.R; 9 | import com.scwang.refreshlayout.util.StatusBarUtil; 10 | 11 | /** 12 | * 个人中心 13 | */ 14 | public class ProfilePracticeActivity extends AppCompatActivity { 15 | 16 | 17 | @Override 18 | protected void onCreate(Bundle savedInstanceState) { 19 | super.onCreate(savedInstanceState); 20 | setContentView(R.layout.activity_practice_profile); 21 | 22 | final Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); 23 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 24 | @Override 25 | public void onClick(View v) { 26 | finish(); 27 | } 28 | }); 29 | 30 | //状态栏透明和间距处理 31 | StatusBarUtil.immersive(this); 32 | StatusBarUtil.setPaddingSmart(this, toolbar); 33 | StatusBarUtil.setPaddingSmart(this, findViewById(R.id.profile)); 34 | StatusBarUtil.setPaddingSmart(this, findViewById(R.id.blurview)); 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/practice/QQBrowserPracticeActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.practice; 2 | 3 | import android.annotation.SuppressLint; 4 | import android.os.Bundle; 5 | import android.support.v7.app.AppCompatActivity; 6 | import android.support.v7.widget.Toolbar; 7 | import android.view.View; 8 | import android.webkit.WebView; 9 | import android.webkit.WebViewClient; 10 | 11 | import com.scwang.refreshlayout.R; 12 | import com.scwang.refreshlayout.util.StatusBarUtil; 13 | 14 | /** 15 | * QQ浏览器-Github 16 | */ 17 | public class QQBrowserPracticeActivity extends AppCompatActivity { 18 | 19 | @SuppressLint("SetJavaScriptEnabled") 20 | @Override 21 | protected void onCreate(Bundle savedInstanceState) { 22 | super.onCreate(savedInstanceState); 23 | setContentView(R.layout.activity_practice_qqbrowser); 24 | 25 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 26 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 27 | @Override 28 | public void onClick(View v) { 29 | finish(); 30 | } 31 | }); 32 | 33 | final WebView webView = (WebView) findViewById(R.id.webView); 34 | webView.loadUrl("https://github.com/scwang90/SmartRefreshLayout"); 35 | webView.getSettings().setJavaScriptEnabled(true); 36 | webView.setWebViewClient(new WebViewClient(){ 37 | @Override 38 | public boolean shouldOverrideUrlLoading(WebView view, String url) { 39 | view.loadUrl(url); 40 | return true; 41 | } 42 | }); 43 | 44 | //状态栏透明和间距处理 45 | StatusBarUtil.immersive(this); 46 | StatusBarUtil.setPaddingSmart(this, toolbar); 47 | } 48 | 49 | } 50 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/practice/WebviewPracticeActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.practice; 2 | 3 | import android.annotation.SuppressLint; 4 | import android.os.Bundle; 5 | import android.support.v7.app.AppCompatActivity; 6 | import android.support.v7.widget.Toolbar; 7 | import android.view.View; 8 | import android.webkit.WebView; 9 | import android.webkit.WebViewClient; 10 | 11 | import com.scwang.refreshlayout.R; 12 | import com.scwang.refreshlayout.util.StatusBarUtil; 13 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 14 | import com.scwang.smartrefresh.layout.listener.OnRefreshListener; 15 | import com.scwang.smartrefresh.layout.util.DensityUtil; 16 | 17 | import java.util.Locale; 18 | 19 | /** 20 | * 网页-Github 21 | */ 22 | public class WebviewPracticeActivity extends AppCompatActivity { 23 | 24 | @SuppressLint("SetJavaScriptEnabled") 25 | @Override 26 | protected void onCreate(Bundle savedInstanceState) { 27 | super.onCreate(savedInstanceState); 28 | setContentView(R.layout.activity_practice_webview); 29 | 30 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 31 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 32 | @Override 33 | public void onClick(View v) { 34 | finish(); 35 | } 36 | }); 37 | 38 | final WebView webView = (WebView) findViewById(R.id.webView); 39 | final RefreshLayout refreshLayout = (RefreshLayout) findViewById(R.id.refreshLayout); 40 | refreshLayout.setOnRefreshListener(new OnRefreshListener() { 41 | @Override 42 | public void onRefresh(RefreshLayout refreshlayout) { 43 | webView.loadUrl("https://github.com/scwang90/SmartRefreshLayout"); 44 | } 45 | }); 46 | refreshLayout.autoRefresh(); 47 | 48 | 49 | webView.getSettings().setJavaScriptEnabled(true); 50 | webView.setWebViewClient(new WebViewClient(){ 51 | @Override 52 | public boolean shouldOverrideUrlLoading(WebView view, String url) { 53 | view.loadUrl(url); 54 | return true; 55 | } 56 | 57 | @Override 58 | public void onPageFinished(WebView view, String url) { 59 | super.onPageFinished(view, url); 60 | refreshLayout.finishRefresh(); 61 | view.loadUrl(String.format(Locale.CHINA, "javascript:document.body.style.paddingTop='%fpx'; void 0", DensityUtil.px2dp(webView.getPaddingTop()))); 62 | } 63 | }); 64 | 65 | //状态栏透明和间距处理 66 | StatusBarUtil.immersive(this); 67 | StatusBarUtil.setPaddingSmart(this, webView); 68 | StatusBarUtil.setPaddingSmart(this, toolbar); 69 | StatusBarUtil.setMargin(this, findViewById(R.id.header)); 70 | StatusBarUtil.setPaddingSmart(this, findViewById(R.id.blurview)); 71 | } 72 | 73 | } 74 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/using/AssignCodeUsingActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.using; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.Toolbar; 6 | import android.view.View; 7 | 8 | import com.scwang.refreshlayout.R; 9 | import com.scwang.smartrefresh.header.MaterialHeader; 10 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 11 | import com.scwang.smartrefresh.layout.constant.RefreshState; 12 | import com.scwang.smartrefresh.layout.constant.SpinnerStyle; 13 | import com.scwang.smartrefresh.layout.footer.BallPulseFooter; 14 | import com.scwang.smartrefresh.layout.listener.SimpleMultiPurposeListener; 15 | 16 | /** 17 | * 在Java代码中指定Header和Footer 18 | */ 19 | public class AssignCodeUsingActivity extends AppCompatActivity { 20 | 21 | private static boolean isFirstEnter = true; 22 | 23 | @Override 24 | protected void onCreate(Bundle savedInstanceState) { 25 | super.onCreate(savedInstanceState); 26 | setContentView(R.layout.activity_using_assign_code); 27 | 28 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 29 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 30 | @Override 31 | public void onClick(View v) { 32 | finish(); 33 | } 34 | }); 35 | 36 | 37 | final RefreshLayout refreshLayout = (RefreshLayout) findViewById(R.id.refreshLayout); 38 | //设置 Header 为 Material风格 39 | refreshLayout.setRefreshHeader(new MaterialHeader(this).setShowBezierWave(true)); 40 | //设置 Footer 为 球脉冲 41 | refreshLayout.setRefreshFooter(new BallPulseFooter(this).setSpinnerStyle(SpinnerStyle.Scale)); 42 | 43 | /** 44 | * 以下代码仅仅为了演示效果而已,不是必须的 45 | */ 46 | //设置主题颜色 47 | refreshLayout.setPrimaryColorsId(R.color.colorPrimary, android.R.color.white); 48 | 49 | if (isFirstEnter) { 50 | isFirstEnter = false; 51 | //触发上啦加载 52 | refreshLayout.autoLoadmore(); 53 | //通过多功能监听接口实现 在第一次加载完成之后 自动刷新 54 | refreshLayout.setOnMultiPurposeListener(new SimpleMultiPurposeListener(){ 55 | @Override 56 | public void onStateChanged(RefreshLayout refreshLayout, RefreshState oldState, RefreshState newState) { 57 | if (oldState == RefreshState.LoadFinish && newState == RefreshState.None) { 58 | refreshLayout.autoRefresh(); 59 | refreshLayout.setOnMultiPurposeListener(null); 60 | } 61 | } 62 | }); 63 | } 64 | } 65 | 66 | } 67 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/using/AssignXmlUsingActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.using; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.Toolbar; 6 | import android.view.View; 7 | 8 | import com.scwang.refreshlayout.R; 9 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 10 | import com.scwang.smartrefresh.layout.constant.RefreshState; 11 | import com.scwang.smartrefresh.layout.listener.SimpleMultiPurposeListener; 12 | 13 | /** 14 | * 在XML中指定Header和Footer 15 | */ 16 | public class AssignXmlUsingActivity extends AppCompatActivity { 17 | 18 | private static boolean isFirstEnter = true; 19 | 20 | @Override 21 | protected void onCreate(Bundle savedInstanceState) { 22 | super.onCreate(savedInstanceState); 23 | setContentView(R.layout.activity_using_assign_xml); 24 | 25 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 26 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 27 | @Override 28 | public void onClick(View v) { 29 | finish(); 30 | } 31 | }); 32 | 33 | 34 | /** 35 | * 以下代码仅仅为了演示效果而已,不是必须的 36 | * 关键代码在 activity_using_assign_xml 中 37 | */ 38 | final RefreshLayout refreshLayout = (RefreshLayout) findViewById(R.id.refreshLayout); 39 | if (isFirstEnter) { 40 | isFirstEnter = false; 41 | //触发上啦加载 42 | refreshLayout.autoLoadmore(); 43 | //通过多功能监听接口实现 在第一次加载完成之后 自动刷新 44 | refreshLayout.setOnMultiPurposeListener(new SimpleMultiPurposeListener(){ 45 | @Override 46 | public void onStateChanged(RefreshLayout refreshLayout, RefreshState oldState, RefreshState newState) { 47 | if (oldState == RefreshState.LoadFinish && newState == RefreshState.None) { 48 | refreshLayout.autoRefresh(); 49 | refreshLayout.setOnMultiPurposeListener(null); 50 | } 51 | } 52 | }); 53 | } 54 | } 55 | 56 | } 57 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/using/OverScrollUsingActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.using; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.Toolbar; 6 | import android.view.View; 7 | import android.webkit.WebView; 8 | import android.webkit.WebViewClient; 9 | 10 | import com.scwang.refreshlayout.R; 11 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 12 | import com.scwang.smartrefresh.layout.listener.OnRefreshListener; 13 | 14 | /** 15 | * 越界回弹使用演示 16 | */ 17 | public class OverScrollUsingActivity extends AppCompatActivity { 18 | 19 | @Override 20 | protected void onCreate(Bundle savedInstanceState) { 21 | super.onCreate(savedInstanceState); 22 | setContentView(R.layout.activity_using_overscroll); 23 | 24 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 25 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 26 | @Override 27 | public void onClick(View v) { 28 | finish(); 29 | } 30 | }); 31 | 32 | final WebView webView = (WebView) findViewById(R.id.webView); 33 | final RefreshLayout refreshLayout = (RefreshLayout) findViewById(R.id.refreshLayout); 34 | refreshLayout.setOnRefreshListener(new OnRefreshListener() { 35 | @Override 36 | public void onRefresh(RefreshLayout refreshlayout) { 37 | webView.loadUrl("http://github.com"); 38 | } 39 | }); 40 | refreshLayout.autoRefresh(); 41 | 42 | 43 | webView.setWebViewClient(new WebViewClient(){ 44 | @Override 45 | public boolean shouldOverrideUrlLoading(WebView view, String url) { 46 | view.loadUrl(url); 47 | return true; 48 | } 49 | @Override 50 | public void onPageCommitVisible(WebView view, String url) { 51 | refreshLayout.finishRefresh(); 52 | } 53 | }); 54 | // TextView textView = (TextView) findViewById(R.id.textView); 55 | // textView.setMovementMethod(new ScrollingMovementMethod()); 56 | } 57 | 58 | } 59 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/activity/using/SnapHelperUsingActivity.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.activity.using; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.app.AppCompatActivity; 5 | import android.support.v7.widget.DefaultItemAnimator; 6 | import android.support.v7.widget.LinearLayoutManager; 7 | import android.support.v7.widget.PagerSnapHelper; 8 | import android.support.v7.widget.RecyclerView; 9 | import android.support.v7.widget.SnapHelper; 10 | import android.support.v7.widget.Toolbar; 11 | import android.view.View; 12 | 13 | import com.scwang.refreshlayout.R; 14 | import com.scwang.refreshlayout.adapter.BaseRecyclerAdapter; 15 | import com.scwang.refreshlayout.adapter.SmartViewHolder; 16 | 17 | import java.util.Arrays; 18 | import java.util.Collection; 19 | 20 | /** 21 | * 结合 SnapHelper 使用 22 | * Created by SCWANG on 2017/8/4. 23 | */ 24 | 25 | public class SnapHelperUsingActivity extends AppCompatActivity { 26 | 27 | @Override 28 | protected void onCreate(Bundle savedInstanceState) { 29 | super.onCreate(savedInstanceState); 30 | setContentView(R.layout.activity_using_snaphelper); 31 | 32 | final Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar); 33 | toolbar.setNavigationOnClickListener(new View.OnClickListener() { 34 | @Override 35 | public void onClick(View v) { 36 | finish(); 37 | } 38 | }); 39 | 40 | //初始化列表和监听 41 | View view = findViewById(R.id.recyclerView); 42 | if (view instanceof RecyclerView) { 43 | RecyclerView recyclerView = (RecyclerView) view; 44 | recyclerView.setLayoutManager(new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false)); 45 | recyclerView.setItemAnimator(new DefaultItemAnimator()); 46 | recyclerView.setAdapter(new BaseRecyclerAdapter(loadModels(), R.layout.listitem_using_snaphelper) { 47 | @Override 48 | protected void onBindViewHolder(SmartViewHolder holder, Integer model, int position) { 49 | holder.image(R.id.imageView, model); 50 | } 51 | }); 52 | SnapHelper snapHelper = new PagerSnapHelper(); 53 | snapHelper.attachToRecyclerView(recyclerView); 54 | } 55 | 56 | } 57 | 58 | private Collection loadModels() { 59 | return Arrays.asList( 60 | R.mipmap.image_weibo_home_1, 61 | R.mipmap.image_weibo_home_2, 62 | R.mipmap.image_weibo_home_1, 63 | R.mipmap.image_weibo_home_2, 64 | R.mipmap.image_weibo_home_1, 65 | R.mipmap.image_weibo_home_2); 66 | } 67 | 68 | } 69 | -------------------------------------------------------------------------------- /app/src/main/java/com/scwang/refreshlayout/adapter/SmartViewHolder.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout.adapter; 2 | 3 | import android.content.res.Resources; 4 | import android.support.annotation.StringRes; 5 | import android.support.v4.content.ContextCompat; 6 | import android.support.v7.widget.RecyclerView; 7 | import android.util.TypedValue; 8 | import android.view.View; 9 | import android.widget.AdapterView; 10 | import android.widget.ImageView; 11 | import android.widget.TextView; 12 | 13 | public class SmartViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener { 14 | 15 | private final AdapterView.OnItemClickListener mListener; 16 | 17 | public SmartViewHolder(View itemView, AdapterView.OnItemClickListener mListener) { 18 | super(itemView); 19 | this.mListener = mListener; 20 | itemView.setOnClickListener(this); 21 | 22 | /** 23 | * 设置水波纹背景 24 | */ 25 | if (itemView.getBackground() == null) { 26 | TypedValue typedValue = new TypedValue(); 27 | Resources.Theme theme = itemView.getContext().getTheme(); 28 | int top = itemView.getPaddingTop(); 29 | int bottom = itemView.getPaddingBottom(); 30 | int left = itemView.getPaddingLeft(); 31 | int right = itemView.getPaddingRight(); 32 | if (theme.resolveAttribute(android.R.attr.selectableItemBackground, typedValue, true)) { 33 | itemView.setBackgroundResource(typedValue.resourceId); 34 | } 35 | itemView.setPadding(left, top, right, bottom); 36 | } 37 | } 38 | 39 | @Override 40 | public void onClick(View v) { 41 | if (mListener != null) { 42 | int position = getAdapterPosition(); 43 | if(position >= 0){ 44 | mListener.onItemClick(null, v, position, getItemId()); 45 | } 46 | } 47 | } 48 | 49 | private View findViewById(int id) { 50 | return id == 0 ? itemView : itemView.findViewById(id); 51 | } 52 | 53 | public SmartViewHolder text(int id, CharSequence sequence) { 54 | View view = findViewById(id); 55 | if (view instanceof TextView) { 56 | ((TextView) view).setText(sequence); 57 | } 58 | return this; 59 | } 60 | 61 | public SmartViewHolder text(int id,@StringRes int stringRes) { 62 | View view = findViewById(id); 63 | if (view instanceof TextView) { 64 | ((TextView) view).setText(stringRes); 65 | } 66 | return this; 67 | } 68 | 69 | public SmartViewHolder textColorId(int id, int colorId) { 70 | View view = findViewById(id); 71 | if (view instanceof TextView) { 72 | ((TextView) view).setTextColor(ContextCompat.getColor(view.getContext(), colorId)); 73 | } 74 | return this; 75 | } 76 | 77 | public SmartViewHolder image(int id, int imageId) { 78 | View view = findViewById(id); 79 | if (view instanceof ImageView) { 80 | ((ImageView) view).setImageResource(imageId); 81 | } 82 | return this; 83 | } 84 | } -------------------------------------------------------------------------------- /app/src/main/res/drawable/bc_background_panel.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 7 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_arrow_back_dark_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_arrow_back_gray_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_arrow_back_white_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_chevron_right.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_chevron_right_gray.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_feed_list_favorite.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_feed_list_mail.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_feed_list_photo.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_fly_refresh_folder.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_fly_refresh_info.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_fly_refresh_poll.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_fly_refresh_send.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_fly_refresh_smartphone.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_index_dashboard.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_index_home.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_index_notifications.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_list_divider.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_progress_hojder.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_experiment.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 13 | 18 | 24 | 29 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_fly_refresh_item.xml: -------------------------------------------------------------------------------- 1 | 2 | 14 | 15 | 23 | 24 | 31 | 32 | 38 | 39 | 48 | 49 | 58 | 59 | 60 | 61 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_index_main.xml: -------------------------------------------------------------------------------- 1 | 2 | 10 | 11 | 15 | 16 | 21 | 22 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_practice_banner.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 24 | 32 | 33 | 34 | 40 | 41 | 46 | 47 | 48 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_practice_qqbrowser.xml: -------------------------------------------------------------------------------- 1 | 2 | 10 | 11 | 15 | 16 | 22 | 35 | 41 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_practice_repast.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 28 | 35 | 41 | 42 | 43 | 48 | 49 | 54 | 55 | 56 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_practice_webview.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 18 | 19 | 20 | 21 | 22 | 23 | 28 | 34 | 35 | 36 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 53 | 54 | 55 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_bezier.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 27 | 32 | 33 | 34 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_circle.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 26 | 31 | 32 | 33 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_classics.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 20 | 33 | 39 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_delivery.xml: -------------------------------------------------------------------------------- 1 | 2 | 10 | 11 | 17 | 18 | 25 | 28 | 35 | 36 | 37 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_dropbox.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 25 | 28 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_fungame_battlecity.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 22 | 25 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_fungame_hitblock.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 22 | 25 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_material.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 26 | 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_phoenix.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 15 | 16 | 23 | 24 | 31 | 32 | 33 | 34 | 35 | 43 | 46 | 51 | 52 | 53 | 63 | 64 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_storehouse.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 28 | 34 | 35 | 36 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_taurus.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 15 | 16 | 23 | 24 | 31 | 32 | 33 | 34 | 35 | 43 | 46 | 51 | 52 | 53 | 63 | 64 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_water_drop.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 24 | 27 | 32 | 33 | 34 | 35 | 36 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_style_wave_swip.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 26 | 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_assign_code.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 20 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_assign_default.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 19 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_assign_xml.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 23 | 24 | 28 | 29 | 35 | 39 | 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_basic.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 19 | 25 | 29 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_custom.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 19 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_listener.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 21 | 25 | 28 | 37 | 38 | 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_overscroll.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 41 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_region.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 15 | 20 | 21 | 26 | 34 | 39 | 43 | 47 | 48 | 49 | 50 | 55 | 56 | 57 | 58 | 59 | 60 | -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_using_snaphelper.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 14 | 18 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /app/src/main/res/layout/fragment_refresh_practive.xml: -------------------------------------------------------------------------------- 1 | 8 | 9 | 12 | 13 | 17 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /app/src/main/res/layout/fragment_refresh_styles.xml: -------------------------------------------------------------------------------- 1 | 8 | 9 | 12 | 13 | 17 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /app/src/main/res/layout/fragment_refresh_using.xml: -------------------------------------------------------------------------------- 1 | 8 | 9 | 12 | 13 | 17 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /app/src/main/res/layout/listitem_movie_banner.xml: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 13 | 14 | 26 | 27 | -------------------------------------------------------------------------------- /app/src/main/res/layout/listitem_movie_header.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | -------------------------------------------------------------------------------- /app/src/main/res/layout/listitem_movie_item.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 17 | 18 | 22 | 27 | 33 | 38 | 43 | 44 | 45 | 46 | 47 | -------------------------------------------------------------------------------- /app/src/main/res/layout/listitem_practive_repast.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 17 | 18 | 24 | 25 | 30 | 31 | 38 | 39 | 46 | 47 | 48 | 49 | 50 | -------------------------------------------------------------------------------- /app/src/main/res/layout/listitem_style_delivery.xml: -------------------------------------------------------------------------------- 1 | 2 | 12 | 13 | 17 | 18 | 24 | 25 | 29 | 34 | 39 | 44 | 45 | 46 | 47 | 48 | 49 | -------------------------------------------------------------------------------- /app/src/main/res/layout/listitem_using_snaphelper.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 21 | 22 | -------------------------------------------------------------------------------- /app/src/main/res/menu/navigation.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 8 | 9 | 13 | 14 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/gif_header_repast.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/gif_header_repast.gif -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_item1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/ic_item1.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_item2.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/ic_item2.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_item3.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/ic_item3.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_avatar_1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_avatar_1.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_avatar_2.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_avatar_2.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_avatar_3.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_avatar_3.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_avatar_4.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_avatar_4.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_avatar_5.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_avatar_5.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_avatar_6.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_avatar_6.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_movie_header_12231501221682438.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_movie_header_12231501221682438.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_movie_header_12981501221820220.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_movie_header_12981501221820220.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_movie_header_48621499931969370.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_movie_header_48621499931969370.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_practice_repast_1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_practice_repast_1.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_practice_repast_2.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_practice_repast_2.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_practice_repast_3.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_practice_repast_3.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_practice_repast_4.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_practice_repast_4.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_practice_repast_5.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_practice_repast_5.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_practice_repast_6.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_practice_repast_6.jpg -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_weibo_home_1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_weibo_home_1.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/image_weibo_home_2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-hdpi/image_weibo_home_2.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-mdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-mdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /app/src/main/res/values-v19/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /app/src/main/res/values-v21/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 11 | 12 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /app/src/main/res/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #33aaff 4 | #2299ee 5 | #cc0094ff 6 | #FF4081 7 | 8 | #333333 9 | #444444 10 | #888888 11 | 12 | #FFFFFF 13 | #f2f2f2 14 | #33aaaaaa 15 | 16 | 17 | -------------------------------------------------------------------------------- /app/src/main/res/values/dimens.xml: -------------------------------------------------------------------------------- 1 | 2 | 240dp 3 | 16dp 4 | 16dp 5 | 6 | 16dp 7 | 16dp 8 | 9 | 10 | 0.5dp 11 | 12 | 10dp 13 | 15dp 14 | 10dp 15 | 5dp 16 | 17 | 12sp 18 | 14sp 19 | 16sp 20 | 17sp 21 | 19sp 22 | 20sp 23 | 24 | 25 | -------------------------------------------------------------------------------- /app/src/test/java/com/scwang/refreshlayout/ExampleUnitTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.refreshlayout; 2 | 3 | import org.junit.Test; 4 | 5 | import static org.junit.Assert.*; 6 | 7 | /** 8 | * Example local unit test, which will execute on the development machine (host). 9 | * 10 | * @see Testing documentation 11 | */ 12 | public class ExampleUnitTest { 13 | @Test 14 | public void addition_isCorrect() throws Exception { 15 | assertEquals(4, 2 + 2); 16 | } 17 | } -------------------------------------------------------------------------------- /art/app-debug.apk: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/app-debug.apk -------------------------------------------------------------------------------- /art/gif_BattleCity.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_BattleCity.gif -------------------------------------------------------------------------------- /art/gif_BezierRadar.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_BezierRadar.gif -------------------------------------------------------------------------------- /art/gif_Circle.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Circle.gif -------------------------------------------------------------------------------- /art/gif_Classics.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Classics.gif -------------------------------------------------------------------------------- /art/gif_Delivery.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Delivery.gif -------------------------------------------------------------------------------- /art/gif_Dropbox.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Dropbox.gif -------------------------------------------------------------------------------- /art/gif_FlyRefresh.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_FlyRefresh.gif -------------------------------------------------------------------------------- /art/gif_HitBlock.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_HitBlock.gif -------------------------------------------------------------------------------- /art/gif_Material.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Material.gif -------------------------------------------------------------------------------- /art/gif_Phoenix.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Phoenix.gif -------------------------------------------------------------------------------- /art/gif_StoreHouse.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_StoreHouse.gif -------------------------------------------------------------------------------- /art/gif_Taurus.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_Taurus.gif -------------------------------------------------------------------------------- /art/gif_WaterDrop.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_WaterDrop.gif -------------------------------------------------------------------------------- /art/gif_WaveSwipe.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_WaveSwipe.gif -------------------------------------------------------------------------------- /art/gif_demo_multitouch_1.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_demo_multitouch_1.gif -------------------------------------------------------------------------------- /art/gif_demo_multitouch_2.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_demo_multitouch_2.gif -------------------------------------------------------------------------------- /art/gif_practive_feedlist.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_practive_feedlist.gif -------------------------------------------------------------------------------- /art/gif_practive_profile.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_practive_profile.gif -------------------------------------------------------------------------------- /art/gif_practive_repast.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_practive_repast.gif -------------------------------------------------------------------------------- /art/gif_practive_smart.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_practive_smart.gif -------------------------------------------------------------------------------- /art/gif_practive_weibo.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_practive_weibo.gif -------------------------------------------------------------------------------- /art/gif_preview_textheader.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/gif_preview_textheader.gif -------------------------------------------------------------------------------- /art/jpg_preview_gifheader.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/jpg_preview_gifheader.jpg -------------------------------------------------------------------------------- /art/jpg_preview_textheader.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/jpg_preview_textheader.jpg -------------------------------------------------------------------------------- /art/jpg_preview_xml_define.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/jpg_preview_xml_define.jpg -------------------------------------------------------------------------------- /art/jpg_uml.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/jpg_uml.jpg -------------------------------------------------------------------------------- /art/md_donationlist.md: -------------------------------------------------------------------------------- 1 | # 捐赠列表 2 | 3 | 非常感谢列表中的朋友,你们的肯定和支持是我前进的最大动力! 4 | 5 | |昵称|日期|方式|留言|友情连接| 6 | |:---:|:---:|:---:|:---:|:---:| 7 | |[pay_join]|2017-9-6|腾讯|👍|| 8 | |[pay_join]|2017-9-6|腾讯|👍|| 9 | |[未留名]|2017-9-5|微信|支持呢!好厉害大神!| | 10 | |[pay_join]|2017-8-29|腾讯|👍|| 11 | |[未留名]|2017-8-28|微信|好棒| | 12 | |[pay_join]|2017-8-27|腾讯|👍|| 13 | |[未留名]|2017-8-24|微信|重要的是支持你| | 14 | |[pay_join]|2017-8-24|腾讯|👍|| 15 | |[pay_join]|2017-8-23|腾讯|👍|| 16 | |[pay_join]|2017-8-20|腾讯|👍|| 17 | |[未留名]|2017-8-16|微信|不错,加油| | 18 | |[pay_join]|2017-8-15|腾讯|👍|| 19 | |[未留名]|2017-8-14|微信|大神,请手下我的膝盖| | 20 | |[未留名]|2017-8-13|微信|| | 21 | |[未留名]|2017-8-13|微信|| | 22 | |[pay_join]|2017-8-11|腾讯|👍|| 23 | |[pay_join]|2017-8-10|腾讯|👍|| 24 | |[pay_join]|2017-8-10|腾讯|👍|| 25 | |[pay_join]|2017-8-9|腾讯|👍|| 26 | |[pay_join]|2017-8-4|腾讯||| 27 | |[pay_join]|2017-8-3|腾讯||| 28 | |[pay_join]|2017-8-2|腾讯||| 29 | |[pay_join]|2017-8-2|腾讯||| 30 | |[未留名]|2017-8-2|微信|给大神端茶-github|| 31 | |[pay_join]|2017-8-1|腾讯||| 32 | |[pay_join]|2017-8-1|腾讯||| 33 | |[pay_join]|2017-7-30|腾讯||| 34 | |[pay_join]|2017-7-29|腾讯||| 35 | |[pay_join]|2017-7-27|腾讯||| 36 | |[pay_join]|2017-7-27|腾讯||| 37 | |□□|2017-7-27|微信|👍👍👍👍👍|| 38 | |XiaoJiaqing|2017-7-26|微信|👍|[XiaoJianqing](https://github.com/XiaoJiaqing)| 39 | |[未留名]|2017-7-26|阿里|👍| | 40 | |[未留名]|2017-7-26|腾讯|大神,请你喝水|| 41 | |Bter|2017-7-23|微信|不错的smart|| 42 | |[pay_join]|2017-7-23|腾讯||| 43 | |[未留名]|2017-7-21|微信|| | 44 | |[未留名]|2017-7-19|阿里|| | 45 | |[未留名]|2017-7-18|阿里|| | 46 | |[未留名]|2017-7-17|微信|| | 47 | |[未留名]|2017-7-17|微信|| | 48 | |[未留名]|2017-7-15|微信|👍| | 49 | |[未留名]|2017-7-15|微信|git小助手给你点赞|| 50 | |[未留名]|2017-7-14|微信|👍| | 51 | |[未留名]|2017-7-14|微信|| | 52 | |[未留名]|2017-7-14|微信|👍| | 53 | |[未留名]|2017-7-13|微信|👍| | 54 | |剑弑九幽|2017-7-13|阿里|👍|[jianshijiuyou](https://github.com/jianshijiuyou)| 55 | |zxy198717|2017-7-13|微信|👍|[zxy198717](https://github.com/zxy198717)| 56 | |[未留名]|2017-7-12|阿里|| | 57 | |matt|2017-7-12|微信|👍|[addappcn](https://github.com/addappcn)| 58 | |[未留名]|2017-7-12|微信|谢谢分享| | 59 | |RainliFu|2017-7-12|微信|👍|[RainliFu](https://github.com/RainliFu)| 60 | |[未留名]|2017-7-12|微信|Six!Six!Six| | 61 | |[未留名]|2017-7-11|微信|👍| | 62 | |[未留名]|2017-7-11|微信|感谢你的开源项目| | 63 | |sugarya|2017-7-11|微信|👍|[sugarya](https://github.com/sugarya)| 64 | |stormzhang|2017-7-11|微信|👍|[stormzhang](https://github.com/stormzhang) 65 | |[未留名]|2017-7-10|微信| | | -------------------------------------------------------------------------------- /art/md_multitouch.md: -------------------------------------------------------------------------------- 1 | # 多点触摸 2 | 3 | 多点触摸就是多个手指一起滑动,直接看效果吧~ 4 | 5 | ![](https://github.com/scwang90/SmartRefreshLayout/raw/master/art/gif_demo_multitouch_1.gif) ![](https://github.com/scwang90/SmartRefreshLayout/raw/master/art/gif_demo_multitouch_2.gif) 6 | 7 | -------------------------------------------------------------------------------- /art/md_update.md: -------------------------------------------------------------------------------- 1 | # 更新日志 2 | 3 | ## V 1.0.4 (开发中) 4 | >添加:类似淘宝二楼的二级下拉刷新 5 | >添加:srlEnableBounceShowHeaderAndFooter 属性和对应的set方法,控制越界回弹时候是否显示Header和Footer 6 | 7 | ## V 1.0.3 8 | >添加:下拉和上拉时,支持多点触摸,手势不冲突 9 | >添加:当 内容视图不满一页时,默认不能上拉加载更多,不过必要时,通过设置还是可以上拉的 10 | >添加:为 Heaer和Footer添加拖动时水平方向坐标 x,实现左右拖动Header的效果 11 | >添加:为 Refreshlayout 添加多点触摸支持,在多个手指触摸式不会发生冲突,并且随意拖动 12 | >添加:为 Refreshlayout 添加 EnableLoadmoreWhenContentNotFull 功能 13 | >添加:为 Refreshlayout 添加 srlEnabledNestedScroll 属性 和 srlEnabledNestedScroll 方法 14 | >添加:为 RefreshHeader 添加 srlEnableHorizontalDrag 属性 和 setEnableHorizontalDrag 方法 15 | >添加:为 ClassicsHeader 添加 srlEnableLastTime 属性 和 setEnableLastTime 方法 控制时间显示 16 | >添加:为 ClassicsHeader 添加 srlDrawableArrow 属性 和 setArrowResource 方法 改变箭头图片 17 | >添加:为 ClassicsHeader 添加 srlProgressDrawable 属性 和 setProgressResource 改变转动图片 18 | >添加:为 ClassicsHeader 添加 srlTextSizeTime 属性 和 setTextSizeTime 方法 设置字体大小 19 | >添加:为 ClassicsHeader 添加 srlTextTimeMarginTop 属性 时间文字的上间距 20 | >添加:为 ClassicsFooter 添加 srlDrawableArrow 属性 和 setArrowResource 方法 改变箭头图片 21 | >添加:为 ClassicsFooter 添加 srlDrawableProgress 属性 和 setProgressResource 改变转动图片 22 | >添加:为 ClassicsHeader 和 ClassicsFooter 添加 srlFinishDuration 属性 和 setFinishDuration 方法 23 | >添加:为 ClassicsHeader 和 ClassicsFooter 添加 srlDrawableMarginRight 属性 设置图片间距 24 | >添加:为 ClassicsHeader 和 ClassicsFooter 添加 srlTextSizeTitle 属性 和 setTextSizeTitle 方法 25 | >添加:为 ClassicsHeader 和 ClassicsFooter 添加 srlDrawableSize 属性 和 setDrawableSize 方法 26 | >添加:为 ClassicsHeader 和 ClassicsFooter 添加 srlDrawableArrowSize 属性 和 setDrawableArrowSize 方法 27 | >添加:为 ClassicsHeader 和 ClassicsFooter 添加 srlDrawableProgressSize 属性 和 setDrawableProgressSize 方法 28 | >修改:改 EnableLoadMore 由默认true->变为false,并增加智能开启功能 29 | >修改:改 EnableNestedScrolling 由默认true->变为false,并增加智能开启功能 30 | >修复:在 ClassicsFooter 加载失败时,显示成了加载完成的错误 31 | >修复:正在刷新时,向上拖动导致的栈溢出崩溃 32 | >修复:autoRefresh(0) 的 延时为没有延时 33 | >修复:StaggeredGridLayoutManager 导致的 autoLoadmore 无效 34 | >修复:列表监听滚动无效的问题 35 | >修复:内存泄漏问题 36 | >修复:隐式去除对 support-design 支持包的依赖 37 | 38 | ## V 1.0.2 39 | >添加:AbsListView 和 RecyclerView 的越界回弹 40 | >添加:srlFixedHeaderViewId 属性,指定固定的视图Id 41 | >添加:srlFixedFooterViewId 属性,指定固定的视图Id 42 | >添加:srlEnablePureScrollMode 属性,是否开启纯滚动模式 43 | >添加:srlEnableNestedScrolling 属性,是否开启嵌套滚动NestedScrolling 44 | >添加:srlEnableScrollContentWhenLoaded 属性,是否在加载完成之后滚动内容显示新数据 45 | >添加:setScrollBoundaryDecider 方法,设置滚动边界判断 46 | >添加:finishRefresh(boolean success);方法,完成刷新,并设置是否成功 47 | >添加:finishLoadmore(boolean success);方法,完成加载,并设置是否成功 48 | >修复:DeliveryHeader,DropboxHeader 在API-17以下显示不全的问题 49 | 50 | ## V 1.0.1 51 | >添加:srlEnableAutoLoadmore 属性 52 | >修改:srlExtendHeaderRate 属性为:srlHeaderMaxDragRate 53 | >修改:srlExtendFooterRate 属性为:srlFooterMaxDragRate 54 | >修复:DeliveryHeader,DropboxHeader 在API-21以下崩溃的问题 55 | 56 | ## V 1.0.0 57 | >添加:DeliveryHeader,DropboxHeader 58 | -------------------------------------------------------------------------------- /art/pay_alipay.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/pay_alipay.jpg -------------------------------------------------------------------------------- /art/pay_tencent.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/pay_tencent.jpg -------------------------------------------------------------------------------- /art/pay_wxpay.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/pay_wxpay.jpg -------------------------------------------------------------------------------- /art/png_apk_rqcode.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/png_apk_rqcode.png -------------------------------------------------------------------------------- /art/png_ptr_elema.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/png_ptr_elema.png -------------------------------------------------------------------------------- /art/png_ptr_meituan.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/png_ptr_meituan.png -------------------------------------------------------------------------------- /art/png_ptr_tianmao.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/wolfking0608/SmartRefreshLayout/1af1907b88dce59e75985094503964b0b4c1d12d/art/png_ptr_tianmao.png -------------------------------------------------------------------------------- /art/svg_minsdkapi.svg: -------------------------------------------------------------------------------- 1 | 4 | 5 | 9 | 10 | 14 | 15 | 18 | 19 | 20 | 21 | 22 | 27 | 28 | 29 | 30 | 31 | 34 | 35 | 38 | 39 | 42 | 43 | 44 | 49 | 50 | MinSdk 55 | 56 | MinSdk 59 | 60 | 12 65 | 66 | 12 69 | 70 | 71 | 72 | -------------------------------------------------------------------------------- /bintrayUpload.bat: -------------------------------------------------------------------------------- 1 | gradlew clean build bintrayUpload -PbintrayUser=scwang90 -PbintrayKey=%1 -PdryRun=false -------------------------------------------------------------------------------- /build.gradle: -------------------------------------------------------------------------------- 1 | // Top-level build file where you can add configuration options common to all sub-projects/modules. 2 | 3 | buildscript { 4 | repositories { 5 | jcenter() 6 | } 7 | dependencies { 8 | classpath 'com.android.tools.build:gradle:2.3.2' 9 | 10 | // NOTE: Do not place your application dependencies here; they belong 11 | // in the individual module build.gradle files 12 | classpath 'com.novoda:bintray-release:0.4.0' 13 | } 14 | } 15 | 16 | allprojects { 17 | repositories { 18 | jcenter() 19 | } 20 | tasks.withType(Javadoc) { 21 | options{ 22 | encoding "UTF-8" 23 | charSet 'UTF-8' 24 | links "http://docs.oracle.com/javase/7/docs/api" 25 | } 26 | } 27 | } 28 | 29 | task clean(type: Delete) { 30 | delete rootProject.buildDir 31 | } 32 | -------------------------------------------------------------------------------- /refresh-footer/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /refresh-footer/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.library' 2 | //apply plugin: 'com.novoda.bintray-release' 3 | //apply plugin: 'me.tatarka.retrolambda' 4 | 5 | android { 6 | compileSdkVersion 26 7 | buildToolsVersion "26.0.1" 8 | 9 | defaultConfig { 10 | minSdkVersion 12 11 | targetSdkVersion 26 12 | versionCode 1 13 | versionName "1.0" 14 | 15 | testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" 16 | 17 | } 18 | buildTypes { 19 | release { 20 | minifyEnabled false 21 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 22 | } 23 | } 24 | lintOptions { 25 | abortOnError false 26 | } 27 | } 28 | 29 | dependencies { 30 | compile fileTree(include: ['*.jar'], dir: 'libs') 31 | androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { 32 | exclude group: 'com.android.support', module: 'support-annotations' 33 | }) 34 | testCompile 'junit:junit:4.12' 35 | provided 'com.android.support:support-compat:26.0.0-alpha1' 36 | provided project(':refresh-layout') 37 | } 38 | 39 | //publish { 40 | // userOrg = 'scwang90' 41 | // groupId = 'com.scwang.smartrefresh' 42 | // artifactId = 'SmartRefreshFooter' 43 | // version = '1.0.0-alpha-1' 44 | // description = 'Some delicate footers of SmartRefreshLayout' 45 | // website = "https://github.com/scwang90/${rootProject.name}" 46 | //} -------------------------------------------------------------------------------- /refresh-footer/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # By default, the flags in this file are appended to flags specified 3 | # in E:\Android\android-sdk/tools/proguard/proguard-android.txt 4 | # You can edit the include path and order by changing the proguardFiles 5 | # directive in build.gradle. 6 | # 7 | # For more details, see 8 | # http://developer.android.com/guide/developing/tools/proguard.html 9 | 10 | # Add any project specific keep options here: 11 | 12 | # If your project uses WebView with JS, uncomment the following 13 | # and specify the fully qualified class name to the JavaScript interface 14 | # class: 15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 16 | # public *; 17 | #} 18 | 19 | # Uncomment this to preserve the line number information for 20 | # debugging stack traces. 21 | #-keepattributes SourceFile,LineNumberTable 22 | 23 | # If you keep the line number information, uncomment this to 24 | # hide the original source file name. 25 | #-renamesourcefileattribute SourceFile 26 | -------------------------------------------------------------------------------- /refresh-footer/src/androidTest/java/com/scwang/smartrefresh/footer/ExampleInstrumentedTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefreshfooter; 2 | 3 | import android.content.Context; 4 | import android.support.test.InstrumentationRegistry; 5 | import android.support.test.runner.AndroidJUnit4; 6 | 7 | import org.junit.Test; 8 | import org.junit.runner.RunWith; 9 | 10 | import static org.junit.Assert.*; 11 | 12 | /** 13 | * Instrumentation test, which will execute on an Android device. 14 | * 15 | * @see Testing documentation 16 | */ 17 | @RunWith(AndroidJUnit4.class) 18 | public class ExampleInstrumentedTest { 19 | @Test 20 | public void useAppContext() throws Exception { 21 | // Context of the app under test. 22 | Context appContext = InstrumentationRegistry.getTargetContext(); 23 | 24 | assertEquals("com.scwang.smartrefreshfooter.test", appContext.getPackageName()); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /refresh-footer/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /refresh-footer/src/main/res/values/attrs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /refresh-footer/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | SmartRefreshFooter 3 | 4 | -------------------------------------------------------------------------------- /refresh-footer/src/test/java/com/scwang/smartrefresh/footer/ExampleUnitTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefreshfooter; 2 | 3 | import org.junit.Test; 4 | 5 | import static org.junit.Assert.*; 6 | 7 | /** 8 | * Example local unit test, which will execute on the development machine (host). 9 | * 10 | * @see Testing documentation 11 | */ 12 | public class ExampleUnitTest { 13 | @Test 14 | public void addition_isCorrect() throws Exception { 15 | assertEquals(4, 2 + 2); 16 | } 17 | } -------------------------------------------------------------------------------- /refresh-header/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /refresh-header/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.library' 2 | apply plugin: 'com.novoda.bintray-release' 3 | 4 | android { 5 | compileSdkVersion 26 6 | buildToolsVersion "26.0.1" 7 | 8 | defaultConfig { 9 | minSdkVersion 12 10 | targetSdkVersion 26 11 | versionCode 1 12 | versionName "1.0" 13 | 14 | testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" 15 | 16 | } 17 | buildTypes { 18 | release { 19 | minifyEnabled false 20 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 21 | } 22 | } 23 | lintOptions { 24 | abortOnError false 25 | } 26 | } 27 | 28 | dependencies { 29 | compile fileTree(include: ['*.jar'], dir: 'libs') 30 | androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { 31 | exclude group: 'com.android.support', module: 'support-annotations' 32 | }) 33 | testCompile 'junit:junit:4.12' 34 | provided 'com.android.support:support-compat:26.0.0-alpha1' 35 | provided project(':refresh-layout') 36 | } 37 | 38 | publish { 39 | userOrg = 'scwang90' 40 | groupId = 'com.scwang.smartrefresh' 41 | artifactId = 'SmartRefreshHeader' 42 | version = '1.0.4-alpha-0' 43 | description = 'Some delicate headers of SmartRefreshLayout' 44 | website = "https://github.com/scwang90/${rootProject.name}" 45 | } 46 | -------------------------------------------------------------------------------- /refresh-header/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # By default, the flags in this file are appended to flags specified 3 | # in E:\Android\android-sdk/tools/proguard/proguard-android.txt 4 | # You can edit the include path and order by changing the proguardFiles 5 | # directive in build.gradle. 6 | # 7 | # For more details, see 8 | # http://developer.android.com/guide/developing/tools/proguard.html 9 | 10 | # Add any project specific keep options here: 11 | 12 | # If your project uses WebView with JS, uncomment the following 13 | # and specify the fully qualified class name to the JavaScript interface 14 | # class: 15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 16 | # public *; 17 | #} 18 | 19 | # Uncomment this to preserve the line number information for 20 | # debugging stack traces. 21 | #-keepattributes SourceFile,LineNumberTable 22 | 23 | # If you keep the line number information, uncomment this to 24 | # hide the original source file name. 25 | #-renamesourcefileattribute SourceFile 26 | -------------------------------------------------------------------------------- /refresh-header/src/androidTest/java/com/scwang/smartrefresh/header/ExampleInstrumentedTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.header; 2 | 3 | import android.content.Context; 4 | import android.support.test.InstrumentationRegistry; 5 | import android.support.test.runner.AndroidJUnit4; 6 | 7 | import org.junit.Test; 8 | import org.junit.runner.RunWith; 9 | 10 | import static org.junit.Assert.*; 11 | 12 | /** 13 | * Instrumentation test, which will execute on an Android device. 14 | * 15 | * @see Testing documentation 16 | */ 17 | @RunWith(AndroidJUnit4.class) 18 | public class ExampleInstrumentedTest { 19 | @Test 20 | public void useAppContext() throws Exception { 21 | // Context of the app under test. 22 | Context appContext = InstrumentationRegistry.getTargetContext(); 23 | 24 | assertEquals("com.scwang.smartrefresh.header.test", appContext.getPackageName()); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /refresh-header/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/flyrefresh/FlyView.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.header.flyrefresh; 2 | 3 | import android.content.Context; 4 | import android.util.AttributeSet; 5 | 6 | import com.scwang.smartrefresh.layout.internal.pathview.PathsView; 7 | import com.scwang.smartrefresh.layout.util.DensityUtil; 8 | 9 | /** 10 | * 纸飞机视图 11 | * Created by SCWANG on 2017/6/6. 12 | */ 13 | 14 | public class FlyView extends PathsView { 15 | 16 | public FlyView(Context context) { 17 | super(context); 18 | this.initView(context, null, 0); 19 | } 20 | 21 | public FlyView(Context context, AttributeSet attrs) { 22 | super(context, attrs); 23 | this.initView(context, attrs, 0); 24 | } 25 | 26 | public FlyView(Context context, AttributeSet attrs, int defStyleAttr) { 27 | super(context, attrs, defStyleAttr); 28 | this.initView(context, attrs, defStyleAttr); 29 | } 30 | 31 | private void initView(Context context, AttributeSet attrs, int defStyleAttr) { 32 | parserColors(0xffffffff); 33 | parserPaths("M2.01,21L23,12 2.01,3 2,10l15,2 -15,2z"); 34 | setMinimumWidth(DensityUtil.dp2px(25)); 35 | setMinimumHeight(DensityUtil.dp2px(25)); 36 | } 37 | 38 | @Override 39 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 40 | setMeasuredDimension(resolveSize(getSuggestedMinimumWidth(), widthMeasureSpec), 41 | resolveSize(getSuggestedMinimumHeight(), heightMeasureSpec)); 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/flyrefresh/PathInterpolatorCompatApi21.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2015 The Android Open Source Project 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package com.scwang.smartrefresh.header.flyrefresh; 18 | 19 | import android.graphics.Path; 20 | import android.support.annotation.RequiresApi; 21 | import android.annotation.TargetApi; 22 | import android.view.animation.Interpolator; 23 | import android.view.animation.PathInterpolator; 24 | 25 | /** 26 | * API 21+ implementation for path interpolator compatibility. 27 | */ 28 | 29 | @RequiresApi(21) 30 | @TargetApi(21) 31 | class PathInterpolatorCompatApi21 { 32 | 33 | private PathInterpolatorCompatApi21() { 34 | // prevent instantiation 35 | } 36 | 37 | public static Interpolator create(Path path) { 38 | return new PathInterpolator(path); 39 | } 40 | 41 | public static Interpolator create(float controlX, float controlY) { 42 | return new PathInterpolator(controlX, controlY); 43 | } 44 | 45 | public static Interpolator create(float controlX1, float controlY1, 46 | float controlX2, float controlY2) { 47 | return new PathInterpolator(controlX1, controlY1, controlX2, controlY2); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/flyrefresh/PathInterpolatorCompatBase.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2015 The Android Open Source Project 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package com.scwang.smartrefresh.header.flyrefresh; 18 | 19 | import android.graphics.Path; 20 | import android.support.annotation.RequiresApi; 21 | import android.annotation.TargetApi; 22 | import android.view.animation.Interpolator; 23 | 24 | /** 25 | * Base implementation for path interpolator compatibility. 26 | */ 27 | 28 | @RequiresApi(9) 29 | @TargetApi(9) 30 | class PathInterpolatorCompatBase { 31 | 32 | private PathInterpolatorCompatBase() { 33 | // prevent instantiation 34 | } 35 | 36 | public static Interpolator create(Path path) { 37 | return new PathInterpolatorGingerbread(path); 38 | } 39 | 40 | public static Interpolator create(float controlX, float controlY) { 41 | return new PathInterpolatorGingerbread(controlX, controlY); 42 | } 43 | 44 | public static Interpolator create(float controlX1, float controlY1, 45 | float controlX2, float controlY2) { 46 | return new PathInterpolatorGingerbread(controlX1, controlY1, controlX2, controlY2); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/internal/LookupTableInterpolator.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2015 The Android Open Source Project 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package com.scwang.smartrefresh.header.internal; 18 | 19 | import android.view.animation.Interpolator; 20 | 21 | /** 22 | * An {@link Interpolator} that uses a lookup table to compute an interpolation based on a 23 | * given input. 24 | */ 25 | abstract class LookupTableInterpolator implements Interpolator { 26 | 27 | private final float[] mValues; 28 | private final float mStepSize; 29 | 30 | public LookupTableInterpolator(float[] values) { 31 | mValues = values; 32 | mStepSize = 1f / (mValues.length - 1); 33 | } 34 | 35 | @Override 36 | public float getInterpolation(float input) { 37 | if (input >= 1.0f) { 38 | return 1.0f; 39 | } 40 | if (input <= 0f) { 41 | return 0f; 42 | } 43 | 44 | // Calculate index - We use min with length - 2 to avoid IndexOutOfBoundsException when 45 | // we lerp (linearly interpolate) in the return statement 46 | int position = Math.min((int) (input * (mValues.length - 1)), mValues.length - 2); 47 | 48 | // Calculate values to account for small offsets as the lookup table has discrete values 49 | float quantized = position * mStepSize; 50 | float diff = input - quantized; 51 | float weight = diff / mStepSize; 52 | 53 | // Linearly interpolate between the table values 54 | return mValues[position] + weight * (mValues[position + 1] - mValues[position]); 55 | } 56 | 57 | } 58 | -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/storehouse/StoreHouseBarItem.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.header.storehouse; 2 | 3 | import android.graphics.Canvas; 4 | import android.graphics.Paint; 5 | import android.graphics.PointF; 6 | import android.view.animation.Animation; 7 | import android.view.animation.Transformation; 8 | 9 | import java.util.Random; 10 | 11 | /** 12 | * 13 | * Created by srain on 11/6/14. 14 | */ 15 | public class StoreHouseBarItem extends Animation { 16 | 17 | public PointF midPoint; 18 | public float translationX; 19 | public int index; 20 | 21 | private final Paint mPaint = new Paint(); 22 | private float mFromAlpha = 1.0f; 23 | private float mToAlpha = 0.4f; 24 | private PointF mCStartPoint; 25 | private PointF mCEndPoint; 26 | 27 | public StoreHouseBarItem(int index, PointF start, PointF end, int color, int lineWidth) { 28 | this.index = index; 29 | 30 | midPoint = new PointF((start.x + end.x) / 2, (start.y + end.y) / 2); 31 | 32 | mCStartPoint = new PointF(start.x - midPoint.x, start.y - midPoint.y); 33 | mCEndPoint = new PointF(end.x - midPoint.x, end.y - midPoint.y); 34 | 35 | setColor(color); 36 | setLineWidth(lineWidth); 37 | mPaint.setAntiAlias(true); 38 | mPaint.setStyle(Paint.Style.STROKE); 39 | } 40 | 41 | public void setLineWidth(int width) { 42 | mPaint.setStrokeWidth(width); 43 | } 44 | 45 | public void setColor(int color) { 46 | mPaint.setColor(color); 47 | } 48 | 49 | public void resetPosition(int horizontalRandomness) { 50 | Random random = new Random(); 51 | int randomNumber = -random.nextInt(horizontalRandomness) + horizontalRandomness; 52 | translationX = randomNumber; 53 | } 54 | 55 | @Override 56 | protected void applyTransformation(float interpolatedTime, Transformation t) { 57 | float alpha = mFromAlpha; 58 | alpha = alpha + ((mToAlpha - alpha) * interpolatedTime); 59 | setAlpha(alpha); 60 | } 61 | 62 | public void start(float fromAlpha, float toAlpha) { 63 | mFromAlpha = fromAlpha; 64 | mToAlpha = toAlpha; 65 | super.start(); 66 | } 67 | 68 | public void setAlpha(float alpha) { 69 | mPaint.setAlpha((int) (alpha * 255)); 70 | } 71 | 72 | public void draw(Canvas canvas) { 73 | canvas.drawLine(mCStartPoint.x, mCStartPoint.y, mCEndPoint.x, mCEndPoint.y, mPaint); 74 | } 75 | } -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/waterdrop/Circle.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.header.waterdrop; 2 | 3 | /** 4 | * Created by xiayong on 2015/6/25. 5 | * 实心圆 6 | */ 7 | public class Circle { 8 | public float x;//圆x坐标 9 | public float y;//圆y坐标 10 | public float radius;//圆半径 11 | public int color;//圆的颜色 12 | } -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/waveswipe/AnimationImageView.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2015 RECRUIT LIFESTYLE CO., LTD. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package com.scwang.smartrefresh.header.waveswipe; 18 | 19 | import android.content.Context; 20 | import android.view.animation.Animation; 21 | import android.widget.ImageView; 22 | 23 | /** 24 | * @author amyu 25 | */ 26 | public class AnimationImageView extends ImageView { 27 | 28 | /** 29 | * AnimationのStartとEnd時にListenerにアレする 30 | */ 31 | private Animation.AnimationListener mListener; 32 | 33 | /** 34 | * コンストラクタ 35 | * {@inheritDoc} 36 | */ 37 | public AnimationImageView(Context context) { 38 | super(context); 39 | } 40 | 41 | /** 42 | * {@link AnimationImageView#mListener} のセット 43 | * 44 | * @param listener {@link android.view.animation.Animation.AnimationListener} 45 | */ 46 | public void setAnimationListener(Animation.AnimationListener listener) { 47 | mListener = listener; 48 | } 49 | 50 | /** 51 | * ViewのAnimationのStart時にセットされたListenerの {@link android.view.animation.Animation.AnimationListener#onAnimationStart(Animation)} 52 | * を呼ぶ 53 | */ 54 | @Override public void onAnimationStart() { 55 | super.onAnimationStart(); 56 | if (mListener != null) { 57 | mListener.onAnimationStart(getAnimation()); 58 | } 59 | } 60 | 61 | /** 62 | * ViewのAnimationのEnd時にセットされたListenerの {@link android.view.animation.Animation.AnimationListener#onAnimationEnd(Animation)} 63 | * (Animation)} を呼ぶ 64 | */ 65 | @Override public void onAnimationEnd() { 66 | super.onAnimationEnd(); 67 | if (mListener != null) { 68 | mListener.onAnimationEnd(getAnimation()); 69 | } 70 | } 71 | } -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/waveswipe/DisplayUtil.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) RECRUIT LIFESTYLE CO., LTD. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package com.scwang.smartrefresh.header.waveswipe; 18 | 19 | import android.content.Context; 20 | import android.content.res.Resources; 21 | import android.util.DisplayMetrics; 22 | 23 | /** 24 | * @author amyu 25 | */ 26 | public class DisplayUtil { 27 | 28 | private DisplayUtil(){} 29 | 30 | /** 31 | * 現在の向きが600dpを超えているかどうか 32 | * 33 | * @param context {@link Context} 34 | * @return 600dpを超えているかどうか 35 | */ 36 | public static boolean isOver600dp(Context context) { 37 | Resources resources = context.getResources(); 38 | DisplayMetrics displayMetrics = resources.getDisplayMetrics(); 39 | return displayMetrics.widthPixels / displayMetrics.density >= 600; 40 | } 41 | } -------------------------------------------------------------------------------- /refresh-header/src/main/java/com/scwang/smartrefresh/header/waveswipe/DropBounceInterpolator.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.header.waveswipe; 2 | /* 3 | * Copyright (C) 2015 RECRUIT LIFESTYLE CO., LTD. 4 | * 5 | * Licensed under the Apache License, Version 2.0 (the "License"); 6 | * you may not use this file except in compliance with the License. 7 | * You may obtain a copy of the License at 8 | * 9 | * http://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | 18 | import android.content.Context; 19 | import android.util.AttributeSet; 20 | import android.view.animation.Interpolator; 21 | 22 | /** 23 | * @author amyu 24 | * 25 | * {@link WaveView#mDropBounceHorizontalAnimator} と {@link WaveView#mDropVertexAnimator} にセットするInterpolator 26 | * WavePullToRefresh/DropBounceInterpolator.gcxにグラフの詳細 27 | */ 28 | public class DropBounceInterpolator implements Interpolator { 29 | 30 | public DropBounceInterpolator() { 31 | } 32 | 33 | @SuppressWarnings({"UnusedDeclaration"}) 34 | public DropBounceInterpolator(Context context, AttributeSet attrs) { 35 | } 36 | 37 | /** 38 | * {@inheritDoc} 39 | * 40 | * @param v 41 | * @return 42 | */ 43 | @Override 44 | public float getInterpolation(float v) { 45 | //y = -19 * (x - 0.125)^2 + 1.3 (0 <= x < 0.25) 46 | //y = -6.5 * (x - 0.625)^2 + 1.1 (0.5 <= x < 0.75) 47 | //y = 0 (0.25 <= x < 0.5 && 0.75 <= x <=1) 48 | 49 | if (v < 0.25f) { 50 | return -38.4f * (float) Math.pow(v - 0.125, 2) + 0.6f; 51 | } else if (v >= 0.5 && v < 0.75) { 52 | return -19.2f * (float) Math.pow(v - 0.625, 2) + 0.3f; 53 | } else { 54 | return 0; 55 | } 56 | } 57 | } -------------------------------------------------------------------------------- /refresh-header/src/main/res/values/attrs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | -------------------------------------------------------------------------------- /refresh-header/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | SmartRefreshHeader 3 | 4 | -------------------------------------------------------------------------------- /refresh-header/src/test/java/com/scwang/smartrefresh/header/ExampleUnitTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.header; 2 | 3 | import org.junit.Test; 4 | 5 | import static org.junit.Assert.*; 6 | 7 | /** 8 | * Example local unit test, which will execute on the development machine (host). 9 | * 10 | * @see Testing documentation 11 | */ 12 | public class ExampleUnitTest { 13 | @Test 14 | public void addition_isCorrect() throws Exception { 15 | assertEquals(4, 2 + 2); 16 | } 17 | } -------------------------------------------------------------------------------- /refresh-layout/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /refresh-layout/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.library' 2 | apply plugin: 'com.novoda.bintray-release' 3 | 4 | android { 5 | compileSdkVersion 26 6 | buildToolsVersion "26.0.1" 7 | 8 | defaultConfig { 9 | minSdkVersion 12 10 | targetSdkVersion 26 11 | versionCode 1 12 | versionName "1.0" 13 | 14 | testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" 15 | 16 | } 17 | buildTypes { 18 | release { 19 | minifyEnabled false 20 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 21 | } 22 | } 23 | lintOptions { 24 | abortOnError false 25 | } 26 | } 27 | 28 | dependencies { 29 | compile fileTree(dir: 'libs', include: ['*.jar']) 30 | androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { 31 | exclude group: 'com.android.support', module: 'support-annotations' 32 | }) 33 | testCompile 'junit:junit:4.12' 34 | provided 'com.android.support:design:26.0.0-alpha1' 35 | } 36 | 37 | publish { 38 | userOrg = 'scwang90' 39 | groupId = 'com.scwang.smartrefresh' 40 | artifactId = 'SmartRefreshLayout' 41 | version = '1.0.3' 42 | description = 'An intelligent refresh layout' 43 | website = "https://github.com/scwang90/${rootProject.name}" 44 | } -------------------------------------------------------------------------------- /refresh-layout/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # By default, the flags in this file are appended to flags specified 3 | # in E:\Android\android-sdk/tools/proguard/proguard-android.txt 4 | # You can edit the include path and order by changing the proguardFiles 5 | # directive in build.gradle. 6 | # 7 | # For more details, see 8 | # http://developer.android.com/guide/developing/tools/proguard.html 9 | 10 | # Add any project specific keep options here: 11 | 12 | # If your project uses WebView with JS, uncomment the following 13 | # and specify the fully qualified class name to the JavaScript interface 14 | # class: 15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 16 | # public *; 17 | #} 18 | 19 | # Uncomment this to preserve the line number information for 20 | # debugging stack traces. 21 | #-keepattributes SourceFile,LineNumberTable 22 | 23 | # If you keep the line number information, uncomment this to 24 | # hide the original source file name. 25 | #-renamesourcefileattribute SourceFile 26 | -------------------------------------------------------------------------------- /refresh-layout/src/androidTest/java/com/scwang/smartrefresh/layout/ExampleInstrumentedTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout; 2 | 3 | import android.content.Context; 4 | import android.support.test.InstrumentationRegistry; 5 | import android.support.test.runner.AndroidJUnit4; 6 | 7 | import org.junit.Test; 8 | import org.junit.runner.RunWith; 9 | 10 | import static org.junit.Assert.*; 11 | 12 | /** 13 | * Instrumentation test, which will execute on an Android device. 14 | * 15 | * @see Testing documentation 16 | */ 17 | @RunWith(AndroidJUnit4.class) 18 | public class ExampleInstrumentedTest { 19 | @Test 20 | public void useAppContext() throws Exception { 21 | // Context of the app under test. 22 | Context appContext = InstrumentationRegistry.getTargetContext(); 23 | 24 | assertEquals("com.scwang.smartrefresh.layout.test", appContext.getPackageName()); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /refresh-layout/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/DefaultRefreshFooterCreater.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | import android.content.Context; 4 | import android.support.annotation.NonNull; 5 | 6 | /** 7 | * 默认Footer创建器 8 | * Created by SCWANG on 2017/5/26. 9 | */ 10 | 11 | public interface DefaultRefreshFooterCreater { 12 | @NonNull 13 | RefreshFooter createRefreshFooter(Context context, RefreshLayout layout); 14 | } 15 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/DefaultRefreshHeaderCreater.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | import android.content.Context; 4 | import android.support.annotation.NonNull; 5 | 6 | /** 7 | * 默认Header创建器 8 | * Created by SCWANG on 2017/5/26. 9 | */ 10 | 11 | public interface DefaultRefreshHeaderCreater { 12 | @NonNull 13 | RefreshHeader createRefreshHeader(Context context, RefreshLayout layout); 14 | } 15 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/RefreshContent.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | import android.animation.ValueAnimator.AnimatorUpdateListener; 4 | import android.view.MotionEvent; 5 | import android.view.View; 6 | import android.view.ViewGroup; 7 | 8 | /** 9 | * 刷新内容组件 10 | * Created by SCWANG on 2017/5/26. 11 | */ 12 | 13 | public interface RefreshContent { 14 | void moveSpinner(int spinner); 15 | boolean canRefresh(); 16 | boolean canLoadmore(); 17 | int getMeasuredWidth(); 18 | int getMeasuredHeight(); 19 | void measure(int widthSpec, int heightSpec); 20 | void layout(int left, int top, int right, int bottom); 21 | 22 | View getView(); 23 | View getScrollableView(); 24 | ViewGroup.LayoutParams getLayoutParams(); 25 | 26 | void onActionDown(MotionEvent e); 27 | void onActionUpOrCancel(); 28 | 29 | void setupComponent(RefreshKernel kernel, View fixedHeader, View fixedFooter); 30 | void onInitialHeaderAndFooter(int headerHeight, int footerHeight); 31 | void setScrollBoundaryDecider(ScrollBoundaryDecider boundary); 32 | void setEnableLoadmoreWhenContentNotFull(boolean enable); 33 | 34 | AnimatorUpdateListener onLoadingFinish(RefreshKernel kernel, int footerHeight, int startDelay, int reboundDuration); 35 | } 36 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/RefreshFooter.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | /** 4 | * 刷新底部 5 | * Created by SCWANG on 2017/5/26. 6 | */ 7 | 8 | public interface RefreshFooter extends RefreshInternal { 9 | /** 10 | * 手指拖动下拉(会连续多次调用) 11 | * @param percent 下拉的百分比 值 = offset/footerHeight (0 - percent - (footerHeight+extendHeight) / footerHeight ) 12 | * @param offset 下拉的像素偏移量 0 - offset - (footerHeight+extendHeight) 13 | * @param footerHeight Footer的高度 14 | * @param extendHeight Footer的扩展高度 15 | */ 16 | void onPullingUp(float percent, int offset, int footerHeight, int extendHeight); 17 | /** 18 | * 手指释放之后的持续动画(会连续多次调用) 19 | * @param percent 下拉的百分比 值 = offset/footerHeight (0 - percent - (footerHeight+extendHeight) / footerHeight ) 20 | * @param offset 下拉的像素偏移量 0 - offset - (footerHeight+extendHeight) 21 | * @param footerHeight Footer的高度 22 | * @param extendHeight Footer的扩展高度 23 | */ 24 | void onPullReleasing(float percent, int offset, int footerHeight, int extendHeight); 25 | 26 | /** 27 | * 设置数据全部加载完成,将不能再次触发加载功能 28 | * @return true 支持全部加载完成的状态显示 false 不支持 29 | */ 30 | boolean setLoadmoreFinished(boolean finished); 31 | } 32 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/RefreshHeader.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | /** 4 | * 刷新头部 5 | * Created by SCWANG on 2017/5/26. 6 | */ 7 | 8 | public interface RefreshHeader extends RefreshInternal { 9 | /** 10 | * 手指拖动下拉(会连续多次调用) 11 | * @param percent 下拉的百分比 值 = offset/headerHeight (0 - percent - (headerHeight+extendHeight) / headerHeight ) 12 | * @param offset 下拉的像素偏移量 0 - offset - (headerHeight+extendHeight) 13 | * @param headerHeight Header的高度 14 | * @param extendHeight Header的扩展高度 15 | */ 16 | void onPullingDown(float percent, int offset, int headerHeight, int extendHeight); 17 | 18 | /** 19 | * 手指释放之后的持续动画 20 | * @param percent 下拉的百分比 值 = offset/headerHeight (0 - percent - (headerHeight+extendHeight) / headerHeight ) 21 | * @param offset 下拉的像素偏移量 0 - offset - (headerHeight+extendHeight) 22 | * @param headerHeight Header的高度 23 | * @param extendHeight Header的扩展高度 24 | */ 25 | void onReleasing(float percent, int offset, int headerHeight, int extendHeight); 26 | } 27 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/RefreshInternal.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | import android.support.annotation.NonNull; 4 | import android.view.View; 5 | 6 | import com.scwang.smartrefresh.layout.constant.SpinnerStyle; 7 | import com.scwang.smartrefresh.layout.listener.OnStateChangedListener; 8 | 9 | 10 | /** 11 | * 刷新内部组件 12 | * Created by SCWANG on 2017/5/26. 13 | */ 14 | 15 | public interface RefreshInternal extends OnStateChangedListener { 16 | /** 17 | * 获取实体视图 18 | */ 19 | @NonNull 20 | View getView(); 21 | 22 | /** 23 | * 获取变换方式 {@link SpinnerStyle} 24 | */ 25 | SpinnerStyle getSpinnerStyle(); 26 | 27 | /** 28 | * 设置主题颜色 29 | * @param colors 对应Xml中配置的 srlPrimaryColor srlAccentColor 30 | */ 31 | void setPrimaryColors(int... colors); 32 | 33 | /** 34 | * 尺寸定义完成 (如果高度不改变(代码修改:setHeader),只调用一次, 在RefreshLayout#onMeasure中调用) 35 | * @param kernel RefreshKernel 36 | * @param height HeaderHeight or FooterHeight 37 | * @param extendHeight extendHeaderHeight or extendFooterHeight 38 | */ 39 | void onInitialized(RefreshKernel kernel, int height, int extendHeight); 40 | 41 | /** 42 | * 水平方向的拖动 43 | * @param percentX 下拉时,手指水平坐标对屏幕的占比(0 - percentX - 1) 44 | * @param offsetX 下拉时,手指水平坐标对屏幕的偏移(0 - offsetX - LayoutWidth) 45 | */ 46 | void onHorizontalDrag(float percentX, int offsetX, int offsetMax); 47 | 48 | /** 49 | * 开始动画 50 | * @param layout RefreshLayout 51 | * @param height HeaderHeight or FooterHeight 52 | * @param extendHeight extendHeaderHeight or extendFooterHeight 53 | */ 54 | void onStartAnimator(RefreshLayout layout, int height, int extendHeight); 55 | 56 | /** 57 | * 动画结束 58 | * @param layout RefreshLayout 59 | * @param success 数据是否成功刷新或加载 60 | * @return 完成动画所需时间 如果返回 Integer.MAX_VALUE 将取消本次完成事件,继续保持原有状态 61 | */ 62 | int onFinish(RefreshLayout layout, boolean success); 63 | 64 | /** 65 | * 是否支持水平方向的拖动(将会影响到onHorizontalDrag的调用) 66 | * @return 水平拖动需要消耗更多的时间和资源,所以如果不支持请返回false 67 | */ 68 | boolean isSupportHorizontalDrag(); 69 | } 70 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/RefreshKernel.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | import android.support.annotation.NonNull; 4 | 5 | /** 6 | * 刷新布局核心功能接口 7 | * 为功能复杂的 Header 或者 Footer 开放的接口 8 | * Created by SCWANG on 2017/5/26. 9 | */ 10 | 11 | public interface RefreshKernel { 12 | 13 | @NonNull 14 | RefreshLayout getRefreshLayout(); 15 | @NonNull 16 | RefreshContent getRefreshContent(); 17 | 18 | // 19 | RefreshKernel setStatePullUpToLoad() ; 20 | RefreshKernel setStateReleaseToLoad() ; 21 | RefreshKernel setStateReleaseToRefresh() ; 22 | RefreshKernel setStatePullDownToRefresh() ; 23 | RefreshKernel setStatePullDownCanceled() ; 24 | RefreshKernel setStatePullUpCanceled() ; 25 | RefreshKernel setStateLoding() ; 26 | RefreshKernel setStateRefresing() ; 27 | RefreshKernel setStateLodingFinish() ; 28 | RefreshKernel setStateRefresingFinish() ; 29 | RefreshKernel resetStatus() ; 30 | // 31 | 32 | // 33 | 34 | /** 35 | * 结束视图位移(调用之后,如果没有在初始位移状态,会执行动画回到初始位置) 36 | * moveSpinner 的取名来自 谷歌官方的 @{@link android.support.v4.widget.SwipeRefreshLayout#moveSpinner(float)} 37 | */ 38 | RefreshKernel overSpinner() ; 39 | 40 | /** 41 | * 移动视图到预设距离(dy 会被内部函数计算,将会出现无限接近最大值(height+extendHeader)的阻尼效果) 42 | * moveSpinner 的取名来自 谷歌官方的 @{@link android.support.v4.widget.SwipeRefreshLayout#moveSpinner(float)} 43 | * @param dy 距离 (px) 大于0表示下拉 小于0表示上啦 44 | */ 45 | RefreshKernel moveSpinnerInfinitely(float dy); 46 | 47 | /** 48 | * 移动视图到指定位置 49 | * moveSpinner 的取名来自 谷歌官方的 @{@link android.support.v4.widget.SwipeRefreshLayout#moveSpinner(float)} 50 | * @param spinner 位置 (px) 51 | * @param isAnimator 标记是否是动画执行 52 | */ 53 | RefreshKernel moveSpinner(int spinner, boolean isAnimator); 54 | 55 | /** 56 | * 执行动画使视图位移到指定的 位置 57 | * moveSpinner 的取名来自 谷歌官方的 @{@link android.support.v4.widget.SwipeRefreshLayout#moveSpinner(float)} 58 | * @param endSpinner 指定的结束位置 (px) 59 | */ 60 | RefreshKernel animSpinner(int endSpinner); 61 | 62 | /** 63 | * 回弹动画 64 | * @param bounceSpinner 回弹的最大位置 (px) 65 | */ 66 | RefreshKernel animSpinnerBounce(int bounceSpinner); 67 | 68 | /** 69 | * 获取 Spinner 70 | */ 71 | int getSpinner(); 72 | // 73 | 74 | // 75 | 76 | /** 77 | * 指定在下拉时候为 Header 绘制背景 78 | * @param backgroundColor 背景颜色 79 | */ 80 | RefreshKernel requestDrawBackgoundForHeader(int backgroundColor); 81 | /** 82 | * 指定在下拉时候为 Footer 绘制背景 83 | * @param backgroundColor 背景颜色 84 | */ 85 | RefreshKernel requestDrawBackgoundForFooter(int backgroundColor); 86 | /** 87 | * 请求事件 88 | */ 89 | RefreshKernel requestHeaderNeedTouchEventWhenRefreshing(boolean request); 90 | /** 91 | * 请求事件 92 | */ 93 | RefreshKernel requestFooterNeedTouchEventWhenLoading(boolean request); 94 | /** 95 | * 请求重新测量 96 | */ 97 | RefreshKernel requestRemeasureHeightForHeader(); 98 | /** 99 | * 请求重新测量 100 | */ 101 | RefreshKernel requestRemeasureHeightForFooter(); 102 | // 103 | } 104 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/api/ScrollBoundaryDecider.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.api; 2 | 3 | import android.view.View; 4 | 5 | /** 6 | * 滚动边界 7 | * Created by SCWANG on 2017/7/8. 8 | */ 9 | 10 | public interface ScrollBoundaryDecider { 11 | /** 12 | * 根据内容视图状态判断是否可以开始下拉刷新 13 | * @param content 内容视图 14 | * @return true 将会触发下拉刷新 15 | */ 16 | boolean canRefresh(View content); 17 | /** 18 | * 根据内容视图状态判断是否可以开始上拉加载 19 | * @param content 内容视图 20 | * @return true 将会触发加载更多 21 | */ 22 | boolean canLoadmore(View content); 23 | } 24 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/constant/DimensionStatus.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.constant; 2 | 3 | /** 4 | * 尺寸值的定义状态,用于在值覆盖的时候决定优先级 5 | * 越往下优先级越高 6 | */ 7 | public enum DimensionStatus { 8 | DefaultUnNotify(false),//默认值,但是还没通知确认 9 | Default(true),//默认值 10 | XmlWrap(true),//Xml计算 11 | XmlExact(true),//Xml 的view 指定 12 | XmlLayoutUnNotify(false),//Xml 的layout 中指定,但是还没通知确认 13 | XmlLayout(true),//Xml 的layout 中指定 14 | CodeExactUnNotify(false),//代码指定,但是还没通知确认 15 | CodeExact(true),//代码指定 16 | DeadLockUnNotify(false),//锁死,但是还没通知确认 17 | DeadLock(true);//锁死 18 | public final boolean notifyed; 19 | 20 | DimensionStatus(boolean notifyed) { 21 | this.notifyed = notifyed; 22 | } 23 | 24 | /** 25 | * 转换为未通知状态 26 | */ 27 | public DimensionStatus unNotify() { 28 | if (notifyed) { 29 | DimensionStatus prev = values()[ordinal() - 1]; 30 | if (!prev.notifyed) { 31 | return prev; 32 | } 33 | return DefaultUnNotify; 34 | } 35 | return this; 36 | } 37 | 38 | /** 39 | * 转换为通知状态 40 | */ 41 | public DimensionStatus notifyed() { 42 | if (!notifyed) { 43 | return values()[ordinal() + 1]; 44 | } 45 | return this; 46 | } 47 | 48 | /** 49 | * 小于等于 50 | */ 51 | public boolean canReplaceWith(DimensionStatus status) { 52 | return ordinal() < status.ordinal() || ((!notifyed || CodeExact == this) && ordinal() == status.ordinal()); 53 | } 54 | 55 | /** 56 | * 大于等于 57 | */ 58 | public boolean gteReplaceWith(DimensionStatus status) { 59 | return ordinal() >= status.ordinal(); 60 | } 61 | } -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/constant/RefreshState.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.constant; 2 | 3 | public enum RefreshState { 4 | None, 5 | PullDownToRefresh, PullToUpLoad, 6 | PullDownCanceled, PullUpCanceled, 7 | ReleaseToRefresh, ReleaseToLoad, 8 | Refreshing, Loading, 9 | RefreshFinish, LoadFinish,; 10 | 11 | public boolean isAnimating() { 12 | return this == Refreshing || 13 | this == Loading; 14 | } 15 | 16 | public boolean isDraging() { 17 | return ordinal() >= PullDownToRefresh.ordinal() 18 | && ordinal() <= ReleaseToLoad.ordinal() 19 | && this != PullDownCanceled 20 | && this != PullUpCanceled; 21 | } 22 | 23 | public boolean isDragingHeader() { 24 | return this == PullDownToRefresh || 25 | this == ReleaseToRefresh; 26 | } 27 | 28 | public boolean isDragingFooter() { 29 | return this == PullToUpLoad || 30 | this == ReleaseToLoad; 31 | } 32 | 33 | public boolean isHeader() { 34 | return (ordinal() & 1) == 1; 35 | } 36 | 37 | public boolean isFooter() { 38 | return (ordinal() & 1) == 0 && ordinal() > 0; 39 | } 40 | 41 | } -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/constant/SpinnerStyle.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.constant; 2 | 3 | /** 4 | * 顶部和底部的组件在拖动时候的变换方式 5 | * Created by SCWANG on 2017/5/26. 6 | */ 7 | 8 | public enum SpinnerStyle { 9 | Translate,//平行移动 特点: HeaderView高度不会改变, 10 | Scale,//拉伸形变 特点:在下拉和上弹(HeaderView高度改变)时候,会自动触发OnDraw事件 11 | FixedBehind,//固定在背后 特点:HeaderView高度不会改变, 12 | FixedFront,//固定在前面 特点:HeaderView高度不会改变, 13 | MatchLayout//填满布局 特点:HeaderView高度不会改变,尺寸充满 RefreshLayout 14 | } 15 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/footer/FalsifyFooter.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.footer; 2 | 3 | import android.annotation.SuppressLint; 4 | import android.content.Context; 5 | import android.graphics.Canvas; 6 | import android.graphics.DashPathEffect; 7 | import android.graphics.Paint; 8 | import android.os.Build; 9 | import android.support.annotation.Nullable; 10 | import android.support.annotation.RequiresApi; 11 | import android.util.AttributeSet; 12 | import android.view.Gravity; 13 | import android.widget.TextView; 14 | 15 | import com.scwang.smartrefresh.layout.api.RefreshFooter; 16 | import com.scwang.smartrefresh.layout.header.FalsifyHeader; 17 | import com.scwang.smartrefresh.layout.util.DensityUtil; 18 | 19 | import static android.view.View.MeasureSpec.EXACTLY; 20 | import static android.view.View.MeasureSpec.makeMeasureSpec; 21 | 22 | /** 23 | * 虚假的 Footer 24 | * 用于 正真的 Footer 在 RefreshLayout 外部时, 25 | * Created by SCWANG on 2017/6/14. 26 | */ 27 | 28 | public class FalsifyFooter extends FalsifyHeader implements RefreshFooter { 29 | 30 | // 31 | public FalsifyFooter(Context context) { 32 | super(context); 33 | } 34 | 35 | public FalsifyFooter(Context context, AttributeSet attrs) { 36 | super(context, attrs); 37 | } 38 | 39 | public FalsifyFooter(Context context, AttributeSet attrs, int defStyleAttr) { 40 | super(context, attrs, defStyleAttr); 41 | } 42 | 43 | @RequiresApi(Build.VERSION_CODES.LOLLIPOP) 44 | public FalsifyFooter(Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) { 45 | super(context, attrs, defStyleAttr, defStyleRes); 46 | } 47 | 48 | @Override@SuppressLint("DrawAllocation") 49 | protected void onDraw(Canvas canvas) { 50 | super.onDraw(canvas); 51 | if (isInEditMode()) {//这段代码在运行时不会执行,只会在Studio编辑预览时运行,不用在意性能问题 52 | int d = DensityUtil.dp2px(5); 53 | 54 | Paint paint = new Paint(); 55 | paint.setStyle(Paint.Style.STROKE); 56 | paint.setColor(0x44ffffff); 57 | paint.setStrokeWidth(DensityUtil.dp2px(1)); 58 | paint.setPathEffect(new DashPathEffect(new float[]{d, d, d, d}, 1)); 59 | canvas.drawRect(d, d, getWidth() - d, getBottom() - d, paint); 60 | 61 | TextView textView = new TextView(getContext()); 62 | textView.setText(getClass().getSimpleName()+" 虚假区域\n运行时代表上拉Footer的高度【" + DensityUtil.px2dp(getHeight()) + "dp】\n而不会显示任何东西"); 63 | textView.setTextColor(0x44ffffff); 64 | textView.setGravity(Gravity.CENTER); 65 | textView.measure(makeMeasureSpec(getWidth(), EXACTLY), makeMeasureSpec(getHeight(), EXACTLY)); 66 | textView.layout(0, 0, getWidth(), getHeight()); 67 | textView.draw(canvas); 68 | } 69 | } 70 | 71 | 72 | // 73 | 74 | // 75 | 76 | @Override 77 | public void onPullingUp(float percent, int offset, int footerHeight, int extendHeight) { 78 | 79 | } 80 | 81 | @Override 82 | public void onPullReleasing(float percent, int offset, int footerHeight, int extendHeight) { 83 | 84 | } 85 | 86 | @Override 87 | public boolean setLoadmoreFinished(boolean finished) { 88 | return false; 89 | } 90 | 91 | // 92 | 93 | } 94 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/header/bezierradar/RippleView.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.header.bezierradar; 2 | 3 | 4 | import android.animation.Animator; 5 | import android.animation.AnimatorListenerAdapter; 6 | import android.animation.ValueAnimator; 7 | import android.content.Context; 8 | import android.graphics.Canvas; 9 | import android.graphics.Paint; 10 | import android.view.View; 11 | 12 | /** 13 | * cjj 14 | */ 15 | public class RippleView extends View { 16 | 17 | private int mRadius; 18 | private Paint mPaint; 19 | private ValueAnimator mAnimator; 20 | 21 | public RippleView(Context context) { 22 | super(context); 23 | mPaint = new Paint(); 24 | mPaint.setAntiAlias(true); 25 | mPaint.setColor(0xffffffff); 26 | mPaint.setStyle(Paint.Style.FILL); 27 | } 28 | 29 | @Override 30 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 31 | setMeasuredDimension(resolveSize(getSuggestedMinimumWidth(), widthMeasureSpec), 32 | resolveSize(getSuggestedMinimumHeight(), heightMeasureSpec)); 33 | } 34 | 35 | public void setFrontColor(int color) { 36 | mPaint.setColor(color); 37 | } 38 | 39 | public void startReveal() { 40 | if (mAnimator == null) { 41 | int bigRadius = (int) (Math.sqrt(Math.pow(getHeight(), 2) + Math.pow(getWidth(), 2))); 42 | mAnimator = ValueAnimator.ofInt(0, bigRadius); 43 | mAnimator.setDuration(400); 44 | mAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 45 | @Override 46 | public void onAnimationUpdate(ValueAnimator animation) { 47 | mRadius = (int) animation.getAnimatedValue(); 48 | invalidate(); 49 | } 50 | }); 51 | mAnimator.addListener(new AnimatorListenerAdapter() { 52 | @Override 53 | public void onAnimationEnd(Animator animation) { 54 | } 55 | }); 56 | } 57 | mAnimator.start(); 58 | } 59 | 60 | @Override 61 | protected void onDraw(Canvas canvas) { 62 | super.onDraw(canvas); 63 | canvas.drawCircle(getWidth() / 2, getHeight() / 2, mRadius, mPaint); 64 | } 65 | 66 | } 67 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/header/bezierradar/RoundDotView.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.header.bezierradar; 2 | 3 | import android.content.Context; 4 | import android.graphics.Canvas; 5 | import android.graphics.Color; 6 | import android.graphics.Paint; 7 | import android.view.View; 8 | 9 | import com.scwang.smartrefresh.layout.util.DensityUtil; 10 | 11 | /** 12 | * 13 | * Created by cjj on 2015/8/27. 14 | */ 15 | public class RoundDotView extends View { 16 | 17 | private int num = 7; 18 | private Paint mPath; 19 | private float mRadius; 20 | private float fraction; 21 | 22 | public RoundDotView(Context context) { 23 | super(context); 24 | mPath = new Paint(); 25 | mPath.setAntiAlias(true); 26 | mPath.setColor(Color.WHITE); 27 | mRadius = DensityUtil.dp2px(7); 28 | } 29 | 30 | @Override 31 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 32 | setMeasuredDimension(resolveSize(getSuggestedMinimumWidth(), widthMeasureSpec), 33 | resolveSize(getSuggestedMinimumHeight(), heightMeasureSpec)); 34 | } 35 | 36 | public void setDotColor(int color) { 37 | mPath.setColor(color); 38 | } 39 | 40 | @Override 41 | protected void onDraw(Canvas canvas) { 42 | super.onDraw(canvas); 43 | int width = getWidth(); 44 | int height = getHeight(); 45 | float wide = (width / num) * fraction-((fraction>1)?((fraction-1)*(width / num)/fraction):0);//y1 = t*(w/n)-(t>1)*((t-1)*(w/n)/t) 46 | float high = height - ((fraction>1)?((fraction-1)*height/2/fraction):0);//y2 = x - (t>1)*((t-1)*x/t); 47 | for (int i = 0 ; i < num; i++) { 48 | float index = 1f + i - (1f + num) / 2;//y3 = (x + 1) - (n + 1)/2; 居中 index 变量:0 1 2 3 4 结果: -2 -1 0 1 2 49 | float alpha = 255 * (1 - (2 * (Math.abs(index) / num)));//y4 = m * ( 1 - 2 * abs(y3) / n); 横向 alpha 差 50 | float x = DensityUtil.px2dp(height); 51 | mPath.setAlpha((int) (alpha * (1d - 1d / Math.pow((x / 800d + 1d), 15))));//y5 = y4 * (1-1/((x/800+1)^15));竖直 alpha 差 52 | float radius = mRadius * (1-1/((x/10+1)));//y6 = mRadius*(1-1/(x/10+1));半径 53 | canvas.drawCircle(width / 2- radius/2 + wide * index , high / 2, radius, mPath); 54 | } 55 | } 56 | 57 | public void setFraction(float fraction) { 58 | this.fraction = fraction; 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/header/bezierradar/WaveView.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.header.bezierradar; 2 | 3 | import android.content.Context; 4 | import android.graphics.Canvas; 5 | import android.graphics.Paint; 6 | import android.graphics.Path; 7 | import android.util.AttributeSet; 8 | import android.view.View; 9 | 10 | /** 11 | * Created by cjj on 2015/8/5. 12 | * 绘制贝塞尔来绘制波浪形 13 | */ 14 | public class WaveView extends View { 15 | 16 | private int waveHeight; 17 | private int headHeight; 18 | private Path path; 19 | private Paint paint; 20 | private int mOffsetX = -1; 21 | 22 | public WaveView(Context context) { 23 | this(context, null, 0); 24 | } 25 | 26 | public WaveView(Context context, AttributeSet attrs) { 27 | this(context, attrs, 0); 28 | } 29 | 30 | public WaveView(Context context, AttributeSet attrs, int defStyleAttr) { 31 | super(context, attrs, defStyleAttr); 32 | initView(); 33 | } 34 | 35 | private void initView() { 36 | path = new Path(); 37 | paint = new Paint(); 38 | paint.setColor(0xff1F2426); 39 | paint.setAntiAlias(true); 40 | } 41 | 42 | @Override 43 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 44 | setMeasuredDimension(resolveSize(getSuggestedMinimumWidth(), widthMeasureSpec), 45 | resolveSize(getSuggestedMinimumHeight(), heightMeasureSpec)); 46 | } 47 | 48 | public void setWaveColor(int color) { 49 | paint.setColor(color); 50 | } 51 | 52 | public int getHeadHeight() { 53 | return headHeight; 54 | } 55 | 56 | public void setHeadHeight(int headHeight) { 57 | this.headHeight = headHeight; 58 | } 59 | 60 | public int getWaveHeight() { 61 | return waveHeight; 62 | } 63 | 64 | public void setWaveHeight(int waveHeight) { 65 | this.waveHeight = waveHeight; 66 | } 67 | 68 | @Override 69 | protected void onDraw(Canvas canvas) { 70 | super.onDraw(canvas); 71 | final int width = getWidth(); 72 | //重置画笔 73 | path.reset(); 74 | //绘制贝塞尔曲线 75 | path.lineTo(0, headHeight); 76 | path.quadTo(mOffsetX >= 0 ? (mOffsetX) : width / 2, headHeight + waveHeight, width, headHeight); 77 | path.lineTo(width, 0); 78 | canvas.drawPath(path, paint); 79 | } 80 | 81 | public void setWaveOffsetX(int offset) { 82 | mOffsetX = offset; 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/impl/ScrollBoundaryDeciderAdapter.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.impl; 2 | 3 | import android.view.MotionEvent; 4 | import android.view.View; 5 | 6 | import com.scwang.smartrefresh.layout.api.ScrollBoundaryDecider; 7 | import com.scwang.smartrefresh.layout.util.ScrollBoundaryUtil; 8 | 9 | /** 10 | * 滚动边界 11 | * Created by SCWANG on 2017/7/8. 12 | */ 13 | 14 | @SuppressWarnings("WeakerAccess") 15 | public class ScrollBoundaryDeciderAdapter implements ScrollBoundaryDecider { 16 | 17 | // 18 | protected MotionEvent mActionEvent; 19 | protected ScrollBoundaryDecider boundary; 20 | protected boolean mEnableLoadmoreWhenContentNotFull; 21 | 22 | void setScrollBoundaryDecider(ScrollBoundaryDecider boundary){ 23 | this.boundary = boundary; 24 | } 25 | 26 | void setActionEvent(MotionEvent event) { 27 | mActionEvent = event; 28 | } 29 | // 30 | 31 | // 32 | @Override 33 | public boolean canRefresh(View content) { 34 | if (boundary != null) { 35 | return boundary.canRefresh(content); 36 | } 37 | return ScrollBoundaryUtil.canRefresh(content, mActionEvent); 38 | } 39 | 40 | @Override 41 | public boolean canLoadmore(View content) { 42 | if (boundary != null) { 43 | return boundary.canLoadmore(content); 44 | } 45 | if (mEnableLoadmoreWhenContentNotFull) { 46 | return !ScrollBoundaryUtil.canScrollDown(content, mActionEvent); 47 | } 48 | return ScrollBoundaryUtil.canLoadmore(content, mActionEvent); 49 | } 50 | 51 | public void setEnableLoadmoreWhenContentNotFull(boolean enable) { 52 | mEnableLoadmoreWhenContentNotFull = enable; 53 | } 54 | // 55 | } 56 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/internal/pathview/PathsView.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.internal.pathview; 2 | 3 | import android.content.Context; 4 | import android.graphics.Canvas; 5 | import android.util.AttributeSet; 6 | import android.view.View; 7 | 8 | /** 9 | * 路径视图 10 | * Created by SCWANG on 2017/5/29. 11 | */ 12 | 13 | public class PathsView extends View { 14 | 15 | protected PathsDrawable mPathsDrawable = new PathsDrawable(); 16 | 17 | public PathsView(Context context) { 18 | super(context); 19 | this.initView(context, null, 0); 20 | } 21 | 22 | public PathsView(Context context, AttributeSet attrs) { 23 | super(context, attrs); 24 | this.initView(context, attrs, 0); 25 | } 26 | 27 | public PathsView(Context context, AttributeSet attrs, int defStyleAttr) { 28 | super(context, attrs, defStyleAttr); 29 | this.initView(context, attrs, defStyleAttr); 30 | } 31 | 32 | private void initView(Context context, AttributeSet attrs, int defStyleAttr) { 33 | mPathsDrawable = new PathsDrawable(); 34 | } 35 | 36 | @Override 37 | protected void onFinishInflate() { 38 | super.onFinishInflate(); 39 | if (getTag() instanceof String) { 40 | parserPaths(getTag().toString()); 41 | } 42 | } 43 | 44 | @Override 45 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 46 | setMeasuredDimension(resolveSize(mPathsDrawable.width()+getPaddingLeft()+getPaddingRight(), widthMeasureSpec), 47 | resolveSize(mPathsDrawable.height()+getPaddingTop()+getPaddingBottom(), heightMeasureSpec)); 48 | } 49 | 50 | @Override 51 | protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 52 | super.onLayout(changed, left, top, right, bottom); 53 | mPathsDrawable.setBounds(getPaddingLeft(), getPaddingTop(), 54 | Math.max((right - left) - getPaddingRight(), getPaddingLeft()), 55 | Math.max((bottom - top) - getPaddingTop(), getPaddingTop())); 56 | } 57 | 58 | @Override 59 | protected void onDraw(Canvas canvas) { 60 | super.onDraw(canvas); 61 | mPathsDrawable.draw(canvas); 62 | } 63 | 64 | public void parserPaths(String... paths) { 65 | mPathsDrawable.parserPaths(paths); 66 | } 67 | 68 | public void parserColors(int... colors) { 69 | mPathsDrawable.parserColors(colors); 70 | } 71 | 72 | 73 | } 74 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/AnimationEndListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | /** 4 | * 动画 5 | * Created by SCWANG on 2017/6/21. 6 | */ 7 | 8 | public interface AnimationEndListener { 9 | void onAnimationEnd(); 10 | } 11 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/OnLoadmoreListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 4 | 5 | /** 6 | * 加载更多监听器 7 | * Created by SCWANG on 2017/5/26. 8 | */ 9 | 10 | public interface OnLoadmoreListener { 11 | void onLoadmore(RefreshLayout refreshlayout); 12 | } 13 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/OnMultiPurposeListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | import com.scwang.smartrefresh.layout.api.RefreshFooter; 4 | import com.scwang.smartrefresh.layout.api.RefreshHeader; 5 | 6 | /** 7 | * 多功能监听器 8 | * Created by SCWANG on 2017/5/26. 9 | */ 10 | 11 | public interface OnMultiPurposeListener extends OnRefreshLoadmoreListener, OnStateChangedListener { 12 | void onHeaderPulling(RefreshHeader header, float percent, int offset, int headerHeight, int extendHeight); 13 | void onHeaderReleasing(RefreshHeader header, float percent, int offset, int headerHeight, int extendHeight); 14 | void onHeaderStartAnimator(RefreshHeader header, int headerHeight, int extendHeight); 15 | void onHeaderFinish(RefreshHeader header, boolean success); 16 | 17 | void onFooterPulling(RefreshFooter footer, float percent, int offset, int footerHeight, int extendHeight); 18 | void onFooterReleasing(RefreshFooter footer, float percent, int offset, int footerHeight, int extendHeight); 19 | void onFooterStartAnimator(RefreshFooter footer, int footerHeight, int extendHeight); 20 | void onFooterFinish(RefreshFooter footer, boolean success); 21 | } 22 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/OnRefreshListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 4 | 5 | /** 6 | * 刷新监听器 7 | * Created by SCWANG on 2017/5/26. 8 | */ 9 | 10 | public interface OnRefreshListener { 11 | void onRefresh(RefreshLayout refreshlayout); 12 | } 13 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/OnRefreshLoadmoreListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | /** 4 | * 刷新加载组合监听器 5 | * Created by SCWANG on 2017/5/26. 6 | */ 7 | 8 | public interface OnRefreshLoadmoreListener extends OnRefreshListener, OnLoadmoreListener{ 9 | } 10 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/OnStateChangedListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | 4 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 5 | import com.scwang.smartrefresh.layout.constant.RefreshState; 6 | 7 | /** 8 | * 刷新状态改变监听器 9 | * Created by SCWANG on 2017/5/26. 10 | */ 11 | 12 | public interface OnStateChangedListener { 13 | /** 14 | * 状态改变事件 {@link RefreshState} 15 | * @param refreshLayout RefreshLayout 16 | * @param oldState 改变之前的状态 17 | * @param newState 改变之后的状态 18 | */ 19 | void onStateChanged(RefreshLayout refreshLayout, RefreshState oldState, RefreshState newState); 20 | } 21 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/listener/SimpleMultiPurposeListener.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.listener; 2 | 3 | import com.scwang.smartrefresh.layout.api.RefreshFooter; 4 | import com.scwang.smartrefresh.layout.api.RefreshHeader; 5 | import com.scwang.smartrefresh.layout.api.RefreshLayout; 6 | import com.scwang.smartrefresh.layout.constant.RefreshState; 7 | 8 | /** 9 | * 多功能监听器 10 | * Created by SCWANG on 2017/5/26. 11 | */ 12 | 13 | public class SimpleMultiPurposeListener implements OnMultiPurposeListener { 14 | 15 | @Override 16 | public void onHeaderPulling(RefreshHeader header, float percent, int offset, int headerHeight, int extendHeight) { 17 | 18 | } 19 | 20 | @Override 21 | public void onHeaderReleasing(RefreshHeader header, float percent, int offset, int footerHeight, int extendHeight) { 22 | 23 | } 24 | 25 | @Override 26 | public void onHeaderStartAnimator(RefreshHeader header, int footerHeight, int extendHeight) { 27 | 28 | } 29 | 30 | @Override 31 | public void onHeaderFinish(RefreshHeader header, boolean success) { 32 | 33 | } 34 | 35 | @Override 36 | public void onFooterPulling(RefreshFooter footer, float percent, int offset, int footerHeight, int extendHeight) { 37 | 38 | } 39 | 40 | @Override 41 | public void onFooterReleasing(RefreshFooter footer, float percent, int offset, int footerHeight, int extendHeight) { 42 | 43 | } 44 | 45 | @Override 46 | public void onFooterStartAnimator(RefreshFooter footer, int headHeight, int extendHeight) { 47 | 48 | } 49 | 50 | @Override 51 | public void onFooterFinish(RefreshFooter footer, boolean success) { 52 | 53 | } 54 | 55 | @Override 56 | public void onRefresh(RefreshLayout refreshlayout) { 57 | 58 | } 59 | 60 | @Override 61 | public void onLoadmore(RefreshLayout refreshlayout) { 62 | 63 | } 64 | 65 | @Override 66 | public void onStateChanged(RefreshLayout refreshLayout, RefreshState oldState, RefreshState newState) { 67 | 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/util/DelayedRunable.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.util; 2 | 3 | public class DelayedRunable implements Runnable { 4 | public long delayMillis; 5 | public Runnable runnable = null; 6 | public DelayedRunable(Runnable runnable) { 7 | this.runnable = runnable; 8 | } 9 | public DelayedRunable(Runnable runnable, long delayMillis) { 10 | this.runnable = runnable; 11 | this.delayMillis = delayMillis; 12 | } 13 | @Override 14 | public void run() { 15 | if (runnable != null) { 16 | runnable.run(); 17 | runnable = null; 18 | } 19 | } 20 | } -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/util/DensityUtil.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.util; 2 | 3 | import android.content.res.Resources; 4 | 5 | public class DensityUtil { 6 | 7 | float density; 8 | 9 | public DensityUtil() { 10 | density = Resources.getSystem().getDisplayMetrics().density; 11 | } 12 | 13 | /** 14 | * 根据手机的分辨率从 dp 的单位 转成为 px(像素) 15 | */ 16 | public static int dp2px(float dpValue) { 17 | return (int) (0.5f + dpValue * Resources.getSystem().getDisplayMetrics().density); 18 | } 19 | 20 | /** 21 | * 根据手机的分辨率从 px(像素) 的单位 转成为 dp 22 | */ 23 | public static float px2dp(float pxValue) { 24 | return (pxValue / Resources.getSystem().getDisplayMetrics().density); 25 | } 26 | 27 | /** 28 | * 根据手机的分辨率从 dp 的单位 转成为 px(像素) 29 | */ 30 | public int dip2px(float dpValue) { 31 | return (int) (0.5f + dpValue * density); 32 | } 33 | 34 | /** 35 | * 根据手机的分辨率从 px(像素) 的单位 转成为 dp 36 | */ 37 | public float px2dip(float pxValue) { 38 | return (pxValue / density); 39 | } 40 | } -------------------------------------------------------------------------------- /refresh-layout/src/main/java/com/scwang/smartrefresh/layout/util/ViscousFluidInterpolator.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout.util; 2 | 3 | import android.view.animation.Interpolator; 4 | 5 | public class ViscousFluidInterpolator implements Interpolator { 6 | /** Controls the viscous fluid effect (how much of it). */ 7 | private static final float VISCOUS_FLUID_SCALE = 8.0f; 8 | 9 | private static final float VISCOUS_FLUID_NORMALIZE; 10 | private static final float VISCOUS_FLUID_OFFSET; 11 | 12 | static { 13 | 14 | // must be set to 1.0 (used in viscousFluid()) 15 | VISCOUS_FLUID_NORMALIZE = 1.0f / viscousFluid(1.0f); 16 | // account for very small floating-point error 17 | VISCOUS_FLUID_OFFSET = 1.0f - VISCOUS_FLUID_NORMALIZE * viscousFluid(1.0f); 18 | } 19 | 20 | private static float viscousFluid(float x) { 21 | x *= VISCOUS_FLUID_SCALE; 22 | if (x < 1.0f) { 23 | x -= (1.0f - (float)Math.exp(-x)); 24 | } else { 25 | float start = 0.36787944117f; // 1/e == exp(-1) 26 | x = 1.0f - (float)Math.exp(1.0f - x); 27 | x = start + x * (1.0f - start); 28 | } 29 | return x; 30 | } 31 | 32 | @Override 33 | public float getInterpolation(float input) { 34 | final float interpolated = VISCOUS_FLUID_NORMALIZE * viscousFluid(input); 35 | if (interpolated > 0) { 36 | return interpolated + VISCOUS_FLUID_OFFSET; 37 | } 38 | return interpolated; 39 | } 40 | } -------------------------------------------------------------------------------- /refresh-layout/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | SmartRefreshLayout 3 | 4 | -------------------------------------------------------------------------------- /refresh-layout/src/test/java/com/scwang/smartrefresh/layout/ExampleUnitTest.java: -------------------------------------------------------------------------------- 1 | package com.scwang.smartrefresh.layout; 2 | 3 | import org.junit.Test; 4 | 5 | import static org.junit.Assert.*; 6 | 7 | /** 8 | * Example local unit test, which will execute on the development machine (host). 9 | * 10 | * @see Testing documentation 11 | */ 12 | public class ExampleUnitTest { 13 | @Test 14 | public void addition_isCorrect() throws Exception { 15 | assertEquals(4, 2 + 2); 16 | } 17 | } -------------------------------------------------------------------------------- /settings.gradle: -------------------------------------------------------------------------------- 1 | include ':app', ':refresh-layout', ':refresh-header', ':refresh-footer' 2 | --------------------------------------------------------------------------------