private lateinit var androidTextView: TextView
private lateinit var securityPatchTextView: TextView
private lateinit var buildTextView: TextView
+ private lateinit var kernelTextView: TextView
private lateinit var webViewProviderTextView: TextView
private lateinit var webViewVersionTextView: TextView
private lateinit var orbotTextView: TextView
}
// Define the save about version text activity result launcher. It must be defined before `onCreate()` is run or the app will crash.
- private val saveAboutVersionTextActivityResultLauncher = registerForActivityResult(ActivityResultContracts.CreateDocument()) { fileUri: Uri? ->
+ private val saveAboutVersionTextActivityResultLauncher = registerForActivityResult(ActivityResultContracts.CreateDocument("text/plain")) { fileUri: Uri? ->
// Only save the file if the URI is not null, which happens if the user exited the file picker by pressing back.
if (fileUri != null) {
try {
}
// Define the save about version image activity result launcher. It must be defined before `onCreate()` is run or the app will crash.
- private val saveAboutVersionImageActivityResultLauncher = registerForActivityResult(ActivityResultContracts.CreateDocument()) { fileUri: Uri? ->
+ private val saveAboutVersionImageActivityResultLauncher = registerForActivityResult(ActivityResultContracts.CreateDocument("image/png")) { fileUri: Uri? ->
// Only save the file if the URI is not null, which happens if the user exited the file picker by pressing back.
if (fileUri != null) {
// Save the about version image.
androidTextView = aboutVersionLayout.findViewById(R.id.android)
securityPatchTextView = aboutVersionLayout.findViewById(R.id.security_patch)
buildTextView = aboutVersionLayout.findViewById(R.id.build)
+ kernelTextView = aboutVersionLayout.findViewById(R.id.kernel)
webViewProviderTextView = aboutVersionLayout.findViewById(R.id.webview_provider)
webViewVersionTextView = aboutVersionLayout.findViewById(R.id.webview_version)
orbotTextView = aboutVersionLayout.findViewById(R.id.orbot)
val bootloaderLabel = getString(R.string.bootloader) + " "
val androidLabel = getString(R.string.android) + " "
val buildLabel = getString(R.string.build) + " "
+ val kernelLabel = getString(R.string.kernel) + " "
val webViewVersionLabel = getString(R.string.webview_version) + " "
appConsumedMemoryLabel = getString(R.string.app_consumed_memory) + " "
appAvailableMemoryLabel = getString(R.string.app_available_memory) + " "
val radio = Build.getRadioVersion()
val android = Build.VERSION.RELEASE + " (" + getString(R.string.api) + " " + Build.VERSION.SDK_INT + ")"
val build = Build.DISPLAY
- // Select the substring that begins after `Chrome/` and goes until the next ` `.
+ val kernel = System.getProperty("os.version")
+
+ // Get the WebView version, selecting the substring that begins after `Chrome/` and goes until the next ` `.
val webView = userAgentString.substring(userAgentString.indexOf("Chrome/") + 7, userAgentString.indexOf(" ", userAgentString.indexOf("Chrome/")))
// Get the Orbot version name if Orbot is installed.
val orbot: String = try {
- // Store the version name.
+ // Store the version name. The newer `getPackageInfo()` may be used once the minimum API >= 33.
+ @Suppress("DEPRECATION")
requireContext().packageManager.getPackageInfo("org.torproject.android", 0).versionName
} catch (exception: PackageManager.NameNotFoundException) { // Orbot is not installed.
// Store an empty string.
// Get the I2P version name if I2P is installed.
val i2p: String = try {
- // Store the version name.
+ // Store the version name. The newer `getPackageInfo()` may be used once the minimum API >= 33.
+ @Suppress("DEPRECATION")
requireContext().packageManager.getPackageInfo("net.i2p.android.router", 0).versionName
} catch (exception: PackageManager.NameNotFoundException) { // I2P is not installed.
// Store an empty string.
// Get the OpenKeychain version name if it is installed.
val openKeychain: String = try {
- // Store the version name.
+ // Store the version name. The newer `getPackageInfo()` may be used once the minimum API >= 33.
+ @Suppress("DEPRECATION")
requireContext().packageManager.getPackageInfo("org.sufficientlysecure.keychain", 0).versionName
} catch (exception: PackageManager.NameNotFoundException) { // OpenKeychain is not installed.
// Store an empty string.
val bootloaderStringBuilder = SpannableStringBuilder(bootloaderLabel + bootloader)
val androidStringBuilder = SpannableStringBuilder(androidLabel + android)
val buildStringBuilder = SpannableStringBuilder(buildLabel + build)
+ val kernelStringBuilder = SpannableStringBuilder(kernelLabel + kernel)
val webViewVersionStringBuilder = SpannableStringBuilder(webViewVersionLabel + webView)
val easyListStringBuilder = SpannableStringBuilder(easyListLabel + blocklistVersions[0])
val easyPrivacyStringBuilder = SpannableStringBuilder(easyPrivacyLabel + blocklistVersions[1])
val ultraPrivacyStringBuilder = SpannableStringBuilder(ultraPrivacyLabel + blocklistVersions[5])
// Set the blue color span according to the theme. The deprecated `getColor()` must be used until the minimum API >= 23.
- blueColorSpan = ForegroundColorSpan(requireContext().getColor(R.color.about_version_blue_text))
+ blueColorSpan = ForegroundColorSpan(requireContext().getColor(R.color.alt_blue_text))
// Set the spans to display the device information in blue. `SPAN_INCLUSIVE_INCLUSIVE` allows the span to grow in either direction.
brandStringBuilder.setSpan(blueColorSpan, brandLabel.length, brandStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
bootloaderStringBuilder.setSpan(blueColorSpan, bootloaderLabel.length, bootloaderStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
androidStringBuilder.setSpan(blueColorSpan, androidLabel.length, androidStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
buildStringBuilder.setSpan(blueColorSpan, buildLabel.length, buildStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
+ kernelStringBuilder.setSpan(blueColorSpan, kernelLabel.length, kernelStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
webViewVersionStringBuilder.setSpan(blueColorSpan, webViewVersionLabel.length, webViewVersionStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
easyListStringBuilder.setSpan(blueColorSpan, easyListLabel.length, easyListStringBuilder.length, Spanned.SPAN_INCLUSIVE_EXCLUSIVE)
easyPrivacyStringBuilder.setSpan(blueColorSpan, easyPrivacyLabel.length, easyPrivacyStringBuilder.length, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
bootloaderTextView.text = bootloaderStringBuilder
androidTextView.text = androidStringBuilder
buildTextView.text = buildStringBuilder
+ kernelTextView.text = kernelStringBuilder
webViewVersionTextView.text = webViewVersionStringBuilder
easyListTextView.text = easyListStringBuilder
easyPrivacyTextView.text = easyPrivacyStringBuilder
// Display the package signature.
try {
// Get the first package signature. Suppress the lint warning about the need to be careful in implementing comparison of certificates for security purposes.
- // Once the minimum API >= 28, `GET_SIGNING_CERTIFICATES` can be used instead.
+ // Once the minimum API >= 28, `GET_SIGNING_CERTIFICATES` can be used instead. Once the minimum API >= 33, the newer `getPackageInfo()` may be used.
+ @Suppress("DEPRECATION")
@SuppressLint("PackageManagerGetSignatures") val packageSignature = requireContext().packageManager.getPackageInfo(requireContext().packageName,PackageManager.GET_SIGNATURES)
.signatures[0]
}
aboutVersionStringBuilder.append(buildTextView.text)
aboutVersionStringBuilder.append("\n")
+ aboutVersionStringBuilder.append(kernelTextView.text)
+ aboutVersionStringBuilder.append("\n")
if (webViewProviderTextView.visibility == View.VISIBLE) {
aboutVersionStringBuilder.append(webViewProviderTextView.text)
aboutVersionStringBuilder.append("\n")