mirror of
https://github.com/tachiyomiorg/tachiyomi.git
synced 2024-11-09 05:25:08 +01:00
Added Tips for filters and chapter swipe
Using tooltip library to showtips Swipe animations for first chapter item Flow preferences to handle this
This commit is contained in:
parent
3bee24e79a
commit
e9efc7d020
@ -204,6 +204,7 @@ dependencies {
|
||||
implementation("com.github.kizitonwose:AndroidTagGroup:1.6.0")
|
||||
implementation("com.github.chrisbanes:PhotoView:2.3.0")
|
||||
implementation("com.github.carlosesco:DirectionalViewPager:a844dbca0a")
|
||||
implementation("com.github.florent37:viewtooltip:1.2.2")
|
||||
|
||||
// Conductor
|
||||
implementation("com.bluelinelabs:conductor:2.1.5")
|
||||
|
@ -7,6 +7,7 @@ import android.os.Environment
|
||||
import androidx.preference.PreferenceManager
|
||||
import com.f2prateek.rx.preferences.Preference
|
||||
import com.f2prateek.rx.preferences.RxSharedPreferences
|
||||
import com.tfcporciuncula.flow.FlowSharedPreferences
|
||||
import eu.kanade.tachiyomi.R
|
||||
import eu.kanade.tachiyomi.data.track.TrackService
|
||||
import eu.kanade.tachiyomi.source.Source
|
||||
@ -40,6 +41,7 @@ class PreferencesHelper(val context: Context) {
|
||||
|
||||
private val prefs = PreferenceManager.getDefaultSharedPreferences(context)
|
||||
private val rxPrefs = RxSharedPreferences.create(prefs)
|
||||
private val flowPrefs = FlowSharedPreferences(prefs)
|
||||
|
||||
private val defaultDownloadsDir = Uri.fromFile(
|
||||
File(Environment.getExternalStorageDirectory().absolutePath + File.separator +
|
||||
@ -258,4 +260,9 @@ class PreferencesHelper(val context: Context) {
|
||||
fun hideFiltersAtStart() = rxPrefs.getBoolean("hide_filters_at_start", false)
|
||||
|
||||
fun alwaysShowChapterTransition() = rxPrefs.getBoolean(Keys.alwaysShowChapterTransition, true)
|
||||
|
||||
// Tutorial preference
|
||||
fun shownFilterTutorial() = flowPrefs.getBoolean("shown_filter_tutorial", false)
|
||||
|
||||
fun shownChapterSwipeTutorial() = flowPrefs.getBoolean("shown_swipe_tutorial", false)
|
||||
}
|
||||
|
@ -14,7 +14,6 @@ import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.view.ViewPropertyAnimator
|
||||
import android.view.inputmethod.InputMethodManager
|
||||
import android.widget.Toast
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.appcompat.view.ActionMode
|
||||
import androidx.appcompat.widget.SearchView
|
||||
@ -27,6 +26,7 @@ import com.afollestad.materialdialogs.MaterialDialog
|
||||
import com.afollestad.materialdialogs.list.listItemsSingleChoice
|
||||
import com.bluelinelabs.conductor.ControllerChangeHandler
|
||||
import com.bluelinelabs.conductor.ControllerChangeType
|
||||
import com.github.florent37.viewtooltip.ViewTooltip
|
||||
import com.google.android.material.bottomsheet.BottomSheetBehavior
|
||||
import com.google.android.material.snackbar.BaseTransientBottomBar
|
||||
import com.google.android.material.snackbar.Snackbar
|
||||
@ -57,7 +57,6 @@ import eu.kanade.tachiyomi.util.system.dpToPx
|
||||
import eu.kanade.tachiyomi.util.system.dpToPxEnd
|
||||
import eu.kanade.tachiyomi.util.system.getResourceColor
|
||||
import eu.kanade.tachiyomi.util.system.launchUI
|
||||
import eu.kanade.tachiyomi.util.system.toast
|
||||
import eu.kanade.tachiyomi.util.view.applyWindowInsetsForRootController
|
||||
import eu.kanade.tachiyomi.util.view.getItemView
|
||||
import eu.kanade.tachiyomi.util.view.gone
|
||||
@ -140,6 +139,7 @@ class LibraryController(
|
||||
private var textAnim: ViewPropertyAnimator? = null
|
||||
private var scrollAnim: ViewPropertyAnimator? = null
|
||||
private var alwaysShowScroller: Boolean = preferences.alwaysShowSeeker().getOrDefault()
|
||||
private var filterTooltip: ViewTooltip? = null
|
||||
|
||||
override fun getTitle(): String? {
|
||||
return view?.context?.getString(R.string.library)
|
||||
@ -198,6 +198,28 @@ class LibraryController(
|
||||
}
|
||||
}
|
||||
|
||||
private fun showFilterTip() {
|
||||
if (preferences.shownFilterTutorial().get()) return
|
||||
val activity = activity ?: return
|
||||
val icon = activity.bottom_nav.getItemView(R.id.nav_library) ?: return
|
||||
filterTooltip =
|
||||
ViewTooltip.on(activity, icon).autoHide(false, 0L).align(ViewTooltip.ALIGN.START)
|
||||
.position(ViewTooltip.Position.TOP).text(R.string.tap_library_to_show_filters)
|
||||
.color(activity.getResourceColor(R.attr.colorAccent))
|
||||
.textSize(TypedValue.COMPLEX_UNIT_SP, 15f).textColor(Color.WHITE).withShadow(false)
|
||||
.corner(30).arrowWidth(15).arrowHeight(15).distanceWithView(0)
|
||||
|
||||
filterTooltip?.show()
|
||||
}
|
||||
|
||||
private fun closeTip() {
|
||||
if (filterTooltip != null) {
|
||||
filterTooltip?.close()
|
||||
filterTooltip = null
|
||||
preferences.shownFilterTutorial().set(true)
|
||||
}
|
||||
}
|
||||
|
||||
private fun hideScroller(duration: Long = 1000) {
|
||||
if (alwaysShowScroller) return
|
||||
scrollAnim =
|
||||
@ -447,7 +469,7 @@ class LibraryController(
|
||||
presenter.getLibrary()
|
||||
DownloadService.callListeners()
|
||||
LibraryUpdateService.setListener(this)
|
||||
}
|
||||
} else closeTip()
|
||||
if (type == ControllerChangeType.POP_ENTER) filter_bottom_sheet.hideIfPossible()
|
||||
}
|
||||
|
||||
@ -836,6 +858,7 @@ class LibraryController(
|
||||
}
|
||||
|
||||
override fun showSheet() {
|
||||
closeTip()
|
||||
when {
|
||||
filter_bottom_sheet.sheetBehavior?.state == BottomSheetBehavior.STATE_HIDDEN -> filter_bottom_sheet.sheetBehavior?.state =
|
||||
BottomSheetBehavior.STATE_COLLAPSED
|
||||
|
@ -1,5 +1,6 @@
|
||||
package eu.kanade.tachiyomi.ui.library
|
||||
|
||||
import android.annotation.SuppressLint
|
||||
import android.graphics.drawable.Drawable
|
||||
import android.text.SpannableString
|
||||
import android.text.style.ForegroundColorSpan
|
||||
@ -164,6 +165,8 @@ class LibraryHeaderItem(
|
||||
updateButton.invisible()
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressLint("RestrictedApi")
|
||||
private fun showCatSortOptions() {
|
||||
val category =
|
||||
(adapter.getItem(adapterPosition) as? LibraryHeaderItem)?.category ?: return
|
||||
|
@ -133,6 +133,7 @@ class FilterBottomSheet @JvmOverloads constructor(context: Context, attrs: Attri
|
||||
pill.alpha = 0f
|
||||
}
|
||||
if (state == BottomSheetBehavior.STATE_HIDDEN) {
|
||||
onGroupClicked(ACTION_HIDE_FILTER_TIP)
|
||||
reSortViews()
|
||||
shadow?.alpha = 0f
|
||||
pager?.updatePaddingRelative(bottom = 0)
|
||||
|
@ -1,6 +1,5 @@
|
||||
package eu.kanade.tachiyomi.ui.manga
|
||||
|
||||
import android.content.Context
|
||||
import android.view.View
|
||||
import androidx.recyclerview.widget.ItemTouchHelper
|
||||
import eu.davidea.flexibleadapter.items.IFlexible
|
||||
@ -13,12 +12,14 @@ import java.text.DecimalFormat
|
||||
import java.text.DecimalFormatSymbols
|
||||
|
||||
class MangaDetailsAdapter(
|
||||
val controller: MangaDetailsController,
|
||||
context: Context
|
||||
val controller: MangaDetailsController
|
||||
) : BaseChapterAdapter<IFlexible<*>>(controller) {
|
||||
|
||||
val preferences: PreferencesHelper by injectLazy()
|
||||
|
||||
val hasShownSwipeTut
|
||||
get() = preferences.shownChapterSwipeTutorial()
|
||||
|
||||
var items: List<ChapterItem> = emptyList()
|
||||
|
||||
val delegate: MangaDetailsInterface = controller
|
||||
|
@ -231,7 +231,7 @@ class MangaDetailsController : BaseController,
|
||||
width = ViewGroup.LayoutParams.MATCH_PARENT
|
||||
}
|
||||
tabletRecycler?.clipToPadding = false
|
||||
tabletAdapter = MangaDetailsAdapter(this, view.context)
|
||||
tabletAdapter = MangaDetailsAdapter(this)
|
||||
tabletRecycler?.adapter = tabletAdapter
|
||||
tabletRecycler?.layoutManager = LinearLayoutManager(view.context)
|
||||
val divider = View(view.context)
|
||||
@ -246,7 +246,7 @@ class MangaDetailsController : BaseController,
|
||||
|
||||
/** Set adapter, insets, and scroll listener for recycler view */
|
||||
private fun setRecycler(view: View) {
|
||||
adapter = MangaDetailsAdapter(this, view.context)
|
||||
adapter = MangaDetailsAdapter(this)
|
||||
|
||||
recycler.adapter = adapter
|
||||
adapter?.isSwipeEnabled = true
|
||||
|
@ -1,5 +1,7 @@
|
||||
package eu.kanade.tachiyomi.ui.manga.chapter
|
||||
|
||||
import android.animation.AnimatorSet
|
||||
import android.animation.ObjectAnimator
|
||||
import android.view.View
|
||||
import eu.kanade.tachiyomi.R
|
||||
import eu.kanade.tachiyomi.data.database.models.Manga
|
||||
@ -7,8 +9,13 @@ import eu.kanade.tachiyomi.data.download.model.Download
|
||||
import eu.kanade.tachiyomi.source.LocalSource
|
||||
import eu.kanade.tachiyomi.ui.manga.MangaDetailsAdapter
|
||||
import eu.kanade.tachiyomi.util.chapter.ChapterUtil
|
||||
import eu.kanade.tachiyomi.util.system.dpToPx
|
||||
import eu.kanade.tachiyomi.util.view.gone
|
||||
import eu.kanade.tachiyomi.util.view.isVisible
|
||||
import eu.kanade.tachiyomi.util.view.visible
|
||||
import eu.kanade.tachiyomi.util.view.visibleIf
|
||||
import eu.kanade.tachiyomi.widget.EndAnimatorListener
|
||||
import eu.kanade.tachiyomi.widget.StartAnimatorListener
|
||||
import kotlinx.android.synthetic.main.chapters_item.*
|
||||
import kotlinx.android.synthetic.main.download_button.*
|
||||
|
||||
@ -86,6 +93,39 @@ class ChapterHolder(
|
||||
|
||||
notifyStatus(status, item.isLocked, item.progress)
|
||||
resetFrontView()
|
||||
if (adapterPosition == 1) {
|
||||
if (!adapter.hasShownSwipeTut.get())
|
||||
showSlideAnimation()
|
||||
}
|
||||
}
|
||||
|
||||
private fun showSlideAnimation() {
|
||||
val slide = 100f.dpToPx
|
||||
val animatorSet = AnimatorSet()
|
||||
val anim1 = slideAnimation(0f, slide)
|
||||
anim1.startDelay = 1000
|
||||
anim1.addListener(StartAnimatorListener { left_view.visible() })
|
||||
val anim2 = slideAnimation(slide, -slide)
|
||||
anim2.duration = 600
|
||||
anim2.startDelay = 500
|
||||
anim2.addUpdateListener {
|
||||
if (left_view.isVisible() && front_view.translationX <= 0) {
|
||||
left_view.gone()
|
||||
right_view.visible()
|
||||
}
|
||||
}
|
||||
val anim3 = slideAnimation(-slide, 0f)
|
||||
anim3.startDelay = 750
|
||||
animatorSet.playSequentially(anim1, anim2, anim3)
|
||||
animatorSet.addListener(EndAnimatorListener {
|
||||
adapter.hasShownSwipeTut.set(true)
|
||||
})
|
||||
animatorSet.start()
|
||||
}
|
||||
|
||||
private fun slideAnimation(from: Float, to: Float): ObjectAnimator {
|
||||
return ObjectAnimator.ofFloat(front_view, View.TRANSLATION_X, from, to)
|
||||
.setDuration(300)
|
||||
}
|
||||
|
||||
override fun getFrontView(): View {
|
||||
|
@ -1,5 +1,6 @@
|
||||
package eu.kanade.tachiyomi.widget
|
||||
|
||||
import android.animation.Animator
|
||||
import android.view.animation.Animation
|
||||
|
||||
open class SimpleAnimationListener : Animation.AnimationListener {
|
||||
@ -9,3 +10,27 @@ open class SimpleAnimationListener : Animation.AnimationListener {
|
||||
|
||||
override fun onAnimationStart(animation: Animation) {}
|
||||
}
|
||||
|
||||
open class SimpleAnimatorListener : Animator.AnimatorListener {
|
||||
|
||||
override fun onAnimationCancel(animation: Animator?) {}
|
||||
override fun onAnimationRepeat(animator: Animator) {}
|
||||
|
||||
override fun onAnimationEnd(animator: Animator) {}
|
||||
|
||||
override fun onAnimationStart(animator: Animator) {}
|
||||
}
|
||||
|
||||
class StartAnimatorListener(private val startAnimationListener: (animator: Animator) -> Unit) :
|
||||
SimpleAnimatorListener() {
|
||||
override fun onAnimationStart(animator: Animator) {
|
||||
startAnimationListener(animator)
|
||||
}
|
||||
}
|
||||
|
||||
class EndAnimatorListener(private val endAnimationListener: (animator: Animator) -> Unit) :
|
||||
SimpleAnimatorListener() {
|
||||
override fun onAnimationEnd(animator: Animator) {
|
||||
endAnimationListener(animator)
|
||||
}
|
||||
}
|
||||
|
@ -1,7 +1,7 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<eu.kanade.tachiyomi.ui.library.filter.FilterBottomSheet xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/bottom_sheet"
|
||||
android:id="@+id/filter_bottom_sheet"
|
||||
style="@style/BottomSheetDialogTheme"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
|
@ -77,7 +77,7 @@
|
||||
android:alpha="0.5"
|
||||
android:background="@drawable/shape_gradient_top_shadow"
|
||||
android:paddingBottom="10dp"
|
||||
app:layout_anchor="@id/bottom_sheet"
|
||||
app:layout_anchor="@id/filter_bottom_sheet"
|
||||
app:layout_anchorGravity="top" />
|
||||
|
||||
<!-- Adding bottom sheet after main content -->
|
||||
|
@ -2,7 +2,7 @@
|
||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/bottom_sheet"
|
||||
android:id="@+id/filter_bottom_sheet"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@drawable/bottom_sheet_rounded_background"
|
||||
|
@ -1,8 +1,8 @@
|
||||
<menu xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
tools:context=".MainActivity"
|
||||
app:tint="@android:color/black">
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
app:tint="@android:color/black"
|
||||
tools:context=".MainActivity">
|
||||
|
||||
<item
|
||||
android:id="@+id/action_search"
|
||||
@ -12,19 +12,10 @@
|
||||
app:actionViewClass="androidx.appcompat.widget.SearchView"
|
||||
app:showAsAction="collapseActionView|ifRoom" />
|
||||
|
||||
<item
|
||||
android:id="@+id/action_library_display"
|
||||
android:icon="@drawable/ic_tune_white_24dp"
|
||||
android:visible="false"
|
||||
android:title="@string/display_options"
|
||||
app:showAsAction="ifRoom"
|
||||
/>
|
||||
|
||||
<item
|
||||
android:id="@+id/action_settings"
|
||||
android:icon="@drawable/ic_settings_white_24dp"
|
||||
android:title="@string/settings"
|
||||
app:showAsAction="ifRoom"
|
||||
/>
|
||||
app:showAsAction="ifRoom" />
|
||||
|
||||
</menu>
|
||||
|
@ -140,7 +140,7 @@
|
||||
<string name="hide_badges">Hide badges</string>
|
||||
<string name="show_badges">Show badges</string>
|
||||
<string name="show_count">Show count</string>
|
||||
<string name="hide_filters_tip">To show filters again, tap the Library icon</string>
|
||||
<string name="tap_library_to_show_filters">Tap the Library icon to show filters</string>
|
||||
<string name="display_as">Display as</string>
|
||||
|
||||
<!-- Library update service notifications -->
|
||||
|
Loading…
Reference in New Issue
Block a user