diff --git a/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferenceKeys.kt b/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferenceKeys.kt index 6a1f2a343..2bbcf1361 100755 --- a/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferenceKeys.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferenceKeys.kt @@ -81,6 +81,10 @@ object PreferenceKeys { const val navigationModeWebtoon = "reader_navigation_mode_webtoon" + const val showNavigationOverlayNewUser = "reader_navigation_overlay_new_user" + + const val showNavigationOverlayOnStart = "reader_navigation_overlay_on_start" + const val webtoonSidePadding = "webtoon_side_padding" const val portraitColumns = "pref_library_columns_portrait_key" diff --git a/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferencesHelper.kt b/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferencesHelper.kt index 4ee231ff3..97b1706a0 100755 --- a/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferencesHelper.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/data/preference/PreferencesHelper.kt @@ -151,6 +151,10 @@ class PreferencesHelper(val context: Context) { fun navigationModeWebtoon() = flowPrefs.getInt(Keys.navigationModeWebtoon, 0) + fun showNavigationOverlayNewUser() = flowPrefs.getBoolean(Keys.showNavigationOverlayNewUser, true) + + fun showNavigationOverlayOnStart() = flowPrefs.getBoolean(Keys.showNavigationOverlayOnStart, false) + fun portraitColumns() = flowPrefs.getInt(Keys.portraitColumns, 0) fun landscapeColumns() = flowPrefs.getInt(Keys.landscapeColumns, 0) diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/ReaderNavigationOverlayView.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/ReaderNavigationOverlayView.kt new file mode 100644 index 000000000..13e0b22f0 --- /dev/null +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/ReaderNavigationOverlayView.kt @@ -0,0 +1,140 @@ +package eu.kanade.tachiyomi.ui.reader + +import android.content.Context +import android.graphics.Canvas +import android.graphics.Color +import android.graphics.Paint +import android.util.AttributeSet +import android.view.MotionEvent +import android.view.View +import android.view.ViewPropertyAnimator +import androidx.core.content.ContextCompat +import androidx.core.view.isVisible +import eu.kanade.tachiyomi.R +import eu.kanade.tachiyomi.ui.reader.viewer.ViewerNavigation +import kotlin.math.abs + +class ReaderNavigationOverlayView(context: Context, attributeSet: AttributeSet) : View(context, attributeSet) { + + private var viewPropertyAnimator: ViewPropertyAnimator? = null + + private var navigation: ViewerNavigation? = null + + fun setNavigation(navigation: ViewerNavigation, showOnStart: Boolean) { + if (!showOnStart && this.navigation == null) { + this.navigation = navigation + isVisible = false + return + } + + this.navigation = navigation + invalidate() + + if (isVisible) return + + viewPropertyAnimator = animate() + .alpha(1f) + .setDuration(1000L) + .withStartAction { + isVisible = true + } + .withEndAction { + viewPropertyAnimator = null + } + viewPropertyAnimator?.start() + } + + private val textPaint = Paint().apply { + textAlign = Paint.Align.CENTER + color = Color.WHITE + textSize = 64f + } + + private val textBorderPaint = Paint().apply { + textAlign = Paint.Align.CENTER + color = Color.BLACK + textSize = 64f + style = Paint.Style.STROKE + strokeWidth = 8f + } + + override fun onDraw(canvas: Canvas?) { + if (navigation == null) return + + navigation?.regions?.forEach { region -> + + val paint = paintForRegion(region.type) + + val rect = region.rectF + + canvas?.save() + + // Scale rect from 1f,1f to screen width and height + canvas?.scale(width.toFloat(), height.toFloat()) + canvas?.drawRect(rect, paint) + + canvas?.restore() + // Don't want scale anymore because it messes with drawText + canvas?.save() + + // Translate origin to rect start (left, top) + canvas?.translate((width * rect.left), (height * rect.top)) + + // Calculate center of rect width on screen + val x = width * (abs(rect.left - rect.right) / 2) + + // Calculate center of rect height on screen + val y = height * (abs(rect.top - rect.bottom) / 2) + + canvas?.drawText(region.type.name, x, y, textBorderPaint) + canvas?.drawText(region.type.name, x, y, textPaint) + + canvas?.restore() + } + } + + private fun paintForRegion(type: ViewerNavigation.NavigationRegion): Paint { + return Paint().apply { + when (type) { + ViewerNavigation.NavigationRegion.NEXT -> { + color = ContextCompat.getColor(context, R.color.navigation_next) + } + ViewerNavigation.NavigationRegion.PREV -> { + color = ContextCompat.getColor(context, R.color.navigation_prev) + } + ViewerNavigation.NavigationRegion.MENU -> { + color = ContextCompat.getColor(context, R.color.navigation_menu) + } + ViewerNavigation.NavigationRegion.RIGHT -> { + color = ContextCompat.getColor(context, R.color.navigation_right) + } + ViewerNavigation.NavigationRegion.LEFT -> { + color = ContextCompat.getColor(context, R.color.navigation_left) + } + } + } + } + + override fun performClick(): Boolean { + super.performClick() + + if (viewPropertyAnimator == null && isVisible) { + viewPropertyAnimator = animate() + .alpha(0f) + .setDuration(1000L) + .withEndAction { + isVisible = false + viewPropertyAnimator = null + } + viewPropertyAnimator?.start() + } + + return true + } + + override fun onTouchEvent(event: MotionEvent?): Boolean { + // Hide overlay if user start tapping or swiping + performClick() + return super.onTouchEvent(event) + } +} diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/ViewerConfig.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/ViewerConfig.kt index 651a64185..2fd6fe1cd 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/ViewerConfig.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/ViewerConfig.kt @@ -15,6 +15,8 @@ abstract class ViewerConfig(preferences: PreferencesHelper, private val scope: C var imagePropertyChangedListener: (() -> Unit)? = null + var navigationModeChangedListener: (() -> Unit)? = null + var tappingEnabled = true var tappingInverted = TappingInvertMode.NONE var longTapEnabled = true @@ -26,6 +28,10 @@ abstract class ViewerConfig(preferences: PreferencesHelper, private val scope: C var navigationMode = 0 protected set + var forceNavigationOverlay = false + + var navigationOverlayOnStart = false + var dualPageSplit = false protected set @@ -56,6 +62,14 @@ abstract class ViewerConfig(preferences: PreferencesHelper, private val scope: C preferences.alwaysShowChapterTransition() .register({ alwaysShowChapterTransition = it }) + + forceNavigationOverlay = preferences.showNavigationOverlayNewUser().get() + if (forceNavigationOverlay) { + preferences.showNavigationOverlayNewUser().set(false) + } + + preferences.showNavigationOverlayOnStart() + .register({ navigationOverlayOnStart = it }) } protected abstract fun defaultNavigation(): ViewerNavigation diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerConfig.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerConfig.kt index b8e7febeb..96ae91b8c 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerConfig.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerConfig.kt @@ -99,6 +99,7 @@ class PagerConfig( 4 -> RightAndLeftNavigation() else -> defaultNavigation() } + navigationModeChangedListener?.invoke() } enum class ZoomType { diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerViewer.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerViewer.kt index 5bc71e60a..732f223c0 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerViewer.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/pager/PagerViewer.kt @@ -119,6 +119,11 @@ abstract class PagerViewer(val activity: ReaderActivity) : BaseViewer { config.imagePropertyChangedListener = { refreshAdapter() } + + config.navigationModeChangedListener = { + val showOnStart = config.navigationOverlayOnStart || config.forceNavigationOverlay + activity.binding.navigationOverlay.setNavigation(config.navigator, showOnStart) + } } override fun destroy() { diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonConfig.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonConfig.kt index 75fb5d815..a826911c6 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonConfig.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonConfig.kt @@ -86,5 +86,6 @@ class WebtoonConfig( 4 -> RightAndLeftNavigation() else -> defaultNavigation() } + navigationModeChangedListener?.invoke() } } diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonViewer.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonViewer.kt index 1bcfc30e3..0a77ca73e 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonViewer.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/reader/viewer/webtoon/WebtoonViewer.kt @@ -136,6 +136,11 @@ class WebtoonViewer(val activity: ReaderActivity, val isContinuous: Boolean = tr refreshAdapter() } + config.navigationModeChangedListener = { + val showOnStart = config.navigationOverlayOnStart || config.forceNavigationOverlay + activity.binding.navigationOverlay.setNavigation(config.navigator, showOnStart) + } + // SY --> config.zoomPropertyChangedListener = { frame.enableZoomOut = it diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/setting/SettingsReaderController.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/setting/SettingsReaderController.kt index 1cd7f41aa..d7bffead7 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/setting/SettingsReaderController.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/setting/SettingsReaderController.kt @@ -50,6 +50,12 @@ class SettingsReaderController : SettingsController() { summaryRes = R.string.pref_show_reading_mode_summary defaultValue = true } + switchPreference { + key = Keys.showNavigationOverlayOnStart + titleRes = R.string.pref_show_navigation_mode + summaryRes = R.string.pref_show_navigation_mode_summary + defaultValue = false + } switchPreference { key = Keys.forceHorizontalSeekbar titleRes = R.string.pref_force_horz_seekbar diff --git a/app/src/main/res/layout/reader_activity.xml b/app/src/main/res/layout/reader_activity.xml index e59069aa6..4446f9904 100755 --- a/app/src/main/res/layout/reader_activity.xml +++ b/app/src/main/res/layout/reader_activity.xml @@ -44,6 +44,12 @@ android:layout_height="match_parent" android:visibility="gone" /> + + #47a84a + + #CB84E296 + #CCFF7733 + #CC95818D + #CCA6CFD5 + #CC7D1128 + #232B30 diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 4b00d93f8..aac332fb8 100755 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -252,6 +252,8 @@ Fullscreen + Show navigation layout overlay + Show overlay when reader is opened Dual page split (ALPHA) Invert dual page split placement If the placement of the dual page split doesn\'t match reading direction