DownloadX - 协程下载器来了

Github地址,觉得赞欢迎star

它来了,它来了,基于协程打造的下载工具,支持多线程下载和断点续传

Prepare

  • 添加仓库:
maven { url 'https://jitpack.io' }
  • 添加依赖:
implementation "com.github.ssseasonnn:DownloadX:1.0.0"

Basic Usage

// 创建下载任务
val downloadTask = coroutineScope.download("url")

// 监听下载进度
downloadTask.progress()
    .onEach { binding.button.setProgress(it)  }
    .launchIn(lifecycleScope)

// 或者监听下载状态
downloadTask.state()
    .onEach { binding.button.setState(it)  }
    .launchIn(lifecycleScope)

// 开始下载
downloadTask.start()

创建任务

  • 指定CoroutineScope

如果下载任务仅限于Activity或Fragment的生命周期内,那么可以直接使用Activity或Fragment的lifecycleScope,即可保证在Activity或Fragment销毁的时候自动结束下载任务

lifecycleScope是androidX中的扩展,需要添加以下依赖:
implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.2.0'

class DemoActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        
        //activity销毁时,该下载任务自动停止
        val downloadTask = lifecycleScope.download("url")
        downloadTask.start()
    }
}

如果下载任务需要在多个Activity之间共享,或者进行后台下载,那么直接使用GlobalScope即可

class DemoActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        
        //activity销毁时,该下载任务仍然继续下载
        val downloadTask = GlobalScope.download("url")
        downloadTask.start()
    }
}
  • 设置保存文件名和保存路径

直接传给download方法:

val downloadTask = GlobalScope.download("url", "saveName", "savePath")

创建自定义DownloadParam:

val downloadParam = DownloadParam("url", "saveName", "savePath")
val downloadTask = lifecycleScope.download(downloadParam)

默认情况下,我们使用url作为DownloadTask的唯一标示,当需要改变这一默认行为时,可以自定义自己的DownloadParam

class CustomDownloadParam(url: String, saveName: String, savePath: String) : DownloadParam(url, saveName, savePath) {
    override fun tag(): String {
        // 使用文件路径作为唯一标示
        return savePath + saveName
    }
}

val customDownloadParam = CustomDownloadParam("url", "saveName", "savePath")
val downloadTask = lifecycleScope.download(customDownloadParam)

在多个页面使用同样的标识(例如相同的url)创建下载任务时,将会返回同一个DownloadTask,例如:

// 同一个url
val url = "xxxx"

class DemoActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        //创建下载任务
        val downloadTask = GlobalScope.download(url)

        downloadTask.progress()
            .onEach { progress ->  /* 更新进度 */ }
            .launchIn(lifecycleScope)

        downloadTask.start()
    }
}

class OtherActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        //以相同的url创建下载任务,即可获取上一个页面创建的下载任务
        val downloadTask = GlobalScope.download(url)

        downloadTask.progress()
            .onEach { progress ->  /* 更新进度 */ }
            .launchIn(lifecycleScope)

        downloadTask.start()
    }
}

基于此,可以在任意多个页面中共享同一个下载进度和下载状态

进度和状态

  • 只监听进度

在某些场景只需要下载的进度时,可使用这种方式

// 创建任务
val downloadTask = lifecycleScope.download("url")

downloadTask.progress()
    .onEach { progress ->  /* 更新进度 */ }
    .launchIn(lifecycleScope) // 使用lifecycleScope

//开始下载
downloadTask.start()

利用lifecycleScope可确保在Activity或Fragment销毁的时候自动解除监听

可以为progress()方法设置更新间隔,默认是200ms更新一次,如:

downloadTask.progress(500) // 设置为500ms更新一次进度
    .onEach { progress ->  
        // 更新进度
        setProgress(progress)
    }
    .launchIn(lifecycleScope)
  • 监听下载状态和进度

当需要下载状态和下载进度的时候,使用这种方式获取

// 创建任务
val downloadTask = lifecycleScope.download("url")

downloadTask.state()
    .onEach { state ->  
        // 更新状态
        setState(state)
        // 更新进度
        setProgress(state.progress)
    }
    .launchIn(lifecycleScope)

//开始下载
downloadTask.start()

state有以下值:None,Waiting,Downloading,Stopped,Failed,Succeed

同样的,可以为state()方法设置进度更新间隔

启动和停止

  • 开始下载
downloadTask.start()
  • 停止下载
downloadTask.stop()

Github地址,觉得赞欢迎star

推荐阅读更多精彩内容