[Android] Implement the new scheduler in the browser fragment

Nicolas Pomepuy git at videolan.org
Tue Jul 25 14:57:29 UTC 2023


vlc-android | branch: master | Nicolas Pomepuy <nicolas at videolabs.io> | Thu Jul 20 09:21:09 2023 +0200| [64faba929b71fb029752129f289722c23ee98e4e] | committer: Duncan McNamara

Implement the new scheduler in the browser fragment

> https://code.videolan.org/videolan/vlc-android/commit/64faba929b71fb029752129f289722c23ee98e4e
---

 .../vlc/gui/browser/BaseBrowserFragment.kt         | 69 +++++++++++-----------
 .../vlc/gui/browser/NetworkBrowserFragment.kt      |  2 +-
 2 files changed, 36 insertions(+), 35 deletions(-)

diff --git a/application/vlc-android/src/org/videolan/vlc/gui/browser/BaseBrowserFragment.kt b/application/vlc-android/src/org/videolan/vlc/gui/browser/BaseBrowserFragment.kt
index 19d46bc7ba..daea72c8fd 100644
--- a/application/vlc-android/src/org/videolan/vlc/gui/browser/BaseBrowserFragment.kt
+++ b/application/vlc-android/src/org/videolan/vlc/gui/browser/BaseBrowserFragment.kt
@@ -25,7 +25,6 @@ package org.videolan.vlc.gui.browser
 import android.content.Intent
 import android.net.Uri
 import android.os.Bundle
-import android.os.Message
 import android.util.Log
 import android.view.*
 import androidx.appcompat.view.ActionMode
@@ -77,7 +76,9 @@ import org.videolan.vlc.interfaces.IRefreshable
 import org.videolan.vlc.media.MediaUtils
 import org.videolan.vlc.media.PlaylistManager
 import org.videolan.vlc.repository.BrowserFavRepository
+import org.videolan.vlc.util.LifecycleAwareScheduler
 import org.videolan.vlc.util.Permissions
+import org.videolan.vlc.util.SchedulerCallback
 import org.videolan.vlc.util.isSchemeSupported
 import org.videolan.vlc.util.isTalkbackIsEnabled
 import org.videolan.vlc.viewmodels.browser.BrowserModel
@@ -87,16 +88,16 @@ private const val TAG = "VLC/BaseBrowserFragment"
 
 internal const val KEY_MEDIA = "key_media"
 const val KEY_PICKER_TYPE = "key_picker_type"
-private const val MSG_SHOW_LOADING = 0
-internal const val MSG_HIDE_LOADING = 1
-private const val MSG_REFRESH = 3
-private const val MSG_SHOW_ENQUEUING = 4
-private const val MSG_HIDE_ENQUEUING = 5
+private const val MSG_SHOW_LOADING = "msg_show_loading"
+internal const val MSG_HIDE_LOADING = "msg_hide_loading"
+private const val MSG_REFRESH = "msg_refresh"
+private const val MSG_SHOW_ENQUEUING = "msg_show_enqueuing"
+private const val MSG_HIDE_ENQUEUING = "msg_hide_enqueuing"
 
-abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefreshable, SwipeRefreshLayout.OnRefreshListener, IEventsHandler<MediaLibraryItem>, CtxActionReceiver, PathAdapterListener, BrowserContainer<MediaLibraryItem> {
+abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefreshable, SwipeRefreshLayout.OnRefreshListener, IEventsHandler<MediaLibraryItem>, CtxActionReceiver, PathAdapterListener, BrowserContainer<MediaLibraryItem>, SchedulerCallback {
 
+    lateinit var scheduler:LifecycleAwareScheduler
     private lateinit var addPlaylistFolderOnly: MenuItem
-    protected val handler = BrowserFragmentHandler(this)
     private lateinit var layoutManager: LinearLayoutManager
     override var mrl: String? = null
     protected var currentMedia: MediaWrapper? = null
@@ -112,9 +113,11 @@ abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefr
     protected abstract fun createFragment(): Fragment
     protected abstract fun browseRoot()
     private var needToRefreshMeta = false
+    private var enqueuingSnackbar: Snackbar? = null
 
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
+        scheduler =  LifecycleAwareScheduler(this)
         val bundle = savedInstanceState ?: arguments
         if (bundle != null) {
             currentMedia = bundle.parcelable(KEY_MEDIA)
@@ -344,37 +347,35 @@ abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefr
         playAll(null)
     }
 
-    class BrowserFragmentHandler(owner: BaseBrowserFragment) : WeakHandler<BaseBrowserFragment>(owner) {
+    override fun onTaskTriggered(id: String) {
+        when (id) {
+            MSG_SHOW_LOADING -> swipeRefreshLayout.isRefreshing = true
+            MSG_HIDE_LOADING -> {
+                scheduler.cancelAction(MSG_SHOW_LOADING)
+                swipeRefreshLayout.isRefreshing = false
+            }
 
-        private var enqueuingSnackbar: Snackbar? = null
+            MSG_REFRESH -> {
+                scheduler.cancelAction(MSG_REFRESH)
+                if (!isDetached) refresh()
+            }
 
-        override fun handleMessage(msg: Message) {
-            val fragment = owner ?: return
-            when (msg.what) {
-                MSG_SHOW_LOADING -> fragment.swipeRefreshLayout.isRefreshing = true
-                MSG_HIDE_LOADING -> {
-                    removeMessages(MSG_SHOW_LOADING)
-                    fragment.swipeRefreshLayout.isRefreshing = false
-                }
-                MSG_REFRESH -> {
-                    removeMessages(MSG_REFRESH)
-                    if (!fragment.isDetached) fragment.refresh()
+            MSG_SHOW_ENQUEUING -> {
+                activity?.let {
+                    enqueuingSnackbar = UiTools.snackerMessageInfinite(it, it.getString(R.string.enqueuing))
                 }
-                MSG_SHOW_ENQUEUING -> {
-                    owner?.activity?.let {
-                        enqueuingSnackbar = UiTools.snackerMessageInfinite(it, it.getString(R.string.enqueuing))
-                    }
-                    enqueuingSnackbar?.show()
+                enqueuingSnackbar?.show()
 
-                }
-                MSG_HIDE_ENQUEUING -> {
-                    enqueuingSnackbar?.dismiss()
-                    removeMessages(MSG_SHOW_ENQUEUING)
-                }
+            }
+
+            MSG_HIDE_ENQUEUING -> {
+                enqueuingSnackbar?.dismiss()
+                scheduler.cancelAction(MSG_SHOW_ENQUEUING)
             }
         }
     }
 
+
     override fun clear() = adapter.clear()
 
     override fun removeItem(item: MediaLibraryItem): Boolean {
@@ -398,7 +399,7 @@ abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefr
         lifecycleScope.launch {
             var positionInPlaylist = 0
             val mediaLocations = LinkedList<MediaWrapper>()
-            handler.sendEmptyMessageDelayed(MSG_SHOW_ENQUEUING, 1000)
+            scheduler.scheduleAction(MSG_SHOW_ENQUEUING, 1000L)
             withContext(Dispatchers.IO) {
                 val files = if (viewModel.url?.startsWith("file") == true) viewModel.provider.browseUrl(viewModel.url!!) else viewModel.dataset.getList()
                     for (file in files.filterIsInstance(MediaWrapper::class.java))
@@ -408,7 +409,7 @@ abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefr
                                 positionInPlaylist = mediaLocations.size - 1
                         }
             }
-            handler.sendEmptyMessage(MSG_HIDE_ENQUEUING)
+            scheduler.startAction(MSG_HIDE_ENQUEUING)
             activity?.let { MediaUtils.openList(it, mediaLocations, positionInPlaylist) }
         }
     }
@@ -667,7 +668,7 @@ abstract class BaseBrowserFragment : MediaBrowserFragment<BrowserModel>(), IRefr
         if (!isStarted()) return
         restoreMultiSelectHelper()
         swipeRefreshLayout.isRefreshing = false
-        handler.sendEmptyMessage(MSG_HIDE_LOADING)
+        scheduler.startAction(MSG_HIDE_LOADING)
         updateEmptyView()
         if (!isRootDirectory) {
             updateFab()
diff --git a/application/vlc-android/src/org/videolan/vlc/gui/browser/NetworkBrowserFragment.kt b/application/vlc-android/src/org/videolan/vlc/gui/browser/NetworkBrowserFragment.kt
index c32b20bde5..4a1dbc5094 100644
--- a/application/vlc-android/src/org/videolan/vlc/gui/browser/NetworkBrowserFragment.kt
+++ b/application/vlc-android/src/org/videolan/vlc/gui/browser/NetworkBrowserFragment.kt
@@ -165,7 +165,7 @@ class NetworkBrowserFragment : BaseBrowserFragment(), IDialogManager {
                         binding.emptyLoading.emptyText = getString(R.string.network_empty)
                     }
                     binding.networkList.visibility = View.GONE
-                    handler.sendEmptyMessage(MSG_HIDE_LOADING)
+                    scheduler.startAction(MSG_HIDE_LOADING)
                 }
             } else {
                 binding.emptyLoading.state = EmptyLoadingState.NONE



More information about the Android mailing list