Bladeren bron

YCVideoPlayer

yangchong 7 jaren geleden
bovenliggende
commit
680f7a9532
39 gewijzigde bestanden met toevoegingen van 2338 en 171 verwijderingen
  1. 1 0
      .idea/inspectionProfiles/Project_Default.xml
  2. 2 2
      YCVideoPlayerLib/build.gradle
  3. 6 0
      YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/AbsVideoPlayerController.java
  4. 10 0
      YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/OnVideoBackListener.java
  5. 1 1
      YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/VideoPlayer.java
  6. 59 14
      YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/VideoPlayerController.java
  7. 6 6
      app/build.gradle
  8. 77 30
      app/src/main/AndroidManifest.xml
  9. 14 6
      app/src/main/java/org/yczbj/ycvideoplayer/api/ConstantVideo.java
  10. 10 0
      app/src/main/java/org/yczbj/ycvideoplayer/listener/OnItemLongClickListener.java
  11. 1 5
      app/src/main/java/org/yczbj/ycvideoplayer/ui/home/view/fragment/HomeFragment.java
  12. 32 2
      app/src/main/java/org/yczbj/ycvideoplayer/ui/me/view/MeFragment.java
  13. 9 9
      app/src/main/java/org/yczbj/ycvideoplayer/ui/special/SpecialFragment.java
  14. 1 1
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test/view/first/TestFirstActivity.java
  15. 9 2
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test2/TestMyActivity.java
  16. 0 10
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLHybridTestActivity.java
  17. 0 10
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLManyTestActivity.java
  18. 0 10
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLNotificationTestActivity.java
  19. 218 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManager.java
  20. 72 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManagerDBController.java
  21. 48 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManagerDBOpenHelper.java
  22. 83 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManagerModel.java
  23. 15 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/model/api.java
  24. 90 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/NotificationItem.java
  25. 284 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLHybridTestActivity.java
  26. 123 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLManyTestActivity.java
  27. 1 1
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLMyFileTestActivity.java
  28. 247 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLNotificationTestActivity.java
  29. 128 38
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLSingleTestActivity.java
  30. 1 1
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/GlideCropActivity.java
  31. 432 0
      app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/adapter/DLManyAdapter.java
  32. 63 0
      app/src/main/res/layout/activity_test_dl_hybrid.xml
  33. 124 0
      app/src/main/res/layout/activity_test_dl_notification.xml
  34. 81 21
      app/src/main/res/layout/activity_test_dl_single.xml
  35. 2 2
      app/src/main/res/layout/activity_test_my.xml
  36. 17 0
      app/src/main/res/layout/base_activity_view.xml
  37. 16 0
      app/src/main/res/layout/fragment_me.xml
  38. 19 0
      app/src/main/res/layout/item_dialog_list_view.xml
  39. 36 0
      app/src/main/res/values/strings.xml

+ 1 - 0
.idea/inspectionProfiles/Project_Default.xml

@@ -1,6 +1,7 @@
 <component name="InspectionProjectProfileManager">
   <profile version="1.0">
     <option name="myName" value="Project Default" />
+    <inspection_tool class="AlibabaAvoidManuallyCreateThread" enabled="false" level="CRITICAL" enabled_by_default="false" />
     <inspection_tool class="JavaDoc" enabled="true" level="WARNING" enabled_by_default="true">
       <option name="TOP_LEVEL_CLASS_OPTIONS">
         <value>

+ 2 - 2
YCVideoPlayerLib/build.gradle

@@ -46,8 +46,8 @@ group = "cn.yc"
 //发布到JCenter上的项目名字,必须填写
 def libName = "YCVideoPlayerLib"
 // 版本号,下次更新是只需要更改版本号即可
-version = "2.2"
-/**  上面配置后上传至jcenter后的编译路径是这样的: compile 'cn.yc:YCVideoPlayerLib:2.2'  **/
+version = "2.3"
+/**  上面配置后上传至jcenter后的编译路径是这样的: compile 'cn.yc:YCVideoPlayerLib:2.3'  **/
 
 //生成源文件
 task sourcesJar(type: Jar) {

+ 6 - 0
YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/AbsVideoPlayerController.java

@@ -63,6 +63,12 @@ public abstract class AbsVideoPlayerController extends FrameLayout implements Vi
         mVideoPlayer = videoPlayer;
     }
 
+    /**
+     * 设置试看视频时间,让使用者自己定制
+     * @param time                  时间
+     */
+    public abstract void setTrySeeTime(long time);
+
     /**
      * 设置不操作后,多久自动隐藏头部和底部布局
      * @param time                  时间

+ 10 - 0
YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/OnVideoBackListener.java

@@ -0,0 +1,10 @@
+package org.yczbj.ycvideoplayerlib;
+
+/**
+ * 点击事件抽象接口
+ */
+public interface OnVideoBackListener {
+
+    void onBackClick();
+
+}

+ 1 - 1
YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/VideoPlayer.java

