PendingTask.kt (3286B) - raw
1 package me.rhunk.snapenhance.task 2 3 4 enum class TaskType( 5 val key: String 6 ) { 7 DOWNLOAD("download"), 8 CHAT_ACTION("chat_action"); 9 10 companion object { 11 fun fromKey(key: String): TaskType { 12 return entries.find { it.key == key } ?: throw IllegalArgumentException("Invalid key $key") 13 } 14 } 15 } 16 17 enum class TaskStatus( 18 val key: String 19 ) { 20 PENDING("pending"), 21 RUNNING("running"), 22 SUCCESS("success"), 23 FAILURE("failure"), 24 CANCELLED("cancelled"); 25 26 fun isFinalStage(): Boolean { 27 return this == SUCCESS || this == FAILURE || this == CANCELLED 28 } 29 30 companion object { 31 fun fromKey(key: String): TaskStatus { 32 return entries.find { it.key == key } ?: throw IllegalArgumentException("Invalid key $key") 33 } 34 } 35 } 36 37 data class PendingTaskListener( 38 val onSuccess: () -> Unit = {}, 39 val onCancel: () -> Unit = {}, 40 val onProgress: (label: String?, progress: Int) -> Unit = { _, _ -> }, 41 val onStateChange: (status: TaskStatus) -> Unit = {}, 42 ) 43 44 data class Task( 45 val type: TaskType, 46 val title: String, 47 val author: String?, 48 val hash: String 49 ) { 50 var changeListener: () -> Unit = {} 51 52 var extra: String? = null 53 set(value) { 54 field = value 55 changeListener() 56 } 57 var status: TaskStatus = TaskStatus.PENDING 58 set(value) { 59 field = value 60 changeListener() 61 } 62 } 63 64 class PendingTask( 65 val taskId: Long, 66 val task: Task 67 ) { 68 private val listeners = mutableListOf<PendingTaskListener>() 69 70 fun addListener(listener: PendingTaskListener) { 71 synchronized(listeners) { listeners.add(listener) } 72 } 73 74 fun removeListener(listener: PendingTaskListener) { 75 synchronized(listeners) { listeners.remove(listener) } 76 } 77 78 var status 79 get() = task.status; 80 set(value) { 81 task.status = value; 82 synchronized(listeners) { 83 listeners.forEach { it.onStateChange(value) } 84 } 85 } 86 87 var progressLabel: String? = null 88 set(value) { 89 field = value 90 synchronized(listeners) { 91 listeners.forEach { it.onProgress(value, progress) } 92 } 93 } 94 95 private var _progress = 0 96 set(value) { 97 assert(value in 0..100 || value == -1) 98 field = value 99 } 100 101 var progress get() = _progress 102 set(value) { 103 _progress = value 104 synchronized(listeners) { 105 listeners.forEach { it.onProgress(progressLabel, value) } 106 } 107 } 108 109 fun updateProgress(label: String, progress: Int = -1) { 110 _progress = progress.coerceIn(-1, 100) 111 progressLabel = label 112 } 113 114 fun fail(reason: String) { 115 status = TaskStatus.FAILURE 116 synchronized(listeners) { 117 listeners.forEach { it.onCancel() } 118 } 119 updateProgress(reason) 120 } 121 122 fun success() { 123 status = TaskStatus.SUCCESS 124 synchronized(listeners) { 125 listeners.forEach { it.onSuccess() } 126 } 127 } 128 129 fun cancel() { 130 status = TaskStatus.CANCELLED 131 synchronized(listeners) { 132 listeners.forEach { it.onCancel() } 133 } 134 } 135 }