Merge pull request #551 from PhilKes/feat/disallow-screenshots

Add security option to disallow screenshots
This commit is contained in:
Phil 2025-04-18 16:14:12 +02:00 committed by GitHub
commit 6d81b6f7c0
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
8 changed files with 50 additions and 1 deletions

View file

@ -1,15 +1,18 @@
package com.philkes.notallyx
import android.app.Activity
import android.app.Application
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.os.Build
import android.os.Bundle
import androidx.appcompat.app.AppCompatDelegate
import androidx.lifecycle.Observer
import androidx.work.WorkInfo
import androidx.work.WorkManager
import com.google.android.material.color.DynamicColors
import com.philkes.notallyx.presentation.setEnabledSecureFlag
import com.philkes.notallyx.presentation.view.misc.NotNullLiveData
import com.philkes.notallyx.presentation.viewmodel.preference.BiometricLock
import com.philkes.notallyx.presentation.viewmodel.preference.NotallyXPreferences
@ -33,7 +36,7 @@ import kotlinx.coroutines.MainScope
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
class NotallyXApplication : Application() {
class NotallyXApplication : Application(), Application.ActivityLifecycleCallbacks {
private lateinit var biometricLockObserver: Observer<BiometricLock>
private lateinit var preferences: NotallyXPreferences
@ -43,6 +46,7 @@ class NotallyXApplication : Application() {
override fun onCreate() {
super.onCreate()
registerActivityLifecycleCallbacks(this)
if (isTestRunner()) return
preferences = NotallyXPreferences.getInstance(this)
if (preferences.useDynamicColors.value) {
@ -168,4 +172,20 @@ class NotallyXApplication : Application() {
return Build.FINGERPRINT.equals("robolectric", ignoreCase = true)
}
}
override fun onActivityCreated(activity: Activity, savedInstanceState: Bundle?) {
activity.setEnabledSecureFlag(preferences.secureFlag.value)
}
override fun onActivityStarted(activity: Activity) {}
override fun onActivityResumed(activity: Activity) {}
override fun onActivityPaused(activity: Activity) {}
override fun onActivityStopped(activity: Activity) {}
override fun onActivitySaveInstanceState(activity: Activity, outState: Bundle) {}
override fun onActivityDestroyed(activity: Activity) {}
}

View file

@ -531,6 +531,17 @@ fun Activity.checkAlarmPermission(
} else onSuccess()
}
fun Activity.setEnabledSecureFlag(enabled: Boolean) {
if (enabled) {
window.setFlags(
WindowManager.LayoutParams.FLAG_SECURE,
WindowManager.LayoutParams.FLAG_SECURE,
)
} else {
window.clearFlags(WindowManager.LayoutParams.FLAG_SECURE)
}
}
fun Fragment.displayEditLabelDialog(
oldValue: String,
model: BaseNoteModel,

View file

@ -33,6 +33,7 @@ import com.philkes.notallyx.databinding.DialogTextInputBinding
import com.philkes.notallyx.databinding.FragmentSettingsBinding
import com.philkes.notallyx.presentation.activity.main.MainActivity
import com.philkes.notallyx.presentation.setCancelButton
import com.philkes.notallyx.presentation.setEnabledSecureFlag
import com.philkes.notallyx.presentation.setupImportProgressDialog
import com.philkes.notallyx.presentation.setupProgressDialog
import com.philkes.notallyx.presentation.showAndFocus
@ -592,6 +593,14 @@ class SettingsFragment : Fragment() {
model.savePreference(backupPassword, newValue)
}
}
secureFlag.observe(viewLifecycleOwner) { value ->
binding.SecureFlag.setup(secureFlag, value, requireContext(), layoutInflater) { newValue
->
model.savePreference(secureFlag, newValue)
activity?.setEnabledSecureFlag(newValue)
}
}
}
private fun NotallyXPreferences.setupSettings(binding: FragmentSettingsBinding) {

View file

@ -135,6 +135,8 @@ class NotallyXPreferences private constructor(private val context: Context) {
val fallbackDatabaseEncryptionKey by lazy {
ByteArrayPreference("fallback_database_encryption_key", encryptedPreferences, ByteArray(0))
}
val secureFlag =
BooleanPreference("secureFlag", preferences, false, R.string.disallow_screenshots)
val dataInPublicFolder =
BooleanPreference("dataOnExternalStorage", preferences, false, R.string.data_in_public)
@ -223,6 +225,7 @@ class NotallyXPreferences private constructor(private val context: Context) {
maxItems,
maxLines,
maxTitle,
secureFlag,
labelsHidden,
labelTagsHiddenInOverview,
maxLabels,

View file

@ -173,6 +173,10 @@
android:id="@+id/BackupPassword"
layout="@layout/preference" />
<include
android:id="@+id/SecureFlag"
layout="@layout/preference" />
<View
android:layout_width="match_parent"
android:layout_height="1dp"

View file

@ -119,6 +119,7 @@
<string name="disable_lock_description">Dies entschlüsselt außerdem die Datenbank</string>
<string name="disable_lock_title">Deaktivierte Biometrie/PIN Sperre</string>
<string name="disabled">Deaktiviert</string>
<string name="disallow_screenshots">Screenshots verbieten</string>
<string name="discard">Verwerfen</string>
<string name="display_text">Anzeigetext</string>
<string name="donate">Spende</string>

View file

@ -121,6 +121,7 @@
<string name="disable_lock_description">This will also decrypt the database</string>
<string name="disable_lock_title">Disable lock via Biometric/PIN</string>
<string name="disabled">Disabled</string>
<string name="disallow_screenshots">Disallow Screenshots</string>
<string name="discard">Discard</string>
<string name="display_text">Text to display</string>
<string name="donate">Make a Donation</string>

Binary file not shown.