@@ -871,7 +871,7 @@ public class VideoPlayer extends FrameLayout implements InterVideoPlayer{
      */
     @Override
     public void release() {
-        // 保存播放位置
+        // 保存播放位置,当正在播放时,缓冲时,缓冲暂停时,暂停时
         if (isPlaying() || isBufferingPlaying() || isBufferingPaused() || isPaused()) {
             VideoPlayerUtils.savePlayPosition(mContext, mUrl, getCurrentPosition());
         } else if (isCompleted()) {

+ 59 - 14
YCVideoPlayerLib/src/main/java/org/yczbj/ycvideoplayerlib/VideoPlayerController.java

@@ -119,7 +119,14 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
     private boolean mSeeEnd = true;
     //会员权限话术内容
     private ArrayList<String> mMemberContent;
+    /**
+     * 这个是time时间不操作界面,则自动隐藏顶部和底部视图布局
+     */
     private long time;
+    /**
+     * 这个是设置试看时间,当然前提是设置试看权限后才能生效,如果不设置,默认为30秒
+     */
+    private long mTrySeeTime;
 
 
     public VideoPlayerController(Context context) {
@@ -236,6 +243,15 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
         }
     }
 
+    /**
+     * 设置试看视频时间,让使用者自己定制
+     * @param time                  时间
+     */
+    @Override
+    public void setTrySeeTime(long time) {
+        this.mTrySeeTime = time;
+    }
+
 
     /**
      * 18年1月12号添加
@@ -383,7 +399,8 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
         switch (playState) {
             case VideoPlayer.STATE_IDLE:
                 break;
-            case VideoPlayer.STATE_PREPARING:                           //播放准备中
+            //播放准备中
+            case VideoPlayer.STATE_PREPARING:
                 mImage.setVisibility(View.GONE);
                 mLoading.setVisibility(View.VISIBLE);
                 mLoadText.setText("正在准备...");
@@ -394,38 +411,45 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
                 mCenterStart.setVisibility(View.GONE);
                 mLength.setVisibility(View.GONE);
                 break;
-            case VideoPlayer.STATE_PREPARED:                            //播放准备就绪
+            //播放准备就绪
+            case VideoPlayer.STATE_PREPARED:
                 startUpdateProgressTimer();
                 break;
-            case VideoPlayer.STATE_PLAYING:                             //正在播放
+            //正在播放
+            case VideoPlayer.STATE_PLAYING:
                 mLoading.setVisibility(View.GONE);
                 mRestartPause.setImageResource(R.drawable.ic_player_pause);
                 startDismissTopBottomTimer();
                 break;
-            case VideoPlayer.STATE_PAUSED:                              //暂停播放
+            //暂停播放
+            case VideoPlayer.STATE_PAUSED:
                 mLoading.setVisibility(View.GONE);
                 mRestartPause.setImageResource(R.drawable.ic_player_start);
                 cancelDismissTopBottomTimer();
                 break;
-            case VideoPlayer.STATE_BUFFERING_PLAYING:                   //正在缓冲(播放器正在播放时,缓冲区数据不足,进行缓冲,缓冲区数据足够后恢复播放)
+            //正在缓冲(播放器正在播放时,缓冲区数据不足,进行缓冲,缓冲区数据足够后恢复播放)
+            case VideoPlayer.STATE_BUFFERING_PLAYING:
                 mLoading.setVisibility(View.VISIBLE);
                 mRestartPause.setImageResource(R.drawable.ic_player_pause);
                 mLoadText.setText("正在缓冲...");
                 startDismissTopBottomTimer();
                 break;
-            case VideoPlayer.STATE_BUFFERING_PAUSED:                    //正在缓冲
+            //正在缓冲
+            case VideoPlayer.STATE_BUFFERING_PAUSED:
                 mLoading.setVisibility(View.VISIBLE);
                 mRestartPause.setImageResource(R.drawable.ic_player_start);
                 mLoadText.setText("正在缓冲...");
                 cancelDismissTopBottomTimer();
                 break;
-            case VideoPlayer.STATE_ERROR:                               //播放错误
+            //播放错误
+            case VideoPlayer.STATE_ERROR:
                 cancelUpdateProgressTimer();
                 setTopBottomVisible(false);
                 mTop.setVisibility(View.VISIBLE);
                 mError.setVisibility(View.VISIBLE);
                 break;
-            case VideoPlayer.STATE_COMPLETED:                           //播放完成
+            //播放完成
+            case VideoPlayer.STATE_COMPLETED:
                 cancelUpdateProgressTimer();
                 setTopBottomVisible(false);
                 mImage.setVisibility(View.VISIBLE);
@@ -567,15 +591,18 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
             }
         } else if (v == mBack) {
             //退出,执行返回逻辑
+            //如果是全屏,则先退出全屏
             if (mVideoPlayer.isFullScreen()) {
                 mVideoPlayer.exitFullScreen();
             } else if (mVideoPlayer.isTinyWindow()) {
+                //如果是小窗口,则退出小窗口
                 mVideoPlayer.exitTinyWindow();
+            }else {
+                //如果两种情况都不是,执行逻辑交给使用者自己实现
+                if(mBackListener!=null){
+                    mBackListener.onBackClick();
+                }
             }
-            //思考,如何退出界面呢???
-            /*else {
-                mVideoPlayer.releasePlayer();
-            }*/
         } else if (v == mRestartPause) {
             //重新播放或者暂停
             if (mVideoPlayer.isPlaying() || mVideoPlayer.isBufferingPlaying()) {
@@ -627,7 +654,11 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
         } else if (v == this) {
             if (mVideoPlayer.isPlaying() || mVideoPlayer.isPaused()
                     || mVideoPlayer.isBufferingPlaying() || mVideoPlayer.isBufferingPaused()) {
-                if(mVideoPlayer.getCurrentPosition()>30000){
+                if(mTrySeeTime==0){
+                    mTrySeeTime = 30000;
+                }
+
+                if(mVideoPlayer.getCurrentPosition()>mTrySeeTime){
                     //在试看3分钟外
                     //如果没有登录或者没有观看权限,则隐藏底部和顶部视图
                     if(mIsLogin || mIsSee){
@@ -723,8 +754,11 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
 
         //添加,如果没有播放权限或者没有登录,并且播放时间大于3分钟,则试看结束
         if (!mIsSee || !mIsLogin) {
+            if(mTrySeeTime==0){
+                mTrySeeTime = 30000;
+            }
             //避免更新中多次走这个方法
-            if(position >= 30000 && mSeeEnd){
+            if(position >= mTrySeeTime && mSeeEnd){
                 // 试看结束
                 setVideoTrySeeEnd();
                 mSeeEnd = false;
@@ -866,5 +900,16 @@ public class VideoPlayerController extends AbsVideoPlayerController implements V
         this.mClickListener = listener;
     }
 
+    /**
+     * 当视频退出全屏或者退出小窗口后,再次点击返回键
+     * 让用户自己处理返回键事件的逻辑
+     * 欢迎同行交流:https://github.com/yangchong211
+     * 如果你觉得项目可以,欢迎star
+     */
+    private OnVideoBackListener mBackListener;
+    public void setOnVideoBackListener(OnVideoBackListener listener) {
+        this.mBackListener = listener;
+    }
+
 
 }

+ 6 - 6
app/build.gradle

@@ -8,8 +8,8 @@ android {
         applicationId "org.yczbj.ycvideoplayer"
         minSdkVersion 17
         targetSdkVersion 25
-        versionCode 1
-        versionName "1.0"
+        versionCode 11
+        versionName "1.1.1"
         testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
     }
     buildTypes {
@@ -75,11 +75,11 @@ dependencies {
     compile 'cn.yc:YCUtilsLib:1.5'                                  //公共类
     compile 'cn.yc:YCStateLib:1.1'                                  //状态管理
     compile 'cn.yc:YCBannerLib:1.2'                                 //轮播图
-    compile 'org.yczbj:YCRefreshViewLib:1.4'                        //RecyclerView封装
+    compile 'org.yczbj:YCRefreshViewLib:2.1'                        //RecyclerView封装
     compile 'cn.yc:YCBaseAdapterLib:1.2'                            //adapter封装
-    compile 'cn.yc:YCDialogLib:3.2'                                 //弹窗
+    compile 'cn.yc:YCDialogLib:3.3'                                 //弹窗
     compile 'cn.yc:YCProgressLib:1.2'                               //进度条
-    compile 'cn.yc:YCVideoPlayerLib:2.2'                            //播放器
-//    compile project(':YCVideoPlayerLib')
+    compile 'cn.yc:YCVideoPlayerLib:2.3'                            //播放器
+    //compile project(':YCVideoPlayerLib')
 
 }

+ 77 - 30
app/src/main/AndroidManifest.xml

@@ -28,32 +28,80 @@
         <activity android:name=".ui.home.view.activity.VideoPlayerJzActivity"
             android:configChanges="orientation|keyboardHidden|screenSize"
             android:screenOrientation="portrait"/>
-        <activity android:name=".ui.test3.GlideCropActivity"/>
+        <activity android:name=".ui.me.view.MeLoginActivity" />
+        <activity android:name=".ui.me.view.MeMemberActivity"/>
+
+
 
 
         <!--下面这些均是测试视频播放器-->
-        <activity android:name=".ui.test.TestActivity"/>
-        <activity android:name=".ui.test.view.first.TestFirstActivity"/>
-        <activity android:name=".ui.test.view.first.TestApiFirstActivity"/>
-        <activity android:name=".ui.test.view.first.TestApiSecondActivity"/>
-        <activity android:name=".ui.test.view.first.TestApiThreeActivity"/>
-        <activity android:name=".ui.test.view.first.TestApiFourActivity"/>
-        <activity android:name=".ui.test.view.first.TestApiFiveActivity"/>
-        <activity android:name=".ui.test.view.first.TestApiSixActivity"/>
-        <activity android:name=".ui.test.view.second.TestSecondActivity"/>
-        <activity android:name=".ui.test.view.second.TestListFirstActivity"/>
-        <activity android:name=".ui.test.view.second.TestListSecondActivity"/>
-        <activity android:name=".ui.test.view.second.TestListThirdActivity"/>
-        <activity android:name=".ui.test.view.second.TestListFourActivity"/>
-        <activity android:name=".ui.test.view.second.TestListFiveActivity"/>
-        <activity android:name=".ui.test.view.three.TestThreeActivity"/>
-        <activity android:name=".ui.test.view.three.TestTinyFirstActivity"/>
-        <activity android:name=".ui.test.view.three.TestTinyThirdActivity"/>
-        <activity android:name=".ui.test.view.three.TestTinyFourActivity"/>
-        <activity android:name=".ui.test.view.three.TestTinyFiveActivity"/>
-        <activity android:name=".ui.test.view.four.TestFourActivity"/>
-        <activity android:name=".ui.test.view.five.TestFiveActivity"/>
-        <activity android:name=".ui.test.view.six.TestSixActivity"/>
+        <activity android:name=".ui.test3.ui.activity.GlideCropActivity"/>
+        <activity android:name=".ui.test.TestActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestFirstActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestApiFirstActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestApiSecondActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestApiThreeActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestApiFourActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestApiFiveActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.first.TestApiSixActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.second.TestSecondActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.second.TestListFirstActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.second.TestListSecondActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.second.TestListThirdActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.second.TestListFourActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.second.TestListFiveActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.three.TestThreeActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.three.TestTinyFirstActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.three.TestTinyThirdActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.three.TestTinyFourActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.three.TestTinyFiveActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.four.TestFourActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.five.TestFiveActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
+        <activity android:name=".ui.test.view.six.TestSixActivity"
+            android:configChanges="orientation|keyboardHidden|screenSize"
+            android:screenOrientation="portrait"/>
 
         <activity android:name=".ui.test2.TestMyActivity"
             android:configChanges="orientation|keyboardHidden|screenSize"
@@ -77,13 +125,12 @@
             android:configChanges="orientation|keyboardHidden|screenSize"
             android:screenOrientation="portrait"/>
 
-        <activity android:name=".ui.test3.DLSingleTestActivity"/>
-        <activity android:name=".ui.test3.DLHybridTestActivity"/>
-        <activity android:name=".ui.test3.DLManyTestActivity"/>
-        <activity android:name=".ui.test3.DLMyFileTestActivity"/>
-        <activity android:name=".ui.test3.DLNotificationTestActivity"/>
-        <activity android:name=".ui.me.view.MeLoginActivity" />
-        <activity android:name=".ui.me.view.MeMemberActivity"/>
+        <activity android:name=".ui.test3.ui.activity.DLSingleTestActivity"/>
+        <activity android:name=".ui.test3.ui.activity.DLHybridTestActivity"/>
+        <activity android:name=".ui.test3.ui.activity.DLManyTestActivity"/>
+        <activity android:name=".ui.test3.ui.activity.DLMyFileTestActivity"/>
+        <activity android:name=".ui.test3.ui.activity.DLNotificationTestActivity"/>
+
     </application>
 
 </manifest>

+ 14 - 6
app/src/main/java/org/yczbj/ycvideoplayer/api/ConstantVideo.java

@@ -5,21 +5,29 @@ package org.yczbj.ycvideoplayer.api;
 public class ConstantVideo {
 
 
-
+    /**
+     * 由于之前,我把视频文章发到七牛云上,有众多限制。
+     * 所有有时导致视频无法播放,流量过高,一个星期竟然用了20多个G。
+     */
     public static String[] VideoPlayerList = {
-            "http://p2modh813.bkt.clouddn.com/ycVideo1.mp4",
-            "http://p2modh813.bkt.clouddn.com/ycVideo2.mp4",
-            "http://p2modh813.bkt.clouddn.com/ycVideo3.mp4",
-            "http://p2modh813.bkt.clouddn.com/ycVideo4.mp4",
-            "http://p2modh813.bkt.clouddn.com/ycVideo5.mp4",
+            "http://jzvd.nathen.cn/c494b340ff704015bb6682ffde3cd302/64929c369124497593205a4190d7d128-5287d2089db37e62345123a1be272f8b.mp4",
+            "http://jzvd.nathen.cn/63f3f73712544394be981d9e4f56b612/69c5767bb9e54156b5b60a1b6edeb3b5-5287d2089db37e62345123a1be272f8b.mp4",
+            "http://jzvd.nathen.cn/b201be3093814908bf987320361c5a73/2f6d913ea25941ffa78cc53a59025383-5287d2089db37e62345123a1be272f8b.mp4",
+            "http://jzvd.nathen.cn/d2438fd1c37c4618a704513ad38d68c5/68626a9d53ca421c896ac8010f172b68-5287d2089db37e62345123a1be272f8b.mp4",
+            "http://jzvd.nathen.cn/25a8d119cfa94b49a7a4117257d8ebd7/f733e65a22394abeab963908f3c336db-5287d2089db37e62345123a1be272f8b.mp4",
+            "http://jzvd.nathen.cn/7512edd1ad834d40bb5b978402274b1a/9691c7f2d7b74b5e811965350a0e5772-5287d2089db37e62345123a1be272f8b.mp4",
+            "http://jzvd.nathen.cn/c6e3dc12a1154626b3476d9bf3bd7266/6b56c5f0dc31428083757a45764763b0-5287d2089db37e62345123a1be272f8b.mp4"
     };
 
+
     public static String[] VideoPlayerTitle = {
             "大家好,我是潇湘剑雨",
             "如果项目可以,可以给个star",
             "有bug,可以直接提出来,欢迎一起探讨",
             "把本地项目代码复制到拷贝的仓库",
             "依次输入命令上传代码",
+            "把本地项目代码复制到拷贝的仓库",
+            "依次输入命令上传代码",
     };
 
 }

+ 10 - 0
app/src/main/java/org/yczbj/ycvideoplayer/listener/OnItemLongClickListener.java

@@ -0,0 +1,10 @@
+package org.yczbj.ycvideoplayer.listener;
+
+import android.view.View;
+
+
+public interface OnItemLongClickListener {
+
+    void onLongClick(View view, int position);
+
+}

+ 1 - 5
app/src/main/java/org/yczbj/ycvideoplayer/ui/home/view/fragment/HomeFragment.java

@@ -11,8 +11,6 @@ import com.alibaba.android.vlayout.DelegateAdapter;
 import com.alibaba.android.vlayout.VirtualLayoutManager;
 import com.alibaba.android.vlayout.layout.GridLayoutHelper;
 import com.alibaba.android.vlayout.layout.LinearLayoutHelper;
-import com.blankj.utilcode.util.ImageUtils;
-import com.blankj.utilcode.util.SizeUtils;
 import com.pedaily.yc.ycdialoglib.toast.ToastUtil;
 import com.yc.cn.ycbannerlib.first.BannerView;
 import com.yc.cn.ycbannerlib.first.util.SizeUtil;
@@ -20,7 +18,6 @@ import com.yc.cn.ycbaseadapterlib.first.BaseViewHolder;
 
 import org.yczbj.ycvideoplayer.R;
 import org.yczbj.ycvideoplayer.api.Constant;
-import org.yczbj.ycvideoplayer.api.ConstantImage;
 import org.yczbj.ycvideoplayer.base.BaseDelegateAdapter;
 import org.yczbj.ycvideoplayer.base.BaseFragment;
 import org.yczbj.ycvideoplayer.ui.home.view.activity.VideoPlayerJzActivity;
@@ -29,8 +26,7 @@ import org.yczbj.ycvideoplayer.ui.home.view.adapter.BannerPagerAdapter;
 import org.yczbj.ycvideoplayer.ui.main.view.activity.MainActivity;
 import org.yczbj.ycvideoplayer.ui.test.TestActivity;
 import org.yczbj.ycvideoplayer.ui.test2.TestMyActivity;
-import org.yczbj.ycvideoplayer.ui.test3.GlideCropActivity;
-import org.yczbj.ycvideoplayer.util.ImageUtil;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.GlideCropActivity;
 
 import java.util.ArrayList;
 import java.util.LinkedList;

+ 32 - 2
app/src/main/java/org/yczbj/ycvideoplayer/ui/me/view/MeFragment.java

@@ -1,8 +1,17 @@
 package org.yczbj.ycvideoplayer.ui.me.view;
 
+import android.os.Bundle;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.TextView;
+
 import org.yczbj.ycvideoplayer.R;
 import org.yczbj.ycvideoplayer.base.BaseFragment;
 
+import butterknife.Bind;
+import butterknife.ButterKnife;
+
 /**
  * Description:
  * Update:
@@ -10,7 +19,13 @@ import org.yczbj.ycvideoplayer.base.BaseFragment;
  * Author:MysteryCode
  */
 
-public class MeFragment extends BaseFragment {
+public class MeFragment extends BaseFragment implements View.OnClickListener {
+
+    @Bind(R.id.tv_1)
+    TextView tv1;
+    @Bind(R.id.tv_2)
+    TextView tv2;
+
     @Override
     public int getContentView() {
         return R.layout.fragment_me;
@@ -23,11 +38,26 @@ public class MeFragment extends BaseFragment {
 
     @Override
     public void initListener() {
-
+        tv1.setOnClickListener(this);
+        tv2.setOnClickListener(this);
     }
 
     @Override
     public void initData() {
 
     }
+
+    @Override
+    public void onClick(View v) {
+        switch (v.getId()){
+            case R.id.tv_1:
+
+                break;
+            case R.id.tv_2:
+
+                break;
+            default:
+                break;
+        }
+    }
 }

+ 9 - 9
app/src/main/java/org/yczbj/ycvideoplayer/ui/special/SpecialFragment.java

@@ -30,8 +30,6 @@ import org.yczbj.ycrefreshviewlib.item.SpaceViewItemLine;
 import org.yczbj.ycvideoplayer.R;
 import org.yczbj.ycvideoplayer.base.BaseFragment;
 import org.yczbj.ycvideoplayer.ui.home.model.VideoPlayerFavorite;
-import org.yczbj.ycvideoplayer.ui.home.view.activity.VideoPlayerJzActivity;
-import org.yczbj.ycvideoplayer.ui.home.view.activity.VideoPlayerMeActivity;
 import org.yczbj.ycvideoplayer.ui.home.view.adapter.BannerPagerAdapter;
 import org.yczbj.ycvideoplayer.ui.home.view.adapter.NarrowImageAdapter;
 import org.yczbj.ycvideoplayer.ui.main.view.activity.MainActivity;
@@ -39,13 +37,11 @@ import org.yczbj.ycvideoplayer.ui.special.contract.SpecialContract;
 import org.yczbj.ycvideoplayer.ui.special.model.SpecialBean;
 import org.yczbj.ycvideoplayer.ui.special.presenter.SpecialPresenter;
 import org.yczbj.ycvideoplayer.ui.special.view.SpecialAdapter;
-import org.yczbj.ycvideoplayer.ui.test2.TestMyActivity;
-import org.yczbj.ycvideoplayer.ui.test3.DLHybridTestActivity;
-import org.yczbj.ycvideoplayer.ui.test3.DLManyTestActivity;
-import org.yczbj.ycvideoplayer.ui.test3.DLMyFileTestActivity;
-import org.yczbj.ycvideoplayer.ui.test3.DLNotificationTestActivity;
-import org.yczbj.ycvideoplayer.ui.test3.GlideCropActivity;
-import org.yczbj.ycvideoplayer.ui.test3.DLSingleTestActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLHybridTestActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLManyTestActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLMyFileTestActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLNotificationTestActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLSingleTestActivity;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -141,6 +137,7 @@ public class SpecialFragment extends BaseFragment implements SpecialContract.Vie
         });
     }
 
+
     private void addHeader() {
         adapter.removeAllHeader();
         initTopHeaderView();
@@ -171,9 +168,11 @@ public class SpecialFragment extends BaseFragment implements SpecialContract.Vie
                     @Override
                     public void onClick(View v) {
                         switch (v.getId()){
+                            //启动单任务下载
                             case R.id.tv_special_first:
                                 startActivity(DLSingleTestActivity.class);
                                 break;
+                            //多任务下载
                             case R.id.tv_special_second:
                                 startActivity(DLManyTestActivity.class);
                                 break;
@@ -318,6 +317,7 @@ public class SpecialFragment extends BaseFragment implements SpecialContract.Vie
     }
 
 
+    @SuppressWarnings("AlibabaAvoidManuallyCreateThread")
     @Override
     public void setAdapterView(List<SpecialBean> list) {
         adapter.addAll(list);

+ 1 - 1
app/src/main/java/org/yczbj/ycvideoplayer/ui/test/view/first/TestFirstActivity.java

@@ -75,7 +75,7 @@ public class TestFirstActivity extends BaseActivity implements View.OnClickListe
         map.put("普清", VideoConstant.videoUrlList[0]);
         Object[] objects = new Object[3];
         objects[0] = map;
-        objects[1] = false;//looping
+        objects[1] = false;
         objects[2] = new HashMap<>();
         ((HashMap) objects[2]).put("key", "value");
         jzVideo.setUp(objects, 2

+ 9 - 2
app/src/main/java/org/yczbj/ycvideoplayer/ui/test2/TestMyActivity.java

@@ -18,6 +18,7 @@ import org.yczbj.ycvideoplayer.util.ImageUtil;
 import org.yczbj.ycvideoplayer.util.LogUtils;
 import org.yczbj.ycvideoplayerlib.ConstantKeys;
 import org.yczbj.ycvideoplayerlib.OnMemberClickListener;
+import org.yczbj.ycvideoplayerlib.OnVideoBackListener;
 import org.yczbj.ycvideoplayerlib.VideoLogUtil;
 import org.yczbj.ycvideoplayerlib.VideoPlayer;
 import org.yczbj.ycvideoplayerlib.VideoPlayerController;
@@ -105,7 +106,6 @@ public class TestMyActivity extends BaseActivity implements View.OnClickListener
     public void initView() {
         //原始封装视频播放,没有设置登录状态和权限
         initVideo();
-
         //设置登录和权限
         initVideo7();
     }
@@ -237,7 +237,6 @@ public class TestMyActivity extends BaseActivity implements View.OnClickListener
 
     /**
      * 没有登录没有权限,一键设置
-     *
      */
     private void initVideo7() {
         videoPlayer.release();
@@ -300,6 +299,12 @@ public class TestMyActivity extends BaseActivity implements View.OnClickListener
                 }
             }
         });
+        controller.setOnVideoBackListener(new OnVideoBackListener() {
+            @Override
+            public void onBackClick() {
+                onBackPressed();
+            }
+        });
         //设置视频清晰度
         //videoPlayer.setClarity(list,720);
         //设置视频控制器
@@ -309,6 +314,7 @@ public class TestMyActivity extends BaseActivity implements View.OnClickListener
 
     /**
      * 登录了,但不是会员没有权限,一键设置
+     * 并且设置试看时间为1分钟
      */
     private void initVideo8() {
         videoPlayer.release();
@@ -326,6 +332,7 @@ public class TestMyActivity extends BaseActivity implements View.OnClickListener
         controller.setTitle("高仿优酷视频播放页面");
         //controller.setLength(98000);
         controller.setLoadingType(1);
+        controller.setTrySeeTime(60000);
         controller.setMemberType(true,false,0,true);
         controller.imageView().setBackgroundResource(R.color.blackText);
         //ImageUtil.loadImgByPicasso(this, R.color.blackText, R.drawable.image_default, controller.imageView());

+ 0 - 10
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLHybridTestActivity.java

@@ -1,10 +0,0 @@
-package org.yczbj.ycvideoplayer.ui.test3;
-
-import android.support.v7.app.AppCompatActivity;
-
-/**
- * Created by yc on 2018/1/12.
- */
-
-public class DLHybridTestActivity extends AppCompatActivity {
-}

+ 0 - 10
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLManyTestActivity.java

@@ -1,10 +0,0 @@
-package org.yczbj.ycvideoplayer.ui.test3;
-
-import android.support.v7.app.AppCompatActivity;
-
-/**
- * Created by yc on 2018/1/12.
- */
-
-public class DLManyTestActivity extends AppCompatActivity {
-}

+ 0 - 10
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLNotificationTestActivity.java

@@ -1,10 +0,0 @@
-package org.yczbj.ycvideoplayer.ui.test3;
-
-import android.support.v7.app.AppCompatActivity;
-
-/**
- * Created by yc on 2018/1/12.
- */
-
-public class DLNotificationTestActivity extends AppCompatActivity {
-}

+ 218 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManager.java

@@ -0,0 +1,218 @@
+package org.yczbj.ycvideoplayer.ui.test3.download;
+
+import android.text.TextUtils;
+import android.util.SparseArray;
+
+import com.blankj.utilcode.util.ToastUtils;
+import com.liulishuo.filedownloader.BaseDownloadTask;
+import com.liulishuo.filedownloader.FileDownloadConnectListener;
+import com.liulishuo.filedownloader.FileDownloader;
+import com.liulishuo.filedownloader.model.FileDownloadStatus;
+import com.liulishuo.filedownloader.util.FileDownloadUtils;
+
+import org.yczbj.ycvideoplayer.api.ConstantVideo;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLManyTestActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.adapter.DLManyAdapter;
+
+import java.lang.ref.WeakReference;
+import java.util.List;
+
+/**
+ * Created by yc on 2018/1/17.
+ */
+
+public class DLTasksManager {
+
+    private SparseArray<BaseDownloadTask> taskSparseArray = new SparseArray<>();
+    private DLTasksManagerDBController dbController;
+    private List<DLTasksManagerModel> modelList;
+
+    private final static class HolderClass {
+        private final static DLTasksManager INSTANCE = new DLTasksManager();
+    }
+
+    public static DLTasksManager getImpl() {
+        return HolderClass.INSTANCE;
+    }
+
+
+
+    private DLTasksManager() {
+        dbController = new DLTasksManagerDBController();
+        modelList = dbController.getAllTasks();
+        //initDemo();
+    }
+
+    private void initDemo() {
+        if (modelList.size() <= 0) {
+            final int demoSize = ConstantVideo.VideoPlayerList.length;
+            for (int i = 0; i < demoSize; i++) {
+                final String url = ConstantVideo.VideoPlayerList[i];
+                addTask(url);
+            }
+        }
+    }
+
+    public void addTaskForViewHolder(final BaseDownloadTask task) {
+        taskSparseArray.put(task.getId(), task);
+    }
+
+    public void removeTaskForViewHolder(final int id) {
+        taskSparseArray.remove(id);
+    }
+
+    public void updateViewHolder(final int id, final DLManyAdapter.MyViewHolder holder) {
+        final BaseDownloadTask task = taskSparseArray.get(id);
+        if (task == null) {
+            return;
+        }
+        task.setTag(holder);
+    }
+
+    public void releaseTask() {
+        taskSparseArray.clear();
+    }
+
+    private FileDownloadConnectListener listener;
+
+    private void registerServiceConnectionListener(final WeakReference<DLManyTestActivity> activityWeakReference) {
+        if (listener != null) {
+            FileDownloader.getImpl().removeServiceConnectListener(listener);
+        }
+
+        listener = new FileDownloadConnectListener() {
+
+            @Override
+            public void connected() {
+                if (activityWeakReference == null || activityWeakReference.get() == null) {
+                    return;
+                }
+                activityWeakReference.get().postNotifyDataChanged();
+            }
+
+            @Override
+            public void disconnected() {
+                if (activityWeakReference == null || activityWeakReference.get() == null) {
+                    return;
+                }
+                activityWeakReference.get().postNotifyDataChanged();
+            }
+        };
+
+        FileDownloader.getImpl().addServiceConnectListener(listener);
+    }
+
+    private void unregisterServiceConnectionListener() {
+        FileDownloader.getImpl().removeServiceConnectListener(listener);
+        listener = null;
+    }
+
+    public void onCreate(final WeakReference<DLManyTestActivity> activityWeakReference) {
+        if (!FileDownloader.getImpl().isServiceConnected()) {
+            FileDownloader.getImpl().bindService();
+            registerServiceConnectionListener(activityWeakReference);
+        }
+    }
+
+    public void onDestroy() {
+        unregisterServiceConnectionListener();
+        releaseTask();
+    }
+
+    public boolean isReady() {
+        return FileDownloader.getImpl().isServiceConnected();
+    }
+
+    public DLTasksManagerModel get(final int position) {
+        return modelList.get(position);
+    }
+
+    public DLTasksManagerModel getById(final int id) {
+        for (DLTasksManagerModel model : modelList) {
+            if (model.getId() == id) {
+                return model;
+            }
+        }
+
+        return null;
+    }
+
+    public boolean isDownloaded(final int status) {
+        return status == FileDownloadStatus.completed;
+    }
+
+    public int getStatus(final int id, String path) {
+        return FileDownloader.getImpl().getStatus(id, path);
+    }
+
+    public long getTotal(final int id) {
+        return FileDownloader.getImpl().getTotal(id);
+    }
+
+    public long getSoFar(final int id) {
+        return FileDownloader.getImpl().getSoFar(id);
+    }
+
+    public int getTaskCounts() {
+        return modelList.size();
+    }
+
+    public DLTasksManagerModel addTask(final String url) {
+        return addTask(url, createPath(url));
+    }
+
+    public DLTasksManagerModel addTask(final String url, final String path) {
+        if (TextUtils.isEmpty(url) || TextUtils.isEmpty(path)) {
+            return null;
+        }
+
+        final int id = FileDownloadUtils.generateId(url, path);
+        DLTasksManagerModel model = getById(id);
+        if (model != null) {
+            return model;
+        }
+        final DLTasksManagerModel newModel = dbController.addTask(url, path);
+        if (newModel != null) {
+            modelList.add(newModel);
+        }
+
+        return newModel;
+    }
+
+    public String createPath(final String url) {
+        if (TextUtils.isEmpty(url)) {
+            return null;
+        }
+        return FileDownloadUtils.getDefaultSaveFilePath(url);
+    }
+
+    public int getId(String url) {
+        if (TextUtils.isEmpty(url)){
+            return -1 ;
+        }
+        return FileDownloadUtils.generateId(url, createPath(url));
+    }
+
+
+    public void removeDownloaded(String videoUrl){
+        if(modelList==null || modelList.size()==0){
+            ToastUtils.showShort("删除失败");
+            return;
+        }
+        for (int i = 0; i < modelList.size(); i++) {
+            DLTasksManagerModel model = modelList.get(i);
+            if (model.getUrl().equals(videoUrl)){
+                modelList.remove(i);
+                break;
+            }
+        }
+        boolean b = dbController.removeDownloaded(videoUrl);
+        if(b){
+            ToastUtils.showShort("删除成功");
+        }else {
+            ToastUtils.showShort("删除失败");
+        }
+    }
+
+
+}

+ 72 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManagerDBController.java

@@ -0,0 +1,72 @@
+package org.yczbj.ycvideoplayer.ui.test3.download;
+
+import android.database.Cursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.text.TextUtils;
+
+import com.liulishuo.filedownloader.util.FileDownloadUtils;
+
+import org.yczbj.ycvideoplayer.base.BaseApplication;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Created by yc on 2018/1/17.
+ */
+
+public class DLTasksManagerDBController {
+
+    public final static String TABLE_NAME = "dlTasksManger";
+    private final SQLiteDatabase db;
+
+    DLTasksManagerDBController() {
+        DLTasksManagerDBOpenHelper openHelper = new DLTasksManagerDBOpenHelper(BaseApplication.getInstance());
+        db = openHelper.getWritableDatabase();
+    }
+
+    public List<DLTasksManagerModel> getAllTasks() {
+        final Cursor c = db.rawQuery("SELECT * FROM " + TABLE_NAME, null);
+        final List<DLTasksManagerModel> list = new ArrayList<>();
+        try {
+            if (!c.moveToLast()) {
+                return list;
+            }
+
+            do {
+                DLTasksManagerModel model = new DLTasksManagerModel();
+                model.setId(c.getInt(c.getColumnIndex(DLTasksManagerModel.ID)));
+                model.setName(c.getString(c.getColumnIndex(DLTasksManagerModel.NAME)));
+                model.setUrl(c.getString(c.getColumnIndex(DLTasksManagerModel.URL)));
+                model.setPath(c.getString(c.getColumnIndex(DLTasksManagerModel.PATH)));
+                list.add(model);
+            } while (c.moveToPrevious());
+        } finally {
+            if (c != null) {
+                c.close();
+            }
+        }
+        return list;
+    }
+
+    public DLTasksManagerModel addTask(final String url, final String path) {
+        if (TextUtils.isEmpty(url) || TextUtils.isEmpty(path)) {
+            return null;
+        }
+        // have to use FileDownloadUtils.generateId to associate TasksManagerModel with FileDownloader
+        final int id = FileDownloadUtils.generateId(url, path);
+        DLTasksManagerModel model = new DLTasksManagerModel();
+        model.setId(id);
+        model.setName("任务-----------");
+        model.setUrl(url);
+        model.setPath(path);
+        final boolean succeed = db.insert(TABLE_NAME, null, model.toContentValues()) != -1;
+        return succeed ? model : null;
+    }
+
+
+    public boolean removeDownloaded(String url){
+        return db.delete(TABLE_NAME ,"url = ?" ,new String[]{url})!=-1;
+    }
+
+}

+ 48 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManagerDBOpenHelper.java

@@ -0,0 +1,48 @@
+package org.yczbj.ycvideoplayer.ui.test3.download;
+
+import android.content.Context;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+
+/**
+ * Created by yc on 2018/1/17.
+ */
+
+public class DLTasksManagerDBOpenHelper extends SQLiteOpenHelper {
+
+
+    public final static String DATABASE_NAME = "tasksmanager.db";
+    public final static int DATABASE_VERSION = 2;
+
+    public DLTasksManagerDBOpenHelper(Context context) {
+        super(context, DATABASE_NAME, null, DATABASE_VERSION);
+    }
+
+
+    @Override
+    public void onCreate(SQLiteDatabase db) {
+        db.execSQL("CREATE TABLE IF NOT EXISTS "
+                + DLTasksManagerDBController.TABLE_NAME
+                + String.format(
+                "("
+                        + "%s INTEGER PRIMARY KEY, " // id, download id
+                        + "%s VARCHAR, " // name
+                        + "%s VARCHAR, " // url
+                        + "%s VARCHAR " // path
+                        + ")"
+                , DLTasksManagerModel.ID
+                , DLTasksManagerModel.NAME
+                , DLTasksManagerModel.URL
+                , DLTasksManagerModel.PATH
+
+        ));
+    }
+
+    @Override
+    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
+        if (oldVersion == 1 && newVersion == 2) {
+            db.delete(DLTasksManagerDBController.TABLE_NAME, null, null);
+        }
+    }
+
+}

+ 83 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/download/DLTasksManagerModel.java

@@ -0,0 +1,83 @@
+package org.yczbj.ycvideoplayer.ui.test3.download;
+
+import android.content.ContentValues;
+
+/**
+ * Created by yc on 2018/1/17.
+ */
+
+public class DLTasksManagerModel {
+
+    public final static String ID = "id";
+    public final static String NAME = "name";
+    public final static String URL = "url";
+    public final static String PATH = "path";
+
+    private int id;
+    private String logo;
+    private String name;
+    private String url;
+    private String path;
+
+    public DLTasksManagerModel() {
+
+    }
+
+    public DLTasksManagerModel(int id, String logo, String name, String url, String path) {
+        this.id = id;
+        this.logo = logo;
+        this.name = name;
+        this.url = url;
+        this.path = path;
+    }
+
+    public String getLogo() {
+        return logo;
+    }
+
+    public void setLogo(String logo) {
+        this.logo = logo;
+    }
+
+    public int getId() {
+        return id;
+    }
+
+    public void setId(int id) {
+        this.id = id;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    public String getUrl() {
+        return url;
+    }
+
+    public void setUrl(String url) {
+        this.url = url;
+    }
+
+    public String getPath() {
+        return path;
+    }
+
+    public void setPath(String path) {
+        this.path = path;
+    }
+
+    public ContentValues toContentValues() {
+        ContentValues cv = new ContentValues();
+        cv.put(ID, id);
+        cv.put(NAME, name);
+        cv.put(URL, url);
+        cv.put(PATH, path);
+        return cv;
+    }
+
+}

+ 15 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/model/api.java

@@ -0,0 +1,15 @@
+package org.yczbj.ycvideoplayer.ui.test3.model;
+
+/**
+ * Created by yc on 2018/1/18.
+ */
+
+public class api {
+
+     /*"http://p2modh813.bkt.clouddn.com/ycVideo1.mp4",
+            "http://p2modh813.bkt.clouddn.com/ycVideo2.mp4",
+            "http://p2modh813.bkt.clouddn.com/ycVideo3.mp4",
+            "http://p2modh813.bkt.clouddn.com/ycVideo4.mp4",
+            "http://p2modh813.bkt.clouddn.com/ycVideo5.mp4",*/
+
+}

+ 90 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/NotificationItem.java

@@ -0,0 +1,90 @@
+package org.yczbj.ycvideoplayer.ui.test3.ui;
+
+import android.app.Notification;
+import android.app.PendingIntent;
+import android.content.ComponentName;
+import android.content.Intent;
+import android.support.v4.app.NotificationCompat;
+
+import com.blankj.utilcode.util.Utils;
+import com.liulishuo.filedownloader.model.FileDownloadStatus;
+import com.liulishuo.filedownloader.notification.BaseNotificationItem;
+import com.liulishuo.filedownloader.util.FileDownloadHelper;
+
+import org.yczbj.ycvideoplayer.R;
+import org.yczbj.ycvideoplayer.ui.main.view.activity.MainActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.activity.DLNotificationTestActivity;
+
+/**
+ * Created by yc on 2018/1/17.
+ */
+
+public class NotificationItem extends BaseNotificationItem {
+
+    PendingIntent pendingIntent;
+    NotificationCompat.Builder builder;
+
+    public NotificationItem(int id, String title, String desc) {
+        super(id, title, desc);
+        Intent[] intents = new Intent[2];
+        intents[0] = Intent.makeMainActivity(new ComponentName(Utils.getContext(), MainActivity.class));
+        intents[1] = new Intent(Utils.getContext(), DLNotificationTestActivity.class);
+
+        this.pendingIntent = PendingIntent.getActivities(Utils.getContext(), 0, intents,
+                PendingIntent.FLAG_UPDATE_CURRENT);
+
+        builder = new NotificationCompat.
+                Builder(FileDownloadHelper.getAppContext());
+
+        builder.setDefaults(Notification.DEFAULT_LIGHTS)
+                .setOngoing(true)
+                .setPriority(NotificationCompat.PRIORITY_MIN)
+                .setContentTitle(getTitle())
+                .setContentText(desc)
+                .setContentIntent(pendingIntent)
+                .setSmallIcon(R.mipmap.ic_launcher);
+    }
+
+    @Override
+    public void show(boolean statusChanged, int status, boolean isShowProgress) {
+
+        String desc = getDesc();
+        switch (status) {
+            case FileDownloadStatus.pending:
+                desc += " pending";
+                break;
+            case FileDownloadStatus.started:
+                desc += " started";
+                break;
+            case FileDownloadStatus.progress:
+                desc += " progress";
+                break;
+            case FileDownloadStatus.retry:
+                desc += " retry";
+                break;
+            case FileDownloadStatus.error:
+                desc += " error";
+                break;
+            case FileDownloadStatus.paused:
+                desc += " paused";
+                break;
+            case FileDownloadStatus.completed:
+                desc += " completed";
+                break;
+            case FileDownloadStatus.warn:
+                desc += " warn";
+                break;
+            default:
+                break;
+        }
+
+        builder.setContentTitle(getTitle()).setContentText(desc);
+        if (statusChanged) {
+            builder.setTicker(desc);
+        }
+        builder.setProgress(getTotal(), getSofar(), !isShowProgress);
+        getManager().notify(getId(), builder.build());
+    }
+
+
+}

+ 284 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLHybridTestActivity.java

@@ -0,0 +1,284 @@
+package org.yczbj.ycvideoplayer.ui.test3.ui.activity;
+
+import android.annotation.SuppressLint;
+import android.os.Bundle;
+import android.text.Html;
+import android.util.Log;
+import android.view.View;
+import android.widget.Button;
+import android.widget.ScrollView;
+import android.widget.TextView;
+
+import com.liulishuo.filedownloader.BaseDownloadTask;
+import com.liulishuo.filedownloader.FileDownloadListener;
+import com.liulishuo.filedownloader.FileDownloadQueueSet;
+import com.liulishuo.filedownloader.FileDownloader;
+import com.liulishuo.filedownloader.util.FileDownloadUtils;
+
+import org.yczbj.ycvideoplayer.R;
+import org.yczbj.ycvideoplayer.api.ConstantVideo;
+import org.yczbj.ycvideoplayer.base.BaseActivity;
+
+import java.io.File;
+import java.util.ArrayList;
+import java.util.List;
+
+import butterknife.Bind;
+import butterknife.ButterKnife;
+
+
+public class DLHybridTestActivity extends BaseActivity implements View.OnClickListener {
+
+    @Bind(R.id.btn_1)
+    Button btn1;
+    @Bind(R.id.btn_2)
+    Button btn2;
+    @Bind(R.id.btn_3)
+    Button btn3;
+    @Bind(R.id.btn_4)
+    Button btn4;
+    @Bind(R.id.download_msg_tv)
+    TextView downloadMsgTv;
+    @Bind(R.id.scrollView)
+    ScrollView scrollView;
+    @Bind(R.id.tip_msg_tv)
+    TextView tipMsgTv;
+
+    private final String TAG = "DLHybridTestActivity";
+    private int totalCounts = 0;
+    private int finalCounts = 0;
+    private boolean needAuto2Bottom = true;
+
+
+
+    @Override
+    public int getContentView() {
+        return R.layout.activity_test_dl_hybrid;
+    }
+
+    @Override
+    public void initView() {
+
+    }
+
+    @Override
+    public void initListener() {
+        btn1.setOnClickListener(this);
+        btn2.setOnClickListener(this);
+        btn3.setOnClickListener(this);
+        btn4.setOnClickListener(this);
+    }
+
+    @Override
+    public void initData() {
+
+    }
+
+    @Override
+    public void onClick(View v) {
+        switch (v.getId()) {
+            case R.id.btn_1:
+                deleteAll();
+                break;
+            case R.id.btn_2:
+                SingleDownload();
+                break;
+            case R.id.btn_3:
+                MultiSerialDl();
+                break;
+            case R.id.btn_4:
+                MultiParallelDl();
+                break;
+            default:
+                break;
+        }
+    }
+
+    /**
+     * 1.删除所有已经下载的文件
+     */
+    private void deleteAll() {
+        File file = new File(FileDownloadUtils.getDefaultSaveRootPath());
+        if (!file.exists()) {
+            Log.w(TAG, String.format("check file files not exists %s", file.getAbsolutePath()));
+            return;
+        }
+
+        if (!file.isDirectory()) {
+            Log.w(TAG, String.format("check file files not directory %s", file.getAbsolutePath()));
+            return;
+        }
+
+        File[] files = file.listFiles();
+
+        if (files == null) {
+            updateDisplay(getString(R.string.del_file_error_empty));
+            return;
+        }
+
+        for (File file1 : files) {
+            file1.delete();
+            updateDisplay(getString(R.string.hybrid_test_deleted_file, file1.getName()));
+        }
+    }
+
+
+    /**
+     * 2.单任务下载测试
+     */
+    private void SingleDownload() {
+        updateDisplay(getString(R.string.hybrid_test_start_single_task, ConstantVideo.VideoPlayerList[2]));
+        totalCounts++;
+        FileDownloader.getImpl()
+                .create( ConstantVideo.VideoPlayerList[2])
+                .setListener(createListener())
+                .setTag(1)
+                .start();
+    }
+
+    /**
+     * 3.启动串行多任务下载
+     */
+    private void MultiSerialDl() {
+        updateDisplay(getString(R.string.hybrid_test_start_multiple_tasks_serial, ConstantVideo.VideoPlayerList.length));
+
+        // 以相同的listener作为target,将不同的下载任务绑定起来
+        final List<BaseDownloadTask> taskList = new ArrayList<>();
+        final FileDownloadListener serialTarget = createListener();
+        int i = 0;
+        for (String url : ConstantVideo.VideoPlayerList) {
+            taskList.add(FileDownloader.getImpl().create(url)
+                    .setTag(++i));
+        }
+        totalCounts += taskList.size();
+        new FileDownloadQueueSet(serialTarget)
+                .setCallbackProgressTimes(1)
+                .downloadSequentially(taskList)
+                .start();
+    }
+
+    /**
+     * 4.启动并行多任务下载
+     */
+    private void MultiParallelDl() {
+        updateDisplay(getString(R.string.hybrid_test_start_multiple_tasks_parallel, ConstantVideo.VideoPlayerList.length));
+        // 以相同的listener作为target,将不同的下载任务绑定起来
+        final FileDownloadListener parallelTarget = createListener();
+        final List<BaseDownloadTask> taskList = new ArrayList<>();
+        int i = 0;
+        for (String url : ConstantVideo.VideoPlayerList) {
+            taskList.add(FileDownloader.getImpl().create(url)
+                    .setTag(++i));
+        }
+        totalCounts += taskList.size();
+
+        new FileDownloadQueueSet(parallelTarget)
+                .setCallbackProgressTimes(1)
+                .downloadTogether(taskList)
+                .start();
+    }
+
+
+
+    @SuppressLint("DefaultLocale")
+    private void updateDisplay(final CharSequence msg) {
+        if (downloadMsgTv.getLineCount() > 2500) {
+            downloadMsgTv.setText("");
+        }
+        downloadMsgTv.append(String.format("\n %s", msg));
+        tipMsgTv.setText(String.format("%d/%d", finalCounts, totalCounts));
+        if (needAuto2Bottom) {
+            scrollView.post(scroll2Bottom);
+        }
+    }
+
+
+    private Runnable scroll2Bottom = new Runnable() {
+        @Override
+        public void run() {
+            if (scrollView != null) {
+                scrollView.fullScroll(View.FOCUS_DOWN);
+            }
+        }
+    };
+
+
+    @SuppressLint("DefaultLocale")
+    private FileDownloadListener createListener() {
+        return new FileDownloadListener() {
+
+            @Override
+            protected boolean isInvalid() {
+                return isFinishing();
+            }
+
+            @Override
+            protected void pending(final BaseDownloadTask task, final int soFarBytes, final int totalBytes) {
+                updateDisplay(String.format("[pending] id[%d] %d/%d", task.getId(), soFarBytes, totalBytes));
+            }
+
+            @Override
+            protected void connected(BaseDownloadTask task, String etag, boolean isContinue, int soFarBytes, int totalBytes) {
+                super.connected(task, etag, isContinue, soFarBytes, totalBytes);
+                updateDisplay(String.format("[connected] id[%d] %s %B %d/%d", task.getId(), etag, isContinue, soFarBytes, totalBytes));
+            }
+
+            @Override
+            protected void progress(final BaseDownloadTask task, final int soFarBytes, final int totalBytes) {
+                updateDisplay(String.format("[progress] id[%d] %d/%d", task.getId(), soFarBytes, totalBytes));
+            }
+
+            @Override
+            protected void blockComplete(final BaseDownloadTask task) {
+                downloadMsgTv.post(new Runnable() {
+                    @Override
+                    public void run() {
+                        updateDisplay(String.format("[blockComplete] id[%d]", task.getId()));
+                    }
+                });
+            }
+
+            @Override
+            protected void retry(BaseDownloadTask task, Throwable ex, int retryingTimes, int soFarBytes) {
+                super.retry(task, ex, retryingTimes, soFarBytes);
+                updateDisplay(String.format("[retry] id[%d] %s %d %d",
+                        task.getId(), ex, retryingTimes, soFarBytes));
+            }
+
+            @Override
+            protected void completed(BaseDownloadTask task) {
+                finalCounts++;
+                updateDisplay(String.format("[completed] id[%d] oldFile[%B]",
+                        task.getId(),
+                        task.isReusedOldFile()));
+                updateDisplay(String.format("---------------------------------- %d", (Integer) task.getTag()));
+            }
+
+            @Override
+            protected void paused(final BaseDownloadTask task, final int soFarBytes, final int totalBytes) {
+                finalCounts++;
+                updateDisplay(String.format("[paused] id[%d] %d/%d", task.getId(), soFarBytes, totalBytes));
+                updateDisplay(String.format("############################## %d", (Integer) task.getTag()));
+            }
+
+            @Override
+            protected void error(BaseDownloadTask task, Throwable e) {
+                finalCounts++;
+                updateDisplay(Html.fromHtml(String.format("[error] id[%d] %s %s",
+                        task.getId(),
+                        e,
+                        FileDownloadUtils.getStack(e.getStackTrace(), false))));
+
+                updateDisplay(String.format("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! %d", (Integer) task.getTag()));
+            }
+
+            @Override
+            protected void warn(BaseDownloadTask task) {
+                finalCounts++;
+                updateDisplay(String.format("[warn] id[%d]", task.getId()));
+                updateDisplay(String.format("^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ %d", (Integer) task.getTag()));
+            }
+        };
+    }
+
+}

+ 123 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLManyTestActivity.java

@@ -0,0 +1,123 @@
+package org.yczbj.ycvideoplayer.ui.test3.ui.activity;
+
+import android.graphics.Color;
+import android.os.Bundle;
+import android.support.annotation.Nullable;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.RecyclerView;
+import android.view.View;
+import android.widget.LinearLayout;
+
+import com.blankj.utilcode.util.SizeUtils;
+import com.liulishuo.filedownloader.FileDownloader;
+
+import org.yczbj.ycrefreshviewlib.item.RecycleViewItemLine;
+import org.yczbj.ycvideoplayer.R;
+import org.yczbj.ycvideoplayer.api.ConstantVideo;
+import org.yczbj.ycvideoplayer.base.BaseActivity;
+import org.yczbj.ycvideoplayer.download.TasksManager;
+import org.yczbj.ycvideoplayer.listener.OnItemLongClickListener;
+import org.yczbj.ycvideoplayer.listener.OnListItemClickListener;
+import org.yczbj.ycvideoplayer.ui.test3.download.DLTasksManager;
+import org.yczbj.ycvideoplayer.ui.test3.download.DLTasksManagerModel;
+import org.yczbj.ycvideoplayer.ui.test3.ui.adapter.DLManyAdapter;
+
+import java.lang.ref.WeakReference;
+import java.util.ArrayList;
+import java.util.List;
+
+import butterknife.Bind;
+
+/**
+ * Created by yc on 2018/1/12.
+ */
+
+public class DLManyTestActivity extends BaseActivity {
+
+
+    @Bind(R.id.recyclerView)
+    RecyclerView recyclerView;
+    private DLManyAdapter adapter;
+
+    @Override
+    protected void onCreate(@Nullable Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        DLTasksManager.getImpl().onCreate(new WeakReference<>(this));
+    }
+
+    @Override
+    protected void onDestroy() {
+        TasksManager.getImpl().onDestroy();
+        adapter = null;
+        FileDownloader.getImpl().pauseAll();
+        super.onDestroy();
+    }
+
+
+    @Override
+    public int getContentView() {
+        return R.layout.base_recycler_view;
+    }
+
+    @Override
+    public void initView() {
+        initRecyclerView();
+    }
+
+    @Override
+    public void initListener() {
+        adapter.setOnItemClickListener(new OnListItemClickListener() {
+            @Override
+            public void onItemClick(View view, int position) {
+
+            }
+        });
+        adapter.setOnItemLongClickListener(new OnItemLongClickListener() {
+            @Override
+            public void onLongClick(View view, int position) {
+
+            }
+        });
+    }
+
+    @Override
+    public void initData() {
+        getData();
+    }
+
+    private void initRecyclerView() {
+        List<DLTasksManagerModel> list = new ArrayList<>();
+        recyclerView.setLayoutManager(new LinearLayoutManager(this));
+        final RecycleViewItemLine line = new RecycleViewItemLine(this, LinearLayout.HORIZONTAL,
+                SizeUtils.dp2px(1), Color.parseColor("#f5f5f7"));
+        recyclerView.addItemDecoration(line);
+        adapter = new DLManyAdapter(list,this);
+        recyclerView.setAdapter(adapter);
+    }
+
+
+
+    public void postNotifyDataChanged() {
+        if (adapter != null) {
+            runOnUiThread(new Runnable() {
+                @Override
+                public void run() {
+                    if (adapter != null) {
+                        adapter.notifyDataSetChanged();
+                    }
+                }
+            });
+        }
+    }
+
+    private void getData() {
+        final List<DLTasksManagerModel> list = new ArrayList<>();
+        for(int a = 0; a< ConstantVideo.VideoPlayerList.length; a++){
+            DLTasksManagerModel bean = new DLTasksManagerModel(0,"logo",
+                    ConstantVideo.VideoPlayerTitle[a], "url",ConstantVideo.VideoPlayerList[a]);
+            list.add(bean);
+        }
+        adapter.addAllData(list);
+    }
+
+}

+ 1 - 1
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLMyFileTestActivity.java → app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLMyFileTestActivity.java

@@ -1,4 +1,4 @@
-package org.yczbj.ycvideoplayer.ui.test3;
+package org.yczbj.ycvideoplayer.ui.test3.ui.activity;
 
 import android.support.v7.app.AppCompatActivity;
 

+ 247 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLNotificationTestActivity.java

@@ -0,0 +1,247 @@
+package org.yczbj.ycvideoplayer.ui.test3.ui.activity;
+
+import android.app.NotificationManager;
+import android.content.Context;
+import android.os.Bundle;
+import android.view.View;
+import android.widget.Button;
+import android.widget.CheckBox;
+import android.widget.ProgressBar;
+import android.widget.Toast;
+
+import com.liulishuo.filedownloader.BaseDownloadTask;
+import com.liulishuo.filedownloader.FileDownloader;
+import com.liulishuo.filedownloader.notification.BaseNotificationItem;
+import com.liulishuo.filedownloader.notification.FileDownloadNotificationHelper;
+import com.liulishuo.filedownloader.notification.FileDownloadNotificationListener;
+import com.liulishuo.filedownloader.util.FileDownloadUtils;
+
+import org.yczbj.ycvideoplayer.R;
+import org.yczbj.ycvideoplayer.api.ConstantVideo;
+import org.yczbj.ycvideoplayer.base.BaseActivity;
+import org.yczbj.ycvideoplayer.ui.test3.ui.NotificationItem;
+
+import java.io.File;
+import java.lang.ref.WeakReference;
+
+import butterknife.Bind;
+import butterknife.ButterKnife;
+
+/**
+ * Created by yc on 2018/1/12.
+ */
+
+public class DLNotificationTestActivity extends BaseActivity implements View.OnClickListener {
+
+
+    @Bind(R.id.show_notification_cb)
+    CheckBox showNotificationCb;
+    @Bind(R.id.progressBar)
+    ProgressBar progressBar;
+    @Bind(R.id.btn_start_1)
+    Button btnStart1;
+    @Bind(R.id.btn_pause_1)
+    Button btnPause1;
+    @Bind(R.id.btn_del_1)
+    Button btnDel1;
+    @Bind(R.id.btn_start_2)
+    Button btnStart2;
+    @Bind(R.id.btn_pause_2)
+    Button btnPause2;
+    @Bind(R.id.btn_del_2)
+    Button btnDel2;
+
+    private final FileDownloadNotificationHelper<NotificationItem> notificationHelper = new FileDownloadNotificationHelper<>();
+    private NotificationListener listener;
+
+    private final String savePath = FileDownloadUtils.getDefaultSaveRootPath() + File.separator + "notification";
+    private final String url = ConstantVideo.VideoPlayerList[1];
+    private int downloadId = 0;
+
+    @Override
+    protected void onDestroy() {
+        super.onDestroy();
+        if (downloadId != 0) {
+            FileDownloader.getImpl().pause(downloadId);
+        }
+        notificationHelper.clear();
+        ((NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE)).cancelAll();
+    }
+
+    @Override
+    public int getContentView() {
+        return R.layout.activity_test_dl_notification;
+    }
+
+    @Override
+    public void initView() {
+        listener = new NotificationListener(new WeakReference<>(this));
+    }
+
+    @Override
+    public void initListener() {
+        btnStart1.setOnClickListener(this);
+        btnStart2.setOnClickListener(this);
+        btnPause1.setOnClickListener(this);
+        btnPause2.setOnClickListener(this);
+        btnDel1.setOnClickListener(this);
+        btnDel2.setOnClickListener(this);
+    }
+
+    @Override
+    public void initData() {
+
+    }
+
+
+    @Override
+    public void onClick(View v) {
+        switch (v.getId()){
+            case R.id.btn_start_1:
+                if (downloadId == 0) {
+                    downloadId = FileDownloader.getImpl().create(url)
+                            .setPath(savePath)
+                            .setListener(listener)
+                            .start();
+                }
+                break;
+            case R.id.btn_start_2:
+                if (downloadId == 0) {
+                    downloadId = FileDownloader.getImpl().create(url)
+                            .setPath(savePath)
+                            .setListener(new SecondNotificationListener(new FileDownloadNotificationHelper<NotificationItem>()))
+                            .start();
+                }
+                break;
+            case R.id.btn_pause_1:
+                if (downloadId != 0) {
+                    FileDownloader.getImpl().pause(downloadId);
+                    downloadId = 0;
+                }
+                break;
+            case R.id.btn_pause_2:
+                if (downloadId != 0) {
+                    FileDownloader.getImpl().pause(downloadId);
+                    downloadId = 0;
+                }
+                break;
+            case R.id.btn_del_1:
+                final File file = new File(savePath);
+                if (file.exists()) {
+                    file.delete();
+                }
+                downloadId = 0;
+                break;
+            case R.id.btn_del_2:
+                final File file2 = new File(savePath);
+                if (file2.exists()) {
+                    file2.delete();
+                }
+                downloadId = 0;
+                break;
+            default:
+                break;
+        }
+    }
+
+    private static class NotificationListener extends FileDownloadNotificationListener {
+
+        private WeakReference<DLNotificationTestActivity> wActivity;
+
+        public NotificationListener(WeakReference<DLNotificationTestActivity> wActivity) {
+            super(wActivity.get().notificationHelper);
+            this.wActivity = wActivity;
+        }
+
+        @Override
+        protected BaseNotificationItem create(BaseDownloadTask task) {
+            return new NotificationItem(task.getId(), "sample demo title", "sample demo desc");
+        }
+
+        @Override
+        public void addNotificationItem(BaseDownloadTask task) {
+            super.addNotificationItem(task);
+            if (wActivity.get() != null) {
+                wActivity.get().showNotificationCb.setEnabled(false);
+            }
+        }
+
+        @Override
+        public void destroyNotification(BaseDownloadTask task) {
+            super.destroyNotification(task);
+            if (wActivity.get() != null) {
+                wActivity.get().showNotificationCb.setEnabled(true);
+                wActivity.get().downloadId = 0;
+            }
+        }
+
+        @Override
+        protected boolean interceptCancel(BaseDownloadTask task,
+                                          BaseNotificationItem n) {
+            // in this demo, I don't want to cancel the notification, just show for the test
+            // so return true
+            return true;
+        }
+
+        @Override
+        protected boolean disableNotification(BaseDownloadTask task) {
+            if (wActivity.get() != null) {
+                return !wActivity.get().showNotificationCb.isChecked();
+            }
+
+            return super.disableNotification(task);
+        }
+
+        @Override
+        protected void pending(BaseDownloadTask task, int soFarBytes, int totalBytes) {
+            super.pending(task, soFarBytes, totalBytes);
+            if (wActivity.get() != null) {
+                wActivity.get().progressBar.setIndeterminate(true);
+            }
+        }
+
+        @Override
+        protected void progress(BaseDownloadTask task, int soFarBytes, int totalBytes) {
+            super.progress(task, soFarBytes, totalBytes);
+            if (wActivity.get() != null) {
+                wActivity.get().progressBar.setIndeterminate(false);
+                wActivity.get().progressBar.setMax(totalBytes);
+                wActivity.get().progressBar.setProgress(soFarBytes);
+            }
+        }
+
+        @Override
+        protected void completed(BaseDownloadTask task) {
+            super.completed(task);
+            if (wActivity.get() != null) {
+                wActivity.get().progressBar.setIndeterminate(false);
+                wActivity.get().progressBar.setProgress(task.getSmallFileTotalBytes());
+            }
+        }
+    }
+
+
+    private class SecondNotificationListener extends FileDownloadNotificationListener {
+
+        private static final String TAG = "NotificationListener";
+
+        public SecondNotificationListener(FileDownloadNotificationHelper helper) {
+            super(helper);
+        }
+
+        @Override
+        protected BaseNotificationItem create(BaseDownloadTask task) {
+            return new NotificationItem(task.getId(), "min set demo title", " min set demo desc");
+        }
+
+        @Override
+        public void destroyNotification(BaseDownloadTask task) {
+            super.destroyNotification(task);
+            Toast.makeText(DLNotificationTestActivity.this, "destroyNotification() called with: status " + task.getStatus(), Toast.LENGTH_LONG).show();
+            downloadId = 0;
+        }
+    }
+
+
+
+}

+ 128 - 38
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/DLSingleTestActivity.java → app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/DLSingleTestActivity.java

@@ -1,15 +1,12 @@
-package org.yczbj.ycvideoplayer.ui.test3;
+package org.yczbj.ycvideoplayer.ui.test3.ui.activity;
 
 import android.annotation.SuppressLint;
-import android.os.Bundle;
-import android.support.design.widget.Snackbar;
 import android.view.View;
 import android.widget.Button;
 import android.widget.ProgressBar;
 import android.widget.TextView;
 
 import com.liulishuo.filedownloader.BaseDownloadTask;
-import com.liulishuo.filedownloader.FileDownloadListener;
 import com.liulishuo.filedownloader.FileDownloadSampleListener;
 import com.liulishuo.filedownloader.FileDownloader;
 import com.liulishuo.filedownloader.util.FileDownloadUtils;
@@ -24,7 +21,6 @@ import java.io.File;
 import java.lang.ref.WeakReference;
 
 import butterknife.Bind;
-import butterknife.ButterKnife;
 
 
 /**
@@ -32,6 +28,10 @@ import butterknife.ButterKnife;
  * Update:2018/1/2
  * CreatedTime:2017/12/29
  * Author:yc
+ * 启动单任务下载
+ * 1.下载遇到的问题,如果下载没有完成,则无法删除下载的文件,这不太友好
+ *
+ *
  */
 
 public class DLSingleTestActivity extends BaseActivity implements View.OnClickListener {
@@ -83,6 +83,14 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
     TextView speedTv4;
     @Bind(R.id.progressBar_4)
     ProgressBar progressBar4;
+    @Bind(R.id.state_tv_1)
+    TextView stateTv1;
+    @Bind(R.id.state_tv_2)
+    TextView stateTv2;
+    @Bind(R.id.state_tv_3)
+    TextView stateTv3;
+    @Bind(R.id.state_tv_4)
+    TextView stateTv4;
     private String filePath1;
     private String filePath2;
     private String filePath3;
@@ -98,6 +106,8 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
         super.onDestroy();
         FileDownloader.getImpl().pause(downloadId1);
         FileDownloader.getImpl().pause(downloadId2);
+        FileDownloader.getImpl().pause(downloadId3);
+        FileDownloader.getImpl().pause(downloadId4);
     }
 
 
@@ -136,54 +146,58 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
      * 设置文件路径
      */
     private void setFilePath() {
-        filePath1 = FileDownloadUtils.getDefaultSaveRootPath() + File.separator + "_1_" + File.separator +"yc.apk";
+        filePath1 = FileDownloadUtils.getDefaultSaveRootPath() + File.separator + "_1_";
         filePath2 = FileDownloadUtils.getDefaultSaveRootPath() + File.separator + "_2_";
         filePath3 = FileDownloadUtils.getDefaultSaveRootPath() + File.separator + "_3_";
         filePath4 = FileDownloadUtils.getDefaultSaveRootPath() + File.separator + "_4_";
-        LogUtils.e(this.getClass().getName()+"--filePath1---"+filePath1);
-        LogUtils.e(this.getClass().getName()+"--filePath2---"+filePath2);
-        LogUtils.e(this.getClass().getName()+"--filePath3---"+filePath3);
-        LogUtils.e(this.getClass().getName()+"--filePath4---"+filePath4);
+        LogUtils.e(this.getClass().getName() + "--filePath1---" + filePath1);
+        LogUtils.e(this.getClass().getName() + "--filePath2---" + filePath2);
+        LogUtils.e(this.getClass().getName() + "--filePath3---" + filePath3);
+        LogUtils.e(this.getClass().getName() + "--filePath4---" + filePath4);
     }
 
     @Override
     public void onClick(View v) {
-        switch (v.getId()){
+        switch (v.getId()) {
             case R.id.start_btn_1:
                 downloadId1 = createDownloadTask(1).start();
                 break;
             case R.id.start_btn_2:
-
+                downloadId2 = createDownloadTask(2).start();
                 break;
             case R.id.start_btn_3:
-
+                downloadId3 = createDownloadTask(3).start();
                 break;
             case R.id.start_btn_4:
-
+                downloadId4 = createDownloadTask(4).start();
                 break;
             case R.id.pause_btn_1:
-
+                FileDownloader.getImpl().pause(downloadId1);
                 break;
             case R.id.pause_btn_2:
-
+                FileDownloader.getImpl().pause(downloadId2);
                 break;
             case R.id.pause_btn_3:
-
+                FileDownloader.getImpl().pause(downloadId3);
                 break;
             case R.id.pause_btn_4:
-
+                FileDownloader.getImpl().pause(downloadId4);
                 break;
             case R.id.delete_btn_1:
-
+                new File(filePath1).delete();
+                new File(FileDownloadUtils.getTempPath(filePath1)).delete();
                 break;
             case R.id.delete_btn_2:
-
+                new File(filePath2).delete();
+                new File(FileDownloadUtils.getTempPath(filePath2)).delete();
                 break;
             case R.id.delete_btn_3:
-
+                new File(filePath3).delete();
+                new File(FileDownloadUtils.getTempPath(filePath3)).delete();
                 break;
             case R.id.delete_btn_4:
-
+                new File(filePath4).delete();
+                new File(FileDownloadUtils.getTempPath(filePath4)).delete();
                 break;
             default:
                 break;
@@ -191,54 +205,64 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
     }
 
     private BaseDownloadTask createDownloadTask(int i) {
-        final TaskTag taskTag ;
+        final TaskTag taskTag;
         //创建下载的链接地址
-        String url = ConstantVideo.VideoPlayerList[0];
+        String url;
         //是否
         boolean isDir = false;
         //文件路径
         String path = null;
 
-        switch (i){
+        switch (i) {
             case 1:
                 url = ConstantVideo.VideoPlayerList[0];
                 path = filePath1;
-                taskTag = new TaskTag(new WeakReference<>(this),filenameTv1, progressBar1, null, speedTv1, 1);
+                taskTag = new TaskTag(new WeakReference<>(this), filenameTv1, progressBar1, null, speedTv1, stateTv1,1);
                 break;
             case 2:
                 url = ConstantVideo.VideoPlayerList[1];
-                taskTag = new TaskTag(new WeakReference<>(this), filenameTv1, progressBar2, null, speedTv2, 2);
+                taskTag = new TaskTag(new WeakReference<>(this), filenameTv1, progressBar2, null, speedTv2, stateTv2,2);
                 path = filePath2;
                 isDir = true;
                 break;
             case 3:
                 url = ConstantVideo.VideoPlayerList[2];
-                taskTag = new TaskTag(new WeakReference<>(this),null, progressBar3, null, speedTv3, 3);
+                taskTag = new TaskTag(new WeakReference<>(this), null, progressBar3, null, speedTv3, stateTv3,3);
                 path = filePath3;
                 break;
             case 4:
-                url = ConstantVideo.VideoPlayerList[2];
-                taskTag = new TaskTag(new WeakReference<>(this),null, progressBar4, detailTv4, speedTv4, 4);
+                url = ConstantVideo.VideoPlayerList[3];
+                taskTag = new TaskTag(new WeakReference<>(this), null, progressBar4, detailTv4, speedTv4,stateTv4, 4);
                 path = filePath4;
                 break;
             default:
-                url = ConstantVideo.VideoPlayerList[2];
-                taskTag = new TaskTag(new WeakReference<>(this),null, progressBar4, detailTv4, speedTv4, 4);
+                url = ConstantVideo.VideoPlayerList[3];
+                taskTag = new TaskTag(new WeakReference<>(this), null, progressBar4, detailTv4, speedTv4, stateTv4,4);
                 path = filePath4;
                 break;
         }
+
         return FileDownloader.getImpl().create(url)
                 .setPath(path, isDir)
                 .setCallbackProgressTimes(300)
                 .setMinIntervalUpdateSpeed(400)
                 .setTag(taskTag)
                 .setListener(new FileDownloadSampleListener() {
+
+                    /**
+                     * 等待,已经进入下载队列
+                     * 带回数据:数据库中的soFarBytes与totalBytes
+                     */
                     @Override
                     protected void pending(BaseDownloadTask task, int soFarBytes, int totalBytes) {
                         super.pending(task, soFarBytes, totalBytes);
                         ((TaskTag) task.getTag()).updatePending(task);
                     }
 
+                    /**
+                     * 下载进度回调
+                     * 带回数据:soFarBytes
+                     */
                     @Override
                     protected void progress(BaseDownloadTask task, int soFarBytes, int totalBytes) {
                         super.progress(task, soFarBytes, totalBytes);
@@ -246,40 +270,95 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
                                 task.getSpeed());
                     }
 
+                    /**
+                     * 下载出现错误
+                     * 带回数据:抛出的Throwable
+                     */
                     @Override
                     protected void error(BaseDownloadTask task, Throwable e) {
                         super.error(task, e);
                         ((TaskTag) task.getTag()).updateError(e, task.getSpeed());
                     }
 
+                    /**
+                     * 已经连接上
+                     * 带回数据:ETag, 是否断点续传, soFarBytes, totalBytes
+                     */
                     @Override
                     protected void connected(BaseDownloadTask task, String etag, boolean isContinue, int soFarBytes, int totalBytes) {
                         super.connected(task, etag, isContinue, soFarBytes, totalBytes);
                         ((TaskTag) task.getTag()).updateConnected(etag, task.getFilename());
                     }
 
+                    /**
+                     * 暂停下载
+                     * 带回数据:soFarBytes
+                     */
                     @Override
                     protected void paused(BaseDownloadTask task, int soFarBytes, int totalBytes) {
                         super.paused(task, soFarBytes, totalBytes);
                         ((TaskTag) task.getTag()).updatePaused(task.getSpeed());
                     }
 
+                    /**
+                     * 完成整个下载过程
+                     * 带回数据:
+                     */
                     @Override
                     protected void completed(BaseDownloadTask task) {
                         super.completed(task);
                         ((TaskTag) task.getTag()).updateCompleted(task);
                     }
 
+                    /**
+                     * 在下载队列中(正在等待/正在下载)已经存在相同下载连接与相同存储路径的任务
+                     * 带回数据:
+                     */
                     @Override
                     protected void warn(BaseDownloadTask task) {
                         super.warn(task);
                         ((TaskTag) task.getTag()).updateWarn();
                     }
+
+                    /**
+                     * 在完成前同步调用该方法,此时已经下载完成
+                     * 带回数据:
+                     */
+                    @Override
+                    protected void blockComplete(BaseDownloadTask task) {
+                        super.blockComplete(task);
+                    }
+
+
+                    @Override
+                    protected boolean isInvalid() {
+                        return super.isInvalid();
+                    }
+
+                    /**
+                     * 结束了pending,并且开始当前任务的Runnable
+                     * 带回数据:
+                     */
+                    @Override
+                    protected void started(BaseDownloadTask task) {
+                        super.started(task);
+                    }
+
+                    /**
+                     * 重试之前把将要重试是第几次回调回来
+                     * 带回数据:之所以重试遇到Throwable, 将要重试是第几次, soFarBytes
+                     */
+                    @Override
+                    protected void retry(BaseDownloadTask task, Throwable ex, int retryingTimes, int soFarBytes) {
+                        super.retry(task, ex, retryingTimes, soFarBytes);
+                    }
                 });
     }
 
+
     public static class TaskTag {
 
+        private TextView stateTv;
         private TextView filenameTv;
         private ProgressBar pb;
         private TextView detailTv;
@@ -287,13 +366,14 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
         private int position;
         private WeakReference<DLSingleTestActivity> activityWeakReference;
 
-        TaskTag(WeakReference<DLSingleTestActivity> activityWeakReference,TextView filenameTv
-                , ProgressBar pb, TextView detailTv, TextView speedTv, int position) {
+        TaskTag(WeakReference<DLSingleTestActivity> activityWeakReference, TextView filenameTv
+                , ProgressBar pb, TextView detailTv, TextView speedTv,TextView stateTv , int position) {
             this.activityWeakReference = activityWeakReference;
             this.filenameTv = filenameTv;
             this.pb = pb;
             this.detailTv = detailTv;
             this.speedTv = speedTv;
+            this.stateTv = stateTv;
             this.position = position;
         }
 
@@ -302,8 +382,10 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
             if (filenameTv != null) {
                 filenameTv.setText(task.getFilename());
             }
+            stateTv.setText("下载状态:下载等待中");
         }
 
+        boolean isProgress = true;
         @SuppressLint("DefaultLocale")
         public void updateProgress(final int sofar, final int total, final int speed) {
             if (total == -1) {
@@ -317,6 +399,10 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
             if (detailTv != null) {
                 detailTv.setText(String.format("sofar: %d total: %d", sofar, total));
             }
+            if(isProgress){
+                stateTv.setText("下载状态:下载中");
+                isProgress = false;
+            }
         }
 
         @SuppressLint("DefaultLocale")
@@ -325,12 +411,14 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
             updateSpeed(speed);
             pb.setIndeterminate(false);
             e.printStackTrace();
+            stateTv.setText("下载状态:下载错误");
         }
 
         public void updateConnected(String etag, String filename) {
             if (filenameTv != null) {
                 filenameTv.setText(filename);
             }
+            stateTv.setText("下载状态:链接中");
         }
 
         @SuppressLint("DefaultLocale")
@@ -338,6 +426,7 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
             toast(String.format("paused %d", position));
             updateSpeed(speed);
             pb.setIndeterminate(false);
+            stateTv.setText("下载状态:暂停");
         }
 
         @SuppressLint("DefaultLocale")
@@ -352,29 +441,30 @@ public class DLSingleTestActivity extends BaseActivity implements View.OnClickLi
             pb.setIndeterminate(false);
             pb.setMax(task.getSmallFileTotalBytes());
             pb.setProgress(task.getSmallFileSoFarBytes());
+            stateTv.setText("下载状态:完成");
         }
 
         @SuppressLint("DefaultLocale")
         public void updateWarn() {
             toast(String.format("warn %d", position));
             pb.setIndeterminate(false);
+            stateTv.setText("下载状态:完成");
         }
 
 
         @SuppressLint("DefaultLocale")
         private void updateSpeed(int speed) {
-            if(speedTv!=null){
-                speedTv.setText(String.format("%dKB/s", speed));
+            if (speedTv != null) {
+                speedTv.setText(String.format("下载速度"+"%dKB/s", speed));
             }
         }
 
         private void toast(final String msg) {
             if (this.activityWeakReference != null && this.activityWeakReference.get() != null) {
-                ToastUtil.showToast(activityWeakReference.get(),msg);
+                ToastUtil.showToast(activityWeakReference.get(), msg);
             }
         }
     }
 
 
-
 }

+ 1 - 1
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/GlideCropActivity.java → app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/activity/GlideCropActivity.java

@@ -1,4 +1,4 @@
-package org.yczbj.ycvideoplayer.ui.test3;
+package org.yczbj.ycvideoplayer.ui.test3.ui.activity;
 
 import android.graphics.Bitmap;
 import android.graphics.Matrix;

+ 432 - 0
app/src/main/java/org/yczbj/ycvideoplayer/ui/test3/ui/adapter/DLManyAdapter.java

@@ -0,0 +1,432 @@
+package org.yczbj.ycvideoplayer.ui.test3.ui.adapter;
+
+import android.content.Context;
+import android.support.v7.widget.RecyclerView;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.ProgressBar;
+import android.widget.TextView;
+
+import com.liulishuo.filedownloader.BaseDownloadTask;
+import com.liulishuo.filedownloader.FileDownloadListener;
+import com.liulishuo.filedownloader.FileDownloadSampleListener;
+import com.liulishuo.filedownloader.FileDownloader;
+import com.liulishuo.filedownloader.model.FileDownloadStatus;
+import com.liulishuo.filedownloader.util.FileDownloadUtils;
+import com.ns.yc.ycprogresslib.CircleProgressbar;
+import com.pedaily.yc.ycdialoglib.toast.ToastUtil;
+
+import org.yczbj.ycvideoplayer.R;
+import org.yczbj.ycvideoplayer.base.BaseApplication;
+import org.yczbj.ycvideoplayer.download.TasksManager;
+import org.yczbj.ycvideoplayer.listener.OnItemLongClickListener;
+import org.yczbj.ycvideoplayer.listener.OnListItemClickListener;
+import org.yczbj.ycvideoplayer.ui.test3.download.DLTasksManager;
+import org.yczbj.ycvideoplayer.ui.test3.download.DLTasksManagerModel;
+
+import java.io.File;
+import java.util.List;
+
+import butterknife.Bind;
+import butterknife.ButterKnife;
+
+
+public class DLManyAdapter extends RecyclerView.Adapter<DLManyAdapter.MyViewHolder> {
+
+    private List<DLTasksManagerModel> list;
+    private Context context;
+    private OnListItemClickListener mItemClickListener;
+    private OnItemLongClickListener mOnItemLongClickListener;
+
+
+    public DLManyAdapter(List<DLTasksManagerModel> list, Context context) {
+        this.list = list;
+        this.context = context;
+    }
+
+
+    public void setOnItemClickListener(OnListItemClickListener listener) {
+        this.mItemClickListener = listener;
+    }
+
+
+    public void setOnItemLongClickListener(OnItemLongClickListener onItemLongClickListener) {
+        mOnItemLongClickListener = onItemLongClickListener;
+    }
+
+
+    @Override
+    public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
+        View view = LayoutInflater.from(context).inflate(R.layout.item_dialog_list_view, parent, false);
+        return new MyViewHolder(view, mItemClickListener);
+    }
+
+
+    @Override
+    public void onBindViewHolder(final MyViewHolder holder, int position) {
+        DLTasksManagerModel model = list.get(position);
+        DLTasksManager.getImpl().addTask(model.getPath());
+        final String path = DLTasksManager.getImpl().createPath(model.getPath());
+        int id = DLTasksManager.getImpl().getId(model.getPath());
+        holder.update(id, position);
+
+
+        //如果是设置tvStartOrPause点击事件,则不要setTag具体值,而是holder,,,为什么???
+        //holder.tvStartOrPause.setTag(R.string.pause);
+        holder.tvStartOrPause.setTag(holder);
+        holder.tvStartOrPause.setOnClickListener(taskActionOnClickListener);
+
+        //如果是设置llDownload点击事件,则该如何处理???
+        //holder.llDownload.setOnClickListener(taskActionOnClickListener);
+
+        //注意这两句话的执行顺序,settag一定要在updateViewHolder之前
+        //holder.llDownload.setTag(holder);
+        DLTasksManager.getImpl().updateViewHolder(holder.id, holder);
+
+        holder.tvTitle.setText(model.getName());
+        holder.tvTime.setVisibility(View.INVISIBLE);
+        holder.ivDownload.setBackgroundResource(R.drawable.icon_cache_download);
+
+        //设置类型
+        holder.circlePb.setProgressType(CircleProgressbar.ProgressType.COUNT);
+        //设置圆形的填充颜色
+        holder.circlePb.setInCircleColor(context.getResources().getColor(R.color.colorTransparent));
+        //设置外部轮廓的颜色
+        holder.circlePb.setOutLineColor(context.getResources().getColor(R.color.gray3));
+        //设置进度监听
+        holder.circlePb.setCountdownProgressListener(1, null);
+        //设置外部轮廓的颜色
+        holder.circlePb.setOutLineWidth(1);
+        //设置进度条线的宽度
+        holder.circlePb.setProgressLineWidth(3);
+        //设置进度
+        holder.circlePb.setProgress(0);
+
+        DLTasksManager.getImpl().updateViewHolder(holder.id, holder);
+
+        if (DLTasksManager.getImpl().isReady()) {
+            final int status = DLTasksManager.getImpl().getStatus(model.getId(), path);
+            if (status == FileDownloadStatus.pending || status == FileDownloadStatus.started ||
+                    status == FileDownloadStatus.connected) {
+                // start task, but file not created yet
+                holder.updateDownloading(status, DLTasksManager.getImpl().getSoFar(model.getId())
+                        , DLTasksManager.getImpl().getTotal(model.getId()));
+            } else if (!new File(path).exists() &&
+                    !new File(FileDownloadUtils.getTempPath(path)).exists()) {
+                // not exist file
+                holder.updateNotDownloaded(status, 0, 0);
+            } else if (DLTasksManager.getImpl().isDownloaded(status)) {
+                // already downloaded and exist
+                holder.updateDownloaded();
+            } else if (status == FileDownloadStatus.progress) {
+                // downloading
+                holder.updateDownloading(status, DLTasksManager.getImpl().getSoFar(model.getId())
+                        , DLTasksManager.getImpl().getTotal(model.getId()));
+            } else {
+                // not start
+                holder.updateNotDownloaded(status, DLTasksManager.getImpl().getSoFar(model.getId())
+                        , DLTasksManager.getImpl().getTotal(model.getId()));
+            }
+        } else {
+            holder.tvDownloadState.setText(R.string.tasks_manager_demo_status_loading);
+            //holder.taskActionBtn.setEnabled(false);
+        }
+    }
+
+
+    @Override
+    public int getItemCount() {
+        return list == null ? 0 : list.size();
+    }
+
+    public void addAllData(List<DLTasksManagerModel> data) {
+        if(list!=null){
+            list.clear();
+            list.addAll(data);
+            notifyDataSetChanged();
+        }
+    }
+
+
+    public class MyViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
+
+        @Bind(R.id.tv_title)
+        TextView tvTitle;
+        @Bind(R.id.tv_time)
+        TextView tvTime;
+        @Bind(R.id.pb)
+        ProgressBar taskPb;
+        @Bind(R.id.iv_download)
+        ImageView ivDownload;
+        @Bind(R.id.circle_pb)
+        CircleProgressbar circlePb;
+        @Bind(R.id.tv_download_state)
+        TextView tvDownloadState;
+        @Bind(R.id.tv_video_size)
+        TextView tvVideoSize;
+        @Bind(R.id.tv_start_or_pause)
+        TextView tvStartOrPause;
+        @Bind(R.id.ll_download)
+        LinearLayout llDownload;
+
+
+        /**
+         * viewHolder position
+         */
+        private int position;
+        /**
+         * download id
+         */
+        private int id;
+        private OnListItemClickListener mListener;
+        public void update(final int id, final int position) {
+            this.id = id;
+            this.position = position;
+        }
+
+        public void updateDownloaded() {
+            taskPb.setMax(1);
+            taskPb.setProgress(1);
+
+            circlePb.setProgress(1);
+            circlePb.setVisibility(View.GONE);
+            tvStartOrPause.setText(R.string.delete);
+            tvDownloadState.setText(R.string.tasks_manager_demo_status_completed);
+            ivDownload.setBackgroundResource(R.drawable.icon_cache_delete);
+        }
+
+
+        MyViewHolder(View view, OnListItemClickListener listener) {
+            super(view);
+            ButterKnife.bind(this, itemView);
+            //关于回调接口的两种写法,都行
+            this.mListener = listener;
+            view.setOnClickListener(this);
+            view.setOnLongClickListener(new View.OnLongClickListener() {
+                @Override
+                public boolean onLongClick(View v) {
+                    mOnItemLongClickListener.onLongClick(v, getAdapterPosition());
+                    return true;
+                }
+            });
+        }
+
+        @Override
+        public void onClick(View view) {
+            if (mListener != null) {
+                mListener.onItemClick(view, getAdapterPosition());
+            }
+        }
+
+        /**
+         * 当下载队列中,连接中,或者下载中,调用该方法
+         */
+        public void updateDownloading(final int status, final long sofar, final long total) {
+            final float percent = sofar / (float) total;
+            circlePb.setProgress((int) (percent * 100));
+            taskPb.setMax(100);
+            taskPb.setProgress((int) (percent * 100));
+
+            switch (status) {
+                case FileDownloadStatus.pending:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_pending);
+                    break;
+                case FileDownloadStatus.started:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_started);
+                    break;
+                case FileDownloadStatus.connected:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_connected);
+                    break;
+                case FileDownloadStatus.progress:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_progress);
+                    break;
+                default:
+                    tvDownloadState.setText(BaseApplication.getInstance().getString(R.string.tasks_manager_demo_status_downloading, status));
+                    break;
+            }
+            tvStartOrPause.setText(R.string.pause);
+            ivDownload.setBackgroundResource(R.drawable.icon_cache_play);
+        }
+
+        /**
+         * 当暂停或者下载出错时,调用这个方法
+         */
+        public void updateNotDownloaded(final int status, final long sofar, final long total) {
+            if (sofar > 0 && total > 0) {
+                final float percent = sofar / (float) total;
+                circlePb.setProgress((int) (percent * 100));
+                taskPb.setMax(100);
+                taskPb.setProgress((int) (percent * 100));
+            } else {
+                circlePb.setProgress(0);
+                taskPb.setMax(1);
+                taskPb.setProgress(0);
+            }
+
+            switch (status) {
+                case FileDownloadStatus.error:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_error);
+                    break;
+                case FileDownloadStatus.paused:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_paused);
+                    break;
+                default:
+                    tvDownloadState.setText(R.string.tasks_manager_demo_status_not_downloaded);
+                    break;
+            }
+            tvStartOrPause.setText(R.string.start);
+            ivDownload.setBackgroundResource(R.drawable.icon_cache_download);
+        }
+    }
+
+
+    private View.OnClickListener taskActionOnClickListener = new View.OnClickListener() {
+        @Override
+        public void onClick(View v) {
+            //注意这个v对应是点击事件那个控件,比如如果是holder.llDownload.setOnClickListener(taskActionOnClickListener);
+            //那么由于llDownload控件没有设置setTag,而是holder.tvStartOrPause.setTag(holder);
+            //那么llDownload点击事件,v.getTag便会取空值
+
+            //如果是llDownload控件做点击事件,但是tvStartOrPause设置tag,则需要设置
+            if (v.getTag() == null) {
+                return;
+            }
+            MyViewHolder holder = (MyViewHolder) v.getTag();
+            CharSequence action = ((TextView) v).getText();
+            //String action = (String) holder.tvDownloadState.getTag();
+
+            DLTasksManagerModel downManyBean = list.get(holder.position);
+            ToastUtil.showToast(context,action.toString());
+            if (action.equals(context.getString(R.string.pause))) {
+                ToastUtil.showToast(context,"暂停");
+                // to pause
+                FileDownloader.getImpl().pause(holder.id);
+            } else if (action.equals(context.getString(R.string.start))) {
+                ToastUtil.showToast(context,"开始");
+                // to start
+                // to start
+                String path = TasksManager.getImpl().createPath(downManyBean.getPath());
+                final DLTasksManagerModel model = DLTasksManager.getImpl().get(holder.position);
+                final BaseDownloadTask task = FileDownloader.getImpl().create(model.getUrl())
+                        .setPath(path)
+                        .setCallbackProgressTimes(100)
+                        .setListener(taskDownloadListener);
+
+                DLTasksManager.getImpl().addTaskForViewHolder(task);
+                DLTasksManager.getImpl().updateViewHolder(holder.id, holder);
+                task.start();
+            } else if (action.equals(v.getResources().getString(R.string.delete))) {
+                // to delete
+                //new File(DLTasksManager.getImpl().get(holder.position).getPath()).delete();
+                new File(TasksManager.getImpl().createPath(downManyBean.getPath())).delete();
+                //holder.taskActionBtn.setEnabled(true);
+                holder.updateNotDownloaded(FileDownloadStatus.INVALID_STATUS, 0, 0);
+                DLTasksManager.getImpl().removeDownloaded(downManyBean.getPath());
+            }
+        }
+    };
+
+
+    private FileDownloadListener taskDownloadListener = new FileDownloadSampleListener() {
+
+        private MyViewHolder checkCurrentHolder(final BaseDownloadTask task) {
+            final MyViewHolder tag = (MyViewHolder) task.getTag();
+            if (tag.id != task.getId()) {
+                return null;
+            }
+            return tag;
+        }
+
+        @Override
+        protected void pending(BaseDownloadTask task, int soFarBytes, int totalBytes) {
+            super.pending(task, soFarBytes, totalBytes);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.updateDownloading(FileDownloadStatus.pending, soFarBytes, totalBytes);
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_pending);
+        }
+
+        @Override
+        protected void started(BaseDownloadTask task) {
+            super.started(task);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_started);
+        }
+
+        @Override
+        protected void connected(BaseDownloadTask task, String etag, boolean isContinue, int soFarBytes, int totalBytes) {
+            super.connected(task, etag, isContinue, soFarBytes, totalBytes);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.updateDownloading(FileDownloadStatus.connected, soFarBytes, totalBytes);
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_connected);
+        }
+
+        @Override
+        protected void progress(BaseDownloadTask task, int soFarBytes, int totalBytes) {
+            super.progress(task, soFarBytes, totalBytes);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.updateDownloading(FileDownloadStatus.progress, soFarBytes, totalBytes);
+        }
+
+        @Override
+        protected void completed(BaseDownloadTask task) {
+            super.completed(task);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.updateDownloaded();
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_completed);
+            DLTasksManager.getImpl().removeTaskForViewHolder(task.getId());
+        }
+
+        @Override
+        protected void paused(BaseDownloadTask task, int soFarBytes, int totalBytes) {
+            super.paused(task, soFarBytes, totalBytes);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.updateNotDownloaded(FileDownloadStatus.paused, soFarBytes, totalBytes);
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_paused);
+            DLTasksManager.getImpl().removeTaskForViewHolder(task.getId());
+        }
+
+        @Override
+        protected void error(BaseDownloadTask task, Throwable e) {
+            super.error(task, e);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_error);
+            tag.updateNotDownloaded(FileDownloadStatus.error, task.getLargeFileSoFarBytes(), task.getLargeFileTotalBytes());
+            DLTasksManager.getImpl().removeTaskForViewHolder(task.getId());
+        }
+
+        @Override
+        protected void warn(BaseDownloadTask task) {
+            super.warn(task);
+            final MyViewHolder tag = checkCurrentHolder(task);
+            if (tag == null) {
+                return;
+            }
+            tag.tvDownloadState.setText(R.string.tasks_manager_demo_status_warn);
+        }
+    };
+
+}

