mirror of
https://github.com/topjohnwu/Magisk.git
synced 2024-11-24 10:35:26 +00:00
Added forced loading per user's demand
Added reselecting action (scroll up real fast)
This commit is contained in:
parent
2105cacce3
commit
711799b194
@ -72,6 +72,9 @@ open class MainActivity : CompatActivity<MainViewModel, ActivityMainMd2Binding>(
|
|||||||
}.dispatchOnSelf()
|
}.dispatchOnSelf()
|
||||||
true
|
true
|
||||||
}
|
}
|
||||||
|
binding.mainNavigation.setOnNavigationItemReselectedListener {
|
||||||
|
navigation.onReselected()
|
||||||
|
}
|
||||||
|
|
||||||
binding.mainNavigation.viewTreeObserver.addOnGlobalLayoutListener(navObserver)
|
binding.mainNavigation.viewTreeObserver.addOnGlobalLayoutListener(navObserver)
|
||||||
|
|
||||||
|
@ -0,0 +1,7 @@
|
|||||||
|
package com.topjohnwu.magisk.redesign
|
||||||
|
|
||||||
|
interface ReselectionTarget {
|
||||||
|
|
||||||
|
fun onReselected()
|
||||||
|
|
||||||
|
}
|
@ -8,6 +8,7 @@ import com.topjohnwu.magisk.R
|
|||||||
import com.topjohnwu.magisk.model.navigation.MagiskAnimBuilder
|
import com.topjohnwu.magisk.model.navigation.MagiskAnimBuilder
|
||||||
import com.topjohnwu.magisk.model.navigation.MagiskNavigationEvent
|
import com.topjohnwu.magisk.model.navigation.MagiskNavigationEvent
|
||||||
import com.topjohnwu.magisk.model.navigation.Navigator
|
import com.topjohnwu.magisk.model.navigation.Navigator
|
||||||
|
import com.topjohnwu.magisk.redesign.ReselectionTarget
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
|
|
||||||
class CompatNavigationDelegate<out Source>(
|
class CompatNavigationDelegate<out Source>(
|
||||||
@ -44,6 +45,10 @@ class CompatNavigationDelegate<out Source>(
|
|||||||
fun onSaveInstanceState(outState: Bundle) =
|
fun onSaveInstanceState(outState: Bundle) =
|
||||||
controller.onSaveInstanceState(outState)
|
controller.onSaveInstanceState(outState)
|
||||||
|
|
||||||
|
fun onReselected() {
|
||||||
|
(controller.currentFrag as? ReselectionTarget)?.onReselected()
|
||||||
|
}
|
||||||
|
|
||||||
fun onBackPressed(): Boolean {
|
fun onBackPressed(): Boolean {
|
||||||
val fragment = controller.currentFrag as? CompatFragment<*, *>
|
val fragment = controller.currentFrag as? CompatFragment<*, *>
|
||||||
|
|
||||||
|
@ -16,6 +16,7 @@ import androidx.core.view.isVisible
|
|||||||
import androidx.core.view.marginBottom
|
import androidx.core.view.marginBottom
|
||||||
import androidx.core.view.marginEnd
|
import androidx.core.view.marginEnd
|
||||||
import androidx.interpolator.view.animation.FastOutSlowInInterpolator
|
import androidx.interpolator.view.animation.FastOutSlowInInterpolator
|
||||||
|
import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
import com.google.android.material.circularreveal.CircularRevealCompat
|
import com.google.android.material.circularreveal.CircularRevealCompat
|
||||||
import com.google.android.material.circularreveal.CircularRevealWidget
|
import com.google.android.material.circularreveal.CircularRevealWidget
|
||||||
import com.google.android.material.floatingactionbutton.FloatingActionButton
|
import com.google.android.material.floatingactionbutton.FloatingActionButton
|
||||||
@ -61,8 +62,10 @@ class HideFragment : CompatFragment<HideViewModel, FragmentHideMd2Binding>() {
|
|||||||
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
||||||
when (item.itemId) {
|
when (item.itemId) {
|
||||||
R.id.action_focus_up -> binding.hideContent
|
R.id.action_focus_up -> binding.hideContent
|
||||||
.also { it.scrollToPosition(10) }
|
.takeIf { (it.layoutManager as? LinearLayoutManager)?.findFirstVisibleItemPosition() ?: 0 > 10 }
|
||||||
.also { it.smoothScrollToPosition(0) }
|
?.also { it.scrollToPosition(10) }
|
||||||
|
.let { binding.hideContent }
|
||||||
|
.also { it.post { it.smoothScrollToPosition(0) } }
|
||||||
}
|
}
|
||||||
return super.onOptionsItemSelected(item)
|
return super.onOptionsItemSelected(item)
|
||||||
}
|
}
|
||||||
|
@ -2,17 +2,23 @@ package com.topjohnwu.magisk.redesign.module
|
|||||||
|
|
||||||
import android.graphics.Insets
|
import android.graphics.Insets
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
|
import android.view.Menu
|
||||||
|
import android.view.MenuInflater
|
||||||
|
import android.view.MenuItem
|
||||||
import android.view.View
|
import android.view.View
|
||||||
|
import androidx.recyclerview.widget.StaggeredGridLayoutManager
|
||||||
import com.topjohnwu.magisk.R
|
import com.topjohnwu.magisk.R
|
||||||
import com.topjohnwu.magisk.databinding.FragmentModuleMd2Binding
|
import com.topjohnwu.magisk.databinding.FragmentModuleMd2Binding
|
||||||
import com.topjohnwu.magisk.redesign.MainActivity
|
import com.topjohnwu.magisk.redesign.MainActivity
|
||||||
|
import com.topjohnwu.magisk.redesign.ReselectionTarget
|
||||||
import com.topjohnwu.magisk.redesign.compat.CompatFragment
|
import com.topjohnwu.magisk.redesign.compat.CompatFragment
|
||||||
import com.topjohnwu.magisk.redesign.compat.hideKeyboard
|
import com.topjohnwu.magisk.redesign.compat.hideKeyboard
|
||||||
import com.topjohnwu.magisk.redesign.hide.MotionRevealHelper
|
import com.topjohnwu.magisk.redesign.hide.MotionRevealHelper
|
||||||
import com.topjohnwu.magisk.utils.EndlessRecyclerScrollListener
|
import com.topjohnwu.magisk.utils.EndlessRecyclerScrollListener
|
||||||
import org.koin.androidx.viewmodel.ext.android.viewModel
|
import org.koin.androidx.viewmodel.ext.android.viewModel
|
||||||
|
|
||||||
class ModuleFragment : CompatFragment<ModuleViewModel, FragmentModuleMd2Binding>() {
|
class ModuleFragment : CompatFragment<ModuleViewModel, FragmentModuleMd2Binding>(),
|
||||||
|
ReselectionTarget {
|
||||||
|
|
||||||
override val layoutRes = R.layout.fragment_module_md2
|
override val layoutRes = R.layout.fragment_module_md2
|
||||||
override val viewModel by viewModel<ModuleViewModel>()
|
override val viewModel by viewModel<ModuleViewModel>()
|
||||||
@ -23,6 +29,7 @@ class ModuleFragment : CompatFragment<ModuleViewModel, FragmentModuleMd2Binding>
|
|||||||
|
|
||||||
override fun onStart() {
|
override fun onStart() {
|
||||||
super.onStart()
|
super.onStart()
|
||||||
|
setHasOptionsMenu(true)
|
||||||
activity.title = resources.getString(R.string.section_modules)
|
activity.title = resources.getString(R.string.section_modules)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -50,6 +57,35 @@ class ModuleFragment : CompatFragment<ModuleViewModel, FragmentModuleMd2Binding>
|
|||||||
super.onDestroyView()
|
super.onDestroyView()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ---
|
||||||
|
|
||||||
|
override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) {
|
||||||
|
inflater.inflate(R.menu.menu_module_md2, menu)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
||||||
|
when (item.itemId) {
|
||||||
|
R.id.action_refresh -> viewModel.loadRemoteImplicit()
|
||||||
|
}
|
||||||
|
return super.onOptionsItemSelected(item)
|
||||||
|
}
|
||||||
|
|
||||||
|
// ---
|
||||||
|
|
||||||
|
override fun onReselected() {
|
||||||
|
binding.moduleRemote
|
||||||
|
.takeIf {
|
||||||
|
(it.layoutManager as? StaggeredGridLayoutManager)?.let {
|
||||||
|
it.findFirstVisibleItemPositions(IntArray(it.spanCount)).min()
|
||||||
|
} ?: 0 > 10
|
||||||
|
}
|
||||||
|
?.also { it.scrollToPosition(10) }
|
||||||
|
.let { binding.moduleRemote }
|
||||||
|
.also { it.post { it.smoothScrollToPosition(0) } }
|
||||||
|
}
|
||||||
|
|
||||||
|
// ---
|
||||||
|
|
||||||
override fun onPreBind(binding: FragmentModuleMd2Binding) = Unit
|
override fun onPreBind(binding: FragmentModuleMd2Binding) = Unit
|
||||||
|
|
||||||
private fun setEndlessScroller() {
|
private fun setEndlessScroller() {
|
||||||
|
@ -111,6 +111,7 @@ class ModuleViewModel(
|
|||||||
.map { it.order() }
|
.map { it.order() }
|
||||||
.map { build(active = it) }
|
.map { build(active = it) }
|
||||||
.map { it to items.calculateDiff(it) }
|
.map { it to items.calculateDiff(it) }
|
||||||
|
.applyViewModel(this)
|
||||||
.subscribeK {
|
.subscribeK {
|
||||||
items.update(it.first, it.second)
|
items.update(it.first, it.second)
|
||||||
if (!items.contains(sectionRemote)) {
|
if (!items.contains(sectionRemote)) {
|
||||||
@ -119,6 +120,13 @@ class ModuleViewModel(
|
|||||||
moveToState()
|
moveToState()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun loadRemoteImplicit() = downloadRepos()
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.doOnComplete { items.clear(); itemsSearch.clear() }
|
||||||
|
.applyViewModel(this, false)
|
||||||
|
.subscribeK { refresh(); submitQuery() }
|
||||||
|
.add()
|
||||||
|
|
||||||
@Synchronized
|
@Synchronized
|
||||||
fun loadRemote() {
|
fun loadRemote() {
|
||||||
// check for existing jobs
|
// check for existing jobs
|
||||||
|
8
app/src/main/res/drawable/ic_refresh_data_md2.xml
Normal file
8
app/src/main/res/drawable/ic_refresh_data_md2.xml
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:height="24dp"
|
||||||
|
android:width="24dp"
|
||||||
|
android:viewportWidth="24"
|
||||||
|
android:viewportHeight="24">
|
||||||
|
<path android:fillColor="?colorOnSurface" android:pathData="M19,12V13.5A4,4 0 0,1 23,17.5C23,18.32 22.75,19.08 22.33,19.71L21.24,18.62C21.41,18.28 21.5,17.9 21.5,17.5A2.5,2.5 0 0,0 19,15V16.5L16.75,14.25L19,12M19,23V21.5A4,4 0 0,1 15,17.5C15,16.68 15.25,15.92 15.67,15.29L16.76,16.38C16.59,16.72 16.5,17.1 16.5,17.5A2.5,2.5 0 0,0 19,20V18.5L21.25,20.75L19,23M12,3C16.42,3 20,4.79 20,7C20,9.21 16.42,11 12,11C7.58,11 4,9.21 4,7C4,4.79 7.58,3 12,3M4,9C4,11.21 7.58,13 12,13C13.11,13 14.17,12.89 15.14,12.68C14.19,13.54 13.5,14.67 13.18,15.96L12,16C7.58,16 4,14.21 4,12V9M20,9V11H19.5L18.9,11.03C19.6,10.43 20,9.74 20,9M4,14C4,16.21 7.58,18 12,18L13,17.97C13.09,19.03 13.42,20 13.95,20.88L12,21C7.58,21 4,19.21 4,17V14Z" />
|
||||||
|
</vector>
|
@ -24,6 +24,7 @@
|
|||||||
adapter="@{viewModel.adapter}"
|
adapter="@{viewModel.adapter}"
|
||||||
dividerHorizontal="@{R.drawable.divider_l1}"
|
dividerHorizontal="@{R.drawable.divider_l1}"
|
||||||
dividerVertical="@{R.drawable.divider_l1}"
|
dividerVertical="@{R.drawable.divider_l1}"
|
||||||
|
gone="@{viewModel.loading}"
|
||||||
itemBinding="@{viewModel.itemBinding}"
|
itemBinding="@{viewModel.itemBinding}"
|
||||||
items="@{viewModel.items}"
|
items="@{viewModel.items}"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
@ -69,6 +70,27 @@
|
|||||||
|
|
||||||
</com.google.android.material.circularreveal.cardview.CircularRevealCardView>
|
</com.google.android.material.circularreveal.cardview.CircularRevealCardView>
|
||||||
|
|
||||||
|
<LinearLayout
|
||||||
|
goneUnless="@{viewModel.loading}"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_gravity="center"
|
||||||
|
android:gravity="center"
|
||||||
|
android:orientation="vertical">
|
||||||
|
|
||||||
|
<androidx.appcompat.widget.AppCompatTextView
|
||||||
|
android:layout_width="wrap_content"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:text="@string/safetynet_attest_loading"
|
||||||
|
android:textAppearance="?appearanceTextTitleNormal"
|
||||||
|
android:textStyle="bold" />
|
||||||
|
|
||||||
|
<ProgressBar
|
||||||
|
style="?styleProgressIndeterminate"
|
||||||
|
android:layout_marginTop="@dimen/l1" />
|
||||||
|
|
||||||
|
</LinearLayout>
|
||||||
|
|
||||||
</FrameLayout>
|
</FrameLayout>
|
||||||
|
|
||||||
|
|
||||||
|
10
app/src/main/res/menu/menu_module_md2.xml
Normal file
10
app/src/main/res/menu/menu_module_md2.xml
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<menu xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
xmlns:app="http://schemas.android.com/apk/res-auto">
|
||||||
|
|
||||||
|
<item
|
||||||
|
android:id="@+id/action_refresh"
|
||||||
|
android:icon="@drawable/ic_refresh_data_md2"
|
||||||
|
android:title="Refresh Local Data"
|
||||||
|
app:showAsAction="ifRoom" />
|
||||||
|
</menu>
|
Loading…
Reference in New Issue
Block a user