Add option to disable auto lock and add manual locking
This commit is contained in:
parent
0dd9e9e015
commit
c48bebe0b2
@ -15,6 +15,8 @@
|
|||||||
<uses-permission android:name="android.permission.GET_TASKS"/>
|
<uses-permission android:name="android.permission.GET_TASKS"/>
|
||||||
<uses-permission android:name="android.permission.PACKAGE_USAGE_STATS"
|
<uses-permission android:name="android.permission.PACKAGE_USAGE_STATS"
|
||||||
tools:ignore="ProtectedPermissions" />
|
tools:ignore="ProtectedPermissions" />
|
||||||
|
<!-- Lock vibrate -->
|
||||||
|
<uses-permission android:name="android.permission.VIBRATE"/>
|
||||||
|
|
||||||
<application
|
<application
|
||||||
android:name=".App"
|
android:name=".App"
|
||||||
|
@ -121,6 +121,16 @@ object PreferenceKeys {
|
|||||||
|
|
||||||
fun trackToken(syncId: Int) = "track_token_$syncId"
|
fun trackToken(syncId: Int) = "track_token_$syncId"
|
||||||
|
|
||||||
|
const val eh_lock_hash = "lock_hash"
|
||||||
|
|
||||||
|
const val eh_lock_salt = "lock_salt"
|
||||||
|
|
||||||
|
const val eh_lock_length = "lock_length"
|
||||||
|
|
||||||
|
const val eh_lock_finger = "lock_finger"
|
||||||
|
|
||||||
|
const val eh_lock_manually = "eh_lock_manually"
|
||||||
|
|
||||||
const val eh_nh_useHighQualityThumbs = "eh_nh_hq_thumbs"
|
const val eh_nh_useHighQualityThumbs = "eh_nh_hq_thumbs"
|
||||||
|
|
||||||
const val eh_showSyncIntro = "eh_show_sync_intro"
|
const val eh_showSyncIntro = "eh_show_sync_intro"
|
||||||
|
@ -203,13 +203,15 @@ class PreferencesHelper(val context: Context) {
|
|||||||
fun eh_sessionCookie() = rxPrefs.getString(Keys.eh_sessionCookie, "")
|
fun eh_sessionCookie() = rxPrefs.getString(Keys.eh_sessionCookie, "")
|
||||||
|
|
||||||
//Lock
|
//Lock
|
||||||
fun lockHash() = rxPrefs.getString("lock_hash", null)
|
fun eh_lockHash() = rxPrefs.getString(Keys.eh_lock_hash, null)
|
||||||
|
|
||||||
fun lockSalt() = rxPrefs.getString("lock_salt", null)
|
fun eh_lockSalt() = rxPrefs.getString(Keys.eh_lock_salt, null)
|
||||||
|
|
||||||
fun lockLength() = rxPrefs.getInteger("lock_length", -1)
|
fun eh_lockLength() = rxPrefs.getInteger(Keys.eh_lock_length, -1)
|
||||||
|
|
||||||
fun lockUseFingerprint() = rxPrefs.getBoolean("lock_finger", false)
|
fun eh_lockUseFingerprint() = rxPrefs.getBoolean(Keys.eh_lock_finger, false)
|
||||||
|
|
||||||
|
fun eh_lockManually() = rxPrefs.getBoolean(Keys.eh_lock_manually, false)
|
||||||
|
|
||||||
fun eh_nh_useHighQualityThumbs() = rxPrefs.getBoolean(Keys.eh_nh_useHighQualityThumbs, false)
|
fun eh_nh_useHighQualityThumbs() = rxPrefs.getBoolean(Keys.eh_nh_useHighQualityThumbs, false)
|
||||||
|
|
||||||
|
@ -12,8 +12,10 @@ import android.os.Bundle
|
|||||||
import android.support.v4.view.GravityCompat
|
import android.support.v4.view.GravityCompat
|
||||||
import android.support.v4.widget.DrawerLayout
|
import android.support.v4.widget.DrawerLayout
|
||||||
import android.support.v7.graphics.drawable.DrawerArrowDrawable
|
import android.support.v7.graphics.drawable.DrawerArrowDrawable
|
||||||
|
import android.support.v7.widget.Toolbar
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import com.bluelinelabs.conductor.*
|
import com.bluelinelabs.conductor.*
|
||||||
|
import com.jakewharton.rxbinding.support.v7.widget.navigationClicks
|
||||||
import eu.kanade.tachiyomi.Migrations
|
import eu.kanade.tachiyomi.Migrations
|
||||||
import eu.kanade.tachiyomi.R
|
import eu.kanade.tachiyomi.R
|
||||||
import eu.kanade.tachiyomi.data.preference.PreferencesHelper
|
import eu.kanade.tachiyomi.data.preference.PreferencesHelper
|
||||||
@ -39,6 +41,11 @@ import exh.ui.migration.MetadataFetchDialog
|
|||||||
import exh.util.defRealm
|
import exh.util.defRealm
|
||||||
import kotlinx.android.synthetic.main.main_activity.*
|
import kotlinx.android.synthetic.main.main_activity.*
|
||||||
import uy.kohesive.injekt.injectLazy
|
import uy.kohesive.injekt.injectLazy
|
||||||
|
import android.view.View.FIND_VIEWS_WITH_CONTENT_DESCRIPTION
|
||||||
|
import android.text.TextUtils
|
||||||
|
import android.view.View
|
||||||
|
import com.jakewharton.rxbinding.view.longClicks
|
||||||
|
import eu.kanade.tachiyomi.util.vibrate
|
||||||
|
|
||||||
|
|
||||||
class MainActivity : BaseActivity() {
|
class MainActivity : BaseActivity() {
|
||||||
@ -144,18 +151,26 @@ class MainActivity : BaseActivity() {
|
|||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// --> EH
|
||||||
|
//Hook long press hamburger menu to lock
|
||||||
|
getToolbarNavigationIcon(toolbar)?.setOnLongClickListener {
|
||||||
|
doLock(true)
|
||||||
|
vibrate(50) // Notify user of lock
|
||||||
|
true
|
||||||
|
}
|
||||||
|
|
||||||
//Show lock
|
//Show lock
|
||||||
if (savedInstanceState == null) {
|
if (savedInstanceState == null) {
|
||||||
val lockEnabled = lockEnabled(preferences)
|
val lockEnabled = lockEnabled(preferences)
|
||||||
if (lockEnabled) {
|
if (lockEnabled) {
|
||||||
//Special case first lock
|
//Special case first lock
|
||||||
toolbar.navigationIcon = null
|
|
||||||
doLock()
|
doLock()
|
||||||
|
|
||||||
//Check lock security
|
//Check lock security
|
||||||
notifyLockSecurity(this)
|
notifyLockSecurity(this)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// <-- EH
|
||||||
|
|
||||||
syncActivityViewWithController(router.backstack.lastOrNull()?.controller())
|
syncActivityViewWithController(router.backstack.lastOrNull()?.controller())
|
||||||
|
|
||||||
@ -233,6 +248,26 @@ class MainActivity : BaseActivity() {
|
|||||||
router.setRoot(controller.withFadeTransaction().tag(id.toString()))
|
router.setRoot(controller.withFadeTransaction().tag(id.toString()))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun getToolbarNavigationIcon(toolbar: Toolbar): View? {
|
||||||
|
//check if contentDescription previously was set
|
||||||
|
val hadContentDescription = TextUtils.isEmpty(toolbar.navigationContentDescription)
|
||||||
|
val contentDescription = if (!hadContentDescription) toolbar.navigationContentDescription else "navigationIcon"
|
||||||
|
toolbar.navigationContentDescription = contentDescription
|
||||||
|
|
||||||
|
val potentialViews = ArrayList<View>()
|
||||||
|
|
||||||
|
//find the view based on it's content description, set programmatically or with android:contentDescription
|
||||||
|
toolbar.findViewsWithText(potentialViews, contentDescription, View.FIND_VIEWS_WITH_CONTENT_DESCRIPTION)
|
||||||
|
|
||||||
|
//Nav icon is always instantiated at this point because calling setNavigationContentDescription ensures its existence
|
||||||
|
val navIcon = potentialViews.firstOrNull()
|
||||||
|
|
||||||
|
//Clear content description if not previously present
|
||||||
|
if (hadContentDescription)
|
||||||
|
toolbar.navigationContentDescription = null
|
||||||
|
return navIcon
|
||||||
|
}
|
||||||
|
|
||||||
private fun syncActivityViewWithController(to: Controller?, from: Controller? = null) {
|
private fun syncActivityViewWithController(to: Controller?, from: Controller? = null) {
|
||||||
if (from is DialogController || to is DialogController) {
|
if (from is DialogController || to is DialogController) {
|
||||||
return
|
return
|
||||||
@ -249,6 +284,7 @@ class MainActivity : BaseActivity() {
|
|||||||
//Special case and hide drawer arrow for lock controller
|
//Special case and hide drawer arrow for lock controller
|
||||||
if(to is LockController) {
|
if(to is LockController) {
|
||||||
supportActionBar?.setDisplayHomeAsUpEnabled(false)
|
supportActionBar?.setDisplayHomeAsUpEnabled(false)
|
||||||
|
toolbar.navigationIcon = null
|
||||||
} else {
|
} else {
|
||||||
supportActionBar?.setDisplayHomeAsUpEnabled(true)
|
supportActionBar?.setDisplayHomeAsUpEnabled(true)
|
||||||
toolbar.navigationIcon = drawerArrow
|
toolbar.navigationIcon = drawerArrow
|
||||||
@ -308,6 +344,10 @@ class MainActivity : BaseActivity() {
|
|||||||
if(router.backstack.lastOrNull()?.controller() is LockController)
|
if(router.backstack.lastOrNull()?.controller() is LockController)
|
||||||
return
|
return
|
||||||
|
|
||||||
|
//Do not lock if manual lock enabled
|
||||||
|
if(preferences.eh_lockManually().getOrDefault())
|
||||||
|
return
|
||||||
|
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
|
||||||
val mUsageStatsManager = getSystemService(Context.USAGE_STATS_SERVICE) as UsageStatsManager
|
val mUsageStatsManager = getSystemService(Context.USAGE_STATS_SERVICE) as UsageStatsManager
|
||||||
val time = System.currentTimeMillis()
|
val time = System.currentTimeMillis()
|
||||||
@ -331,9 +371,9 @@ class MainActivity : BaseActivity() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun doLock() {
|
fun doLock(animate: Boolean = false) {
|
||||||
router.pushController(RouterTransaction.with(LockController())
|
router.pushController(RouterTransaction.with(LockController())
|
||||||
.popChangeHandler(LockChangeHandler()))
|
.popChangeHandler(LockChangeHandler(animate)))
|
||||||
}
|
}
|
||||||
// <-- EH
|
// <-- EH
|
||||||
|
|
||||||
|
@ -4,7 +4,6 @@ import android.app.Dialog
|
|||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.os.Handler
|
import android.os.Handler
|
||||||
import android.support.v7.preference.PreferenceScreen
|
import android.support.v7.preference.PreferenceScreen
|
||||||
import android.support.v7.preference.SwitchPreference
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import com.afollestad.materialdialogs.MaterialDialog
|
import com.afollestad.materialdialogs.MaterialDialog
|
||||||
import eu.kanade.tachiyomi.R
|
import eu.kanade.tachiyomi.R
|
||||||
@ -197,6 +196,14 @@ class SettingsGeneralController : SettingsController() {
|
|||||||
//Call after addPreference
|
//Call after addPreference
|
||||||
dependency = "pref_app_lock"
|
dependency = "pref_app_lock"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
switchPreference {
|
||||||
|
key = Keys.eh_lock_manually
|
||||||
|
|
||||||
|
title = "Lock manually only"
|
||||||
|
summary = "Disable automatic app locking. The app can still be locked manually by long-pressing the three-lines/back button in the top left corner."
|
||||||
|
defaultValue = false
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5,13 +5,17 @@ import android.app.Notification
|
|||||||
import android.app.NotificationManager
|
import android.app.NotificationManager
|
||||||
import android.content.BroadcastReceiver
|
import android.content.BroadcastReceiver
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
|
import android.content.Context.VIBRATOR_SERVICE
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.content.IntentFilter
|
import android.content.IntentFilter
|
||||||
import android.content.pm.PackageManager
|
import android.content.pm.PackageManager
|
||||||
import android.content.res.Resources
|
import android.content.res.Resources
|
||||||
import android.net.ConnectivityManager
|
import android.net.ConnectivityManager
|
||||||
import android.net.wifi.WifiManager
|
import android.net.wifi.WifiManager
|
||||||
|
import android.os.Build
|
||||||
import android.os.PowerManager
|
import android.os.PowerManager
|
||||||
|
import android.os.VibrationEffect
|
||||||
|
import android.os.Vibrator
|
||||||
import android.support.annotation.StringRes
|
import android.support.annotation.StringRes
|
||||||
import android.support.v4.app.NotificationCompat
|
import android.support.v4.app.NotificationCompat
|
||||||
import android.support.v4.content.ContextCompat
|
import android.support.v4.content.ContextCompat
|
||||||
@ -20,6 +24,8 @@ import android.widget.Toast
|
|||||||
import com.nononsenseapps.filepicker.FilePickerActivity
|
import com.nononsenseapps.filepicker.FilePickerActivity
|
||||||
import eu.kanade.tachiyomi.widget.CustomLayoutPickerActivity
|
import eu.kanade.tachiyomi.widget.CustomLayoutPickerActivity
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Display a toast in this context.
|
* Display a toast in this context.
|
||||||
*
|
*
|
||||||
@ -168,4 +174,13 @@ fun Context.isServiceRunning(serviceClass: Class<*>): Boolean {
|
|||||||
@Suppress("DEPRECATION")
|
@Suppress("DEPRECATION")
|
||||||
return manager.getRunningServices(Integer.MAX_VALUE)
|
return manager.getRunningServices(Integer.MAX_VALUE)
|
||||||
.any { className == it.service.className }
|
.any { className == it.service.className }
|
||||||
|
}
|
||||||
|
|
||||||
|
fun Context.vibrate(time: Long) {
|
||||||
|
val vibeService = getSystemService(VIBRATOR_SERVICE) as Vibrator
|
||||||
|
if (Build.VERSION.SDK_INT >= 26) {
|
||||||
|
vibeService.vibrate(VibrationEffect.createOneShot(time, VibrationEffect.DEFAULT_AMPLITUDE))
|
||||||
|
} else {
|
||||||
|
vibeService.vibrate(time)
|
||||||
|
}
|
||||||
}
|
}
|
@ -34,7 +34,7 @@ class FingerLockPreference @JvmOverloads constructor(context: Context, attrs: At
|
|||||||
|
|
||||||
val useFingerprint
|
val useFingerprint
|
||||||
get() = fingerprintSupported
|
get() = fingerprintSupported
|
||||||
&& prefs.lockUseFingerprint().getOrDefault()
|
&& prefs.eh_lockUseFingerprint().getOrDefault()
|
||||||
|
|
||||||
@SuppressLint("NewApi")
|
@SuppressLint("NewApi")
|
||||||
override fun onAttached() {
|
override fun onAttached() {
|
||||||
@ -45,7 +45,7 @@ class FingerLockPreference @JvmOverloads constructor(context: Context, attrs: At
|
|||||||
if(it as Boolean)
|
if(it as Boolean)
|
||||||
tryChange()
|
tryChange()
|
||||||
else
|
else
|
||||||
prefs.lockUseFingerprint().set(false)
|
prefs.eh_lockUseFingerprint().set(false)
|
||||||
!it
|
!it
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -121,7 +121,7 @@ class FingerLockPreference @JvmOverloads constructor(context: Context, attrs: At
|
|||||||
when (result.status) {
|
when (result.status) {
|
||||||
AuthenticationResult.Status.SUCCESS -> {
|
AuthenticationResult.Status.SUCCESS -> {
|
||||||
iconView.setState(SwirlView.State.ON)
|
iconView.setState(SwirlView.State.ON)
|
||||||
prefs.lockUseFingerprint().set(true)
|
prefs.eh_lockUseFingerprint().set(true)
|
||||||
dialog.dismiss()
|
dialog.dismiss()
|
||||||
updateSummary()
|
updateSummary()
|
||||||
}
|
}
|
||||||
|
@ -41,12 +41,12 @@ class LockController : NucleusController<LockPresenter>() {
|
|||||||
//Setup pin lock
|
//Setup pin lock
|
||||||
pin_lock_view.attachIndicatorDots(indicator_dots)
|
pin_lock_view.attachIndicatorDots(indicator_dots)
|
||||||
|
|
||||||
pin_lock_view.pinLength = prefs.lockLength().getOrDefault()
|
pin_lock_view.pinLength = prefs.eh_lockLength().getOrDefault()
|
||||||
pin_lock_view.setPinLockListener(object : PinLockListener {
|
pin_lock_view.setPinLockListener(object : PinLockListener {
|
||||||
override fun onEmpty() {}
|
override fun onEmpty() {}
|
||||||
|
|
||||||
override fun onComplete(pin: String) {
|
override fun onComplete(pin: String) {
|
||||||
if (sha512(pin, prefs.lockSalt().get()!!) == prefs.lockHash().get()) {
|
if (sha512(pin, prefs.eh_lockSalt().get()!!) == prefs.eh_lockHash().get()) {
|
||||||
//Yay!
|
//Yay!
|
||||||
closeLock()
|
closeLock()
|
||||||
} else {
|
} else {
|
||||||
@ -120,7 +120,7 @@ class LockController : NucleusController<LockPresenter>() {
|
|||||||
|
|
||||||
private fun resolvColor(color: Int): Int {
|
private fun resolvColor(color: Int): Int {
|
||||||
val typedVal = TypedValue()
|
val typedVal = TypedValue()
|
||||||
activity!!.theme!!.resolveAttribute(android.R.attr.windowBackground, typedVal, true)
|
activity!!.theme!!.resolveAttribute(color, typedVal, true)
|
||||||
return typedVal.data
|
return typedVal.data
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,8 +1,6 @@
|
|||||||
package exh.ui.lock
|
package exh.ui.lock
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.support.v7.preference.Preference
|
|
||||||
import android.support.v7.preference.SwitchPreference
|
|
||||||
import android.support.v7.preference.SwitchPreferenceCompat
|
import android.support.v7.preference.SwitchPreferenceCompat
|
||||||
import android.text.InputType
|
import android.text.InputType
|
||||||
import android.util.AttributeSet
|
import android.util.AttributeSet
|
||||||
@ -87,8 +85,8 @@ class LockPreference @JvmOverloads constructor(context: Context, attrs: Attribut
|
|||||||
hash = sha512(password, salt)
|
hash = sha512(password, salt)
|
||||||
length = password.length
|
length = password.length
|
||||||
}
|
}
|
||||||
prefs.lockSalt().set(salt)
|
prefs.eh_lockSalt().set(salt)
|
||||||
prefs.lockHash().set(hash)
|
prefs.eh_lockHash().set(hash)
|
||||||
prefs.lockLength().set(length)
|
prefs.eh_lockLength().set(length)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -14,6 +14,6 @@ class LockPresenter: BasePresenter<LockController>() {
|
|||||||
get() = Build.VERSION.SDK_INT >= Build.VERSION_CODES.M
|
get() = Build.VERSION.SDK_INT >= Build.VERSION_CODES.M
|
||||||
&& Reprint.isHardwarePresent()
|
&& Reprint.isHardwarePresent()
|
||||||
&& Reprint.hasFingerprintRegistered()
|
&& Reprint.hasFingerprintRegistered()
|
||||||
&& prefs.lockUseFingerprint().getOrDefault()
|
&& prefs.eh_lockUseFingerprint().getOrDefault()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
package exh.ui.lock
|
package exh.ui.lock
|
||||||
|
|
||||||
import android.annotation.TargetApi
|
import android.annotation.TargetApi
|
||||||
import android.app.Activity
|
|
||||||
import android.app.AppOpsManager
|
import android.app.AppOpsManager
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
@ -40,17 +39,20 @@ fun sha512(passwordToHash: String, salt: String): String {
|
|||||||
* Check if lock is enabled
|
* Check if lock is enabled
|
||||||
*/
|
*/
|
||||||
fun lockEnabled(prefs: PreferencesHelper = Injekt.get())
|
fun lockEnabled(prefs: PreferencesHelper = Injekt.get())
|
||||||
= prefs.lockHash().get() != null
|
= prefs.eh_lockHash().get() != null
|
||||||
&& prefs.lockSalt().get() != null
|
&& prefs.eh_lockSalt().get() != null
|
||||||
&& prefs.lockLength().getOrDefault() != -1
|
&& prefs.eh_lockLength().getOrDefault() != -1
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check if the lock will function properly
|
* Check if the lock will function properly
|
||||||
*
|
*
|
||||||
* @return true if action is required, false if lock is working properly
|
* @return true if action is required, false if lock is working properly
|
||||||
*/
|
*/
|
||||||
fun notifyLockSecurity(context: Context): Boolean {
|
fun notifyLockSecurity(context: Context,
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && !hasAccessToUsageStats(context)) {
|
prefs: PreferencesHelper = Injekt.get()): Boolean {
|
||||||
|
if (!prefs.eh_lockManually().getOrDefault()
|
||||||
|
&& Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP
|
||||||
|
&& !hasAccessToUsageStats(context)) {
|
||||||
MaterialDialog.Builder(context)
|
MaterialDialog.Builder(context)
|
||||||
.title("Permission required")
|
.title("Permission required")
|
||||||
.content("${context.getString(R.string.app_name)} requires the usage stats permission to detect when you leave the app. " +
|
.content("${context.getString(R.string.app_name)} requires the usage stats permission to detect when you leave the app. " +
|
||||||
|
Loading…
x
Reference in New Issue
Block a user