+ 63 - 0
app/src/main/res/layout/activity_test_dl_hybrid.xml

@@ -0,0 +1,63 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:orientation="vertical"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent">
+
+    <Button
+        android:id="@+id/btn_1"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:gravity="left|center"
+        android:text="1.删除所有已经下载的文件"/>
+
+    <Button
+        android:id="@+id/btn_2"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:gravity="left|center"
+        android:text="2.单任务下载测试"/>
+
+
+    <Button
+        android:id="@+id/btn_3"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:gravity="left|center"
+        android:text="3.多任务队列串行下载"/>
+
+    <Button
+        android:id="@+id/btn_4"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:gravity="left|center"
+        android:text="4.多任务队列并行下载"/>
+
+    <ScrollView
+        android:id="@+id/scrollView"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:layout_below="@+id/top_group">
+
+        <TextView
+            android:id="@+id/download_msg_tv"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:padding="10dp"
+            android:text="日志"
+            android:textColor="@color/colorPrimaryDark"
+            android:textSize="12sp" />
+    </ScrollView>
+
+    <TextView
+        android:id="@+id/tip_msg_tv"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_alignParentBottom="true"
+        android:layout_centerHorizontal="true"
+        android:alpha="0.5"
+        android:textColor="@color/colorAccent"
+        android:textSize="16sp" />
+
+</LinearLayout>

+ 124 - 0
app/src/main/res/layout/activity_test_dl_notification.xml

@@ -0,0 +1,124 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:orientation="vertical"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:padding="10dp">
+
+    <LinearLayout
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:orientation="vertical">
+        <TextView
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="5dp"
+            android:text="@string/notification_sample_desc"
+            android:textColor="@color/colorAccent"
+            android:textSize="16sp" />
+
+        <LinearLayout
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="5dp"
+            android:orientation="horizontal">
+
+            <Button
+                android:id="@+id/btn_start_1"
+                android:layout_width="0dp"
+                android:layout_height="wrap_content"
+                android:layout_weight="1.0"
+                android:text="@string/start"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+
+            <Button
+                android:id="@+id/btn_pause_1"
+                android:layout_width="0dp"
+                android:layout_height="wrap_content"
+                android:layout_weight="1.0"
+                android:text="@string/pause"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+
+            <Button
+                android:id="@+id/btn_del_1"
+                android:layout_width="0dp"
+                android:layout_height="wrap_content"
+                android:layout_weight="1.0"
+                android:text="@string/delete"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+        </LinearLayout>
+
+        <CheckBox
+            android:id="@+id/show_notification_cb"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:checked="true"
+            android:text="@string/notification_sample_show"
+            android:textColor="@android:color/black"
+            android:textSize="16sp" />
+
+        <ProgressBar
+            android:id="@+id/progressBar"
+            style="?android:attr/progressBarStyleHorizontal"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_gravity="center_horizontal"
+            android:layout_margin="5dp" />
+    </LinearLayout>
+
+
+
+    <LinearLayout
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:layout_marginTop="20dp"
+        android:orientation="vertical">
+        <TextView
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="5dp"
+            android:text="@string/notification_min_set_desc"
+            android:textColor="@color/colorAccent"
+            android:textSize="16sp" />
+
+        <LinearLayout
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="5dp"
+            android:orientation="horizontal">
+
+            <Button
+                android:id="@+id/btn_start_2"
+                android:layout_width="0dp"
+                android:layout_height="wrap_content"
+                android:layout_weight="1.0"
+                android:text="@string/start"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+
+            <Button
+                android:id="@+id/btn_pause_2"
+                android:layout_width="0dp"
+                android:layout_height="wrap_content"
+                android:layout_weight="1.0"
+                android:text="@string/pause"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+
+            <Button
+                android:id="@+id/btn_del_2"
+                android:layout_width="0dp"
+                android:layout_height="wrap_content"
+                android:layout_weight="1.0"
+                android:text="@string/delete"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+        </LinearLayout>
+    </LinearLayout>
+
+
+</LinearLayout>

+ 81 - 21
app/src/main/res/layout/activity_test_dl_single.xml

@@ -61,13 +61,28 @@
             android:textColor="@color/colorPrimary"
             android:textSize="14sp" />
 
-        <TextView
-            android:id="@+id/speed_tv_1"
+        <LinearLayout
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
-            android:gravity="center_horizontal"
-            android:textColor="#000000"
-            android:textSize="14sp" />
+            android:orientation="horizontal"
+            android:gravity="center">
+            <TextView
+                android:id="@+id/speed_tv_1"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="下载速度"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+            <TextView
+                android:id="@+id/state_tv_1"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:layout_marginLeft="30dp"
+                android:text="下载状态"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+        </LinearLayout>
+
 
         <ProgressBar
             android:id="@+id/progressBar_1"
@@ -119,13 +134,28 @@
             android:textColor="@color/colorPrimary"
             android:textSize="14sp" />
 
-        <TextView
-            android:id="@+id/speed_tv_2"
+        <LinearLayout
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
-            android:gravity="center_horizontal"
-            android:textColor="#000000"
-            android:textSize="14sp" />
+            android:orientation="horizontal"
+            android:gravity="center">
+            <TextView
+                android:id="@+id/speed_tv_2"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="下载速度"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+            <TextView
+                android:id="@+id/state_tv_2"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:layout_marginLeft="30dp"
+                android:text="下载状态"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+        </LinearLayout>
+
 
         <ProgressBar
             android:id="@+id/progressBar_2"
@@ -176,14 +206,29 @@
                 android:textSize="14sp" />
         </LinearLayout>
 
-
-        <TextView
-            android:id="@+id/speed_tv_3"
+        <LinearLayout
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
-            android:gravity="center_horizontal"
-            android:textColor="#000000"
-            android:textSize="14sp" />
+            android:orientation="horizontal"
+            android:gravity="center">
+            <TextView
+                android:id="@+id/speed_tv_3"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="下载速度"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+            <TextView
+                android:id="@+id/state_tv_3"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:layout_marginLeft="30dp"
+                android:text="下载状态"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+        </LinearLayout>
+
+
 
         <ProgressBar
             android:id="@+id/progressBar_3"
@@ -245,13 +290,28 @@
             android:textSize="14sp" />
 
 
-        <TextView
-            android:id="@+id/speed_tv_4"
+        <LinearLayout
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
-            android:gravity="center_horizontal"
-            android:textColor="#000000"
-            android:textSize="14sp" />
+            android:orientation="horizontal"
+            android:gravity="center">
+            <TextView
+                android:id="@+id/speed_tv_4"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="下载速度"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+            <TextView
+                android:id="@+id/state_tv_4"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:layout_marginLeft="30dp"
+                android:text="下载状态"
+                android:textColor="#000000"
+                android:textSize="14sp" />
+        </LinearLayout>
+
 
         <ProgressBar
             android:id="@+id/progressBar_4"

+ 2 - 2
app/src/main/res/layout/activity_test_my.xml

@@ -124,7 +124,7 @@
                 android:layout_height="wrap_content"
                 android:layout_marginTop="8dp"
                 android:gravity="left|center_vertical"
-                android:text="7.没有登录没有权限,一键设置"/>
+                android:text="7.没有登录没有权限,默认试看时间30秒,一键设置"/>
 
             <Button
                 android:id="@+id/btn_my_8"
@@ -132,7 +132,7 @@
                 android:layout_height="wrap_content"
                 android:layout_marginTop="8dp"
                 android:gravity="left|center_vertical"
-                android:text="8.登录了,但不是会员没有权限,一键设置"/>
+                android:text="8.登录了,但会员没有权限,试看一分钟,一键设置"/>
 
             <Button
                 android:id="@+id/btn_my_9"

+ 17 - 0
app/src/main/res/layout/base_activity_view.xml

@@ -0,0 +1,17 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:orientation="vertical"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent">
+
+    <View
+        android:id="@+id/view_status_bar"
+        android:layout_width="match_parent"
+        android:layout_height="24dp"/>
+    <FrameLayout
+        android:id="@+id/frame_layout_content_place"
+        android:layout_width="match_parent"
+        android:layout_height="match_parent"/>
+
+</LinearLayout>

+ 16 - 0
app/src/main/res/layout/fragment_me.xml

@@ -5,6 +5,22 @@
     android:layout_width="match_parent"
     android:layout_height="match_parent">
 
+    <TextView
+        android:id="@+id/tv_1"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:padding="10dp"
+        android:layout_margin="10dp"
+        android:background="@color/gray3"
+        android:text="我的视频缓存"/>
 
+    <TextView
+        android:id="@+id/tv_2"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:padding="10dp"
+        android:layout_margin="10dp"
+        android:background="@color/gray3"
+        android:text="我的音频缓存"/>
 
 </LinearLayout>

+ 19 - 0
app/src/main/res/layout/item_dialog_list_view.xml

@@ -27,8 +27,27 @@
             android:textColor="@color/blackText3"
             android:textSize="12sp"
             android:text="96:09"/>
+        <ProgressBar
+            android:id="@+id/pb"
+            style="?android:attr/progressBarStyleHorizontal"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="5dp"
+            android:layout_weight="1.0" />
     </LinearLayout>
 
+    <TextView
+        android:id="@+id/tv_start_or_pause"
+        android:layout_width="wrap_content"
+        android:layout_height="match_parent"
+        android:layout_margin="10dp"
+        android:gravity="center"
+        android:layout_marginTop="3dp"
+        android:background="@color/gray3"
+        android:padding="10dp"
+        android:textSize="14sp"
+        android:textColor="@color/blackText3"
+        android:text="暂停"/>
 
     <LinearLayout
         android:id="@+id/ll_download"

+ 36 - 0
app/src/main/res/values/strings.xml

@@ -5,4 +5,40 @@
     <string name="pause">暂停</string>
     <string name="delete">删除</string>
 
+
+    <string name="del_file_error_empty">已经为空文件夹</string>
+    <string name="del_cache_files">删除所有已下载文件</string>
+
+    <string name="tasks_manager_demo_name" formatted="false">任务: %d</string>
+    <string name="tasks_manager_demo_status_loading">状态: 加载中...</string>
+    <string name="tasks_manager_demo_status_pending">状态: 队列中</string>
+    <string name="tasks_manager_demo_status_started">状态: 开始下载</string>
+    <string name="tasks_manager_demo_status_connected">状态: 已连接上</string>
+    <string name="tasks_manager_demo_status_progress">状态: 下载中...</string>
+    <string name="tasks_manager_demo_status_downloading" formatted="false">状态: 正在下载 %d</string>
+    <string name="tasks_manager_demo_status_error">状态: 出错</string>
+    <string name="tasks_manager_demo_status_warn">状态: 警告</string>
+    <string name="tasks_manager_demo_status_paused">状态: 暂停</string>
+    <string name="tasks_manager_demo_status_completed">状态: 下载完成</string>
+    <string name="tasks_manager_demo_status_not_downloaded">状态: 未下载</string>
+
+    <string name="hybrid_test_title">混合测试</string>
+    <string name="hybrid_test_deleted_file" formatted="false">已删除: %s</string>
+    <string name="hybrid_test_start_single_task" formatted="false">启动单任务下载: %s</string>
+    <string name="hybrid_test_start_multiple_tasks_parallel" formatted="false">启动%d个任务并行下载</string>
+    <string name="hybrid_test_start_multiple_tasks_serial" formatted="false">启动%d个任务串行下载</string>
+    <string name="hybrid_test_multiple_tasks_parallel_title">多任务队列并行下载</string>
+    <string name="hybrid_test_multiple_tasks_serial_title">多任务队列串行下载</string>
+    <string name="hybrid_test_single_task_title">单任务下载测试</string>
+    <string name="avoid_missing_screen_frames">避免掉帧</string>
+
+
+    <string name="notification_demo_title">下载通知案例</string>
+    <string name="notification_sample_title">下载通知简单案例</string>
+    <string name="notification_sample_show">显示通知</string>
+    <string name="notification_min_set_title">下载通知最简单案例</string>
+    <string name="notification_min_set_desc">这是一个最少代码的Notification案例,在这里我们使用尽量少的代码将下载任务与通知绑定在一起。</string>
+    <string name="notification_sample_desc">这是一个简单的Notification案例,在这里我们显示下载信息在通知面板的同时,还获取下载信息显示在Activity上,并且在下载任务结束或者暂停之后,我们依然保留任务的Notification在Notification面板上。</string>
+
+
 </resources>