diff --git a/CHANGES.md b/CHANGES.md
index f747e9ded9..1d248fbfcc 100644
--- a/CHANGES.md
+++ b/CHANGES.md
@@ -1,3 +1,20 @@
+Changes in Element X v25.06.2
+=============================
+
+## What's Changed
+### 🐛 Bugfixes
+* Fix crash when using Element Call on API <= 30 by @jmartinesp in https://github.com/element-hq/element-x-android/pull/4847
+* Element Call: add delay before selecting the default audio device by @jmartinesp in https://github.com/element-hq/element-x-android/pull/4854
+* Fix for message composer losing focus in Compose 1.8.0 by @jmartinesp in https://github.com/element-hq/element-x-android/pull/4853
+### Dependency upgrades
+* chore(deps): update plugin dependencycheck to v12.1.2 by @renovate in https://github.com/element-hq/element-x-android/pull/4840
+* deps (matrix rust sdk) : bump version to 25.06.10 by @ganfra in https://github.com/element-hq/element-x-android/pull/4855
+### Others
+* feat: Support matrix: links by @ShadowRZ in https://github.com/element-hq/element-x-android/pull/4839
+
+
+**Full Changelog**: https://github.com/element-hq/element-x-android/compare/v25.06.1...v25.06.2
+
## What's Changed
### ✨ Features
* Enable support for Android Auto. by @bmarty in https://github.com/element-hq/element-x-android/pull/4818
diff --git a/appnav/src/main/res/values-in/translations.xml b/appnav/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..8314323845
--- /dev/null
+++ b/appnav/src/main/res/values-in/translations.xml
@@ -0,0 +1,5 @@
+
+
+ "Keluar & Tingkatkan"
+ "Homeserver Anda tidak lagi mendukung protokol lama. Silakan keluar dan masuk kembali untuk terus menggunakan aplikasi."
+
diff --git a/appnav/src/test/kotlin/io/element/android/appnav/di/MatrixSessionCacheTest.kt b/appnav/src/test/kotlin/io/element/android/appnav/di/MatrixSessionCacheTest.kt
index 52443fa4a1..47237d5f77 100644
--- a/appnav/src/test/kotlin/io/element/android/appnav/di/MatrixSessionCacheTest.kt
+++ b/appnav/src/test/kotlin/io/element/android/appnav/di/MatrixSessionCacheTest.kt
@@ -16,7 +16,6 @@ import io.element.android.libraries.matrix.test.FakeMatrixClient
import io.element.android.libraries.matrix.test.auth.FakeMatrixAuthenticationService
import io.element.android.services.appnavstate.test.FakeAppForegroundStateService
import io.element.android.tests.testutils.testCoroutineDispatchers
-import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.test.TestScope
import kotlinx.coroutines.test.runTest
import org.junit.Test
@@ -29,7 +28,6 @@ class MatrixSessionCacheTest {
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull()
}
- @OptIn(ExperimentalCoroutinesApi::class)
@Test
fun `test getSyncOrchestratorOrNull`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService()
diff --git a/fastlane/metadata/android/en-US/changelogs/202506030.txt b/fastlane/metadata/android/en-US/changelogs/202506030.txt
new file mode 100644
index 0000000000..f52df1a372
--- /dev/null
+++ b/fastlane/metadata/android/en-US/changelogs/202506030.txt
@@ -0,0 +1,2 @@
+Main changes in this version: add support for tombstoned rooms, improve notification reliability.
+Full changelog: https://github.com/element-hq/element-x-android/releases
\ No newline at end of file
diff --git a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenPresenter.kt b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenPresenter.kt
index 363ace4b79..e16428de3b 100644
--- a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenPresenter.kt
+++ b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenPresenter.kt
@@ -44,6 +44,7 @@ import io.element.android.services.appnavstate.api.ActiveRoomsHolder
import io.element.android.services.appnavstate.api.AppForegroundStateService
import io.element.android.services.toolbox.api.systemclock.SystemClock
import kotlinx.coroutines.CoroutineScope
+import kotlinx.coroutines.delay
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
import kotlinx.coroutines.launch
@@ -52,6 +53,7 @@ import kotlinx.serialization.json.jsonObject
import kotlinx.serialization.json.jsonPrimitive
import timber.log.Timber
import java.util.UUID
+import kotlin.time.Duration.Companion.seconds
class CallScreenPresenter @AssistedInject constructor(
@Assisted private val callType: CallType,
@@ -165,6 +167,13 @@ class CallScreenPresenter @AssistedInject constructor(
// If the call was joined, we need to hang up first. Then the UI will be dismissed automatically.
sendHangupMessage(widgetId, interceptor)
isJoinedCall = false
+
+ coroutineScope.launch {
+ // Wait for a couple of seconds to receive the hangup message
+ // If we don't get it in time, we close the screen anyway
+ delay(2.seconds)
+ close(callWidgetDriver.value, navigator)
+ }
} else {
coroutineScope.launch {
close(callWidgetDriver.value, navigator)
diff --git a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenView.kt b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenView.kt
index f1aa192d28..7547d8e7c7 100644
--- a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenView.kt
+++ b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/ui/CallScreenView.kt
@@ -38,6 +38,7 @@ import io.element.android.features.call.impl.pip.PictureInPictureEvents
import io.element.android.features.call.impl.pip.PictureInPictureState
import io.element.android.features.call.impl.pip.PictureInPictureStateProvider
import io.element.android.features.call.impl.pip.aPictureInPictureState
+import io.element.android.features.call.impl.utils.InvalidAudioDeviceReason
import io.element.android.features.call.impl.utils.WebViewAudioManager
import io.element.android.features.call.impl.utils.WebViewPipController
import io.element.android.features.call.impl.utils.WebViewWidgetMessageInterceptor
@@ -105,6 +106,14 @@ internal fun CallScreenView(
} else {
var webViewAudioManager by remember { mutableStateOf(null) }
val coroutineScope = rememberCoroutineScope()
+
+ var invalidAudioDeviceReason by remember { mutableStateOf(null) }
+ invalidAudioDeviceReason?.let {
+ InvalidAudioDeviceDialog(invalidAudioDeviceReason = it) {
+ invalidAudioDeviceReason = null
+ }
+ }
+
CallWebView(
modifier = Modifier
.padding(padding)
@@ -130,7 +139,11 @@ internal fun CallScreenView(
},
onError = { state.eventSink(CallScreenEvents.OnWebViewError(it)) },
)
- webViewAudioManager = WebViewAudioManager(webView, coroutineScope)
+ webViewAudioManager = WebViewAudioManager(
+ webView = webView,
+ coroutineScope = coroutineScope,
+ onInvalidAudioDeviceAdded = { invalidAudioDeviceReason = it },
+ )
state.eventSink(CallScreenEvents.SetupMessageChannels(interceptor))
val pipController = WebViewPipController(webView)
pipState.eventSink(PictureInPictureEvents.SetPipController(pipController))
@@ -157,6 +170,21 @@ internal fun CallScreenView(
}
}
+@Composable
+private fun InvalidAudioDeviceDialog(
+ invalidAudioDeviceReason: InvalidAudioDeviceReason,
+ onDismiss: () -> Unit,
+) {
+ ErrorDialog(
+ content = when (invalidAudioDeviceReason) {
+ InvalidAudioDeviceReason.BT_AUDIO_DEVICE_DISABLED -> {
+ stringResource(R.string.call_invalid_audio_device_bluetooth_devices_disabled)
+ }
+ },
+ onSubmit = onDismiss,
+ )
+}
+
@Composable
private fun CallWebView(
url: AsyncData,
@@ -277,3 +305,9 @@ internal fun CallScreenPipViewPreview(
requestPermissions = { _, _ -> },
)
}
+
+@PreviewsDayNight
+@Composable
+internal fun InvalidAudioDeviceDialogPreview() = ElementPreview {
+ InvalidAudioDeviceDialog(invalidAudioDeviceReason = InvalidAudioDeviceReason.BT_AUDIO_DEVICE_DISABLED) {}
+}
diff --git a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewAudioManager.kt b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewAudioManager.kt
index dc55ff2ac4..b7d1fdf466 100644
--- a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewAudioManager.kt
+++ b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewAudioManager.kt
@@ -40,8 +40,22 @@ import kotlin.time.Duration.Companion.milliseconds
class WebViewAudioManager(
private val webView: WebView,
private val coroutineScope: CoroutineScope,
+ private val onInvalidAudioDeviceAdded: (InvalidAudioDeviceReason) -> Unit,
) {
- // The list of device types that are considered as communication devices, sorted by likelihood of it being used for communication.
+ /**
+ * Whether to disable bluetooth audio devices. This must be done on Android versions lower than Android 12,
+ * since the WebView approach breaks when using the legacy Bluetooth audio APIs.
+ */
+ private val disableBluetoothAudioDevices = Build.VERSION.SDK_INT < Build.VERSION_CODES.S
+
+ /**
+ * This flag indicates whether the WebView audio is enabled or not. By default, it is enabled.
+ */
+ private val isWebViewAudioEnabled = AtomicBoolean(true)
+
+ /**
+ * The list of device types that are considered as communication devices, sorted by likelihood of it being used for communication.
+ */
private val wantedDeviceTypes = listOf(
// Paired bluetooth device with microphone
AudioDeviceInfo.TYPE_BLUETOOTH_SCO,
@@ -60,6 +74,10 @@ class WebViewAudioManager(
private val audioManager = webView.context.getSystemService(Context.AUDIO_SERVICE) as AudioManager
+ /**
+ * This wake lock is used to turn off the screen when the proximity sensor is triggered during a call,
+ * if the selected audio device is the built-in earpiece.
+ */
private val proximitySensorWakeLock by lazy {
webView.context.getSystemService()
?.takeIf { it.isWakeLockLevelSupported(PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK) }
@@ -296,12 +314,13 @@ class WebViewAudioManager(
* @param availableDevices The list of available audio devices to select from. If not provided, it will use the current list of audio devices.
*/
private fun selectDefaultAudioDevice(availableDevices: List = listAudioDevices()) {
- val selectedDevice = availableDevices.minByOrNull {
- wantedDeviceTypes.indexOf(it.type).let { index ->
- // If the device type is not in the wantedDeviceTypes list, we give it a low priority
- if (index == -1) Int.MAX_VALUE else index
+ val selectedDevice = availableDevices
+ .minByOrNull {
+ wantedDeviceTypes.indexOf(it.type).let { index ->
+ // If the device type is not in the wantedDeviceTypes list, we give it a low priority
+ if (index == -1) Int.MAX_VALUE else index
+ }
}
- }
expectedNewCommunicationDeviceId = selectedDevice?.id
audioManager.selectAudioDevice(selectedDevice)
@@ -361,6 +380,13 @@ class WebViewAudioManager(
// On Android 11 and lower, we don't have the concept of communication devices
// We have to call the right methods based on the device type
if (device != null) {
+ if (device.type == AudioDeviceInfo.TYPE_BLUETOOTH_SCO && disableBluetoothAudioDevices) {
+ Timber.w("Bluetooth audio devices are disabled on this Android version")
+ setAudioEnabled(false)
+ onInvalidAudioDeviceAdded(InvalidAudioDeviceReason.BT_AUDIO_DEVICE_DISABLED)
+ return
+ }
+ setAudioEnabled(true)
isSpeakerphoneOn = device.type == AudioDeviceInfo.TYPE_BUILTIN_SPEAKER
isBluetoothScoOn = device.type == AudioDeviceInfo.TYPE_BLUETOOTH_SCO
} else {
@@ -380,6 +406,19 @@ class WebViewAudioManager(
proximitySensorWakeLock?.release()
}
}
+
+ /**
+ * Sets whether the audio is enabled for Element Call in the WebView.
+ * It will only perform the change if the audio state has changed.
+ */
+ private fun setAudioEnabled(enabled: Boolean) {
+ coroutineScope.launch(Dispatchers.Main) {
+ Timber.d("Setting audio enabled in Element Call: $enabled")
+ if (isWebViewAudioEnabled.getAndSet(enabled) != enabled) {
+ webView.evaluateJavascript("controls.setAudioEnabled($enabled);", null)
+ }
+ }
+ }
}
/**
@@ -434,6 +473,10 @@ private fun isBuiltIn(type: Int): Boolean = when (type) {
else -> false
}
+enum class InvalidAudioDeviceReason {
+ BT_AUDIO_DEVICE_DISABLED,
+}
+
/**
* This class is used to serialize the audio device information to JSON.
*/
diff --git a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewPipController.kt b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewPipController.kt
index 8fea797425..f46db3ca2b 100644
--- a/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewPipController.kt
+++ b/features/call/impl/src/main/kotlin/io/element/android/features/call/impl/utils/WebViewPipController.kt
@@ -11,6 +11,10 @@ import android.webkit.WebView
import kotlin.coroutines.resume
import kotlin.coroutines.suspendCoroutine
+/**
+ * Documentation about the `controls` command can be found here:
+ * https://github.com/element-hq/element-call/blob/livekit/docs/controls.md#picture-in-picture
+ */
class WebViewPipController(
private val webView: WebView,
) : PipController {
diff --git a/features/call/impl/src/main/res/values-fr/translations.xml b/features/call/impl/src/main/res/values-fr/translations.xml
index bd04a5b362..bab8f6376d 100644
--- a/features/call/impl/src/main/res/values-fr/translations.xml
+++ b/features/call/impl/src/main/res/values-fr/translations.xml
@@ -3,5 +3,6 @@
"Appel en cours"
"Cliquez pour retourner à l’appel."
"☎️ Appel en cours"
+ "Element Call ne prend pas en charge l’utilisation d’accessoires Bluetooth dans cette version d’Android. Sélectionnez une autre sortie audio."
"Appel Element entrant"
diff --git a/features/call/impl/src/main/res/values-nb/translations.xml b/features/call/impl/src/main/res/values-nb/translations.xml
index 5ae5554314..b93abc6d87 100644
--- a/features/call/impl/src/main/res/values-nb/translations.xml
+++ b/features/call/impl/src/main/res/values-nb/translations.xml
@@ -3,5 +3,6 @@
"Pågående samtale"
"Trykk for å gå tilbake til samtalen"
"☎️ Samtale pågår"
+ "Element Call støtter ikke bruk av Bluetooth-lydenheter i denne Android-versjonen. Velg en annen lydenhet."
"Innkommende Element-anrop"
diff --git a/features/call/impl/src/main/res/values/localazy.xml b/features/call/impl/src/main/res/values/localazy.xml
index 5a386b2416..5ab2caa4fd 100644
--- a/features/call/impl/src/main/res/values/localazy.xml
+++ b/features/call/impl/src/main/res/values/localazy.xml
@@ -3,5 +3,6 @@
"Ongoing call"
"Tap to return to the call"
"☎️ Call in progress"
+ "Element Call does not support using Bluetooth audio devices in this Android version. Please select a different audio device."
"Incoming Element Call"
diff --git a/features/createroom/impl/src/main/res/values-es/translations.xml b/features/createroom/impl/src/main/res/values-es/translations.xml
index 4611c7a211..c11f08fc14 100644
--- a/features/createroom/impl/src/main/res/values-es/translations.xml
+++ b/features/createroom/impl/src/main/res/values-es/translations.xml
@@ -21,6 +21,10 @@ Puedes cambiar esto en cualquier momento en los ajustes de la sala."
"Tema (opcional)"
"Directorio de salas"
"Se ha producido un error al intentar iniciar un chat"
+ "Unirse a una sala por su dirección"
+ "Dirección no válida"
"Introducir…"
+ "Sala encontrada"
+ "No se encontró la sala"
"p. ej., #nombre-de-la-sala:matrix.org"
diff --git a/features/deactivation/impl/src/main/kotlin/io/element/android/features/logout/impl/AccountDeactivationView.kt b/features/deactivation/impl/src/main/kotlin/io/element/android/features/logout/impl/AccountDeactivationView.kt
index 9e61f030c5..3b0d8b6e1a 100644
--- a/features/deactivation/impl/src/main/kotlin/io/element/android/features/logout/impl/AccountDeactivationView.kt
+++ b/features/deactivation/impl/src/main/kotlin/io/element/android/features/logout/impl/AccountDeactivationView.kt
@@ -5,8 +5,6 @@
* Please see LICENSE files in the repository root for full details.
*/
-@file:OptIn(ExperimentalComposeUiApi::class)
-
package io.element.android.features.logout.impl
import androidx.compose.foundation.clickable
@@ -32,7 +30,6 @@ import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
-import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.autofill.ContentType
import androidx.compose.ui.graphics.Color
diff --git a/features/deactivation/impl/src/main/res/values-in/translations.xml b/features/deactivation/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..e255ad34e9
--- /dev/null
+++ b/features/deactivation/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,14 @@
+
+
+ "Harap konfirmasi bahwa Anda ingin menonaktifkan akun Anda. Tindakan ini tidak dapat diurungkan."
+ "Hapus semua pesan saya"
+ "Peringatan: Pengguna masa depan mungkin melihat percakapan yang tidak lengkap."
+ "Penonaktifan akun Anda %1$s, ini akan:"
+ "tidak dapat diurungkan"
+ "%1$s akun Anda (Anda tidak dapat masuk kembali, dan ID Anda tidak dapat digunakan kembali)."
+ "Nonaktifkan secara permanen"
+ "Mengeluarkan Anda dari semua ruangan obrolan."
+ "Hapus informasi akun Anda dari server identitas kami."
+ "Pesan Anda akan tetap terlihat oleh pengguna terdaftar tetapi tidak akan tersedia bagi pengguna baru atau tidak terdaftar jika Anda memilih untuk menghapusnya."
+ "Nonaktifkan akun"
+
diff --git a/features/ftue/impl/src/main/res/values-es/translations.xml b/features/ftue/impl/src/main/res/values-es/translations.xml
index 20338b999f..36015aa6dd 100644
--- a/features/ftue/impl/src/main/res/values-es/translations.xml
+++ b/features/ftue/impl/src/main/res/values-es/translations.xml
@@ -12,7 +12,7 @@
"Esperando en otro dispositivo…"
"Puedes cambiar la configuración más tarde."
"Activa las notificaciones y nunca te pierdas un mensaje"
- "Introduzca la clave de recuperación"
+ "Introduce la clave de recuperación"
"Las llamadas, las encuestas, la búsqueda y más se agregarán más adelante este año."
"El historial de mensajes de las salas cifradas aún no está disponible."
"Nos encantaría saber de ti, haznos saber lo que piensas a través de la página de configuración."
diff --git a/features/invite/impl/src/main/res/values-es/translations.xml b/features/invite/impl/src/main/res/values-es/translations.xml
index c3660e35af..a88f9bc28d 100644
--- a/features/invite/impl/src/main/res/values-es/translations.xml
+++ b/features/invite/impl/src/main/res/values-es/translations.xml
@@ -1,5 +1,10 @@
+ "No verás ningún mensaje ni invitación a sala que provenga de este usuario"
+ "Bloquear usuario"
+ "Denunciar esta sala a tu proveedor de cuentas."
+ "Describe el motivo de la denuncia…"
+ "Rechazar y bloquear"
"¿Estás seguro de que quieres rechazar la invitación a unirte a %1$s?"
"Rechazar la invitación"
"¿Estás seguro de que quieres rechazar este chat privado con %1$s?"
diff --git a/features/invite/impl/src/main/res/values-ru/translations.xml b/features/invite/impl/src/main/res/values-ru/translations.xml
index da7bb1c449..90d467e62c 100644
--- a/features/invite/impl/src/main/res/values-ru/translations.xml
+++ b/features/invite/impl/src/main/res/values-ru/translations.xml
@@ -1,6 +1,8 @@
+ "Вы не увидите сообщений или приглашений в комнату от этого пользователя"
"Заблокировать пользователя"
+ "Сообщите об этой комнате своему поставщику учетной записи."
"Опишите причину жалобы…"
"Отклонить и заблокировать"
"Вы уверены, что хотите отклонить приглашение в %1$s?"
diff --git a/features/joinroom/impl/src/main/kotlin/io/element/android/features/joinroom/impl/JoinRoomFlowNode.kt b/features/joinroom/impl/src/main/kotlin/io/element/android/features/joinroom/impl/JoinRoomFlowNode.kt
index 4d3d9be86c..ecd4c920c8 100644
--- a/features/joinroom/impl/src/main/kotlin/io/element/android/features/joinroom/impl/JoinRoomFlowNode.kt
+++ b/features/joinroom/impl/src/main/kotlin/io/element/android/features/joinroom/impl/JoinRoomFlowNode.kt
@@ -79,7 +79,7 @@ class JoinRoomFlowNode @AssistedInject constructor(
JoinRoomView(
state = state,
onBackClick = ::navigateUp,
- onJoinSuccess = ::navigateUp,
+ onJoinSuccess = {},
onForgetSuccess = ::navigateUp,
onCancelKnockSuccess = {},
onKnockSuccess = {},
diff --git a/features/joinroom/impl/src/main/res/values-in/translations.xml b/features/joinroom/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..4988e2dd58
--- /dev/null
+++ b/features/joinroom/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,18 @@
+
+
+ "Batalkan permintaan"
+ "Ya, batalkan"
+ "Apakah Anda yakin ingin membatalkan permintaan Anda untuk bergabung dengan ruangan ini?"
+ "Batalkan permintaan untuk bergabung"
+ "Gabung dengan ruangan"
+ "Ketuk untuk bergabung"
+ "Pesan (opsional)"
+ "Anda akan menerima undangan untuk bergabung dengan ruangan jika permintaan Anda diterima."
+ "Permintaan untuk bergabung dikirim"
+ "%1$s belum mendukung space. Anda dapat mengakses space di web."
+ "Space belum didukung"
+ "Klik tombol di bawah ini dan administrator kamar akan diberi tahu. Anda akan dapat bergabung dengan percakapan setelah disetujui."
+ "Anda harus menjadi anggota ruangan ini untuk melihat riwayat pesan."
+ "Ingin bergabung dengan ruangan ini?"
+ "Pratinjau tidak tersedia"
+
diff --git a/features/knockrequests/impl/src/main/res/values-in/translations.xml b/features/knockrequests/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..08480082c5
--- /dev/null
+++ b/features/knockrequests/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,35 @@
+
+
+ "Ya, terima semua"
+ "Apakah Anda yakin ingin menerima semua permintaan untuk bergabung?"
+ "Terima semua permintaan"
+ "Terima semua"
+ "Kami tidak dapat menerima semua permintaan. Apakah Anda ingin mencoba lagi?"
+ "Gagal menerima semua permintaan"
+ "Menerima semua permintaan untuk bergabung"
+ "Kami tidak dapat menerima permintaan ini. Apakah Anda ingin mencoba lagi?"
+ "Gagal menerima permintaan"
+ "Menerima permintaan untuk bergabung"
+ "Ya, tolak dan cekal"
+ "Apakah Anda yakin ingin menolak dan mencekal %1$s? Pengguna ini tidak akan dapat meminta akses untuk bergabung ke ruangan ini lagi."
+ "Tolak dan cekal akses"
+ "Menolak dan mencekal akses"
+ "Ya, tolak"
+ "Apakah Anda yakin ingin menolak permintaan %1$s untuk bergabung ke ruangan ini?"
+ "Tolak akses"
+ "Tolak dan cekal"
+ "Kami tidak dapat menolak permintaan ini. Apakah Anda ingin mencoba lagi?"
+ "Gagal menolak permintaan"
+ "Menolak permintaan untuk bergabung"
+ "Ketika seseorang akan meminta untuk bergabung dengan ruangan, Anda akan dapat melihat permintaan mereka di sini."
+ "Tidak ada permintaan yang tertunda untuk bergabung"
+ "Memuat permintaan untuk bergabung…"
+ "Permintaan untuk bergabung"
+
+ - "%1$s +%2$d lainnya ingin bergabung ke ruangan ini"
+
+ "Lihat semua"
+ "Terima"
+ "%1$s ingin bergabung ke ruangan ini"
+ "Lihat"
+
diff --git a/features/leaveroom/api/src/main/res/values-es/translations.xml b/features/leaveroom/api/src/main/res/values-es/translations.xml
index cb393481d8..81b169e5c9 100644
--- a/features/leaveroom/api/src/main/res/values-es/translations.xml
+++ b/features/leaveroom/api/src/main/res/values-es/translations.xml
@@ -2,6 +2,6 @@
"¿Estás seguro de que quieres salir de esta conversación? Esta conversación no es pública y no podrás volver a unirte sin una invitación."
"¿Estás seguro de que quieres salir de esta sala? Eres la única persona aquí. Si te vas, nadie podrá unirse en el futuro, ni siquiera tú."
- "¿Estás seguro de que quieres abandonar esta sala? Esta sala no es pública y no podrás volver a entrar sin una invitación."
+ "¿Seguro que quieres salir de esta sala? Esta sala no es pública y no podrás volver a entrar sin una invitación."
"¿Seguro que quieres salir de la sala?"
diff --git a/features/location/impl/src/main/kotlin/io/element/android/features/location/impl/send/SendLocationPresenter.kt b/features/location/impl/src/main/kotlin/io/element/android/features/location/impl/send/SendLocationPresenter.kt
index f92b058786..4710e4bd50 100644
--- a/features/location/impl/src/main/kotlin/io/element/android/features/location/impl/send/SendLocationPresenter.kt
+++ b/features/location/impl/src/main/kotlin/io/element/android/features/location/impl/send/SendLocationPresenter.kt
@@ -26,6 +26,10 @@ import io.element.android.libraries.architecture.Presenter
import io.element.android.libraries.core.meta.BuildMeta
import io.element.android.libraries.matrix.api.room.JoinedRoom
import io.element.android.libraries.matrix.api.room.location.AssetType
+import io.element.android.libraries.matrix.api.room.message.ReplyParameters
+import io.element.android.libraries.matrix.api.room.message.replyInThread
+import io.element.android.libraries.matrix.ui.messages.reply.eventId
+import io.element.android.libraries.textcomposer.model.MessageComposerMode
import io.element.android.services.analytics.api.AnalyticsService
import kotlinx.coroutines.launch
import javax.inject.Inject
@@ -98,6 +102,18 @@ class SendLocationPresenter @Inject constructor(
event: SendLocationEvents.SendLocation,
mode: SendLocationState.Mode,
) {
+ val replyMode = messageComposerContext.composerMode as? MessageComposerMode.Reply
+ val replyParams = replyMode?.replyToDetails?.let { details ->
+ if (replyMode.inThread) {
+ replyInThread(details.eventId())
+ } else {
+ ReplyParameters(
+ inReplyToEventId = details.eventId(),
+ enforceThreadReply = false,
+ replyWithinThread = false
+ )
+ }
+ }
when (mode) {
SendLocationState.Mode.PinLocation -> {
val geoUri = event.cameraPosition.toGeoUri()
@@ -106,7 +122,8 @@ class SendLocationPresenter @Inject constructor(
geoUri = geoUri,
description = null,
zoomLevel = MapDefaults.DEFAULT_ZOOM.toInt(),
- assetType = AssetType.PIN
+ assetType = AssetType.PIN,
+ replyParameters = replyParams,
)
analyticsService.capture(
Composer(
@@ -124,7 +141,8 @@ class SendLocationPresenter @Inject constructor(
geoUri = geoUri,
description = null,
zoomLevel = MapDefaults.DEFAULT_ZOOM.toInt(),
- assetType = AssetType.SENDER
+ assetType = AssetType.SENDER,
+ replyParameters = replyParams,
)
analyticsService.capture(
Composer(
diff --git a/features/location/impl/src/test/kotlin/io/element/android/features/location/impl/send/SendLocationPresenterTest.kt b/features/location/impl/src/test/kotlin/io/element/android/features/location/impl/send/SendLocationPresenterTest.kt
index 267a359608..7addee38e4 100644
--- a/features/location/impl/src/test/kotlin/io/element/android/features/location/impl/send/SendLocationPresenterTest.kt
+++ b/features/location/impl/src/test/kotlin/io/element/android/features/location/impl/send/SendLocationPresenterTest.kt
@@ -22,6 +22,7 @@ import io.element.android.features.location.impl.common.permissions.PermissionsS
import io.element.android.features.messages.test.FakeMessageComposerContext
import io.element.android.libraries.matrix.api.room.JoinedRoom
import io.element.android.libraries.matrix.api.room.location.AssetType
+import io.element.android.libraries.matrix.api.room.message.ReplyParameters
import io.element.android.libraries.matrix.api.timeline.item.event.toEventOrTransactionId
import io.element.android.libraries.matrix.test.AN_EVENT_ID
import io.element.android.libraries.matrix.test.core.aBuildMeta
@@ -263,7 +264,7 @@ class SendLocationPresenterTest {
@Test
fun `share sender location`() = runTest {
- val sendLocationResult = lambdaRecorder> { _, _, _, _, _ ->
+ val sendLocationResult = lambdaRecorder> { _, _, _, _, _, _ ->
Result.success(Unit)
}
val joinedRoom = FakeJoinedRoom(
@@ -310,6 +311,7 @@ class SendLocationPresenterTest {
value(null),
value(15),
value(AssetType.SENDER),
+ value(null),
)
assertThat(fakeAnalyticsService.capturedEvents.size).isEqualTo(1)
@@ -326,7 +328,7 @@ class SendLocationPresenterTest {
@Test
fun `share pin location`() = runTest {
- val sendLocationResult = lambdaRecorder> { _, _, _, _, _ ->
+ val sendLocationResult = lambdaRecorder> { _, _, _, _, _, _ ->
Result.success(Unit)
}
val joinedRoom = FakeJoinedRoom(
@@ -373,6 +375,7 @@ class SendLocationPresenterTest {
value(null),
value(15),
value(AssetType.PIN),
+ value(null),
)
assertThat(fakeAnalyticsService.capturedEvents.size).isEqualTo(1)
@@ -389,7 +392,7 @@ class SendLocationPresenterTest {
@Test
fun `composer context passes through analytics`() = runTest {
- val sendLocationResult = lambdaRecorder> { _, _, _, _, _ ->
+ val sendLocationResult = lambdaRecorder> { _, _, _, _, _, _ ->
Result.success(Unit)
}
val joinedRoom = FakeJoinedRoom(
diff --git a/features/lockscreen/impl/src/main/kotlin/io/element/android/features/lockscreen/impl/setup/pin/SetupPinView.kt b/features/lockscreen/impl/src/main/kotlin/io/element/android/features/lockscreen/impl/setup/pin/SetupPinView.kt
index 3e51849a76..81bfa4c1a4 100644
--- a/features/lockscreen/impl/src/main/kotlin/io/element/android/features/lockscreen/impl/setup/pin/SetupPinView.kt
+++ b/features/lockscreen/impl/src/main/kotlin/io/element/android/features/lockscreen/impl/setup/pin/SetupPinView.kt
@@ -19,6 +19,7 @@ import androidx.compose.foundation.verticalScroll
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
@@ -124,6 +125,7 @@ private fun SetupPinContent(
}
@Composable
+@ReadOnlyComposable
private fun SetupPinFailure.content(): String {
return when (this) {
SetupPinFailure.ForbiddenPin -> stringResource(id = R.string.screen_app_lock_setup_pin_forbidden_dialog_content)
@@ -132,6 +134,7 @@ private fun SetupPinFailure.content(): String {
}
@Composable
+@ReadOnlyComposable
private fun SetupPinFailure.title(): String {
return when (this) {
SetupPinFailure.ForbiddenPin -> stringResource(id = R.string.screen_app_lock_setup_pin_forbidden_dialog_title)
diff --git a/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/error/ChangeServerError.kt b/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/error/ChangeServerError.kt
index e3fdfc2d04..6d678854c1 100644
--- a/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/error/ChangeServerError.kt
+++ b/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/error/ChangeServerError.kt
@@ -9,6 +9,7 @@ package io.element.android.features.login.impl.error
import androidx.annotation.StringRes
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.ui.res.stringResource
import io.element.android.features.login.impl.R
import io.element.android.features.login.impl.changeserver.UnauthorizedAccountProviderException
@@ -21,6 +22,7 @@ sealed class ChangeServerError : Throwable() {
val messageStr: String? = null,
) : ChangeServerError() {
@Composable
+ @ReadOnlyComposable
fun message(): String = messageStr ?: stringResource(messageId ?: CommonStrings.error_unknown)
}
diff --git a/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/screens/loginpassword/LoginPasswordView.kt b/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/screens/loginpassword/LoginPasswordView.kt
index c72f1a0308..5cb0c23d9c 100644
--- a/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/screens/loginpassword/LoginPasswordView.kt
+++ b/features/login/impl/src/main/kotlin/io/element/android/features/login/impl/screens/loginpassword/LoginPasswordView.kt
@@ -29,7 +29,6 @@ import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
-import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.autofill.ContentType
import androidx.compose.ui.focus.FocusDirection
@@ -170,7 +169,6 @@ fun LoginPasswordView(
}
}
-@OptIn(ExperimentalComposeUiApi::class)
@Composable
private fun LoginForm(
state: LoginPasswordState,
diff --git a/features/login/impl/src/main/res/values-es/translations.xml b/features/login/impl/src/main/res/values-es/translations.xml
index 390f701b0a..d4841e2171 100644
--- a/features/login/impl/src/main/res/values-es/translations.xml
+++ b/features/login/impl/src/main/res/values-es/translations.xml
@@ -1,22 +1,27 @@
- "Cambiar el proveedor de la cuenta"
- "Dirección del servidor principal"
- "Introduzca un término de búsqueda o una dirección de dominio."
+ "Cambiar proveedor de cuentas"
+ "Dirección del servidor base"
+ "Introduce un término de búsqueda o una dirección de dominio."
"Busca una empresa, comunidad o servidor privado."
- "Encontrar un proveedor de cuenta"
+ "Encontrar un proveedor de cuentas"
"Aquí es donde se alojarán tus conversaciones — justo como utilizarías un proveedor de correo electrónico para guardar tus correos electrónicos."
"Estás a punto de iniciar sesión en %s"
"Aquí es donde se alojarán tus conversaciones — justo como utilizarías un proveedor de correo electrónico para guardar tus correos electrónicos."
"Estás a punto de crear una cuenta en %s"
"Matrix.org es un servidor grande y gratuito en la red pública Matrix para una comunicación segura y descentralizada, administrado por la Fundación Matrix.org."
"Otro"
- "Usa un proveedor de cuenta diferente, como tu propio servidor privado o una cuenta de trabajo."
- "Cambiar el proveedor de la cuenta"
- "No hemos podido acceder a este servidor. Comprueba que has introducido correctamente la dirección del servidor. Si la dirección es correcta, ponte en contacto con el administrador del servidor para obtener más ayuda."
- "Sliding sync no está disponible debido a un problema en el archivo well-known:
+ "Usa un proveedor de cuentas diferente, como tu propio servidor privado o una cuenta de trabajo."
+ "Cambiar proveedor de cuentas"
+ "No hemos podido acceder a este servidor base. Comprueba que has introducido correctamente la dirección. Si es correcta, ponte en contacto con el administrador de tu servidor base para obtener más ayuda."
+ "El servidor no está disponible debido a un problema en el archivo .well-known:
%1$s"
- "Dirección del homeserver"
+ "El proveedor de cuentas seleccionado no admite sliding sync. Es necesario actualizar el servidor para usar %1$s."
+ "%1$s no está autorizado para conectarse a %2$s."
+ "Esta aplicación se ha configurado para permitir: %1$s."
+ "No se permite el proveedor de cuentas %1$s."
+ "URL del servidor base"
+ "Introduce una dirección de dominio."
"¿Cuál es la dirección de tu servidor?"
"Selecciona tu servidor"
"Crear cuenta"
@@ -24,12 +29,13 @@
"Usuario y/o contraseña incorrectos"
"Este no es un id de usuario válido. Formato esperado: \'@user:homeserver.org\'"
"Este servidor está configurado para utilizar tokens de actualización. Estos no son compatibles cuando se utiliza el inicio de sesión basado en contraseña."
- "El servidor seleccionado no admite contraseñas ni inicio de sesión OIDC. Póngase en contacto con su administrador o elija otro homeserver."
+ "El servidor base seleccionado no admite el inicio de sesión usando contraseña ni OIDC. Ponte en contacto con tu administrador o elige otro servidor base."
"Introduce tus datos"
"Matrix es una red abierta para una comunicación segura y descentralizada."
"¡Hola de nuevo!"
"Iniciar sesión en %1$s"
"Iniciar sesión manualmente"
+ "Iniciar sesión en %1$s"
"Iniciar sesión con un código QR"
"Crear cuenta"
"Bienvenido al %1$s más rápido de todos los tiempos. Diseñado para la velocidad y la simplicidad."
@@ -56,7 +62,7 @@
Intenta iniciar sesión manualmente o escanea el código QR con otro dispositivo."
"Código QR no admitido"
- "Tu proveedor de cuenta no es compatible con %1$s."
+ "Tu proveedor de cuentas no es compatible con %1$s."
"%1$s no admitido"
"Listo para escanear"
"Abre %1$s en un dispositivo de escritorio"
@@ -64,7 +70,7 @@ Intenta iniciar sesión manualmente o escanea el código QR con otro dispositivo
"Selecciona %1$s"
"«Vincular un dispositivo nuevo»"
"Escanea el código QR con este dispositivo"
- "Solo disponible si tu proveedor de cuenta lo admite."
+ "Sólo disponible si tu proveedor de cuentas lo admite."
"Abre %1$s en otro dispositivo para obtener el código QR"
"Usa el código QR que se muestra en el otro dispositivo."
"Intentar de nuevo"
@@ -76,12 +82,13 @@ Intenta iniciar sesión manualmente o escanea el código QR con otro dispositivo
"Empezar de nuevo"
"Se ha producido un error inesperado. Vuelve a intentarlo."
"A la espera de tu otro dispositivo"
- "Puede que el proveedor de tu cuenta te pida el siguiente código para verificar el inicio de sesión."
+ "Puede que tu proveedor de cuentas te pida el siguiente código para verificar el inicio de sesión."
"Tu código de verificación"
- "Cambiar el proveedor de la cuenta"
+ "Cambiar proveedor de cuentas"
"Un servidor privado para los empleados de Element."
"Matrix es una red abierta para una comunicación segura y descentralizada."
"Aquí es donde se alojarán tus conversaciones — justo como utilizarías un proveedor de correo electrónico para guardar tus correos electrónicos."
"Estás a punto de iniciar sesión en %1$s"
+ "Elegir proveedor de cuentas"
"Estás a punto de crear una cuenta en %1$s"
diff --git a/features/login/impl/src/main/res/values-nb/translations.xml b/features/login/impl/src/main/res/values-nb/translations.xml
index 88c063d701..0054906e65 100644
--- a/features/login/impl/src/main/res/values-nb/translations.xml
+++ b/features/login/impl/src/main/res/values-nb/translations.xml
@@ -89,5 +89,6 @@ Prøv å logge på manuelt, eller skann QR-koden med en annen enhet."
"Matrix er et åpent nettverk for sikker, desentralisert kommunikasjon."
"Det er her samtalene dine vil ligge - akkurat som du ville brukt en e-postleverandør til å oppbevare e-postene dine."
"Du er i ferd med å logge inn på %1$s"
+ "Velg kontoleverandør"
"Du er i ferd med å opprette en konto på %1$s"
diff --git a/features/login/impl/src/main/res/values-ru/translations.xml b/features/login/impl/src/main/res/values-ru/translations.xml
index b16ff24a92..17aaaa4530 100644
--- a/features/login/impl/src/main/res/values-ru/translations.xml
+++ b/features/login/impl/src/main/res/values-ru/translations.xml
@@ -14,8 +14,12 @@
"Используйте другого поставщика учетных записей, например, собственный частный сервер или рабочую учетную запись."
"Сменить поставщика учетной записи"
"Нам не удалось связаться с этим домашним сервером. Убедитесь, что вы правильно ввели URL-адрес домашнего сервера. Если URL-адрес указан правильно, обратитесь к администратору домашнего сервера за дополнительной помощью."
- "Sliding sync недоступен из-за проблемы в известном файле:
+ "Сервер недоступен из-за проблемы в файле .well-known:
%1$s"
+ "Выбранный провайдер аккаунтов не поддерживает Sliding sync. Для использования %1$s необходимо обновление сервера."
+ "%1$s отказано в подключении к %2$s."
+ "Это приложение настроено таким образом, чтобы разрешить: %1$s."
+ "Поставщик учетной записи %1$s не разрешен."
"URL-адрес домашнего сервера"
"Введите адрес домена."
"Какой адрес у вашего сервера?"
@@ -31,6 +35,7 @@
"Рады видеть вас снова!"
"Войти в %1$s"
"Войти вручную"
+ "Войти в %1$s"
"Войти QR-кодом"
"Создать учетную запись"
"Добро пожаловать в самый быстрый клиент %1$s. Ориентирован на скорость и простоту."
@@ -84,5 +89,6 @@
"Matrix — это открытая сеть для безопасной децентрализованной связи."
"Здесь будут храниться ваши разговоры — точно так же, как если бы вы использовали почтового провайдера для хранения своих писем."
"Вы собираетесь войти в %1$s"
+ "Выберите поставщика учетной записи"
"Вы собираетесь создать учетную запись на %1$s"
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNavigator.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNavigator.kt
index b045d10199..c66ec1ee51 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNavigator.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNavigator.kt
@@ -9,6 +9,7 @@ package io.element.android.features.messages.impl
import io.element.android.features.messages.impl.attachments.Attachment
import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.timeline.item.TimelineItemDebugInfo
import kotlinx.collections.immutable.ImmutableList
@@ -19,4 +20,5 @@ interface MessagesNavigator {
fun onReportContentClick(eventId: EventId, senderId: UserId)
fun onEditPollClick(eventId: EventId)
fun onPreviewAttachment(attachments: ImmutableList)
+ fun onNavigateToRoom(roomId: RoomId)
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNode.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNode.kt
index fc6d01d3a9..84d20fbf94 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNode.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesNode.kt
@@ -49,18 +49,21 @@ import io.element.android.libraries.architecture.NodeInputs
import io.element.android.libraries.architecture.inputs
import io.element.android.libraries.core.bool.orFalse
import io.element.android.libraries.designsystem.utils.OnLifecycleEvent
+import io.element.android.libraries.di.ApplicationContext
import io.element.android.libraries.di.RoomScope
import io.element.android.libraries.di.annotations.SessionCoroutineScope
import io.element.android.libraries.matrix.api.analytics.toAnalyticsViewRoom
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
+import io.element.android.libraries.matrix.api.core.toRoomIdOrAlias
import io.element.android.libraries.matrix.api.permalink.PermalinkData
import io.element.android.libraries.matrix.api.permalink.PermalinkParser
import io.element.android.libraries.matrix.api.room.BaseRoom
import io.element.android.libraries.matrix.api.room.alias.matches
import io.element.android.libraries.matrix.api.timeline.item.TimelineItemDebugInfo
import io.element.android.libraries.mediaplayer.api.MediaPlayer
+import io.element.android.libraries.ui.strings.CommonStrings
import io.element.android.services.analytics.api.AnalyticsService
import kotlinx.collections.immutable.ImmutableList
import kotlinx.coroutines.CoroutineScope
@@ -70,6 +73,7 @@ import kotlinx.coroutines.launch
class MessagesNode @AssistedInject constructor(
@Assisted buildContext: BuildContext,
@Assisted plugins: List,
+ @ApplicationContext private val context: Context,
@SessionCoroutineScope
private val sessionCoroutineScope: CoroutineScope,
private val room: BaseRoom,
@@ -157,7 +161,7 @@ class MessagesNode @AssistedInject constructor(
callbacks.forEach { it.onUserDataClick(permalink.userId) }
}
is PermalinkData.RoomLink -> {
- handleRoomLinkClick(activity, permalink, eventSink)
+ handleRoomLinkClick(permalink, eventSink)
}
is PermalinkData.FallbackLink -> {
if (customTab) {
@@ -173,7 +177,6 @@ class MessagesNode @AssistedInject constructor(
}
private fun handleRoomLinkClick(
- context: Context,
roomLink: PermalinkData.RoomLink,
eventSink: (TimelineEvents) -> Unit,
) {
@@ -183,7 +186,7 @@ class MessagesNode @AssistedInject constructor(
eventSink(TimelineEvents.FocusOnEvent(eventId))
} else {
// Click on the same room, ignore
- context.toast("Already viewing this room!")
+ displaySameRoomToast()
}
} else {
callbacks.forEach { it.onPermalinkClick(roomLink) }
@@ -210,6 +213,15 @@ class MessagesNode @AssistedInject constructor(
callbacks.forEach { it.onPreviewAttachments(attachments) }
}
+ override fun onNavigateToRoom(roomId: RoomId) {
+ if (roomId == room.roomId) {
+ displaySameRoomToast()
+ } else {
+ val permalinkData = PermalinkData.RoomLink(roomId.toRoomIdOrAlias())
+ callbacks.forEach { it.onPermalinkClick(permalinkData) }
+ }
+ }
+
private fun onViewAllPinnedMessagesClick() {
callbacks.forEach { it.onViewAllPinnedEvents() }
}
@@ -230,6 +242,10 @@ class MessagesNode @AssistedInject constructor(
callbacks.forEach { it.onViewKnockRequests() }
}
+ private fun displaySameRoomToast() {
+ context.toast(CommonStrings.screen_room_permalink_same_room_android)
+ }
+
@Composable
override fun View(modifier: Modifier) {
val activity = requireNotNull(LocalActivity.current)
@@ -255,13 +271,13 @@ class MessagesNode @AssistedInject constructor(
onCreatePollClick = this::onCreatePollClick,
onJoinCallClick = this::onJoinCallClick,
onViewAllPinnedMessagesClick = this::onViewAllPinnedMessagesClick,
+ modifier = modifier,
knockRequestsBannerView = {
knockRequestsBannerRenderer.View(
modifier = Modifier,
onViewRequestsClick = this::onViewKnockRequestsClick
)
},
- modifier = modifier,
)
roomMemberModerationRenderer.Render(
state = state.roomMemberModerationState,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesPresenter.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesPresenter.kt
index 74cb9799f2..3390b55d5e 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesPresenter.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesPresenter.kt
@@ -152,11 +152,8 @@ class MessagesPresenter @AssistedInject constructor(
val userEventPermissions by userEventPermissions(syncUpdateFlow.value)
- val roomName: AsyncData by remember {
- derivedStateOf { roomInfo.name?.let { AsyncData.Success(it) } ?: AsyncData.Uninitialized }
- }
- val roomAvatar: AsyncData by remember {
- derivedStateOf { AsyncData.Success(roomInfo.avatarData()) }
+ val roomAvatar by remember {
+ derivedStateOf { roomInfo.avatarData() }
}
val heroes by remember {
derivedStateOf { roomInfo.heroes().toPersistentList() }
@@ -245,7 +242,7 @@ class MessagesPresenter @AssistedInject constructor(
return MessagesState(
roomId = room.roomId,
- roomName = roomName,
+ roomName = roomInfo.name,
roomAvatar = roomAvatar,
heroes = heroes,
composerState = composerState,
@@ -270,6 +267,7 @@ class MessagesPresenter @AssistedInject constructor(
pinnedMessagesBannerState = pinnedMessagesBannerState,
dmUserVerificationState = dmUserVerificationState,
roomMemberModerationState = roomMemberModerationState,
+ successorRoom = roomInfo.successorRoom,
eventSink = { handleEvents(it) }
)
}
@@ -291,7 +289,7 @@ class MessagesPresenter @AssistedInject constructor(
return AvatarData(
id = id.value,
name = name,
- url = avatarUrl ?: room.info().avatarUrl,
+ url = avatarUrl,
size = AvatarSize.TimelineRoom
)
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesState.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesState.kt
index 8ba2cbd039..bedce147dc 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesState.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesState.kt
@@ -26,13 +26,14 @@ import io.element.android.libraries.designsystem.components.avatar.AvatarData
import io.element.android.libraries.designsystem.utils.snackbar.SnackbarMessage
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.encryption.identity.IdentityState
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import kotlinx.collections.immutable.ImmutableList
@Immutable
data class MessagesState(
val roomId: RoomId,
- val roomName: AsyncData,
- val roomAvatar: AsyncData,
+ val roomName: String?,
+ val roomAvatar: AvatarData,
val heroes: ImmutableList,
val userEventPermissions: UserEventPermissions,
val composerState: MessageComposerState,
@@ -56,5 +57,8 @@ data class MessagesState(
val pinnedMessagesBannerState: PinnedMessagesBannerState,
val dmUserVerificationState: IdentityState?,
val roomMemberModerationState: RoomMemberModerationState,
+ val successorRoom: SuccessorRoom?,
val eventSink: (MessagesEvents) -> Unit
-)
+) {
+ val isTombstoned = successorRoom != null
+}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesStateProvider.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesStateProvider.kt
index c366a1e4cf..8fa539dd94 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesStateProvider.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesStateProvider.kt
@@ -44,6 +44,7 @@ import io.element.android.libraries.designsystem.components.avatar.AvatarData
import io.element.android.libraries.designsystem.components.avatar.AvatarSize
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.encryption.identity.IdentityState
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.textcomposer.model.MessageComposerMode
import io.element.android.libraries.textcomposer.model.aTextEditorStateRich
import kotlinx.collections.immutable.persistentListOf
@@ -57,10 +58,7 @@ open class MessagesStateProvider : PreviewParameterProvider {
aMessagesState(composerState = aMessageComposerState(showAttachmentSourcePicker = true)),
aMessagesState(userEventPermissions = aUserEventPermissions(canSendMessage = false)),
aMessagesState(showReinvitePrompt = true),
- aMessagesState(
- roomName = AsyncData.Uninitialized,
- roomAvatar = AsyncData.Uninitialized,
- ),
+ aMessagesState(roomName = null),
aMessagesState(composerState = aMessageComposerState(showTextFormatting = true)),
aMessagesState(
enableVoiceMessages = true,
@@ -85,14 +83,15 @@ open class MessagesStateProvider : PreviewParameterProvider {
currentPinnedMessageIndex = 0,
),
),
- aMessagesState(roomName = AsyncData.Success("A DM with a very looong name"), dmUserVerificationState = IdentityState.Verified),
- aMessagesState(roomName = AsyncData.Success("A DM with a very looong name"), dmUserVerificationState = IdentityState.VerificationViolation),
+ aMessagesState(roomName = "A DM with a very looong name", dmUserVerificationState = IdentityState.Verified),
+ aMessagesState(roomName = "A DM with a very looong name", dmUserVerificationState = IdentityState.VerificationViolation),
+ aMessagesState(successorRoom = SuccessorRoom(RoomId("!id:domain"), null)),
)
}
fun aMessagesState(
- roomName: AsyncData = AsyncData.Success("Room name"),
- roomAvatar: AsyncData = AsyncData.Success(AvatarData("!id:domain", "Room name", size = AvatarSize.TimelineRoom)),
+ roomName: String? = "Room name",
+ roomAvatar: AvatarData = AvatarData("!id:domain", "Room name", size = AvatarSize.TimelineRoom),
userEventPermissions: UserEventPermissions = aUserEventPermissions(),
composerState: MessageComposerState = aMessageComposerState(
textEditorState = aTextEditorStateRich(initialText = "Hello", initialFocus = true),
@@ -119,6 +118,7 @@ fun aMessagesState(
pinnedMessagesBannerState: PinnedMessagesBannerState = aLoadedPinnedMessagesBannerState(),
dmUserVerificationState: IdentityState? = null,
roomMemberModerationState: RoomMemberModerationState = aRoomMemberModerationState(),
+ successorRoom: SuccessorRoom? = null,
eventSink: (MessagesEvents) -> Unit = {},
) = MessagesState(
roomId = RoomId("!id:domain"),
@@ -147,6 +147,7 @@ fun aMessagesState(
pinnedMessagesBannerState = pinnedMessagesBannerState,
dmUserVerificationState = dmUserVerificationState,
roomMemberModerationState = roomMemberModerationState,
+ successorRoom = successorRoom,
eventSink = eventSink,
)
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesView.kt
index ee76562b2c..a772015787 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesView.kt
@@ -82,14 +82,14 @@ import io.element.android.features.messages.impl.voicemessages.composer.VoiceMes
import io.element.android.features.networkmonitor.api.ui.ConnectivityIndicatorView
import io.element.android.features.roomcall.api.RoomCallState
import io.element.android.libraries.androidutils.ui.hideKeyboard
-import io.element.android.libraries.designsystem.atomic.molecules.IconTitlePlaceholdersRowMolecule
+import io.element.android.libraries.designsystem.atomic.molecules.ComposerAlertMolecule
import io.element.android.libraries.designsystem.components.avatar.AvatarData
-import io.element.android.libraries.designsystem.components.avatar.AvatarSize
-import io.element.android.libraries.designsystem.components.avatar.CompositeAvatar
+import io.element.android.libraries.designsystem.components.avatar.RoomAvatar
import io.element.android.libraries.designsystem.components.button.BackButton
import io.element.android.libraries.designsystem.components.dialogs.ConfirmationDialog
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
+import io.element.android.libraries.designsystem.text.toAnnotatedString
import io.element.android.libraries.designsystem.theme.components.BottomSheetDragHandle
import io.element.android.libraries.designsystem.theme.components.Icon
import io.element.android.libraries.designsystem.theme.components.Scaffold
@@ -101,8 +101,10 @@ import io.element.android.libraries.designsystem.utils.OnLifecycleEvent
import io.element.android.libraries.designsystem.utils.snackbar.SnackbarHost
import io.element.android.libraries.designsystem.utils.snackbar.rememberSnackbarHostState
import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.encryption.identity.IdentityState
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.matrix.api.user.MatrixUser
import io.element.android.libraries.textcomposer.model.TextEditorState
import io.element.android.libraries.ui.strings.CommonStrings
@@ -190,8 +192,9 @@ fun MessagesView(
Column {
ConnectivityIndicatorView(isOnline = state.hasNetworkConnection)
MessagesViewTopBar(
- roomName = state.roomName.dataOrNull(),
- roomAvatar = state.roomAvatar.dataOrNull(),
+ roomName = state.roomName,
+ roomAvatar = state.roomAvatar,
+ isTombstoned = state.isTombstoned,
heroes = state.heroes,
roomCallState = state.roomCallState,
dmUserIdentityState = state.dmUserVerificationState,
@@ -211,8 +214,8 @@ fun MessagesView(
onMessageLongClick = ::onMessageLongClick,
onUserDataClick = {
hidingKeyboard {
- state.eventSink(MessagesEvents.OnUserClicked(it))
- }
+ state.eventSink(MessagesEvents.OnUserClicked(it))
+ }
},
onLinkClick = { link, customTab ->
if (customTab) {
@@ -410,6 +413,9 @@ private fun MessagesViewContent(
MessagesViewComposerBottomSheetContents(
subcomposing = subcomposing,
state = state,
+ onRoomSuccessorClick = { roomId ->
+ state.timelineState.eventSink(TimelineEvents.NavigateToRoom(roomId = roomId))
+ },
onLinkClick = { url, customTab -> onLinkClick(Link(url), customTab) },
)
},
@@ -424,52 +430,59 @@ private fun MessagesViewContent(
private fun MessagesViewComposerBottomSheetContents(
subcomposing: Boolean,
state: MessagesState,
+ onRoomSuccessorClick: (RoomId) -> Unit,
onLinkClick: (String, Boolean) -> Unit,
) {
- if (state.userEventPermissions.canSendMessage) {
- Column(modifier = Modifier.fillMaxWidth()) {
- SuggestionsPickerView(
- modifier = Modifier
- .heightIn(max = 230.dp)
- // Consume all scrolling, preventing the bottom sheet from being dragged when interacting with the list of suggestions
- .nestedScroll(object : NestedScrollConnection {
- override fun onPostScroll(consumed: Offset, available: Offset, source: NestedScrollSource): Offset {
- return available
- }
- }),
- roomId = state.roomId,
- roomName = state.roomName.dataOrNull(),
- roomAvatarData = state.roomAvatar.dataOrNull(),
- suggestions = state.composerState.suggestions,
- onSelectSuggestion = {
- state.composerState.eventSink(MessageComposerEvents.InsertSuggestion(it))
+ when {
+ state.successorRoom != null -> {
+ SuccessorRoomBanner(roomSuccessor = state.successorRoom, onRoomSuccessorClick = onRoomSuccessorClick)
+ }
+ state.userEventPermissions.canSendMessage -> {
+ Column(modifier = Modifier.fillMaxWidth()) {
+ SuggestionsPickerView(
+ modifier = Modifier
+ .heightIn(max = 230.dp)
+ // Consume all scrolling, preventing the bottom sheet from being dragged when interacting with the list of suggestions
+ .nestedScroll(object : NestedScrollConnection {
+ override fun onPostScroll(consumed: Offset, available: Offset, source: NestedScrollSource): Offset {
+ return available
+ }
+ }),
+ roomId = state.roomId,
+ roomName = state.roomName,
+ roomAvatarData = state.roomAvatar,
+ suggestions = state.composerState.suggestions,
+ onSelectSuggestion = {
+ state.composerState.eventSink(MessageComposerEvents.InsertSuggestion(it))
+ }
+ )
+ // Do not show the identity change if user is composing a Rich message or is seeing suggestion(s).
+ if (state.composerState.suggestions.isEmpty() &&
+ state.composerState.textEditorState is TextEditorState.Markdown) {
+ IdentityChangeStateView(
+ state = state.identityChangeState,
+ onLinkClick = onLinkClick,
+ )
+ }
+ val verificationViolation = state.identityChangeState.roomMemberIdentityStateChanges.firstOrNull {
+ it.identityState == IdentityState.VerificationViolation
+ }
+ if (verificationViolation != null) {
+ DisabledComposerView(modifier = Modifier.fillMaxWidth())
+ } else {
+ MessageComposerView(
+ state = state.composerState,
+ voiceMessageState = state.voiceMessageComposerState,
+ subcomposing = subcomposing,
+ enableVoiceMessages = state.enableVoiceMessages,
+ modifier = Modifier.fillMaxWidth(),
+ )
}
- )
- // Do not show the identity change if user is composing a Rich message or is seeing suggestion(s).
- if (state.composerState.suggestions.isEmpty() &&
- state.composerState.textEditorState is TextEditorState.Markdown) {
- IdentityChangeStateView(
- state = state.identityChangeState,
- onLinkClick = onLinkClick,
- )
- }
- val verificationViolation = state.identityChangeState.roomMemberIdentityStateChanges.firstOrNull {
- it.identityState == IdentityState.VerificationViolation
- }
- if (verificationViolation != null) {
- DisabledComposerView(modifier = Modifier.fillMaxWidth())
- } else {
- MessageComposerView(
- state = state.composerState,
- voiceMessageState = state.voiceMessageComposerState,
- subcomposing = subcomposing,
- enableVoiceMessages = state.enableVoiceMessages,
- modifier = Modifier.fillMaxWidth(),
- )
}
}
- } else {
- CantSendMessageBanner()
+ else -> {
+ CantSendMessageBanner()
+ }
}
}
@@ -477,7 +490,8 @@ private fun MessagesViewComposerBottomSheetContents(
@Composable
private fun MessagesViewTopBar(
roomName: String?,
- roomAvatar: AvatarData?,
+ roomAvatar: AvatarData,
+ isTombstoned: Boolean,
heroes: ImmutableList,
roomCallState: RoomCallState,
dmUserIdentityState: IdentityState?,
@@ -499,19 +513,13 @@ private fun MessagesViewTopBar(
verticalAlignment = Alignment.CenterVertically,
) {
val titleModifier = Modifier.weight(1f, fill = false)
- if (roomName != null && roomAvatar != null) {
- RoomAvatarAndNameRow(
- roomName = roomName,
- roomAvatar = roomAvatar,
- heroes = heroes,
- modifier = titleModifier
- )
- } else {
- IconTitlePlaceholdersRowMolecule(
- iconSize = AvatarSize.TimelineRoom.dp,
- modifier = titleModifier
- )
- }
+ RoomAvatarAndNameRow(
+ roomName = roomName,
+ roomAvatar = roomAvatar,
+ isTombstoned = isTombstoned,
+ heroes = heroes,
+ modifier = titleModifier
+ )
when (dmUserIdentityState) {
IdentityState.Verified -> {
@@ -545,23 +553,26 @@ private fun MessagesViewTopBar(
@Composable
private fun RoomAvatarAndNameRow(
- roomName: String,
+ roomName: String?,
roomAvatar: AvatarData,
heroes: ImmutableList,
+ isTombstoned: Boolean,
modifier: Modifier = Modifier
) {
Row(
modifier = modifier,
verticalAlignment = Alignment.CenterVertically
) {
- CompositeAvatar(
+ RoomAvatar(
avatarData = roomAvatar,
heroes = heroes,
+ isTombstoned = isTombstoned,
)
Text(
modifier = Modifier.padding(horizontal = 8.dp),
- text = roomName,
+ text = roomName ?: stringResource(CommonStrings.common_no_room_name),
style = ElementTheme.typography.fontBodyLgMedium,
+ fontStyle = FontStyle.Italic.takeIf { roomName == null },
maxLines = 1,
overflow = TextOverflow.Ellipsis
)
@@ -588,6 +599,22 @@ private fun CantSendMessageBanner() {
}
}
+@Composable
+private fun SuccessorRoomBanner(
+ roomSuccessor: SuccessorRoom,
+ onRoomSuccessorClick: (RoomId) -> Unit,
+ modifier: Modifier = Modifier,
+) {
+ ComposerAlertMolecule(
+ avatar = null,
+ content = stringResource(R.string.screen_room_timeline_tombstoned_room_message).toAnnotatedString(),
+ onSubmitClick = { onRoomSuccessorClick(roomSuccessor.roomId) },
+ modifier = modifier,
+ isCritical = false,
+ submitText = stringResource(R.string.screen_room_timeline_tombstoned_room_action)
+ )
+}
+
@PreviewsDayNight
@Composable
internal fun MessagesViewPreview(@PreviewParameter(MessagesStateProvider::class) state: MessagesState) = ElementPreview {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenter.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenter.kt
index ee4f278366..9c2760bf6c 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenter.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenter.kt
@@ -169,7 +169,7 @@ class DefaultActionListPresenter @AssistedInject constructor(
if (timelineItem.isRemote && timelineItem.content.canBeForwarded()) {
add(TimelineItemAction.Forward)
}
- if (timelineItem.isEditable) {
+ if (timelineItem.isEditable && usersEventPermissions.canSendMessage) {
if (timelineItem.content is TimelineItemEventContentWithAttachment) {
// Caption
if (timelineItem.content.caption == null) {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListView.kt
index 8eb4bb8554..a16f1efa19 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/actionlist/ActionListView.kt
@@ -30,6 +30,7 @@ import androidx.compose.material3.ListItemDefaults
import androidx.compose.material3.rememberModalBottomSheetState
import androidx.compose.material3.ripple
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Alignment
@@ -38,7 +39,7 @@ import androidx.compose.ui.graphics.Color
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.semantics.clearAndSetSemantics
-import androidx.compose.ui.semantics.contentDescription
+import androidx.compose.ui.semantics.onClick
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.semantics.traversalIndex
import androidx.compose.ui.text.style.TextAlign
@@ -52,6 +53,7 @@ import io.element.android.features.messages.impl.crypto.sendfailure.VerifiedUser
import io.element.android.features.messages.impl.crypto.sendfailure.VerifiedUserSendFailure.ChangedIdentity
import io.element.android.features.messages.impl.crypto.sendfailure.VerifiedUserSendFailure.None
import io.element.android.features.messages.impl.crypto.sendfailure.VerifiedUserSendFailure.UnsignedDevice
+import io.element.android.features.messages.impl.timeline.a11y.a11yReactionAction
import io.element.android.features.messages.impl.timeline.components.MessageShieldView
import io.element.android.features.messages.impl.timeline.model.TimelineItem
import io.element.android.features.messages.impl.timeline.model.event.TimelineItemAudioContent
@@ -394,6 +396,7 @@ private fun VerifiedUserSendFailureView(
modifier: Modifier = Modifier,
) {
@Composable
+ @ReadOnlyComposable
fun VerifiedUserSendFailure.headline(): String {
return when (this) {
is None -> ""
@@ -436,11 +439,10 @@ private fun EmojiButton(
} else {
Color.Transparent
}
- val description = if (isHighlighted) {
- stringResource(id = CommonStrings.a11y_remove_reaction_with, emoji)
- } else {
- stringResource(id = CommonStrings.a11y_react_with, emoji)
- }
+ val a11yClickLabel = a11yReactionAction(
+ emoji = emoji,
+ userAlreadyReacted = isHighlighted,
+ )
Box(
modifier = modifier
.size(48.dp)
@@ -452,7 +454,12 @@ private fun EmojiButton(
interactionSource = remember { MutableInteractionSource() }
)
.semantics {
- contentDescription = description
+ onClick(
+ label = a11yClickLabel,
+ ) {
+ onClick(emoji)
+ true
+ }
},
contentAlignment = Alignment.Center
) {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftService.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftService.kt
index d34651f7a4..489e5bd046 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftService.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftService.kt
@@ -8,9 +8,10 @@
package io.element.android.features.messages.impl.draft
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
interface ComposerDraftService {
- suspend fun loadDraft(roomId: RoomId, isVolatile: Boolean): ComposerDraft?
- suspend fun updateDraft(roomId: RoomId, draft: ComposerDraft?, isVolatile: Boolean)
+ suspend fun loadDraft(roomId: RoomId, threadRoot: ThreadId?, isVolatile: Boolean): ComposerDraft?
+ suspend fun updateDraft(roomId: RoomId, threadRoot: ThreadId?, draft: ComposerDraft?, isVolatile: Boolean)
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftStore.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftStore.kt
index d1297c1056..c460acb065 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftStore.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/ComposerDraftStore.kt
@@ -8,9 +8,10 @@
package io.element.android.features.messages.impl.draft
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
interface ComposerDraftStore {
- suspend fun loadDraft(roomId: RoomId): ComposerDraft?
- suspend fun updateDraft(roomId: RoomId, draft: ComposerDraft?)
+ suspend fun loadDraft(roomId: RoomId, threadRoot: ThreadId?): ComposerDraft?
+ suspend fun updateDraft(roomId: RoomId, threadRoot: ThreadId?, draft: ComposerDraft?)
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/DefaultComposerDraftService.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/DefaultComposerDraftService.kt
index 1499aeac1d..57909c5a8a 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/DefaultComposerDraftService.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/DefaultComposerDraftService.kt
@@ -10,6 +10,7 @@ package io.element.android.features.messages.impl.draft
import com.squareup.anvil.annotations.ContributesBinding
import io.element.android.libraries.di.RoomScope
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import javax.inject.Inject
@@ -18,12 +19,12 @@ class DefaultComposerDraftService @Inject constructor(
private val volatileComposerDraftStore: VolatileComposerDraftStore,
private val matrixComposerDraftStore: MatrixComposerDraftStore,
) : ComposerDraftService {
- override suspend fun loadDraft(roomId: RoomId, isVolatile: Boolean): ComposerDraft? {
- return getStore(isVolatile).loadDraft(roomId)
+ override suspend fun loadDraft(roomId: RoomId, threadRoot: ThreadId?, isVolatile: Boolean): ComposerDraft? {
+ return getStore(isVolatile).loadDraft(roomId, threadRoot)
}
- override suspend fun updateDraft(roomId: RoomId, draft: ComposerDraft?, isVolatile: Boolean) {
- getStore(isVolatile).updateDraft(roomId, draft)
+ override suspend fun updateDraft(roomId: RoomId, threadRoot: ThreadId?, draft: ComposerDraft?, isVolatile: Boolean) {
+ getStore(isVolatile).updateDraft(roomId, threadRoot, draft)
}
private fun getStore(isVolatile: Boolean): ComposerDraftStore {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/MatrixComposerDraftStore.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/MatrixComposerDraftStore.kt
index b850e7b559..88000546dd 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/MatrixComposerDraftStore.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/MatrixComposerDraftStore.kt
@@ -9,6 +9,7 @@ package io.element.android.features.messages.impl.draft
import io.element.android.libraries.matrix.api.MatrixClient
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import timber.log.Timber
import javax.inject.Inject
@@ -20,26 +21,26 @@ import javax.inject.Inject
class MatrixComposerDraftStore @Inject constructor(
private val client: MatrixClient,
) : ComposerDraftStore {
- override suspend fun loadDraft(roomId: RoomId): ComposerDraft? {
+ override suspend fun loadDraft(roomId: RoomId, threadRoot: ThreadId?): ComposerDraft? {
return client.getRoom(roomId)?.use { room ->
- room.loadComposerDraft()
+ room.loadComposerDraft(threadRoot)
.onFailure {
Timber.e(it, "Failed to load composer draft for room $roomId")
}
.onSuccess { draft ->
- room.clearComposerDraft()
+ room.clearComposerDraft(threadRoot)
Timber.d("Loaded composer draft for room $roomId : $draft")
}
.getOrNull()
}
}
- override suspend fun updateDraft(roomId: RoomId, draft: ComposerDraft?) {
+ override suspend fun updateDraft(roomId: RoomId, threadRoot: ThreadId?, draft: ComposerDraft?) {
client.getRoom(roomId)?.use { room ->
val updateDraftResult = if (draft == null) {
- room.clearComposerDraft()
+ room.clearComposerDraft(threadRoot)
} else {
- room.saveComposerDraft(draft)
+ room.saveComposerDraft(draft, threadRoot)
}
updateDraftResult
.onFailure {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStore.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStore.kt
index 568f68a2d6..b7b714f5c9 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStore.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStore.kt
@@ -8,6 +8,7 @@
package io.element.android.features.messages.impl.draft
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import javax.inject.Inject
@@ -17,18 +18,20 @@ import javax.inject.Inject
* Currently it's used to store draft message when moving to edit mode.
*/
class VolatileComposerDraftStore @Inject constructor() : ComposerDraftStore {
- private val drafts: MutableMap = mutableMapOf()
+ private val drafts: MutableMap = mutableMapOf()
- override suspend fun loadDraft(roomId: RoomId): ComposerDraft? {
+ override suspend fun loadDraft(roomId: RoomId, threadRoot: ThreadId?): ComposerDraft? {
+ val key = threadRoot?.value ?: roomId.value
// Remove the draft from the map when it is loaded
- return drafts.remove(roomId)
+ return drafts.remove(key)
}
- override suspend fun updateDraft(roomId: RoomId, draft: ComposerDraft?) {
+ override suspend fun updateDraft(roomId: RoomId, threadRoot: ThreadId?, draft: ComposerDraft?) {
+ val key = threadRoot?.value ?: roomId.value
if (draft == null) {
- drafts.remove(roomId)
+ drafts.remove(key)
} else {
- drafts[roomId] = draft
+ drafts[key] = draft
}
}
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenter.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenter.kt
index 728087fe1c..f7187c5021 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenter.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenter.kt
@@ -219,7 +219,12 @@ class MessageComposerPresenter @AssistedInject constructor(
)
LaunchedEffect(Unit) {
- val draft = draftService.loadDraft(room.roomId, isVolatile = false)
+ val draft = draftService.loadDraft(
+ roomId = room.roomId,
+ // TODO support threads in composer
+ threadRoot = null,
+ isVolatile = false
+ )
if (draft != null) {
applyDraft(draft, markdownTextEditorState, richTextEditorState)
}
@@ -539,7 +544,9 @@ class MessageComposerPresenter @AssistedInject constructor(
draftService.updateDraft(
roomId = room.roomId,
draft = draft,
- isVolatile = isVolatile
+ isVolatile = isVolatile,
+ // TODO support threads in composer
+ threadRoot = null,
)
}
@@ -700,7 +707,12 @@ class MessageComposerPresenter @AssistedInject constructor(
fromEdit: Boolean,
) {
// Use the volatile draft only when coming from edit mode otherwise.
- val draft = draftService.loadDraft(room.roomId, isVolatile = true).takeIf { fromEdit }
+ val draft = draftService.loadDraft(
+ roomId = room.roomId,
+ // TODO support threads in composer
+ threadRoot = null,
+ isVolatile = true
+ ).takeIf { fromEdit }
if (draft != null) {
applyDraft(draft, markdownTextEditorState, richTextEditorState)
} else {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/suggestions/SuggestionsPickerView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/suggestions/SuggestionsPickerView.kt
index 9d774d5841..cc8f536f5f 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/suggestions/SuggestionsPickerView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/messagecomposer/suggestions/SuggestionsPickerView.kt
@@ -27,6 +27,7 @@ import io.element.android.features.messages.impl.R
import io.element.android.libraries.designsystem.components.avatar.Avatar
import io.element.android.libraries.designsystem.components.avatar.AvatarData
import io.element.android.libraries.designsystem.components.avatar.AvatarSize
+import io.element.android.libraries.designsystem.components.avatar.anAvatarData
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.theme.components.HorizontalDivider
@@ -45,7 +46,7 @@ import kotlinx.collections.immutable.persistentListOf
fun SuggestionsPickerView(
roomId: RoomId,
roomName: String?,
- roomAvatarData: AvatarData?,
+ roomAvatarData: AvatarData,
suggestions: ImmutableList,
onSelectSuggestion: (ResolvedSuggestion) -> Unit,
modifier: Modifier = Modifier,
@@ -155,7 +156,7 @@ internal fun SuggestionsPickerViewPreview() {
SuggestionsPickerView(
roomId = RoomId("!room:matrix.org"),
roomName = "Room",
- roomAvatarData = null,
+ roomAvatarData = anAvatarData(),
suggestions = persistentListOf(
ResolvedSuggestion.AtRoom,
ResolvedSuggestion.Member(roomMember),
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/pinned/list/PinnedMessagesListPresenter.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/pinned/list/PinnedMessagesListPresenter.kt
index a7901ff52d..1c9e18c9e6 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/pinned/list/PinnedMessagesListPresenter.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/pinned/list/PinnedMessagesListPresenter.kt
@@ -106,7 +106,8 @@ class PinnedMessagesListPresenter @AssistedInject constructor(
renderTypingNotifications = false,
typingMembers = persistentListOf(),
reserveSpace = false,
- )
+ ),
+ predecessorRoom = room.predecessorRoom(),
)
}
val timelineProtectionState = timelineProtectionPresenter.present()
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineEvents.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineEvents.kt
index 464a5caa22..da6837df21 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineEvents.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineEvents.kt
@@ -9,6 +9,7 @@ package io.element.android.features.messages.impl.timeline
import io.element.android.features.messages.impl.timeline.model.TimelineItem
import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.timeline.Timeline
import io.element.android.libraries.matrix.api.timeline.item.event.MessageShield
import kotlin.time.Duration
@@ -30,6 +31,7 @@ sealed interface TimelineEvents {
data class ComputeVerifiedUserSendFailure(val event: TimelineItem.Event) : EventFromTimelineItem
data class ShowShieldDialog(val messageShield: MessageShield) : EventFromTimelineItem
data class LoadMore(val direction: Timeline.PaginationDirection) : EventFromTimelineItem
+ data class NavigateToRoom(val roomId: RoomId) : EventFromTimelineItem
/**
* Events coming from a poll item.
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenter.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenter.kt
index 4684b8cfdd..d8c43e7de7 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenter.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenter.kt
@@ -178,6 +178,9 @@ class TimelinePresenter @AssistedInject constructor(
is TimelineEvents.ComputeVerifiedUserSendFailure -> {
resolveVerifiedUserSendFailureState.eventSink(ResolveVerifiedUserSendFailureEvents.ComputeForMessage(event.event))
}
+ is TimelineEvents.NavigateToRoom -> {
+ navigator.onNavigateToRoom(event.roomId)
+ }
}
}
@@ -257,8 +260,9 @@ class TimelinePresenter @AssistedInject constructor(
userHasPermissionToSendMessage = userHasPermissionToSendMessage,
userHasPermissionToSendReaction = userHasPermissionToSendReaction,
roomCallState = roomCallState,
- pinnedEventIds = roomInfo.pinnedEventIds.orEmpty(),
+ pinnedEventIds = roomInfo.pinnedEventIds,
typingNotificationState = typingNotificationState,
+ predecessorRoom = room.predecessorRoom(),
)
}
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineState.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineState.kt
index af4b7622fe..a3cdb34c94 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineState.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineState.kt
@@ -15,6 +15,7 @@ import io.element.android.features.messages.impl.typing.TypingNotificationState
import io.element.android.features.roomcall.api.RoomCallState
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.UniqueId
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
import io.element.android.libraries.matrix.api.timeline.item.event.MessageShield
import kotlinx.collections.immutable.ImmutableList
import kotlin.time.Duration
@@ -77,4 +78,5 @@ data class TimelineRoomInfo(
val roomCallState: RoomCallState,
val pinnedEventIds: List,
val typingNotificationState: TypingNotificationState,
+ val predecessorRoom: PredecessorRoom?,
)
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineStateProvider.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineStateProvider.kt
index d47379da3d..8bb66b4f60 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineStateProvider.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineStateProvider.kt
@@ -30,6 +30,7 @@ import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.TransactionId
import io.element.android.libraries.matrix.api.core.UniqueId
import io.element.android.libraries.matrix.api.core.UserId
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
import io.element.android.libraries.matrix.api.timeline.item.TimelineItemDebugInfo
import io.element.android.libraries.matrix.api.timeline.item.event.LocalEventSendState
import io.element.android.libraries.matrix.api.timeline.item.event.MessageShield
@@ -246,6 +247,7 @@ internal fun aTimelineRoomInfo(
userHasPermissionToSendMessage: Boolean = true,
pinnedEventIds: List = emptyList(),
typingNotificationState: TypingNotificationState = aTypingNotificationState(),
+ predecessorRoom: PredecessorRoom? = null,
) = TimelineRoomInfo(
isDm = isDm,
name = name,
@@ -254,4 +256,5 @@ internal fun aTimelineRoomInfo(
roomCallState = aStandByCallState(),
pinnedEventIds = pinnedEventIds,
typingNotificationState = typingNotificationState,
+ predecessorRoom = predecessorRoom,
)
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineView.kt
index b3b8331a16..cc9bf3cf84 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/TimelineView.kt
@@ -76,8 +76,6 @@ import io.element.android.libraries.testtags.testTag
import io.element.android.libraries.ui.strings.CommonStrings
import io.element.android.libraries.ui.utils.time.isTalkbackActive
import io.element.android.wysiwyg.link.Link
-import kotlinx.coroutines.ExperimentalCoroutinesApi
-import kotlinx.coroutines.FlowPreview
import kotlinx.coroutines.delay
import kotlinx.coroutines.flow.collectLatest
import kotlinx.coroutines.flow.combine
@@ -225,7 +223,6 @@ private fun MessageShieldDialog(state: TimelineState) {
)
}
-@OptIn(ExperimentalCoroutinesApi::class, FlowPreview::class)
@Composable
private fun TimelinePrefetchingHelper(
lazyListState: LazyListState,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/a11y/Reactions.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/a11y/Reactions.kt
new file mode 100644
index 0000000000..9da0168b38
--- /dev/null
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/a11y/Reactions.kt
@@ -0,0 +1,61 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.features.messages.impl.timeline.a11y
+
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
+import androidx.compose.ui.res.pluralStringResource
+import androidx.compose.ui.res.stringResource
+import io.element.android.features.messages.impl.R
+import io.element.android.libraries.ui.strings.CommonStrings
+
+@Composable
+@ReadOnlyComposable
+fun a11yReactionAction(
+ emoji: String,
+ userAlreadyReacted: Boolean,
+): String {
+ return if (userAlreadyReacted) {
+ stringResource(id = CommonStrings.a11y_remove_reaction_with, emoji)
+ } else {
+ stringResource(id = CommonStrings.a11y_react_with, emoji)
+ }
+}
+
+@Composable
+@ReadOnlyComposable
+fun a11yReactionDetails(
+ emoji: String,
+ userAlreadyReacted: Boolean,
+ reactionCount: Int,
+): String {
+ val reaction = if (emoji.startsWith("mxc://")) {
+ stringResource(CommonStrings.common_an_image)
+ } else {
+ emoji
+ }
+ return if (userAlreadyReacted) {
+ if (reactionCount == 1) {
+ stringResource(R.string.screen_room_timeline_reaction_you_a11y, reaction)
+ } else {
+ pluralStringResource(
+ R.plurals.screen_room_timeline_reaction_including_you_a11y,
+ reactionCount - 1,
+ reactionCount - 1,
+ reaction,
+ )
+ }
+ } else {
+ pluralStringResource(
+ R.plurals.screen_room_timeline_reaction_a11y,
+ reactionCount,
+ reactionCount,
+ reaction,
+ )
+ }
+}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/ATimelineItemEventRow.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/ATimelineItemEventRow.kt
index 4bcf8df61c..8434242abd 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/ATimelineItemEventRow.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/ATimelineItemEventRow.kt
@@ -21,7 +21,6 @@ internal fun ATimelineItemEventRow(
timelineRoomInfo: TimelineRoomInfo = aTimelineRoomInfo(),
renderReadReceipts: Boolean = false,
isLastOutgoingMessage: Boolean = false,
- isHighlighted: Boolean = false,
timelineProtectionState: TimelineProtectionState = aTimelineProtectionState(),
) = TimelineItemEventRow(
event = event,
@@ -29,7 +28,6 @@ internal fun ATimelineItemEventRow(
renderReadReceipts = renderReadReceipts,
timelineProtectionState = timelineProtectionState,
isLastOutgoingMessage = isLastOutgoingMessage,
- isHighlighted = isHighlighted,
onEventClick = {},
onLongClick = {},
onLinkClick = {},
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageEventBubble.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageEventBubble.kt
index 2b48a99dcd..c8bae78f13 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageEventBubble.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageEventBubble.kt
@@ -7,7 +7,6 @@
package io.element.android.features.messages.impl.timeline.components
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.interaction.MutableInteractionSource
import androidx.compose.foundation.layout.Box
@@ -59,7 +58,6 @@ private val avatarRadius = AvatarSize.TimelineSender.dp / 2
private const val BUBBLE_WIDTH_RATIO = 0.78f
private val MIN_BUBBLE_WIDTH = 80.dp
-@OptIn(ExperimentalFoundationApi::class)
@Composable
fun MessageEventBubble(
state: BubbleState,
@@ -184,7 +182,7 @@ internal fun MessageEventBubblePreview(@PreviewParameter(BubbleStateProvider::cl
contentAlignment = Alignment.Center,
) {
Text(
- text = "${state.groupPosition.javaClass.simpleName} m:${state.isMine.to01()} h:${state.isHighlighted.to01()}",
+ text = "${state.groupPosition.javaClass.simpleName} isMine:${state.isMine.to01()}",
style = ElementTheme.typography.fontBodyXsRegular,
)
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageShieldView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageShieldView.kt
index c2d2c3a3de..9d7d4caac5 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageShieldView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageShieldView.kt
@@ -80,6 +80,7 @@ internal fun MessageShield.toText(): String {
is MessageShield.UnverifiedIdentity -> CommonStrings.event_shield_reason_unverified_identity
is MessageShield.SentInClear -> CommonStrings.event_shield_reason_sent_in_clear
is MessageShield.VerificationViolation -> CommonStrings.event_shield_reason_previously_verified
+ is MessageShield.MismatchedSender -> CommonStrings.event_shield_mismatched_sender
}
)
}
@@ -91,7 +92,8 @@ internal fun MessageShield.toIcon(): ImageVector {
is MessageShield.UnknownDevice,
is MessageShield.UnsignedDevice,
is MessageShield.UnverifiedIdentity,
- is MessageShield.VerificationViolation -> CompoundIcons.HelpSolid()
+ is MessageShield.VerificationViolation,
+ is MessageShield.MismatchedSender -> CompoundIcons.HelpSolid()
is MessageShield.SentInClear -> CompoundIcons.LockOff()
}
}
@@ -122,6 +124,9 @@ internal fun MessageShieldViewPreview() {
MessageShieldView(
shield = MessageShield.VerificationViolation(false)
)
+ MessageShieldView(
+ shield = MessageShield.MismatchedSender(false)
+ )
}
}
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageStateEventContainer.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageStateEventContainer.kt
index 010132b47a..ac9be4de74 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageStateEventContainer.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessageStateEventContainer.kt
@@ -7,12 +7,8 @@
package io.element.android.features.messages.impl.timeline.components
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.interaction.MutableInteractionSource
-import androidx.compose.foundation.layout.Column
-import androidx.compose.foundation.layout.Spacer
-import androidx.compose.foundation.layout.size
import androidx.compose.foundation.layout.widthIn
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material3.ripple
@@ -28,17 +24,14 @@ import io.element.android.libraries.designsystem.theme.components.Surface
private val CORNER_RADIUS = 8.dp
-@OptIn(ExperimentalFoundationApi::class)
@Composable
fun MessageStateEventContainer(
- @Suppress("UNUSED_PARAMETER") isHighlighted: Boolean,
interactionSource: MutableInteractionSource,
onClick: () -> Unit,
onLongClick: () -> Unit,
modifier: Modifier = Modifier,
content: @Composable () -> Unit = {},
) {
- // Ignore isHighlighted for now, we need a design decision on it.
val backgroundColor = Color.Transparent
val shape = RoundedCornerShape(CORNER_RADIUS)
Surface(
@@ -60,22 +53,9 @@ fun MessageStateEventContainer(
@PreviewsDayNight
@Composable
internal fun MessageStateEventContainerPreview() = ElementPreview {
- Column {
- MessageStateEventContainer(
- isHighlighted = false,
- interactionSource = remember { MutableInteractionSource() },
- onClick = {},
- onLongClick = {},
- ) {
- Spacer(modifier = Modifier.size(width = 120.dp, height = 32.dp))
- }
- MessageStateEventContainer(
- isHighlighted = true,
- interactionSource = remember { MutableInteractionSource() },
- onClick = {},
- onLongClick = {},
- ) {
- Spacer(modifier = Modifier.size(width = 120.dp, height = 32.dp))
- }
- }
+ MessageStateEventContainer(
+ interactionSource = remember { MutableInteractionSource() },
+ onClick = {},
+ onLongClick = {},
+ )
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessagesReactionButton.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessagesReactionButton.kt
index dec03748ce..b0026fb449 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessagesReactionButton.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/MessagesReactionButton.kt
@@ -9,7 +9,6 @@ package io.element.android.features.messages.impl.timeline.components
import androidx.annotation.DrawableRes
import androidx.compose.foundation.BorderStroke
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.border
import androidx.compose.foundation.combinedClickable
@@ -30,12 +29,17 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.res.stringResource
+import androidx.compose.ui.semantics.clearAndSetSemantics
+import androidx.compose.ui.semantics.contentDescription
+import androidx.compose.ui.semantics.onClick
import androidx.compose.ui.tooling.preview.PreviewParameter
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import coil3.compose.AsyncImage
import io.element.android.compound.theme.ElementTheme
import io.element.android.features.messages.impl.R
+import io.element.android.features.messages.impl.timeline.a11y.a11yReactionAction
+import io.element.android.features.messages.impl.timeline.a11y.a11yReactionDetails
import io.element.android.features.messages.impl.timeline.model.AggregatedReaction
import io.element.android.features.messages.impl.timeline.model.AggregatedReactionProvider
import io.element.android.features.messages.impl.timeline.model.aTimelineItemReactions
@@ -50,7 +54,6 @@ import io.element.android.libraries.matrix.api.media.MediaSource
import io.element.android.libraries.matrix.ui.media.MediaRequestData
@Composable
-@OptIn(ExperimentalFoundationApi::class)
@Suppress("ModifierClickableOrder") // This is needed to display the right ripple shape
fun MessagesReactionButton(
onClick: () -> Unit,
@@ -70,6 +73,27 @@ fun MessagesReactionButton(
buttonColor
}
+ val a11yText = when (content) {
+ is MessagesReactionsButtonContent.Icon -> stringResource(id = R.string.screen_room_timeline_add_reaction)
+ is MessagesReactionsButtonContent.Text -> content.text
+ is MessagesReactionsButtonContent.Reaction -> {
+ a11yReactionDetails(
+ emoji = content.reaction.key,
+ userAlreadyReacted = content.isHighlighted,
+ reactionCount = content.reaction.count,
+ )
+ }
+ }
+
+ val a11yClickLabel = if (content is MessagesReactionsButtonContent.Reaction) {
+ a11yReactionAction(
+ emoji = content.reaction.key,
+ userAlreadyReacted = content.isHighlighted
+ )
+ } else {
+ ""
+ }
+
Surface(
modifier = modifier
.background(Color.Transparent)
@@ -88,7 +112,18 @@ fun MessagesReactionButton(
// Inner border, to highlight when selected
.border(BorderStroke(1.dp, borderColor), RoundedCornerShape(corner = CornerSize(12.dp)))
.background(buttonColor, RoundedCornerShape(corner = CornerSize(12.dp)))
- .padding(vertical = 4.dp, horizontal = 10.dp),
+ .padding(vertical = 4.dp, horizontal = 10.dp)
+ .clearAndSetSemantics {
+ contentDescription = a11yText
+ if (content is MessagesReactionsButtonContent.Reaction) {
+ onClick(
+ label = a11yClickLabel
+ ) {
+ onClick()
+ true
+ }
+ }
+ },
color = buttonColor
) {
when (content) {
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemCallNotifyView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemCallNotifyView.kt
index 1386a5a666..ed26d6558e 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemCallNotifyView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemCallNotifyView.kt
@@ -7,7 +7,6 @@
package io.element.android.features.messages.impl.timeline.components
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.border
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.layout.Arrangement
@@ -39,7 +38,6 @@ import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.text.toDp
import io.element.android.libraries.ui.strings.CommonStrings
-@OptIn(ExperimentalFoundationApi::class)
@Composable
internal fun TimelineItemCallNotifyView(
event: TimelineItem.Event,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemEventRow.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemEventRow.kt
index 55ee0d7a4f..18d0658dd6 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemEventRow.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemEventRow.kt
@@ -32,7 +32,6 @@ import androidx.compose.runtime.movableContentOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Alignment
-import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.platform.LocalViewConfiguration
@@ -120,7 +119,6 @@ fun TimelineItemEventRow(
timelineProtectionState: TimelineProtectionState,
renderReadReceipts: Boolean,
isLastOutgoingMessage: Boolean,
- isHighlighted: Boolean,
onEventClick: () -> Unit,
onLongClick: () -> Unit,
onLinkClick: (Link) -> Unit,
@@ -196,7 +194,6 @@ fun TimelineItemEventRow(
TimelineItemEventRowContent(
event = event,
timelineProtectionState = timelineProtectionState,
- isHighlighted = isHighlighted,
timelineRoomInfo = timelineRoomInfo,
interactionSource = interactionSource,
onContentClick = onContentClick,
@@ -230,7 +227,6 @@ fun TimelineItemEventRow(
TimelineItemEventRowContent(
event = event,
timelineProtectionState = timelineProtectionState,
- isHighlighted = isHighlighted,
timelineRoomInfo = timelineRoomInfo,
interactionSource = interactionSource,
onContentClick = onContentClick,
@@ -281,12 +277,10 @@ private fun SwipeSensitivity(
}
}
-@OptIn(ExperimentalComposeUiApi::class)
@Composable
private fun TimelineItemEventRowContent(
event: TimelineItem.Event,
timelineProtectionState: TimelineProtectionState,
- isHighlighted: Boolean,
timelineRoomInfo: TimelineRoomInfo,
interactionSource: MutableInteractionSource,
onContentClick: () -> Unit,
@@ -340,7 +334,6 @@ private fun TimelineItemEventRowContent(
val bubbleState = BubbleState(
groupPosition = event.groupPosition,
isMine = event.isMine,
- isHighlighted = isHighlighted,
timelineRoomInfo = timelineRoomInfo,
)
MessageEventBubble(
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemRow.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemRow.kt
index 771940da0b..c537c89b6d 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemRow.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemRow.kt
@@ -7,7 +7,6 @@
package io.element.android.features.messages.impl.timeline.components
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxWidth
@@ -21,6 +20,7 @@ import androidx.compose.ui.geometry.Size
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.semantics.contentDescription
+import androidx.compose.ui.semantics.isTraversalGroup
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
@@ -32,6 +32,7 @@ import io.element.android.features.messages.impl.timeline.components.layout.Cont
import io.element.android.features.messages.impl.timeline.model.TimelineItem
import io.element.android.features.messages.impl.timeline.model.event.TimelineItemCallNotifyContent
import io.element.android.features.messages.impl.timeline.model.event.TimelineItemLegacyCallInviteContent
+import io.element.android.features.messages.impl.timeline.model.event.TimelineItemPollContent
import io.element.android.features.messages.impl.timeline.model.event.TimelineItemStateContent
import io.element.android.features.messages.impl.timeline.model.event.TimelineItemVoiceContent
import io.element.android.features.messages.impl.timeline.protection.TimelineProtectionEvent
@@ -48,7 +49,6 @@ import io.element.android.libraries.ui.utils.time.isTalkbackActive
import io.element.android.wysiwyg.link.Link
import kotlin.time.DurationUnit
-@OptIn(ExperimentalFoundationApi::class)
@Composable
internal fun TimelineItemRow(
timelineItem: TimelineItem,
@@ -113,7 +113,6 @@ internal fun TimelineItemRow(
event = timelineItem,
renderReadReceipts = renderReadReceipts,
isLastOutgoingMessage = isLastOutgoingMessage,
- isHighlighted = timelineItem.isEvent(focusedEventId),
onClick = { onContentClick(timelineItem) },
onReadReceiptsClick = onReadReceiptClick,
onLongClick = { onLongClick(timelineItem) },
@@ -140,6 +139,8 @@ internal fun TimelineItemRow(
} else {
timelineItem.safeSenderName
}
+ // For Polls, allow the answers to be traversed by Talkback
+ isTraversalGroup = timelineItem.content is TimelineItemPollContent
}
// Custom clickable that applies over the whole item for accessibility
.then(
@@ -157,7 +158,6 @@ internal fun TimelineItemRow(
renderReadReceipts = renderReadReceipts,
timelineProtectionState = timelineProtectionState,
isLastOutgoingMessage = isLastOutgoingMessage,
- isHighlighted = timelineItem.isEvent(focusedEventId),
onEventClick = { onContentClick(timelineItem) },
onLongClick = { onLongClick(timelineItem) },
onLinkClick = onLinkClick,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemStateEventRow.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemStateEventRow.kt
index 6bd0e24908..2f66d586a9 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemStateEventRow.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemStateEventRow.kt
@@ -40,7 +40,6 @@ fun TimelineItemStateEventRow(
event: TimelineItem.Event,
renderReadReceipts: Boolean,
isLastOutgoingMessage: Boolean,
- isHighlighted: Boolean,
onClick: () -> Unit,
onLongClick: () -> Unit,
onReadReceiptsClick: (event: TimelineItem.Event) -> Unit,
@@ -60,7 +59,6 @@ fun TimelineItemStateEventRow(
contentAlignment = Alignment.Center
) {
MessageStateEventContainer(
- isHighlighted = isHighlighted,
interactionSource = interactionSource,
onClick = onClick,
onLongClick = onLongClick,
@@ -107,7 +105,6 @@ internal fun TimelineItemStateEventRowPreview() = ElementPreview {
),
renderReadReceipts = true,
isLastOutgoingMessage = false,
- isHighlighted = false,
onClick = {},
onLongClick = {},
onReadReceiptsClick = {},
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemVirtualRow.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemVirtualRow.kt
index 2507fb9f01..45b167b68f 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemVirtualRow.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/TimelineItemVirtualRow.kt
@@ -41,7 +41,16 @@ fun TimelineItemVirtualRow(
when (virtual.model) {
is TimelineItemDaySeparatorModel -> TimelineItemDaySeparatorView(virtual.model)
TimelineItemReadMarkerModel -> TimelineItemReadMarkerView()
- TimelineItemRoomBeginningModel -> TimelineItemRoomBeginningView(roomName = timelineRoomInfo.name)
+ TimelineItemRoomBeginningModel -> {
+ TimelineItemRoomBeginningView(
+ predecessorRoom = timelineRoomInfo.predecessorRoom,
+ roomName = timelineRoomInfo.name,
+ isDm = timelineRoomInfo.isDm,
+ onPredecessorRoomClick = { roomId ->
+ eventSink(TimelineEvents.NavigateToRoom(roomId))
+ },
+ )
+ }
is TimelineItemLoadingIndicatorModel -> {
TimelineLoadingMoreIndicator(virtual.model.direction)
val latestEventSink by rememberUpdatedState(eventSink)
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/customreaction/EmojiItem.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/customreaction/EmojiItem.kt
index a27de9c324..b6ad695aa8 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/customreaction/EmojiItem.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/customreaction/EmojiItem.kt
@@ -22,7 +22,6 @@ import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
-import androidx.compose.ui.res.stringResource
import androidx.compose.ui.semantics.clearAndSetSemantics
import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.unit.TextUnit
@@ -30,11 +29,11 @@ import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import io.element.android.compound.theme.ElementTheme
import io.element.android.emojibasebindings.Emoji
+import io.element.android.features.messages.impl.timeline.a11y.a11yReactionAction
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.text.toDp
import io.element.android.libraries.designsystem.theme.components.Text
-import io.element.android.libraries.ui.strings.CommonStrings
@Composable
fun EmojiItem(
@@ -49,11 +48,10 @@ fun EmojiItem(
} else {
Color.Transparent
}
- val description = if (isSelected) {
- stringResource(id = CommonStrings.a11y_remove_reaction_with, item.unicode)
- } else {
- stringResource(id = CommonStrings.a11y_react_with, item.unicode)
- }
+ val description = a11yReactionAction(
+ emoji = item.unicode,
+ userAlreadyReacted = isSelected,
+ )
Box(
modifier = modifier
.sizeIn(minWidth = 40.dp, minHeight = 40.dp)
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemImageView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemImageView.kt
index d419197146..41d3873a65 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemImageView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemImageView.kt
@@ -8,7 +8,6 @@
package io.element.android.features.messages.impl.timeline.components.event
import android.text.SpannedString
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.layout.Column
@@ -57,7 +56,6 @@ import io.element.android.libraries.ui.utils.time.isTalkbackActive
import io.element.android.wysiwyg.compose.EditorStyledText
import io.element.android.wysiwyg.link.Link
-@OptIn(ExperimentalFoundationApi::class)
@Composable
fun TimelineItemImageView(
content: TimelineItemImageContent,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemStickerView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemStickerView.kt
index daabcba4d5..dd16f2faf3 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemStickerView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemStickerView.kt
@@ -7,7 +7,6 @@
package io.element.android.features.messages.impl.timeline.components.event
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.layout.Column
@@ -39,7 +38,6 @@ import io.element.android.libraries.ui.strings.CommonStrings
private const val STICKER_SIZE_IN_DP = 128
-@OptIn(ExperimentalFoundationApi::class)
@Composable
fun TimelineItemStickerView(
content: TimelineItemStickerContent,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemVideoView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemVideoView.kt
index edd37d0b5c..18a59325d5 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemVideoView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemVideoView.kt
@@ -8,7 +8,6 @@
package io.element.android.features.messages.impl.timeline.components.event
import android.text.SpannedString
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.Image
import androidx.compose.foundation.background
import androidx.compose.foundation.combinedClickable
@@ -67,7 +66,6 @@ import io.element.android.libraries.ui.utils.time.isTalkbackActive
import io.element.android.wysiwyg.compose.EditorStyledText
import io.element.android.wysiwyg.link.Link
-@OptIn(ExperimentalFoundationApi::class)
@Composable
fun TimelineItemVideoView(
content: TimelineItemVideoContent,
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/reactionsummary/ReactionSummaryView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/reactionsummary/ReactionSummaryView.kt
index b1aa726628..c14d792252 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/reactionsummary/ReactionSummaryView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/reactionsummary/ReactionSummaryView.kt
@@ -27,6 +27,7 @@ import androidx.compose.foundation.lazy.items
import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.foundation.pager.HorizontalPager
import androidx.compose.foundation.pager.rememberPagerState
+import androidx.compose.foundation.selection.selectable
import androidx.compose.foundation.shape.CornerSize
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material3.ExperimentalMaterial3Api
@@ -45,12 +46,17 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.semantics.Role
+import androidx.compose.ui.semantics.clearAndSetSemantics
+import androidx.compose.ui.semantics.contentDescription
+import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.PreviewParameter
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import coil3.compose.AsyncImage
import io.element.android.compound.theme.ElementTheme
+import io.element.android.features.messages.impl.timeline.a11y.a11yReactionDetails
import io.element.android.features.messages.impl.timeline.components.REACTION_IMAGE_ASPECT_RATIO
import io.element.android.features.messages.impl.timeline.model.AggregatedReaction
import io.element.android.libraries.designsystem.components.avatar.Avatar
@@ -140,9 +146,7 @@ private fun ReactionSummaryViewContent(
HorizontalPager(state = pagerState) { page ->
LazyColumn(modifier = Modifier.fillMaxHeight()) {
items(summary.reactions[page].senders) { sender ->
-
val user = sender.user ?: MatrixUser(userId = sender.senderId)
-
SenderRow(
avatarData = user.getAvatarData(AvatarSize.UserListItem),
name = user.displayName ?: user.userId.value,
@@ -166,21 +170,32 @@ private fun AggregatedReactionButton(
} else {
Color.Transparent
}
-
val textColor = if (isHighlighted) {
MaterialTheme.colorScheme.inversePrimary
} else {
ElementTheme.colors.textPrimary
}
-
val roundedCornerShape = RoundedCornerShape(corner = CornerSize(percent = 50))
+ val a11yText = a11yReactionDetails(
+ emoji = reaction.key,
+ userAlreadyReacted = reaction.isHighlighted,
+ reactionCount = reaction.count,
+ )
Surface(
modifier = Modifier
.background(buttonColor, roundedCornerShape)
.clip(roundedCornerShape)
.clickable(onClick = onClick)
- .padding(vertical = 8.dp, horizontal = 12.dp),
- color = buttonColor
+ .padding(vertical = 8.dp, horizontal = 12.dp)
+ .selectable(
+ selected = isHighlighted,
+ role = Role.Tab,
+ onClick = onClick,
+ )
+ .clearAndSetSemantics {
+ contentDescription = a11yText
+ },
+ color = buttonColor,
) {
Row(
verticalAlignment = Alignment.CenterVertically,
@@ -230,7 +245,8 @@ private fun SenderRow(
modifier = Modifier
.fillMaxWidth()
.heightIn(min = 56.dp)
- .padding(start = 16.dp, top = 4.dp, end = 16.dp, bottom = 4.dp),
+ .padding(start = 16.dp, top = 4.dp, end = 16.dp, bottom = 4.dp)
+ .semantics(mergeDescendants = true) {},
verticalAlignment = Alignment.CenterVertically
) {
Avatar(avatarData)
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/virtual/TimelineItemRoomBeginningView.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/virtual/TimelineItemRoomBeginningView.kt
index 645f36602c..72035cdc3d 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/virtual/TimelineItemRoomBeginningView.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/components/virtual/TimelineItemRoomBeginningView.kt
@@ -7,6 +7,7 @@
package io.element.android.features.messages.impl.timeline.components.virtual
+import androidx.compose.foundation.layout.Arrangement.spacedBy
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxWidth
@@ -19,44 +20,83 @@ import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import io.element.android.compound.theme.ElementTheme
import io.element.android.features.messages.impl.R
+import io.element.android.libraries.designsystem.atomic.molecules.ComposerAlertMolecule
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
+import io.element.android.libraries.designsystem.text.toAnnotatedString
import io.element.android.libraries.designsystem.theme.components.Text
+import io.element.android.libraries.designsystem.utils.allBooleans
+import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
@Composable
fun TimelineItemRoomBeginningView(
roomName: String?,
+ predecessorRoom: PredecessorRoom?,
+ isDm: Boolean,
+ onPredecessorRoomClick: (RoomId) -> Unit,
modifier: Modifier = Modifier
) {
- Box(
- modifier = modifier
- .fillMaxWidth()
- .padding(horizontal = 16.dp, vertical = 8.dp),
- contentAlignment = Alignment.Center,
+ Column(
+ modifier = modifier.fillMaxWidth()
) {
- val text = if (roomName == null) {
- stringResource(id = R.string.screen_room_timeline_beginning_of_room_no_name)
- } else {
- stringResource(id = R.string.screen_room_timeline_beginning_of_room, roomName)
+ if (predecessorRoom != null) {
+ ComposerAlertMolecule(
+ avatar = null,
+ content = stringResource(R.string.screen_room_timeline_upgraded_room_message).toAnnotatedString(),
+ onSubmitClick = { onPredecessorRoomClick(predecessorRoom.roomId) },
+ isCritical = false,
+ submitText = stringResource(R.string.screen_room_timeline_upgraded_room_action)
+ )
+ }
+ // Only display for non-DM room
+ if (!isDm) {
+ Box(
+ modifier = Modifier
+ .fillMaxWidth()
+ .padding(horizontal = 16.dp, vertical = 8.dp),
+ contentAlignment = Alignment.Center,
+ ) {
+ val text = if (roomName == null) {
+ stringResource(id = R.string.screen_room_timeline_beginning_of_room_no_name)
+ } else {
+ stringResource(id = R.string.screen_room_timeline_beginning_of_room, roomName)
+ }
+ Text(
+ color = ElementTheme.colors.textSecondary,
+ style = ElementTheme.typography.fontBodyMdRegular,
+ text = text,
+ textAlign = TextAlign.Center,
+ )
+ }
}
- Text(
- color = ElementTheme.colors.textSecondary,
- style = ElementTheme.typography.fontBodyMdRegular,
- text = text,
- textAlign = TextAlign.Center,
- )
}
}
@PreviewsDayNight
@Composable
internal fun TimelineItemRoomBeginningViewPreview() = ElementPreview {
- Column {
- TimelineItemRoomBeginningView(
- roomName = null,
- )
- TimelineItemRoomBeginningView(
- roomName = "Room Name",
- )
+ Column(verticalArrangement = spacedBy(16.dp)) {
+ allBooleans.forEach { isDm ->
+ TimelineItemRoomBeginningView(
+ predecessorRoom = null,
+ roomName = null,
+ isDm = isDm,
+ onPredecessorRoomClick = {},
+ )
+ TimelineItemRoomBeginningView(
+ predecessorRoom = null,
+ roomName = "Room Name",
+ isDm = isDm,
+ onPredecessorRoomClick = {},
+ )
+ TimelineItemRoomBeginningView(
+ predecessorRoom = PredecessorRoom(RoomId("!roomId:matrix.org"), EventId("\$eventId:matrix.org")),
+ roomName = "Room Name",
+ isDm = isDm,
+ onPredecessorRoomClick = {},
+ )
+ }
}
}
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleState.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleState.kt
index 07219f4281..81aa459413 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleState.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleState.kt
@@ -13,7 +13,6 @@ import io.element.android.features.messages.impl.timeline.model.TimelineItemGrou
data class BubbleState(
val groupPosition: TimelineItemGroupPosition,
val isMine: Boolean,
- val isHighlighted: Boolean,
val timelineRoomInfo: TimelineRoomInfo,
) {
/** True to cut out the top start corner of the bubble, to give margin for the sender avatar. */
diff --git a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleStateProvider.kt b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleStateProvider.kt
index 97b69b1f64..02a6e19504 100644
--- a/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleStateProvider.kt
+++ b/features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/timeline/model/bubble/BubbleStateProvider.kt
@@ -21,15 +21,11 @@ open class BubbleStateProvider : PreviewParameterProvider {
TimelineItemGroupPosition.None,
).map { groupPosition ->
sequenceOf(false, true).map { isMine ->
- sequenceOf(false, true).map { isHighlighted ->
- aBubbleState(
- groupPosition = groupPosition,
- isMine = isMine,
- isHighlighted = isHighlighted,
- )
- }
+ aBubbleState(
+ groupPosition = groupPosition,
+ isMine = isMine,
+ )
}
- .flatten()
}
.flatten()
}
@@ -37,11 +33,9 @@ open class BubbleStateProvider : PreviewParameterProvider {
internal fun aBubbleState(
groupPosition: TimelineItemGroupPosition = TimelineItemGroupPosition.First,
isMine: Boolean = false,
- isHighlighted: Boolean = false,
timelineRoomInfo: TimelineRoomInfo = aTimelineRoomInfo(),
) = BubbleState(
groupPosition = groupPosition,
isMine = isMine,
- isHighlighted = isHighlighted,
timelineRoomInfo = timelineRoomInfo,
)
diff --git a/features/messages/impl/src/main/res/values-cs/translations.xml b/features/messages/impl/src/main/res/values-cs/translations.xml
index af33e7376d..3b43f897e2 100644
--- a/features/messages/impl/src/main/res/values-cs/translations.xml
+++ b/features/messages/impl/src/main/res/values-cs/translations.xml
@@ -43,6 +43,10 @@
- "%1$d změny místnosti"
- "%1$d změn místnosti"
+ "Přejít do nové místnosti"
+ "Tato místnost byla nahrazena a již není aktivní"
+ "Zobrazit staré zprávy"
+ "Tato místnost je pokračováním jiné místnosti"
- "%1$s, %2$s a %3$d další"
- "%1$s, %2$s a %3$d další"
diff --git a/features/messages/impl/src/main/res/values-es/translations.xml b/features/messages/impl/src/main/res/values-es/translations.xml
index f078bf28d7..54b15f66a5 100644
--- a/features/messages/impl/src/main/res/values-es/translations.xml
+++ b/features/messages/impl/src/main/res/values-es/translations.xml
@@ -9,8 +9,8 @@
"Viajes y lugares"
"Símbolos"
"Bloquear usuario"
- "Marque si quieres ocultar todos los mensajes actuales y futuros de este usuario"
- "Este mensaje se notificará al administrador de su homeserver. No podrán leer ningún mensaje cifrado."
+ "Marca esta casilla si quieres ocultar todos los mensajes actuales y futuros de este usuario"
+ "Se denunciará este mensaje al administrador de tu servidor base. No será capaz de leer ningún mensaje cifrado."
"Motivo para denunciar este contenido"
"Cámara"
"Hacer foto"
diff --git a/features/messages/impl/src/main/res/values-fr/translations.xml b/features/messages/impl/src/main/res/values-fr/translations.xml
index 132d175eb8..2f45ed5e56 100644
--- a/features/messages/impl/src/main/res/values-fr/translations.xml
+++ b/features/messages/impl/src/main/res/values-fr/translations.xml
@@ -35,6 +35,15 @@
"Afficher moins"
"Message copié"
"Vous n’êtes pas autorisé à publier dans ce salon"
+
+ - "%1$d membre a réagi avec %2$s"
+ - "%1$d membres ont réagi avec %2$s"
+
+
+ - "Vous et %1$d membre avez réagi avec %2$s"
+ - "Vous et %1$d membres avez réagi avec %2$s"
+
+ "Vous avez réagi avec %1$s"
"Afficher moins"
"Afficher plus"
"Nouveau"
diff --git a/features/messages/impl/src/main/res/values-nb/translations.xml b/features/messages/impl/src/main/res/values-nb/translations.xml
index beb88017f2..f5fb2229fa 100644
--- a/features/messages/impl/src/main/res/values-nb/translations.xml
+++ b/features/messages/impl/src/main/res/values-nb/translations.xml
@@ -35,6 +35,15 @@
"Vis mindre"
"Melding kopiert"
"Du har ikke tillatelse til å legge ut innlegg i dette rommet"
+
+ - "%1$d medlem reagerte med %2$s"
+ - "%1$d medlemmer reagerte med %2$s"
+
+
+ - "Du og %1$d medlem reagerte med%2$s"
+ - "Du og %1$d medlemmer reagerte med%2$s"
+
+ "Du reagerte med %1$s"
"Vis mindre"
"Vis mer"
"Ny"
diff --git a/features/messages/impl/src/main/res/values/localazy.xml b/features/messages/impl/src/main/res/values/localazy.xml
index 73d266f799..984eb1231f 100644
--- a/features/messages/impl/src/main/res/values/localazy.xml
+++ b/features/messages/impl/src/main/res/values/localazy.xml
@@ -28,13 +28,22 @@
"Everyone"
"Send again"
"Your message failed to send"
- "Add emoji"
+ "Add a reaction"
"This is the beginning of %1$s."
"This is the beginning of this conversation."
"Unsupported call. Ask if the caller can use the new Element X app."
"Show less"
"Message copied"
"You do not have permission to post to this room"
+
+ - "%1$d member reacted with %2$s"
+ - "%1$d members reacted with %2$s"
+
+
+ - "You and %1$d member reacted with %2$s"
+ - "You and %1$d members reacted with %2$s"
+
+ "You reacted with %1$s"
"Show less"
"Show more"
"New"
@@ -42,6 +51,10 @@
- "%1$d room change"
- "%1$d room changes"
+ "Jump to new room"
+ "This room has been replaced and is no longer active"
+ "See old messages"
+ "This room is a continuation of another room"
- "%1$s, %2$s and %3$d other"
- "%1$s, %2$s and %3$d others"
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/FakeMessagesNavigator.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/FakeMessagesNavigator.kt
index 92fc0d8171..32638d7b8d 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/FakeMessagesNavigator.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/FakeMessagesNavigator.kt
@@ -9,6 +9,7 @@ package io.element.android.features.messages.impl
import io.element.android.features.messages.impl.attachments.Attachment
import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.timeline.item.TimelineItemDebugInfo
import io.element.android.tests.testutils.lambda.lambdaError
@@ -20,6 +21,7 @@ class FakeMessagesNavigator(
private val onReportContentClickLambda: (eventId: EventId, senderId: UserId) -> Unit = { _, _ -> lambdaError() },
private val onEditPollClickLambda: (eventId: EventId) -> Unit = { _ -> lambdaError() },
private val onPreviewAttachmentLambda: (attachments: ImmutableList) -> Unit = { _ -> lambdaError() },
+ private val onNavigateToRoomLambda: (roomId: RoomId) -> Unit = { _ -> lambdaError() }
) : MessagesNavigator {
override fun onShowEventDebugInfoClick(eventId: EventId?, debugInfo: TimelineItemDebugInfo) {
onShowEventDebugInfoClickLambda(eventId, debugInfo)
@@ -40,4 +42,8 @@ class FakeMessagesNavigator(
override fun onPreviewAttachment(attachments: ImmutableList) {
onPreviewAttachmentLambda(attachments)
}
+
+ override fun onNavigateToRoom(roomId: RoomId) {
+ onNavigateToRoomLambda(roomId)
+ }
}
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesPresenterTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesPresenterTest.kt
index e42941da0d..f24175c33e 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesPresenterTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesPresenterTest.kt
@@ -50,6 +50,7 @@ import io.element.android.libraries.featureflag.api.FeatureFlagService
import io.element.android.libraries.featureflag.api.FeatureFlags
import io.element.android.libraries.featureflag.test.FakeFeatureFlagService
import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.encryption.identity.IdentityState
import io.element.android.libraries.matrix.api.media.MediaSource
@@ -57,6 +58,7 @@ import io.element.android.libraries.matrix.api.permalink.PermalinkParser
import io.element.android.libraries.matrix.api.room.MessageEventType
import io.element.android.libraries.matrix.api.room.RoomMembersState
import io.element.android.libraries.matrix.api.room.RoomMembershipState
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.matrix.api.timeline.item.TimelineItemDebugInfo
import io.element.android.libraries.matrix.api.timeline.item.event.EventOrTransactionId
import io.element.android.libraries.matrix.api.timeline.item.event.toEventOrTransactionId
@@ -117,9 +119,9 @@ class MessagesPresenterTest {
presenter.testWithLifecycleOwner {
val initialState = consumeItemsUntilTimeout().last()
assertThat(initialState.roomId).isEqualTo(A_ROOM_ID)
- assertThat(initialState.roomName).isEqualTo(AsyncData.Success(""))
+ assertThat(initialState.roomName).isEqualTo("")
assertThat(initialState.roomAvatar)
- .isEqualTo(AsyncData.Success(AvatarData(id = A_ROOM_ID.value, name = "", url = AN_AVATAR_URL, size = AvatarSize.TimelineRoom)))
+ .isEqualTo(AvatarData(id = A_ROOM_ID.value, name = "", url = AN_AVATAR_URL, size = AvatarSize.TimelineRoom))
assertThat(initialState.userEventPermissions.canSendMessage).isTrue()
assertThat(initialState.userEventPermissions.canRedactOwn).isTrue()
assertThat(initialState.hasNetworkConnection).isTrue()
@@ -1130,6 +1132,57 @@ class MessagesPresenterTest {
}
}
+ @Test
+ fun `present - room with successor room includes successor info in state`() = runTest {
+ val successorRoomId = RoomId("!successor:server.org")
+ val successorReason = "This room has been moved to a new location"
+ val room = FakeJoinedRoom(
+ baseRoom = FakeBaseRoom(
+ canUserSendMessageResult = { _, _ -> Result.success(true) },
+ canRedactOwnResult = { Result.success(true) },
+ canRedactOtherResult = { Result.success(true) },
+ canUserJoinCallResult = { Result.success(true) },
+ canUserPinUnpinResult = { Result.success(true) },
+ initialRoomInfo = aRoomInfo(
+ successorRoom = SuccessorRoom(
+ roomId = successorRoomId,
+ reason = successorReason
+ )
+ )
+ ),
+ typingNoticeResult = { Result.success(Unit) },
+ )
+ val presenter = createMessagesPresenter(joinedRoom = room)
+ presenter.testWithLifecycleOwner {
+ skipItems(1)
+ val initialState = awaitItem()
+ assertThat(initialState.successorRoom).isNotNull()
+ assertThat(initialState.successorRoom?.roomId).isEqualTo(successorRoomId)
+ assertThat(initialState.successorRoom?.reason).isEqualTo(successorReason)
+ }
+ }
+
+ @Test
+ fun `present - room without successor room has null successor info in state`() = runTest {
+ val room = FakeJoinedRoom(
+ baseRoom = FakeBaseRoom(
+ canUserSendMessageResult = { _, _ -> Result.success(true) },
+ canRedactOwnResult = { Result.success(true) },
+ canRedactOtherResult = { Result.success(true) },
+ canUserJoinCallResult = { Result.success(true) },
+ canUserPinUnpinResult = { Result.success(true) },
+ initialRoomInfo = aRoomInfo(successorRoom = null)
+ ),
+ typingNoticeResult = { Result.success(Unit) },
+ )
+ val presenter = createMessagesPresenter(joinedRoom = room)
+ presenter.testWithLifecycleOwner {
+ skipItems(1)
+ val initialState = awaitItem()
+ assertThat(initialState.successorRoom).isNull()
+ }
+ }
+
@Test
fun `present - when room is encrypted and a DM, the DM user's identity state is fetched onResume`() = runTest {
val room = FakeJoinedRoom(
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesViewTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesViewTest.kt
index 4f6ac91890..51f5640ece 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesViewTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/MessagesViewTest.kt
@@ -52,7 +52,9 @@ import io.element.android.features.messages.impl.timeline.components.receipt.aRe
import io.element.android.features.messages.impl.timeline.components.receipt.bottomsheet.ReadReceiptBottomSheetEvents
import io.element.android.features.messages.impl.timeline.model.TimelineItem
import io.element.android.features.messages.impl.timeline.model.event.aTimelineItemTextContent
+import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.matrix.api.timeline.item.event.getAvatarUrl
import io.element.android.libraries.matrix.api.timeline.item.event.getDisplayName
import io.element.android.libraries.matrix.api.user.MatrixUser
@@ -65,6 +67,7 @@ import io.element.android.tests.testutils.EnsureNeverCalledWithParam
import io.element.android.tests.testutils.EnsureNeverCalledWithTwoParams
import io.element.android.tests.testutils.EnsureNeverCalledWithTwoParamsAndResult
import io.element.android.tests.testutils.EventsRecorder
+import io.element.android.tests.testutils.assertNoNodeWithText
import io.element.android.tests.testutils.clickOn
import io.element.android.tests.testutils.ensureCalledOnce
import io.element.android.tests.testutils.pressBack
@@ -107,7 +110,7 @@ class MessagesViewTest {
state = state,
onRoomDetailsClick = callback,
)
- rule.onNodeWithText(state.roomName.dataOrNull().orEmpty(), useUnmergedTree = true).performClick()
+ rule.onNodeWithText(state.roomName.orEmpty(), useUnmergedTree = true).performClick()
}
}
@@ -391,7 +394,10 @@ class MessagesViewTest {
rule.setMessagesView(
state = state,
)
- rule.onAllNodesWithText("👍️").onFirst().performClick()
+ rule.onAllNodesWithText(
+ text = "👍️",
+ useUnmergedTree = true,
+ ).onFirst().performClick()
eventsRecorder.assertSingle(MessagesEvents.ToggleReaction("👍️", timelineItem.eventOrTransactionId))
}
@@ -411,7 +417,10 @@ class MessagesViewTest {
rule.setMessagesView(
state = state,
)
- rule.onAllNodesWithText("👍️").onFirst().performTouchInput { longClick() }
+ rule.onAllNodesWithText(
+ text = "👍️",
+ useUnmergedTree = true,
+ ).onFirst().performTouchInput { longClick() }
eventsRecorder.assertSingle(ReactionSummaryEvents.ShowReactionSummary(timelineItem.eventId!!, timelineItem.reactionsState.reactions, "👍️"))
}
@@ -554,6 +563,36 @@ class MessagesViewTest {
rule.onNodeWithText("This is a pinned message").performClick()
eventsRecorder.assertSingle(TimelineEvents.FocusOnEvent(AN_EVENT_ID, debounce = FOCUS_ON_PINNED_EVENT_DEBOUNCE_DURATION_IN_MILLIS.milliseconds))
}
+
+ @Test
+ fun `clicking on successor room button emits expected event`() {
+ val eventsRecorder = EventsRecorder()
+ val successorRoomId = RoomId("!successor:server.org")
+ val state = aMessagesState(
+ successorRoom = SuccessorRoom(
+ roomId = successorRoomId,
+ reason = "This room has been upgraded"
+ ),
+ timelineState = aTimelineState(eventSink = eventsRecorder)
+ )
+ rule.setMessagesView(state = state)
+ val text = rule.activity.getString(R.string.screen_room_timeline_tombstoned_room_action)
+ // The bottomsheet subcompose seems to make the node to appear twice
+ rule.onAllNodesWithText(text).onFirst().performClick()
+ eventsRecorder.assertSingle(TimelineEvents.NavigateToRoom(successorRoomId))
+ }
+
+ @Test
+ fun `no banner shown when there is no successor room`() {
+ val eventsRecorder = EventsRecorder(expectEvents = false)
+ val state = aMessagesState(
+ successorRoom = null,
+ eventSink = eventsRecorder
+ )
+ rule.setMessagesView(state = state)
+ rule.assertNoNodeWithText(R.string.screen_room_timeline_tombstoned_room_message)
+ rule.assertNoNodeWithText(R.string.screen_room_timeline_tombstoned_room_action)
+ }
}
private fun AndroidComposeTestRule.setMessagesView(
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenterTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenterTest.kt
index 6e9c525214..a082b36b39 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenterTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/actionlist/ActionListPresenterTest.kt
@@ -81,8 +81,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -124,8 +122,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -167,8 +163,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -262,8 +256,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -405,8 +397,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -500,8 +490,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -525,6 +513,49 @@ class ActionListPresenterTest {
}
}
+ @Test
+ fun `present - compute for my message no permission`() = runTest {
+ val presenter = createActionListPresenter(isDeveloperModeEnabled = true, isPinFeatureEnabled = true)
+ moleculeFlow(RecompositionMode.Immediate) {
+ presenter.present()
+ }.test {
+ val initialState = awaitItem()
+ val messageEvent = aMessageEvent(
+ isMine = true,
+ content = TimelineItemTextContent(body = A_MESSAGE, htmlDocument = null, isEdited = false, formattedBody = A_MESSAGE)
+ )
+ initialState.eventSink.invoke(
+ ActionListEvents.ComputeForMessage(
+ event = messageEvent,
+ userEventPermissions = aUserEventPermissions(
+ canRedactOwn = false,
+ canRedactOther = false,
+ canSendMessage = false,
+ canSendReaction = false,
+ canPinUnpin = false,
+ )
+ )
+ )
+ val successState = awaitItem()
+ assertThat(successState.target).isEqualTo(
+ ActionListState.Target.Success(
+ event = messageEvent,
+ sentTimeFull = "0 Full true",
+ displayEmojiReactions = false,
+ verifiedUserSendFailure = VerifiedUserSendFailure.None,
+ actions = persistentListOf(
+ TimelineItemAction.Forward,
+ TimelineItemAction.CopyLink,
+ TimelineItemAction.CopyText,
+ TimelineItemAction.ViewSource,
+ )
+ )
+ )
+ initialState.eventSink.invoke(ActionListEvents.Clear)
+ assertThat(awaitItem().target).isEqualTo(ActionListState.Target.None)
+ }
+ }
+
@Test
fun `present - compute for a media item`() = runTest {
val presenter = createActionListPresenter(isDeveloperModeEnabled = true, isPinFeatureEnabled = true)
@@ -747,8 +778,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -789,8 +818,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
assertThat(awaitItem().target).isEqualTo(ActionListState.Target.None)
}
}
@@ -818,8 +845,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -866,8 +891,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
@@ -921,8 +944,6 @@ class ActionListPresenterTest {
)
)
)
- // val loadingState = awaitItem()
- // assertThat(loadingState.target).isEqualTo(ActionListState.Target.Loading(messageEvent))
val successState = awaitItem()
assertThat(successState.target).isEqualTo(
ActionListState.Target.Success(
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/FakeComposerDraftService.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/FakeComposerDraftService.kt
index 6fd4172340..d87b11c951 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/FakeComposerDraftService.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/FakeComposerDraftService.kt
@@ -8,12 +8,22 @@
package io.element.android.features.messages.impl.draft
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
class FakeComposerDraftService : ComposerDraftService {
- var loadDraftLambda: (RoomId, Boolean) -> ComposerDraft? = { _, _ -> null }
- override suspend fun loadDraft(roomId: RoomId, isVolatile: Boolean): ComposerDraft? = loadDraftLambda(roomId, isVolatile)
+ var loadDraftLambda: (RoomId, ThreadId?, Boolean) -> ComposerDraft? = { _, _, _ -> null }
+ override suspend fun loadDraft(
+ roomId: RoomId,
+ threadRoot: ThreadId?,
+ isVolatile: Boolean
+ ): ComposerDraft? = loadDraftLambda(roomId, threadRoot, isVolatile)
- var saveDraftLambda: (RoomId, ComposerDraft?, Boolean) -> Unit = { _, _, _ -> }
- override suspend fun updateDraft(roomId: RoomId, draft: ComposerDraft?, isVolatile: Boolean) = saveDraftLambda(roomId, draft, isVolatile)
+ var saveDraftLambda: (RoomId, ThreadId?, ComposerDraft?, Boolean) -> Unit = { _, _, _, _ -> }
+ override suspend fun updateDraft(
+ roomId: RoomId,
+ threadRoot: ThreadId?,
+ draft: ComposerDraft?,
+ isVolatile: Boolean
+ ) = saveDraftLambda(roomId, threadRoot, draft, isVolatile)
}
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStoreTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStoreTest.kt
index 176037358e..9ec43f3621 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStoreTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/draft/VolatileComposerDraftStoreTest.kt
@@ -11,6 +11,7 @@ import com.google.common.truth.Truth.assertThat
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import io.element.android.libraries.matrix.api.room.draft.ComposerDraftType
import io.element.android.libraries.matrix.test.A_ROOM_ID
+import io.element.android.libraries.matrix.test.A_THREAD_ID
import kotlinx.coroutines.test.runTest
import org.junit.Test
@@ -21,27 +22,51 @@ class VolatileComposerDraftStoreTest {
@Test
fun `when storing a non-null draft and then loading it, it's loaded and removed`() = runTest {
- val initialDraft = sut.loadDraft(roomId)
+ val initialDraft = sut.loadDraft(roomId = roomId, threadRoot = null)
assertThat(initialDraft).isNull()
- sut.updateDraft(roomId, draft)
+ sut.updateDraft(roomId = roomId, threadRoot = null, draft = draft)
- val loadedDraft = sut.loadDraft(roomId)
+ val loadedDraft = sut.loadDraft(roomId = roomId, threadRoot = null)
assertThat(loadedDraft).isEqualTo(draft)
- val loadedDraftAfter = sut.loadDraft(roomId)
+ val loadedDraftAfter = sut.loadDraft(roomId = roomId, threadRoot = null)
assertThat(loadedDraftAfter).isNull()
+
+ // In thread:
+ val threadRoot = A_THREAD_ID
+ val initialThreadDraft = sut.loadDraft(roomId = roomId, threadRoot = threadRoot)
+ assertThat(initialThreadDraft).isNull()
+
+ sut.updateDraft(roomId = roomId, threadRoot = threadRoot, draft = draft)
+
+ val loadedThreadDraft = sut.loadDraft(roomId = roomId, threadRoot = threadRoot)
+ assertThat(loadedThreadDraft).isEqualTo(draft)
+
+ val loadedThreadDraftAfter = sut.loadDraft(roomId = roomId, threadRoot = threadRoot)
+ assertThat(loadedThreadDraftAfter).isNull()
}
@Test
fun `when storing a null draft and then loading it, it's removing the previous one`() = runTest {
- val initialDraft = sut.loadDraft(roomId)
+ val initialDraft = sut.loadDraft(roomId = roomId, threadRoot = null)
assertThat(initialDraft).isNull()
- sut.updateDraft(roomId, draft)
- sut.updateDraft(roomId, null)
+ sut.updateDraft(roomId = roomId, threadRoot = null, draft = draft)
+ sut.updateDraft(roomId = roomId, threadRoot = null, draft = null)
- val loadedDraft = sut.loadDraft(roomId)
+ val loadedDraft = sut.loadDraft(roomId = roomId, threadRoot = null)
assertThat(loadedDraft).isNull()
+
+ // In thread:
+ val threadRoot = A_THREAD_ID
+ val initialThreadDraft = sut.loadDraft(roomId = roomId, threadRoot = threadRoot)
+ assertThat(initialThreadDraft).isNull()
+
+ sut.updateDraft(roomId = roomId, threadRoot = threadRoot, draft = draft)
+ sut.updateDraft(roomId = roomId, threadRoot = threadRoot, draft = null)
+
+ val loadedThreadDraft = sut.loadDraft(roomId = roomId, threadRoot = threadRoot)
+ assertThat(loadedThreadDraft).isNull()
}
}
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenterTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenterTest.kt
index f3d815d563..1a7a1d930e 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenterTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/messagecomposer/MessageComposerPresenterTest.kt
@@ -37,6 +37,7 @@ import io.element.android.libraries.featureflag.api.FeatureFlags
import io.element.android.libraries.featureflag.test.FakeFeatureFlagService
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.media.ImageInfo
import io.element.android.libraries.matrix.api.media.VideoInfo
import io.element.android.libraries.matrix.api.permalink.PermalinkBuilder
@@ -178,10 +179,10 @@ class MessageComposerPresenterTest {
@Test
fun `present - change mode to edit`() = runTest {
- val loadDraftLambda = lambdaRecorder { _: RoomId, _: Boolean ->
+ val loadDraftLambda = lambdaRecorder { _: RoomId, _: ThreadId?, _: Boolean ->
ComposerDraft(A_MESSAGE, A_MESSAGE, ComposerDraftType.NewMessage)
}
- val updateDraftLambda = lambdaRecorder { _: RoomId, _: ComposerDraft?, _: Boolean -> }
+ val updateDraftLambda = lambdaRecorder { _: RoomId, _: ThreadId?, _: ComposerDraft?, _: Boolean -> }
val draftService = FakeComposerDraftService().apply {
this.loadDraftLambda = loadDraftLambda
this.saveDraftLambda = updateDraftLambda
@@ -207,23 +208,23 @@ class MessageComposerPresenterTest {
.isCalledExactly(2)
.withSequence(
// Automatic load of draft
- listOf(value(A_ROOM_ID), value(false)),
+ listOf(value(A_ROOM_ID), value(null), value(false)),
// Load of volatile draft when closing edit mode
- listOf(value(A_ROOM_ID), value(true))
+ listOf(value(A_ROOM_ID), value(null), value(true))
)
assert(updateDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), any(), value(true))
+ .with(value(A_ROOM_ID), value(null), any(), value(true))
}
}
@Test
fun `present - change mode to edit caption`() = runTest {
- val loadDraftLambda = lambdaRecorder { _: RoomId, _: Boolean ->
+ val loadDraftLambda = lambdaRecorder { _: RoomId, _: ThreadId?, _: Boolean ->
ComposerDraft(A_MESSAGE, A_MESSAGE, ComposerDraftType.NewMessage)
}
- val updateDraftLambda = lambdaRecorder { _: RoomId, _: ComposerDraft?, _: Boolean -> }
+ val updateDraftLambda = lambdaRecorder { _: RoomId, _: ThreadId?, _: ComposerDraft?, _: Boolean -> }
val draftService = FakeComposerDraftService().apply {
this.loadDraftLambda = loadDraftLambda
this.saveDraftLambda = updateDraftLambda
@@ -249,13 +250,13 @@ class MessageComposerPresenterTest {
.isCalledExactly(2)
.withSequence(
// Automatic load of draft
- listOf(value(A_ROOM_ID), value(false)),
+ listOf(value(A_ROOM_ID), value(null), value(false)),
// Load of volatile draft when closing edit mode
- listOf(value(A_ROOM_ID), value(true))
+ listOf(value(A_ROOM_ID), value(null), value(true))
)
assert(updateDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), any(), value(true))
+ .with(value(A_ROOM_ID), value(null), any(), value(true))
}
}
@@ -303,10 +304,10 @@ class MessageComposerPresenterTest {
@Test
fun `present - change mode to reply after edit`() = runTest {
- val loadDraftLambda = lambdaRecorder { _: RoomId, _: Boolean ->
+ val loadDraftLambda = lambdaRecorder { _: RoomId, _: ThreadId?, _: Boolean ->
ComposerDraft(A_MESSAGE, A_MESSAGE, ComposerDraftType.NewMessage)
}
- val updateDraftLambda = lambdaRecorder { _: RoomId, _: ComposerDraft?, _: Boolean -> }
+ val updateDraftLambda = lambdaRecorder { _: RoomId, _: ThreadId?, _: ComposerDraft?, _: Boolean -> }
val draftService = FakeComposerDraftService().apply {
this.loadDraftLambda = loadDraftLambda
this.saveDraftLambda = updateDraftLambda
@@ -333,11 +334,11 @@ class MessageComposerPresenterTest {
assert(loadDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(false))
+ .with(value(A_ROOM_ID), value(null), value(false))
assert(updateDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), any(), value(true))
+ .with(value(A_ROOM_ID), value(null), any(), value(true))
}
}
@@ -1246,7 +1247,7 @@ class MessageComposerPresenterTest {
@Test
fun `present - when there is no draft, nothing is restored`() = runTest {
- val loadDraftLambda = lambdaRecorder { _, _ -> null }
+ val loadDraftLambda = lambdaRecorder { _, _, _ -> null }
val composerDraftService = FakeComposerDraftService().apply {
this.loadDraftLambda = loadDraftLambda
}
@@ -1257,7 +1258,7 @@ class MessageComposerPresenterTest {
awaitFirstItem()
assert(loadDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(false))
+ .with(value(A_ROOM_ID), value(null), value(false))
ensureAllEventsConsumed()
}
@@ -1265,7 +1266,7 @@ class MessageComposerPresenterTest {
@Test
fun `present - when there is a draft for new message with plain text, it is restored`() = runTest {
- val loadDraftLambda = lambdaRecorder { _, _ ->
+ val loadDraftLambda = lambdaRecorder { _, _, _ ->
ComposerDraft(plainText = A_MESSAGE, htmlText = null, draftType = ComposerDraftType.NewMessage)
}
val composerDraftService = FakeComposerDraftService().apply {
@@ -1286,7 +1287,7 @@ class MessageComposerPresenterTest {
}
assert(loadDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(false))
+ .with(value(A_ROOM_ID), value(null), value(false))
ensureAllEventsConsumed()
}
@@ -1294,7 +1295,7 @@ class MessageComposerPresenterTest {
@Test
fun `present - when there is a draft for new message with rich text, it is restored`() = runTest {
- val loadDraftLambda = lambdaRecorder { _, _ ->
+ val loadDraftLambda = lambdaRecorder { _, _, _ ->
ComposerDraft(
plainText = A_MESSAGE,
htmlText = A_MESSAGE,
@@ -1320,14 +1321,14 @@ class MessageComposerPresenterTest {
}
assert(loadDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(false))
+ .with(value(A_ROOM_ID), value(null), value(false))
ensureAllEventsConsumed()
}
}
@Test
fun `present - when there is a draft for edit, it is restored`() = runTest {
- val loadDraftLambda = lambdaRecorder { _, _ ->
+ val loadDraftLambda = lambdaRecorder { _, _, _ ->
ComposerDraft(
plainText = A_MESSAGE,
htmlText = null,
@@ -1354,7 +1355,7 @@ class MessageComposerPresenterTest {
}
assert(loadDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(false))
+ .with(value(A_ROOM_ID), value(null), value(false))
ensureAllEventsConsumed()
}
@@ -1362,7 +1363,7 @@ class MessageComposerPresenterTest {
@Test
fun `present - when there is a draft for reply, it is restored`() = runTest {
- val loadDraftLambda = lambdaRecorder { _, _ ->
+ val loadDraftLambda = lambdaRecorder { _, _, _ ->
ComposerDraft(
plainText = A_MESSAGE,
htmlText = null,
@@ -1400,7 +1401,7 @@ class MessageComposerPresenterTest {
}
assert(loadDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(false))
+ .with(value(A_ROOM_ID), value(null), value(false))
assert(loadReplyDetailsLambda)
.isCalledOnce()
@@ -1412,7 +1413,7 @@ class MessageComposerPresenterTest {
@Test
fun `present - when save draft event is invoked and composer is empty then service is called with null draft`() = runTest {
- val saveDraftLambda = lambdaRecorder { _, _, _ -> }
+ val saveDraftLambda = lambdaRecorder { _, _, _, _ -> }
val composerDraftService = FakeComposerDraftService().apply {
this.saveDraftLambda = saveDraftLambda
}
@@ -1425,13 +1426,13 @@ class MessageComposerPresenterTest {
advanceUntilIdle()
assert(saveDraftLambda)
.isCalledOnce()
- .with(value(A_ROOM_ID), value(null), value(false))
+ .with(value(A_ROOM_ID), value(null), value(null), value(false))
}
}
@Test
fun `present - when save draft event is invoked and composer is not empty then service is called`() = runTest {
- val saveDraftLambda = lambdaRecorder { _, _, _ -> }
+ val saveDraftLambda = lambdaRecorder { _, _, _, _ -> }
val composerDraftService = FakeComposerDraftService().apply {
this.saveDraftLambda = saveDraftLambda
}
@@ -1478,27 +1479,32 @@ class MessageComposerPresenterTest {
.withSequence(
listOf(
value(A_ROOM_ID),
+ value(null),
value(ComposerDraft(plainText = A_MESSAGE, htmlText = null, draftType = ComposerDraftType.NewMessage)),
value(false)
),
listOf(
value(A_ROOM_ID),
+ value(null),
value(ComposerDraft(plainText = A_MESSAGE, htmlText = A_MESSAGE, draftType = ComposerDraftType.NewMessage)),
value(false)
),
listOf(
value(A_ROOM_ID),
+ value(null),
value(ComposerDraft(plainText = A_MESSAGE, htmlText = A_MESSAGE, draftType = ComposerDraftType.NewMessage)),
// The volatile draft created when switching to edit mode.
value(true)
),
listOf(
value(A_ROOM_ID),
+ value(null),
value(ComposerDraft(plainText = A_MESSAGE, htmlText = A_MESSAGE, draftType = ComposerDraftType.Edit(AN_EVENT_ID))),
value(false)
),
listOf(
value(A_ROOM_ID),
+ value(null),
// When moving from edit mode, text composer is cleared, so the draft is null
value(null),
value(false)
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenterTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenterTest.kt
index a95cf4f31f..2cc7d9764a 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenterTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/TimelinePresenterTest.kt
@@ -32,6 +32,7 @@ import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UniqueId
import io.element.android.libraries.matrix.api.room.RoomMembersState
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
import io.element.android.libraries.matrix.api.timeline.MatrixTimelineItem
import io.element.android.libraries.matrix.api.timeline.ReceiptType
import io.element.android.libraries.matrix.api.timeline.Timeline
@@ -64,6 +65,7 @@ import io.element.android.tests.testutils.test
import io.element.android.tests.testutils.testCoroutineDispatchers
import kotlinx.collections.immutable.persistentListOf
import kotlinx.coroutines.ExperimentalCoroutinesApi
+import kotlinx.coroutines.FlowPreview
import kotlinx.coroutines.delay
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.flowOf
@@ -80,7 +82,7 @@ import kotlin.time.Duration
import kotlin.time.Duration.Companion.seconds
@Suppress("LargeClass")
-@OptIn(ExperimentalCoroutinesApi::class)
+@OptIn(ExperimentalCoroutinesApi::class, FlowPreview::class)
class TimelinePresenterTest {
@get:Rule
val warmUpRule = WarmUpRule()
@@ -705,6 +707,73 @@ class TimelinePresenterTest {
}
}
+ @Test
+ fun `present - timeline room info includes predecessor room when room has predecessor`() = runTest {
+ val predecessorRoomId = RoomId("!predecessor:server.org")
+ val predecessorEventId = EventId("\$predecessorEvent:server.org")
+ val predecessorRoom = PredecessorRoom(
+ roomId = predecessorRoomId,
+ lastEventId = predecessorEventId
+ )
+
+ val room = FakeJoinedRoom(
+ baseRoom = FakeBaseRoom(
+ canUserSendMessageResult = { _, _ -> Result.success(true) },
+ predecessorRoomResult = { predecessorRoom }
+ ),
+ )
+
+ val presenter = createTimelinePresenter(room = room)
+ moleculeFlow(RecompositionMode.Immediate) {
+ presenter.present()
+ }.test {
+ val initialState = awaitFirstItem()
+ assertThat(initialState.timelineRoomInfo.predecessorRoom).isNotNull()
+ assertThat(initialState.timelineRoomInfo.predecessorRoom?.roomId).isEqualTo(predecessorRoomId)
+ assertThat(initialState.timelineRoomInfo.predecessorRoom?.lastEventId).isEqualTo(predecessorEventId)
+ }
+ }
+
+ @Test
+ fun `present - timeline room info no predecessor`() = runTest {
+ val room = FakeJoinedRoom(
+ baseRoom = FakeBaseRoom(
+ canUserSendMessageResult = { _, _ -> Result.success(true) },
+ predecessorRoomResult = { null }
+ ),
+ )
+ val presenter = createTimelinePresenter(room = room)
+ moleculeFlow(RecompositionMode.Immediate) {
+ presenter.present()
+ }.test {
+ val initialState = awaitFirstItem()
+ assertThat(initialState.timelineRoomInfo.predecessorRoom).isNull()
+ }
+ }
+
+ @Test
+ fun `present - timeline event navigate to room`() = runTest {
+ val room = FakeJoinedRoom(
+ baseRoom = FakeBaseRoom(
+ canUserSendMessageResult = { _, _ -> Result.success(true) },
+ ),
+ )
+ val onNavigateToRoomLambda = lambdaRecorder {}
+ val navigator = FakeMessagesNavigator(
+ onNavigateToRoomLambda = onNavigateToRoomLambda
+ )
+ val presenter = createTimelinePresenter(room = room, messagesNavigator = navigator)
+ presenter.test {
+ val initialState = awaitFirstItem()
+ initialState.eventSink(TimelineEvents.NavigateToRoom(A_ROOM_ID))
+ assert(onNavigateToRoomLambda)
+ .isCalledOnce()
+ .with(
+ value(A_ROOM_ID)
+ )
+ }
+ }
+
private suspend fun ReceiveTurbine.awaitFirstItem(): T {
return awaitItem()
}
diff --git a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemPollViewTest.kt b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemPollViewTest.kt
index b89a3830be..3935d6d615 100644
--- a/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemPollViewTest.kt
+++ b/features/messages/impl/src/test/kotlin/io/element/android/features/messages/impl/timeline/components/event/TimelineItemPollViewTest.kt
@@ -47,7 +47,10 @@ class TimelineItemPollViewTest {
)
}
val answer = content.answerItems[answerIndex].answer
- rule.onNode(hasText(answer.text)).performClick()
+ rule.onNode(
+ matcher = hasText(answer.text),
+ useUnmergedTree = true,
+ ).performClick()
eventsRecorder.assertSingle(TimelineEvents.SelectPollAnswer(content.eventId!!, answer.id))
}
diff --git a/features/poll/api/src/main/kotlin/io/element/android/features/poll/api/pollcontent/PollAnswerView.kt b/features/poll/api/src/main/kotlin/io/element/android/features/poll/api/pollcontent/PollAnswerView.kt
index 6243bd38d9..59d13fed1e 100644
--- a/features/poll/api/src/main/kotlin/io/element/android/features/poll/api/pollcontent/PollAnswerView.kt
+++ b/features/poll/api/src/main/kotlin/io/element/android/features/poll/api/pollcontent/PollAnswerView.kt
@@ -20,9 +20,13 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.StrokeCap
import androidx.compose.ui.res.pluralStringResource
+import androidx.compose.ui.res.stringResource
+import androidx.compose.ui.semantics.clearAndSetSemantics
+import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.unit.dp
import io.element.android.compound.theme.ElementTheme
import io.element.android.compound.tokens.generated.CompoundIcons
+import io.element.android.features.poll.api.R
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.theme.components.Icon
@@ -32,14 +36,42 @@ import io.element.android.libraries.designsystem.theme.progressIndicatorTrackCol
import io.element.android.libraries.designsystem.toEnabledColor
import io.element.android.libraries.designsystem.utils.CommonDrawables
import io.element.android.libraries.ui.strings.CommonPlurals
+import io.element.android.libraries.ui.strings.CommonStrings
@Composable
internal fun PollAnswerView(
answerItem: PollAnswerItem,
modifier: Modifier = Modifier,
) {
+ val nbVotesText = pluralStringResource(
+ id = CommonPlurals.common_poll_votes_count,
+ count = answerItem.votesCount,
+ answerItem.votesCount,
+ )
+ val a11yText = buildString {
+ val sentenceDelimiter = stringResource(CommonStrings.common_sentence_delimiter)
+ append(answerItem.answer.text.removeSuffix("."))
+ if (answerItem.showVotes) {
+ append(sentenceDelimiter)
+ append(nbVotesText)
+ if (answerItem.votesCount != 0) {
+ append(sentenceDelimiter)
+ (answerItem.percentage * 100).toInt().let { percent ->
+ append(pluralStringResource(R.plurals.a11y_polls_percent_of_total, percent, percent))
+ }
+ }
+ if (answerItem.isWinner) {
+ append(sentenceDelimiter)
+ append(stringResource(R.string.a11y_polls_winning_answer))
+ }
+ }
+ }
Row(
- modifier = modifier.fillMaxWidth(),
+ modifier = modifier
+ .fillMaxWidth()
+ .clearAndSetSemantics {
+ contentDescription = a11yText
+ },
) {
Icon(
imageVector = if (answerItem.isSelected) {
@@ -70,11 +102,6 @@ internal fun PollAnswerView(
style = if (answerItem.isWinner) ElementTheme.typography.fontBodyLgMedium else ElementTheme.typography.fontBodyLgRegular,
)
if (answerItem.showVotes) {
- val text = pluralStringResource(
- id = CommonPlurals.common_poll_votes_count,
- count = answerItem.votesCount,
- answerItem.votesCount
- )
Row(
modifier = Modifier.align(Alignment.Bottom),
verticalAlignment = Alignment.CenterVertically,
@@ -87,13 +114,13 @@ internal fun PollAnswerView(
)
Spacer(modifier = Modifier.width(2.dp))
Text(
- text = text,
+ text = nbVotesText,
style = ElementTheme.typography.fontBodySmMedium,
color = ElementTheme.colors.textPrimary,
)
} else {
Text(
- text = text,
+ text = nbVotesText,
style = ElementTheme.typography.fontBodySmRegular,
color = ElementTheme.colors.textSecondary,
)
diff --git a/features/poll/api/src/main/res/values-fr/translations.xml b/features/poll/api/src/main/res/values-fr/translations.xml
new file mode 100644
index 0000000000..a085a9d40e
--- /dev/null
+++ b/features/poll/api/src/main/res/values-fr/translations.xml
@@ -0,0 +1,8 @@
+
+
+
+ - "%1$d pour cent du total des votes"
+ - "%1$d pour cent du total des votes"
+
+ "C’est la réponse gagnante"
+
diff --git a/features/poll/api/src/main/res/values-nb/translations.xml b/features/poll/api/src/main/res/values-nb/translations.xml
new file mode 100644
index 0000000000..332f319e7c
--- /dev/null
+++ b/features/poll/api/src/main/res/values-nb/translations.xml
@@ -0,0 +1,8 @@
+
+
+
+ - "%1$d prosent av totalt antall stemmer"
+ - "%1$d prosent av totalt antall stemmer"
+
+ "Dette er vinnersvaret"
+
diff --git a/features/poll/api/src/main/res/values/localazy.xml b/features/poll/api/src/main/res/values/localazy.xml
new file mode 100644
index 0000000000..2d1142194c
--- /dev/null
+++ b/features/poll/api/src/main/res/values/localazy.xml
@@ -0,0 +1,8 @@
+
+
+
+ - "%1$d percent of total votes"
+ - "%1$d percents of total votes"
+
+ "This is the winning answer"
+
diff --git a/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/create/CreatePollView.kt b/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/create/CreatePollView.kt
index f8384279bf..038fb397f3 100644
--- a/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/create/CreatePollView.kt
+++ b/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/create/CreatePollView.kt
@@ -143,7 +143,7 @@ fun CreatePollView(
trailingContent = ListItemContent.Custom {
Icon(
imageVector = CompoundIcons.Delete(),
- contentDescription = null,
+ contentDescription = stringResource(R.string.screen_create_poll_delete_option_a11y, answer.text),
modifier = Modifier.clickable(answer.canDelete) {
state.eventSink(CreatePollEvents.RemoveAnswer(index))
},
diff --git a/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/history/PollHistoryView.kt b/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/history/PollHistoryView.kt
index 0ad8f8fe84..1101276577 100644
--- a/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/history/PollHistoryView.kt
+++ b/features/poll/impl/src/main/kotlin/io/element/android/features/poll/impl/history/PollHistoryView.kt
@@ -8,7 +8,6 @@
package io.element.android.features.poll.impl.history
import androidx.compose.foundation.BorderStroke
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Spacer
@@ -30,6 +29,8 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.stringResource
+import androidx.compose.ui.semantics.isTraversalGroup
+import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.PreviewParameter
import androidx.compose.ui.unit.dp
@@ -52,7 +53,7 @@ import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.ui.strings.CommonStrings
import kotlinx.collections.immutable.ImmutableList
-@OptIn(ExperimentalMaterial3Api::class, ExperimentalFoundationApi::class)
+@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun PollHistoryView(
state: PollHistoryState,
@@ -179,7 +180,9 @@ private fun PollHistoryList(
if (pollHistoryItems.isEmpty()) {
item {
Column(
- modifier = Modifier.fillParentMaxSize().padding(bottom = 24.dp),
+ modifier = Modifier
+ .fillParentMaxSize()
+ .padding(bottom = 24.dp),
verticalArrangement = Arrangement.Center,
horizontalAlignment = Alignment.CenterHorizontally,
) {
@@ -192,7 +195,9 @@ private fun PollHistoryList(
text = emptyStringResource,
style = ElementTheme.typography.fontBodyLgRegular,
color = ElementTheme.colors.textSecondary,
- modifier = Modifier.fillMaxWidth().padding(vertical = 24.dp, horizontal = 16.dp),
+ modifier = Modifier
+ .fillMaxWidth()
+ .padding(vertical = 24.dp, horizontal = 16.dp),
textAlign = TextAlign.Center,
)
@@ -228,7 +233,10 @@ private fun PollHistoryItemRow(
modifier: Modifier = Modifier,
) {
Surface(
- modifier = modifier,
+ modifier = modifier.semantics(mergeDescendants = true) {
+ // Allow the answers to be traversed by Talkback
+ isTraversalGroup = true
+ },
border = BorderStroke(1.dp, ElementTheme.colors.borderInteractiveSecondary),
shape = RoundedCornerShape(size = 12.dp)
) {
diff --git a/features/poll/impl/src/main/res/values-fr/translations.xml b/features/poll/impl/src/main/res/values-fr/translations.xml
index 8a0c8ea5d5..badf3888e2 100644
--- a/features/poll/impl/src/main/res/values-fr/translations.xml
+++ b/features/poll/impl/src/main/res/values-fr/translations.xml
@@ -5,6 +5,7 @@
"Masquer les votes"
"Option %1$d"
"Vos modifications n’ont pas été enregistrées. Êtes-vous certain de vouloir quitter ?"
+ "Supprimer l’option %1$s"
"Question ou sujet"
"Quel est le sujet du sondage ?"
"Créer un sondage"
diff --git a/features/poll/impl/src/main/res/values-nb/translations.xml b/features/poll/impl/src/main/res/values-nb/translations.xml
index 5e363ff4a2..7396cf9cf9 100644
--- a/features/poll/impl/src/main/res/values-nb/translations.xml
+++ b/features/poll/impl/src/main/res/values-nb/translations.xml
@@ -5,6 +5,7 @@
"Skjul stemmer"
"Alternativ %1$d"
"Endringene dine er ikke lagret. Er du sikker på at du vil gå tilbake?"
+ "Slett alternativet %1$s"
"Spørsmål eller emne"
"Hva handler avstemningen om?"
"Opprett avstemning"
diff --git a/features/poll/impl/src/main/res/values/localazy.xml b/features/poll/impl/src/main/res/values/localazy.xml
index 7a7a15ea3c..6019d908b4 100644
--- a/features/poll/impl/src/main/res/values/localazy.xml
+++ b/features/poll/impl/src/main/res/values/localazy.xml
@@ -5,6 +5,7 @@
"Hide votes"
"Option %1$d"
"Your changes have not been saved. Are you sure you want to go back?"
+ "Delete option %1$s"
"Question or topic"
"What is the poll about?"
"Create Poll"
diff --git a/features/poll/impl/src/test/kotlin/io/element/android/features/poll/impl/history/PollHistoryViewTest.kt b/features/poll/impl/src/test/kotlin/io/element/android/features/poll/impl/history/PollHistoryViewTest.kt
index 3da8d50d49..54df066bbe 100644
--- a/features/poll/impl/src/test/kotlin/io/element/android/features/poll/impl/history/PollHistoryViewTest.kt
+++ b/features/poll/impl/src/test/kotlin/io/element/android/features/poll/impl/history/PollHistoryViewTest.kt
@@ -131,7 +131,10 @@ class PollHistoryViewTest {
rule.setPollHistoryViewView(
state = state,
)
- rule.onNodeWithText(answer.text).performClick()
+ rule.onNodeWithText(
+ text = answer.text,
+ useUnmergedTree = true,
+ ).performClick()
eventsRecorder.assertSingle(
PollHistoryEvents.SelectPollAnswer(eventId, answer.id)
)
diff --git a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/advanced/AdvancedSettingsState.kt b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/advanced/AdvancedSettingsState.kt
index 5b91c65f08..58f93fc665 100644
--- a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/advanced/AdvancedSettingsState.kt
+++ b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/advanced/AdvancedSettingsState.kt
@@ -8,6 +8,7 @@
package io.element.android.features.preferences.impl.advanced
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.ui.res.stringResource
import io.element.android.libraries.designsystem.components.preferences.DropdownOption
import io.element.android.libraries.matrix.api.media.MediaPreviewValue
@@ -26,14 +27,17 @@ data class AdvancedSettingsState(
enum class ThemeOption : DropdownOption {
System {
@Composable
+ @ReadOnlyComposable
override fun getText(): String = stringResource(CommonStrings.common_system)
},
Dark {
@Composable
+ @ReadOnlyComposable
override fun getText(): String = stringResource(CommonStrings.common_dark)
},
Light {
@Composable
+ @ReadOnlyComposable
override fun getText(): String = stringResource(CommonStrings.common_light)
}
}
diff --git a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/NotificationSettingsView.kt b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/NotificationSettingsView.kt
index 8f2543c161..f73fecaf3c 100644
--- a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/NotificationSettingsView.kt
+++ b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/NotificationSettingsView.kt
@@ -38,6 +38,7 @@ import io.element.android.libraries.designsystem.theme.components.IconSource
import io.element.android.libraries.designsystem.theme.components.ListItem
import io.element.android.libraries.designsystem.theme.components.Text
import io.element.android.libraries.designsystem.utils.OnLifecycleEvent
+import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsEvents
import io.element.android.libraries.matrix.api.room.RoomNotificationMode
import io.element.android.libraries.ui.strings.CommonStrings
import kotlinx.collections.immutable.toImmutableList
@@ -149,7 +150,7 @@ private fun NotificationSettingsContentView(
Text(stringResource(R.string.full_screen_intent_banner_message))
},
onClick = {
- state.fullScreenIntentPermissionsState.openFullScreenIntentSettings()
+ state.fullScreenIntentPermissionsState.eventSink(FullScreenIntentPermissionsEvents.OpenSettings)
}
)
}
diff --git a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/edit/EditDefaultNotificationSettingView.kt b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/edit/EditDefaultNotificationSettingView.kt
index 6a94670c7d..b9a001e812 100644
--- a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/edit/EditDefaultNotificationSettingView.kt
+++ b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/notifications/edit/EditDefaultNotificationSettingView.kt
@@ -16,7 +16,7 @@ import androidx.compose.ui.text.font.FontStyle
import androidx.compose.ui.tooling.preview.PreviewParameter
import io.element.android.features.preferences.impl.R
import io.element.android.libraries.designsystem.components.async.AsyncActionView
-import io.element.android.libraries.designsystem.components.avatar.CompositeAvatar
+import io.element.android.libraries.designsystem.components.avatar.RoomAvatar
import io.element.android.libraries.designsystem.components.list.ListItemContent
import io.element.android.libraries.designsystem.components.preferences.PreferenceCategory
import io.element.android.libraries.designsystem.components.preferences.PreferencePage
@@ -97,7 +97,7 @@ fun EditDefaultNotificationSettingView(
Text(text = subtitle)
},
leadingContent = ListItemContent.Custom {
- CompositeAvatar(
+ RoomAvatar(
avatarData = summary.avatarData,
heroes = summary.heroesAvatar,
)
diff --git a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/tasks/ClearCacheUseCase.kt b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/tasks/ClearCacheUseCase.kt
index 5662e4fd46..9b90c8ba53 100644
--- a/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/tasks/ClearCacheUseCase.kt
+++ b/features/preferences/impl/src/main/kotlin/io/element/android/features/preferences/impl/tasks/ClearCacheUseCase.kt
@@ -59,6 +59,7 @@ class DefaultClearCacheUseCase @Inject constructor(
seenInvitesStore.clear()
// Ensure any error will be displayed again
pushService.setIgnoreRegistrationError(matrixClient.sessionId, false)
+ pushService.resetBatteryOptimizationState()
// Ensure the app is restarted
defaultCacheService.onClearedCache(matrixClient.sessionId)
}
diff --git a/features/preferences/impl/src/main/res/values-es/translations.xml b/features/preferences/impl/src/main/res/values-es/translations.xml
index 1ae1660faa..afdc23d90b 100644
--- a/features/preferences/impl/src/main/res/values-es/translations.xml
+++ b/features/preferences/impl/src/main/res/values-es/translations.xml
@@ -8,14 +8,22 @@
"URL base personalizada de Element Call"
"Define una URL base personalizada para Element Call."
"URL no válida, asegúrate de incluir el protocolo (http/https) y la dirección correcta."
+ "Ocultar avatares en las invitaciones a salas"
+ "Ocultar vistas previas de multimedia en la cronología"
"Sube fotos y vídeos más rápido y reduce el uso de datos"
"Optimizar la calidad de los medios"
+ "Moderación y seguridad"
"Proveedor de notificaciones push"
"Desactiva el editor de texto enriquecido para escribir Markdown manualmente."
"Confirmaciones de lectura"
"Si se desactiva, las confirmaciones de lectura no se enviarán a nadie. Seguirás recibiendo confirmaciones de lectura de otros usuarios."
"Compartir presencia"
"Si se desactiva, no podrás enviar ni recibir confirmaciones de lectura ni notificaciones de escritura."
+ "Ocultar siempre"
+ "Mostrar siempre"
+ "En las salas privadas"
+ "Siempre se puede mostrar un ítem multimedia oculto pulsando sobre él"
+ "Mostrar multimedia en la cronología"
"Habilita la opción para ver el contenido en bruto del mensaje en la cronología."
"No tienes usuarios bloqueados"
"Desbloquear"
@@ -45,7 +53,7 @@ Si continúas, es posible que algunos de tus ajustes cambien."
"La configuración no se ha corregido, por favor inténtalo de nuevo."
"Chats grupales"
"Invitaciones"
- "Tu servidor principal no admite esta opción en salas cifradas, puede que no recibas notificaciones en algunas salas."
+ "Tu servidor base no admite esta opción en salas cifradas, puede que no recibas notificaciones de algunas salas."
"Menciones"
"Todos"
"Menciones"
@@ -55,6 +63,7 @@ Si continúas, es posible que algunos de tus ajustes cambien."
"ajustes del sistema"
"Notificaciones del sistema desactivadas"
"Notificaciones"
+ "Historial de notificaciones push"
"Solucionar problemas"
"Solucionar problemas con las notificaciones"
diff --git a/features/preferences/impl/src/main/res/values-ru/translations.xml b/features/preferences/impl/src/main/res/values-ru/translations.xml
index dcdebe4282..70b15002a6 100644
--- a/features/preferences/impl/src/main/res/values-ru/translations.xml
+++ b/features/preferences/impl/src/main/res/values-ru/translations.xml
@@ -23,6 +23,7 @@
"Всегда показывать"
"В личных комнатах"
"Скрытый медиафайл всегда можно отобразить, нажав на него."
+ "Показать медиафайлы в хронологии"
"Включить опцию просмотра источника сообщения в ленте."
"У вас нет заблокированных пользователей"
"Разблокировать"
@@ -62,6 +63,7 @@
"настройки системы"
"Системные уведомления выключены"
"Уведомления"
+ "История уведомлений"
"Устранение неполадок"
"Уведомления об устранении неполадок"
diff --git a/features/preferences/impl/src/test/kotlin/io/element/android/features/preferences/impl/tasks/DefaultClearCacheUseCaseTest.kt b/features/preferences/impl/src/test/kotlin/io/element/android/features/preferences/impl/tasks/DefaultClearCacheUseCaseTest.kt
index ab391bfc62..cfdc63984c 100644
--- a/features/preferences/impl/src/test/kotlin/io/element/android/features/preferences/impl/tasks/DefaultClearCacheUseCaseTest.kt
+++ b/features/preferences/impl/src/test/kotlin/io/element/android/features/preferences/impl/tasks/DefaultClearCacheUseCaseTest.kt
@@ -46,8 +46,10 @@ class DefaultClearCacheUseCaseTest {
resetLambda = resetFtueLambda,
)
val setIgnoreRegistrationErrorLambda = lambdaRecorder { _, _ -> }
+ val resetBatteryOptimizationStateResult = lambdaRecorder { }
val pushService = FakePushService(
- setIgnoreRegistrationErrorLambda = setIgnoreRegistrationErrorLambda
+ setIgnoreRegistrationErrorLambda = setIgnoreRegistrationErrorLambda,
+ resetBatteryOptimizationStateResult = resetBatteryOptimizationStateResult,
)
val seenInvitesStore = InMemorySeenInvitesStore(setOf(A_ROOM_ID))
assertThat(seenInvitesStore.seenRoomIds().first()).isNotEmpty()
@@ -68,6 +70,7 @@ class DefaultClearCacheUseCaseTest {
resetFtueLambda.assertions().isCalledOnce()
setIgnoreRegistrationErrorLambda.assertions().isCalledOnce()
.with(value(matrixClient.sessionId), value(false))
+ resetBatteryOptimizationStateResult.assertions().isCalledOnce()
assertThat(awaitItem()).isEqualTo(matrixClient.sessionId)
assertThat(seenInvitesStore.seenRoomIds().first()).isEmpty()
assertThat(activeRoomsHolder.getActiveRoom(A_SESSION_ID)).isNull()
diff --git a/features/rageshake/impl/src/main/res/values-es/translations.xml b/features/rageshake/impl/src/main/res/values-es/translations.xml
index 7398dbc6de..cdeb467cfa 100644
--- a/features/rageshake/impl/src/main/res/values-es/translations.xml
+++ b/features/rageshake/impl/src/main/res/values-es/translations.xml
@@ -6,12 +6,12 @@
"Editar captura de pantalla"
"Describe el problema. ¿Qué has hecho? ¿Qué esperabas que ocurriera? ¿Qué ocurrió realmente? Por favor, detállalo todo lo que puedas."
"Describe el problema…"
- "Si es posible, escriba la descripción en inglés."
- "La descripción es demasiado corta. Proporcione más detalles sobre lo sucedido. ¡Gracias!"
+ "Si es posible, escribe la descripción en inglés."
+ "La descripción es demasiado corta. Proporciona más detalles sobre lo sucedido. ¡Gracias!"
"Enviar registros de fallos"
"Permitir registros"
"Enviar captura de pantalla"
- "Los registros se incluirán con su mensaje para asegurarse de que todo funciona correctamente. Para enviar tu mensaje sin registros, desactiva esta configuración."
+ "Los registros se incluirán con tu mensaje para asegurarse de que todo funciona correctamente. Para enviar tu mensaje sin registros, desactiva esta opción."
"%1$s se cerró inesperadamente la última vez que se lo usaste. ¿Quieres compartir un informe de error con nosotros?"
"Ver los registros"
diff --git a/features/reportroom/impl/src/main/res/values-es/translations.xml b/features/reportroom/impl/src/main/res/values-es/translations.xml
new file mode 100644
index 0000000000..7391dc7ca3
--- /dev/null
+++ b/features/reportroom/impl/src/main/res/values-es/translations.xml
@@ -0,0 +1,8 @@
+
+
+ "Tu denuncia se ha enviado correctamente, pero hemos encontrado un problema al intentar salir de la sala. Inténtalo de nuevo."
+ "No se pudo salir de la sala"
+ "Denuncia esta sala a tu administrador. Si los mensajes están cifrados, tu administrador no podrá leerlos."
+ "Describe el motivo de la denuncia…"
+ "Denunciar sala"
+
diff --git a/features/reportroom/impl/src/main/res/values-ru/translations.xml b/features/reportroom/impl/src/main/res/values-ru/translations.xml
index de5871f29f..d413f25b44 100644
--- a/features/reportroom/impl/src/main/res/values-ru/translations.xml
+++ b/features/reportroom/impl/src/main/res/values-ru/translations.xml
@@ -1,6 +1,8 @@
+ "Ваш отчет был успешно отправлен, но мы столкнулись с проблемой при попытке покинуть комнату. Пожалуйста, попробуйте еще раз."
"Невозможно покинуть комнату"
"Сообщите об этой комнате своему администратору. Если сообщения зашифрованы, ваш администратор не сможет их прочитать."
"Опишите причину…"
+ "Комната отчетов"
diff --git a/features/roomaliasresolver/impl/src/main/res/values-in/translations.xml b/features/roomaliasresolver/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..b5745b8827
--- /dev/null
+++ b/features/roomaliasresolver/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,4 @@
+
+
+ "Gagal menyelesaikan alias ruangan."
+
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsPresenter.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsPresenter.kt
index 505751c412..3e34f8d62b 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsPresenter.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsPresenter.kt
@@ -210,6 +210,7 @@ class RoomDetailsPresenter @Inject constructor(
canShowSecurityAndPrivacy = canShowSecurityAndPrivacy,
hasMemberVerificationViolations = hasMemberVerificationViolations,
canReportRoom = canReportRoom,
+ isTombstoned = roomInfo.successorRoom != null,
eventSink = ::handleEvents,
)
}
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsState.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsState.kt
index 5addbf3db8..e589eaaed9 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsState.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsState.kt
@@ -49,6 +49,7 @@ data class RoomDetailsState(
val canShowSecurityAndPrivacy: Boolean,
val hasMemberVerificationViolations: Boolean,
val canReportRoom: Boolean,
+ val isTombstoned: Boolean,
val eventSink: (RoomDetailsEvent) -> Unit
) {
val roomBadges = buildList {
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsStateProvider.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsStateProvider.kt
index d2cb4c5944..64f9976841 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsStateProvider.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsStateProvider.kt
@@ -53,6 +53,7 @@ open class RoomDetailsStateProvider : PreviewParameterProvider
aRoomDetailsState(knockRequestsCount = null, canShowKnockRequests = true),
aRoomDetailsState(knockRequestsCount = 4, canShowKnockRequests = true),
aRoomDetailsState(hasMemberVerificationViolations = true),
+ aRoomDetailsState(isTombstoned = true),
aDmRoomDetailsState(dmRoomMemberVerificationState = UserProfileVerificationState.VERIFIED),
aDmRoomDetailsState(dmRoomMemberVerificationState = UserProfileVerificationState.VERIFICATION_VIOLATION),
// Add other state here
@@ -118,6 +119,7 @@ fun aRoomDetailsState(
canShowSecurityAndPrivacy: Boolean = true,
hasMemberVerificationViolations: Boolean = false,
canReportRoom: Boolean = true,
+ isTombstoned: Boolean = false,
eventSink: (RoomDetailsEvent) -> Unit = {},
) = RoomDetailsState(
roomId = roomId,
@@ -148,6 +150,7 @@ fun aRoomDetailsState(
canShowSecurityAndPrivacy = canShowSecurityAndPrivacy,
hasMemberVerificationViolations = hasMemberVerificationViolations,
canReportRoom = canReportRoom,
+ isTombstoned = isTombstoned,
eventSink = eventSink,
)
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsView.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsView.kt
index 8f7502dee5..254c31023d 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsView.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsView.kt
@@ -48,8 +48,8 @@ import io.element.android.libraries.designsystem.atomic.molecules.MatrixBadgeRow
import io.element.android.libraries.designsystem.components.ClickableLinkText
import io.element.android.libraries.designsystem.components.avatar.AvatarData
import io.element.android.libraries.designsystem.components.avatar.AvatarSize
-import io.element.android.libraries.designsystem.components.avatar.CompositeAvatar
import io.element.android.libraries.designsystem.components.avatar.DmAvatars
+import io.element.android.libraries.designsystem.components.avatar.RoomAvatar
import io.element.android.libraries.designsystem.components.button.BackButton
import io.element.android.libraries.designsystem.components.button.MainActionButton
import io.element.android.libraries.designsystem.components.list.ListItemContent
@@ -138,6 +138,7 @@ fun RoomDetailsView(
roomName = state.roomName,
roomAlias = state.roomAlias,
heroes = state.heroes,
+ isTombstoned = state.isTombstoned,
openAvatarPreview = { avatarUrl ->
openAvatarPreview(state.roomName, avatarUrl)
},
@@ -380,6 +381,7 @@ private fun RoomHeaderSection(
roomName: String,
roomAlias: RoomAlias?,
heroes: ImmutableList,
+ isTombstoned: Boolean,
openAvatarPreview: (url: String) -> Unit,
onSubtitleClick: (String) -> Unit,
) {
@@ -389,11 +391,12 @@ private fun RoomHeaderSection(
.padding(horizontal = 16.dp),
horizontalAlignment = Alignment.CenterHorizontally,
) {
- CompositeAvatar(
+ RoomAvatar(
avatarData = AvatarData(roomId.value, roomName, avatarUrl, AvatarSize.RoomHeader),
heroes = heroes.map { user ->
user.getAvatarData(size = AvatarSize.RoomHeader)
}.toPersistentList(),
+ isTombstoned = isTombstoned,
modifier = Modifier
.clickable(enabled = avatarUrl != null) { openAvatarPreview(avatarUrl!!) }
.testTag(TestTags.roomDetailAvatar)
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/RoomMemberListView.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/RoomMemberListView.kt
index c5d2a93e2a..88da5b6ebc 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/RoomMemberListView.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/RoomMemberListView.kt
@@ -12,7 +12,6 @@ import androidx.compose.animation.expandVertically
import androidx.compose.animation.fadeIn
import androidx.compose.animation.fadeOut
import androidx.compose.animation.shrinkVertically
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
@@ -136,7 +135,6 @@ fun RoomMemberListView(
}
}
-@OptIn(ExperimentalMaterial3Api::class, ExperimentalFoundationApi::class)
@Composable
private fun RoomMemberList(
roomMembers: AsyncData,
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/RoomMemberDetailsPresenter.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/RoomMemberDetailsPresenter.kt
index 55126b33cd..d2d5db00e9 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/RoomMemberDetailsPresenter.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/RoomMemberDetailsPresenter.kt
@@ -33,7 +33,6 @@ import io.element.android.libraries.matrix.api.room.JoinedRoom
import io.element.android.libraries.matrix.ui.room.getRoomMemberAsState
import io.element.android.libraries.matrix.ui.room.roomMemberIdentityStateChange
import io.element.android.libraries.ui.strings.CommonStrings
-import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.flow.filterNotNull
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.launch
@@ -55,7 +54,6 @@ class RoomMemberDetailsPresenter @AssistedInject constructor(
private val userProfilePresenter = userProfilePresenterFactory.create(roomMemberId)
- @OptIn(ExperimentalCoroutinesApi::class)
@Composable
override fun present(): UserProfileState {
val coroutineScope = rememberCoroutineScope()
diff --git a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/rolesandpermissions/changeroles/ChangeRolesView.kt b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/rolesandpermissions/changeroles/ChangeRolesView.kt
index 74a7d992b7..b1a7a7df21 100644
--- a/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/rolesandpermissions/changeroles/ChangeRolesView.kt
+++ b/features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/rolesandpermissions/changeroles/ChangeRolesView.kt
@@ -11,7 +11,6 @@ import androidx.activity.compose.BackHandler
import androidx.compose.animation.AnimatedVisibility
import androidx.compose.animation.fadeIn
import androidx.compose.animation.fadeOut
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Box
@@ -225,7 +224,6 @@ fun ChangeRolesView(
}
}
-@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun SearchResultsList(
currentRole: RoomMember.Role,
diff --git a/features/roomdetails/impl/src/main/res/values-es/translations.xml b/features/roomdetails/impl/src/main/res/values-es/translations.xml
index c98d65b90a..ffce0a6b76 100644
--- a/features/roomdetails/impl/src/main/res/values-es/translations.xml
+++ b/features/roomdetails/impl/src/main/res/values-es/translations.xml
@@ -3,7 +3,7 @@
"Necesitarás una dirección de sala para que sea visible en el directorio."
"Dirección de la sala"
"Se ha producido un error al actualizar la configuración de notificaciones."
- "Tu servidor principal no admite esta opción en salas cifradas, puede que no recibas notificaciones en algunas salas."
+ "Tu servidor base no admite esta opción en salas cifradas, puede que no recibas notificaciones de algunas salas."
"Encuestas"
"Solo administradores"
"Vetar personas"
@@ -74,7 +74,7 @@
"Sacar y vetar a un miembro"
"Solo eliminar miembro"
"Quitar veto"
- "Podrán volver a unirse a esta sala si son invitados de nuevo."
+ "Podrá volver a unirse a esta sala si se le invita."
"Quitar veto al usuario"
"Vetados"
"Miembros"
@@ -93,7 +93,7 @@
"Se ha producido un error al cargar la configuración de las notificaciones."
"No se pudo restaurar el modo predeterminado, por favor vuelve a intentarlo de nuevo."
"No se pudo cambiar el modo, por favor inténtalo de nuevo."
- "Tu servidor principal no admite esta opción en salas cifradas, no recibirás notificaciones en esta sala."
+ "Tu servidor base no admite esta opción en salas cifradas, no recibirás notificaciones de esta sala."
"Todos los mensajes"
"Únicamente Menciones y Palabras clave"
"En esta sala, notificarme por"
diff --git a/features/roomdetails/impl/src/main/res/values-fr/translations.xml b/features/roomdetails/impl/src/main/res/values-fr/translations.xml
index fc311b403f..559c020986 100644
--- a/features/roomdetails/impl/src/main/res/values-fr/translations.xml
+++ b/features/roomdetails/impl/src/main/res/values-fr/translations.xml
@@ -71,7 +71,7 @@
- "%1$d personne"
- "%1$d personnes"
- "Retirer et bannir ce membre"
+ "Bannir du salon"
"Retirer le membre uniquement"
"Débannir"
"Il pourra rejoindre le salon à nouveau si il est invité."
diff --git a/features/roomdirectory/impl/src/main/res/values-in/translations.xml b/features/roomdirectory/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..3cf6342e1b
--- /dev/null
+++ b/features/roomdirectory/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,5 @@
+
+
+ "Gagal memuat"
+ "Direktori ruangan"
+
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListContentStateProvider.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListContentStateProvider.kt
index 7435424b15..5825c0a1e5 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListContentStateProvider.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListContentStateProvider.kt
@@ -12,6 +12,8 @@ import io.element.android.features.roomlist.impl.model.RoomListRoomSummary
import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsState
import io.element.android.libraries.fullscreenintent.api.aFullScreenIntentPermissionsState
import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.push.api.battery.BatteryOptimizationState
+import io.element.android.libraries.push.api.battery.aBatteryOptimizationState
import kotlinx.collections.immutable.ImmutableList
import kotlinx.collections.immutable.persistentListOf
import kotlinx.collections.immutable.toPersistentSet
@@ -31,10 +33,12 @@ internal fun aRoomsContentState(
securityBannerState: SecurityBannerState = SecurityBannerState.None,
summaries: ImmutableList = aRoomListRoomSummaryList(),
fullScreenIntentPermissionsState: FullScreenIntentPermissionsState = aFullScreenIntentPermissionsState(),
+ batteryOptimizationState: BatteryOptimizationState = aBatteryOptimizationState(),
seenRoomInvites: Set = emptySet(),
) = RoomListContentState.Rooms(
securityBannerState = securityBannerState,
fullScreenIntentPermissionsState = fullScreenIntentPermissionsState,
+ batteryOptimizationState = batteryOptimizationState,
summaries = summaries,
seenRoomInvites = seenRoomInvites.toPersistentSet(),
)
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListPresenter.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListPresenter.kt
index 7746f98204..9e8199cd80 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListPresenter.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListPresenter.kt
@@ -52,6 +52,7 @@ import io.element.android.libraries.matrix.api.sync.SyncService
import io.element.android.libraries.matrix.api.timeline.ReceiptType
import io.element.android.libraries.preferences.api.store.AppPreferencesStore
import io.element.android.libraries.preferences.api.store.SessionPreferencesStore
+import io.element.android.libraries.push.api.battery.BatteryOptimizationState
import io.element.android.libraries.push.api.notifications.NotificationCleaner
import io.element.android.services.analytics.api.AnalyticsService
import io.element.android.services.analyticsproviders.api.trackers.captureInteraction
@@ -88,6 +89,7 @@ class RoomListPresenter @Inject constructor(
private val analyticsService: AnalyticsService,
private val acceptDeclineInvitePresenter: Presenter,
private val fullScreenIntentPermissionsPresenter: Presenter,
+ private val batteryOptimizationPresenter: Presenter,
private val notificationCleaner: NotificationCleaner,
private val logoutPresenter: Presenter,
private val appPreferencesStore: AppPreferencesStore,
@@ -248,6 +250,7 @@ class RoomListPresenter @Inject constructor(
RoomListContentState.Rooms(
securityBannerState = securityBannerState,
fullScreenIntentPermissionsState = fullScreenIntentPermissionsPresenter.present(),
+ batteryOptimizationState = batteryOptimizationPresenter.present(),
summaries = roomSummaries.dataOrNull().orEmpty().toPersistentList(),
seenRoomInvites = seenRoomInvites.toPersistentSet(),
)
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListState.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListState.kt
index f685d5f379..0cf6147df7 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListState.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListState.kt
@@ -18,6 +18,7 @@ import io.element.android.libraries.designsystem.utils.snackbar.SnackbarMessage
import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsState
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.user.MatrixUser
+import io.element.android.libraries.push.api.battery.BatteryOptimizationState
import kotlinx.collections.immutable.ImmutableList
import kotlinx.collections.immutable.ImmutableSet
@@ -78,6 +79,7 @@ sealed interface RoomListContentState {
data class Rooms(
val securityBannerState: SecurityBannerState,
val fullScreenIntentPermissionsState: FullScreenIntentPermissionsState,
+ val batteryOptimizationState: BatteryOptimizationState,
val summaries: ImmutableList,
val seenRoomInvites: ImmutableSet,
) : RoomListContentState
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListStateProvider.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListStateProvider.kt
index 4a221d3c97..cb4818ddd1 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListStateProvider.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/RoomListStateProvider.kt
@@ -27,6 +27,7 @@ import io.element.android.libraries.designsystem.components.avatar.AvatarSize
import io.element.android.libraries.designsystem.utils.snackbar.SnackbarMessage
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.user.MatrixUser
+import io.element.android.libraries.push.api.battery.aBatteryOptimizationState
import io.element.android.libraries.ui.strings.CommonStrings
import kotlinx.collections.immutable.ImmutableList
import kotlinx.collections.immutable.persistentListOf
@@ -45,6 +46,7 @@ open class RoomListStateProvider : PreviewParameterProvider {
aRoomListState(contentState = aSkeletonContentState()),
aRoomListState(searchState = aRoomListSearchState(isSearchActive = true, query = "Test")),
aRoomListState(contentState = aRoomsContentState(securityBannerState = SecurityBannerState.SetUpRecovery)),
+ aRoomListState(contentState = aRoomsContentState(batteryOptimizationState = aBatteryOptimizationState(shouldDisplayBanner = true))),
)
}
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/BatteryOptimizationBanner.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/BatteryOptimizationBanner.kt
new file mode 100644
index 0000000000..8fde1834d2
--- /dev/null
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/BatteryOptimizationBanner.kt
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.features.roomlist.impl.components
+
+import androidx.compose.runtime.Composable
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.res.stringResource
+import io.element.android.features.roomlist.impl.R
+import io.element.android.libraries.designsystem.components.Announcement
+import io.element.android.libraries.designsystem.components.AnnouncementType
+import io.element.android.libraries.designsystem.preview.ElementPreview
+import io.element.android.libraries.designsystem.preview.PreviewsDayNight
+import io.element.android.libraries.push.api.battery.BatteryOptimizationEvents
+import io.element.android.libraries.push.api.battery.BatteryOptimizationState
+import io.element.android.libraries.push.api.battery.aBatteryOptimizationState
+
+@Composable
+internal fun BatteryOptimizationBanner(
+ state: BatteryOptimizationState,
+ modifier: Modifier = Modifier,
+) {
+ Announcement(
+ modifier = modifier.roomListBannerPadding(),
+ title = stringResource(R.string.banner_battery_optimization_title_android),
+ description = stringResource(R.string.banner_battery_optimization_content_android),
+ type = AnnouncementType.Actionable(
+ actionText = stringResource(R.string.banner_battery_optimization_submit_android),
+ onActionClick = { state.eventSink(BatteryOptimizationEvents.RequestDisableOptimizations) },
+ onDismissClick = { state.eventSink(BatteryOptimizationEvents.Dismiss) },
+ ),
+ )
+}
+
+@PreviewsDayNight
+@Composable
+internal fun BatteryOptimizationBannerPreview() = ElementPreview {
+ BatteryOptimizationBanner(
+ state = aBatteryOptimizationState(),
+ )
+}
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/FullScreenIntentPermissionBanner.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/FullScreenIntentPermissionBanner.kt
index 7e84a26ab3..339b5f4fa6 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/FullScreenIntentPermissionBanner.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/FullScreenIntentPermissionBanner.kt
@@ -15,6 +15,7 @@ import io.element.android.libraries.designsystem.components.Announcement
import io.element.android.libraries.designsystem.components.AnnouncementType
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
+import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsEvents
import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsState
import io.element.android.libraries.fullscreenintent.api.aFullScreenIntentPermissionsState
import io.element.android.libraries.ui.strings.CommonStrings
@@ -29,8 +30,8 @@ fun FullScreenIntentPermissionBanner(
description = stringResource(R.string.full_screen_intent_banner_message),
type = AnnouncementType.Actionable(
actionText = stringResource(CommonStrings.action_continue),
- onDismissClick = state.dismissFullScreenIntentBanner,
- onActionClick = state.openFullScreenIntentSettings,
+ onDismissClick = { state.eventSink(FullScreenIntentPermissionsEvents.Dismiss) },
+ onActionClick = { state.eventSink(FullScreenIntentPermissionsEvents.OpenSettings) },
),
modifier = modifier.roomListBannerPadding(),
)
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomListContentView.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomListContentView.kt
index 0118a4fb81..b27f21c7f6 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomListContentView.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomListContentView.kt
@@ -149,7 +149,7 @@ private fun EmptyView(
onDismissClick = { eventSink(RoomListEvents.DismissBanner) },
)
}
- else -> Unit
+ SecurityBannerState.None -> Unit
}
}
}
@@ -234,6 +234,10 @@ private fun RoomsViewList(
item {
FullScreenIntentPermissionBanner(state = state.fullScreenIntentPermissionsState)
}
+ } else if (state.batteryOptimizationState.shouldDisplayBanner) {
+ item {
+ BatteryOptimizationBanner(state = state.batteryOptimizationState)
+ }
}
}
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomSummaryRow.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomSummaryRow.kt
index 7e5265c965..1be57d631a 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomSummaryRow.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/components/RoomSummaryRow.kt
@@ -7,7 +7,6 @@
package io.element.android.features.roomlist.impl.components
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.interaction.MutableInteractionSource
import androidx.compose.foundation.layout.Arrangement
@@ -45,7 +44,7 @@ import io.element.android.features.roomlist.impl.model.RoomListRoomSummaryProvid
import io.element.android.features.roomlist.impl.model.RoomSummaryDisplayType
import io.element.android.libraries.core.extensions.orEmpty
import io.element.android.libraries.designsystem.atomic.atoms.UnreadIndicatorAtom
-import io.element.android.libraries.designsystem.components.avatar.CompositeAvatar
+import io.element.android.libraries.designsystem.components.avatar.RoomAvatar
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.theme.components.Button
@@ -122,7 +121,7 @@ internal fun RoomSummaryRow(
timestamp = room.timestamp,
isHighlighted = room.isHighlighted
)
- LastMessageAndIndicatorRow(room = room)
+ MessagePreviewAndIndicatorRow(room = room)
}
}
RoomSummaryDisplayType.KNOCKED -> {
@@ -149,7 +148,7 @@ internal fun RoomSummaryRow(
Spacer(modifier = Modifier.height(4.dp))
}
Text(
- text = stringResource(id = R.string.screen_join_room_knock_sent_title),
+ text = stringResource(id = R.string.screen_roomlist_knock_event_sent_description),
maxLines = 1,
overflow = TextOverflow.Ellipsis,
style = ElementTheme.typography.fontBodyMdRegular,
@@ -161,7 +160,6 @@ internal fun RoomSummaryRow(
}
}
-@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun RoomSummaryScaffoldRow(
room: RoomListRoomSummary,
@@ -186,10 +184,11 @@ private fun RoomSummaryScaffoldRow(
.padding(horizontal = 16.dp, vertical = 11.dp)
.height(IntrinsicSize.Min),
) {
- CompositeAvatar(
+ RoomAvatar(
avatarData = room.avatarData,
heroes = room.heroes,
- hideAvatarImages = hideAvatarImage,
+ isTombstoned = room.isTombstoned,
+ hideAvatarImage = hideAvatarImage,
)
Spacer(modifier = Modifier.width(16.dp))
Column(
@@ -257,7 +256,7 @@ private fun InviteSubtitle(
}
@Composable
-private fun LastMessageAndIndicatorRow(
+private fun MessagePreviewAndIndicatorRow(
room: RoomListRoomSummary,
modifier: Modifier = Modifier,
) {
@@ -265,12 +264,15 @@ private fun LastMessageAndIndicatorRow(
modifier = modifier.fillMaxWidth(),
horizontalArrangement = spacedBy(28.dp)
) {
- // Last Message
- val attributedLastMessage = room.lastMessage as? AnnotatedString
- ?: AnnotatedString(room.lastMessage.orEmpty().toString())
+ val messagePreview = if (room.isTombstoned) {
+ stringResource(R.string.screen_roomlist_tombstoned_room_description)
+ } else {
+ room.lastMessage.orEmpty()
+ }
+ val annotatedMessagePreview = messagePreview as? AnnotatedString ?: AnnotatedString(text = messagePreview.toString())
Text(
modifier = Modifier.weight(1f),
- text = attributedLastMessage,
+ text = annotatedMessagePreview,
color = ElementTheme.roomListRoomMessage(),
style = ElementTheme.typography.fontBodyMdRegular,
minLines = 2,
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/datasource/RoomListRoomSummaryFactory.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/datasource/RoomListRoomSummaryFactory.kt
index d1581f545b..98b7f8d853 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/datasource/RoomListRoomSummaryFactory.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/datasource/RoomListRoomSummaryFactory.kt
@@ -67,6 +67,7 @@ class RoomListRoomSummaryFactory @Inject constructor(
heroes = roomInfo.heroes.map { user ->
user.getAvatarData(size = AvatarSize.RoomListItem)
}.toImmutableList(),
+ isTombstoned = roomInfo.successorRoom != null,
)
}
}
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummary.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummary.kt
index a1c1156c2a..4b2c1e7afc 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummary.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummary.kt
@@ -36,6 +36,7 @@ data class RoomListRoomSummary(
val isDm: Boolean,
val isFavorite: Boolean,
val inviteSender: InviteSender?,
+ val isTombstoned: Boolean,
val heroes: ImmutableList,
) {
val isHighlighted = userDefinedNotificationMode != RoomNotificationMode.MUTE &&
diff --git a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummaryProvider.kt b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummaryProvider.kt
index e71c8849b7..111c4bc86b 100644
--- a/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummaryProvider.kt
+++ b/features/roomlist/impl/src/main/kotlin/io/element/android/features/roomlist/impl/model/RoomListRoomSummaryProvider.kt
@@ -110,6 +110,11 @@ open class RoomListRoomSummaryProvider : PreviewParameterProvider = emptyList(),
+ isTombstoned: Boolean = false,
) = RoomListRoomSummary(
id = id,
roomId = RoomId(id),
@@ -165,4 +171,5 @@ internal fun aRoomListRoomSummary(
displayType = displayType,
canonicalAlias = canonicalAlias,
heroes = heroes.toImmutableList(),
+ isTombstoned = isTombstoned,
)
diff --git a/features/roomlist/impl/src/main/res/values-cs/translations.xml b/features/roomlist/impl/src/main/res/values-cs/translations.xml
index 927f9a40b9..7c15f1c82a 100644
--- a/features/roomlist/impl/src/main/res/values-cs/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-cs/translations.xml
@@ -15,7 +15,6 @@
"Odmítnout chat"
"Žádné pozvánky"
"%1$s (%2$s) vás pozval(a)"
- "Žádost o vstup odeslána"
"Jedná se o jednorázový proces, prosíme o strpení."
"Nastavení vašeho účtu"
"Vytvořte novou konverzaci nebo místnost"
@@ -37,9 +36,11 @@ Prozatím můžete zrušit výběr filtrů, abyste viděli své další chaty"
"Nepřečtené"
"Gratulujeme!
Nemáte žádné nepřečtené zprávy!"
+ "Žádost o vstup odeslána"
"Všechny chaty"
"Označit jako přečtené"
"Označit jako nepřečtené"
+ "Tato místnost byla aktualizována"
"Zdá se, že používáte nové zařízení. Ověřte přihlášení, abyste měli přístup k zašifrovaným zprávám."
"Ověřte, že jste to vy"
diff --git a/features/roomlist/impl/src/main/res/values-cy/translations.xml b/features/roomlist/impl/src/main/res/values-cy/translations.xml
index de6fe0cf0f..7d779e0904 100644
--- a/features/roomlist/impl/src/main/res/values-cy/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-cy/translations.xml
@@ -15,7 +15,6 @@
"Gwrthod sgwrs"
"Dim Gwahoddiadau"
"Mae %1$s (%2$s) wedi eich gwahodd"
- "Anfonwyd y cais i ymuno"
"Mae hon yn broses un tro, diolch am aros."
"Creu eich cyfrif."
"Crëwch sgwrs neu ystafell newydd"
@@ -37,6 +36,7 @@ Am y tro, gallwch ddad-ddewis hidlwyr er mwyn gweld eich sgyrsiau eraill""Heb ei ddarllen"
"Llongyfarchiadau!
Does gennych chi ddim negeseuon heb eu darllen!"
+ "Anfonwyd y cais i ymuno"
"Sgyrsiau"
"Marcio fel wedi\'i ddarllen"
"Marcio fel heb ei ddarllen"
diff --git a/features/roomlist/impl/src/main/res/values-de/translations.xml b/features/roomlist/impl/src/main/res/values-de/translations.xml
index 59cd4dc0c6..bd09aad06d 100644
--- a/features/roomlist/impl/src/main/res/values-de/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-de/translations.xml
@@ -15,7 +15,6 @@
"Einladung ablehnen"
"Keine Einladungen"
"%1$s (%2$s) hat dich eingeladen"
- "Beitrittsanfrage geschickt"
"Dies ist ein einmaliger Vorgang, danke fürs Warten."
"Dein Konto wird eingerichtet."
"Eine Unterthaltung oder Raum erstellen"
@@ -37,6 +36,7 @@ Deaktivieren Sie den entsprechenden Filter, um Ihre anderen Chatrooms zu sehen"<
"Ungelesen"
"Glückwunsch!
Sie haben keine ungelesenen Nachrichten!"
+ "Beitrittsanfrage geschickt"
"Chats"
"Als gelesen markieren"
"Als ungelesen markieren"
diff --git a/features/roomlist/impl/src/main/res/values-el/translations.xml b/features/roomlist/impl/src/main/res/values-el/translations.xml
index cd91ad7efa..596592f594 100644
--- a/features/roomlist/impl/src/main/res/values-el/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-el/translations.xml
@@ -15,7 +15,6 @@
"Απόρριψη συνομιλίας"
"Χωρίς προσκλήσεις"
"%1$s (%2$s) σέ προσκάλεσε"
- "Το αίτημα συμμετοχής στάλθηκε"
"Αυτή είναι μια εφάπαξ διαδικασία, ευχαριστώ που περίμενες."
"Ρύθμιση του λογαριασμού σου."
"Δημιουργία νέας συνομιλίας ή δωματίου"
@@ -37,6 +36,7 @@
"Μη αναγνωσμένα"
"Συγχαρητήρια!
Δεν έχεις μη αναγνωσμένα μηνύματα!"
+ "Το αίτημα συμμετοχής στάλθηκε"
"Συνομιλίες"
"Επισήμανση ως αναγνωσμένου"
"Επισήμανση ως μη αναγνωσμένου"
diff --git a/features/roomlist/impl/src/main/res/values-es/translations.xml b/features/roomlist/impl/src/main/res/values-es/translations.xml
index fced9f1141..a58f9e743a 100644
--- a/features/roomlist/impl/src/main/res/values-es/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-es/translations.xml
@@ -15,7 +15,6 @@
"Rechazar el chat"
"Sin invitaciones"
"%1$s (%2$s) te invitó"
- "Solicitud de unión enviada"
"Este proceso solo se hace una vez, gracias por esperar."
"Configura tu cuenta"
"Crear una nueva conversación o sala"
@@ -37,6 +36,7 @@ Por ahora, puedes deseleccionar los filtros para ver tus otros chats"
"No leídos"
"¡Felicidades!
¡No tienes ningún mensaje sin leer!"
+ "Solicitud de unión enviada"
"Chats"
"Marcar como leído"
"Marcar como no leído"
diff --git a/features/roomlist/impl/src/main/res/values-et/translations.xml b/features/roomlist/impl/src/main/res/values-et/translations.xml
index a7e3f822bf..ecba029e6e 100644
--- a/features/roomlist/impl/src/main/res/values-et/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-et/translations.xml
@@ -15,7 +15,6 @@
"Keeldu vestlusest"
"Kutseid pole"
"%1$s (%2$s) saatis sulle kutse"
- "Liitumispalve on saadetud"
"Tänud, et ootad - seda toimingut on vaja teha vaid üks kord."
"Seadistame sinu kasutajakontot."
"Loo uus vestlus või jututuba"
@@ -37,6 +36,7 @@ Aga seni… oma teiste vestluste nägemiseks pead eemaldama filtrid"
"Lugemata"
"Õnnitleme!
Sul pole ühtegi lugemata sõnumit!"
+ "Liitumispalve on saadetud"
"Vestlused"
"Märgi loetuks"
"Märgi mitteloetuks"
diff --git a/features/roomlist/impl/src/main/res/values-eu/translations.xml b/features/roomlist/impl/src/main/res/values-eu/translations.xml
index 977ae65fe3..8289dc97d4 100644
--- a/features/roomlist/impl/src/main/res/values-eu/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-eu/translations.xml
@@ -11,7 +11,6 @@
"Baztertu txata"
"Ez dago gonbidapenik"
"%1$s(e)k (%2$s) gonbidatu zaitu"
- "Sartzeko eskaera bidali da"
"Behin egin beharreko prozesua da; eskerrik asko itxaroteagatik."
"Zure kontua konfiguratzen."
"Sortu elkarrizketa edo gela berria"
@@ -33,6 +32,7 @@ Oraingoz, iragazkiak desautatu ditzakezu zure gainerako txatak ikusteko""Irakurri gabeak"
"Bejondeizula!
Ez duzu irakurri gabeko mezurik!"
+ "Sartzeko eskaera bidali da"
"Txatak"
"Markatu irakurritzat"
"Markatu irakurri gabetzat"
diff --git a/features/roomlist/impl/src/main/res/values-fa/translations.xml b/features/roomlist/impl/src/main/res/values-fa/translations.xml
index b5a277bb3a..f2b8757107 100644
--- a/features/roomlist/impl/src/main/res/values-fa/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-fa/translations.xml
@@ -11,7 +11,6 @@
"رد گپ"
"بدون دعوت"
"%1$s (%2$s) دعوتتان کرد"
- "درخواست پیوستن فرستاده شد"
"فرایندی یک باره است. ممنون از شکیباییتان."
"برپایی حسابتان."
"ایجاد اتاق یا گفتوگویی جدید"
@@ -31,6 +30,7 @@
"نخواندهها"
"تبریک!
هیچ پیام نخواندهای ندارید!"
+ "درخواست پیوستن فرستاده شد"
"گپها"
"علامتگذاری به عنوان خوانده شده"
"نشان به ناخوانده"
diff --git a/features/roomlist/impl/src/main/res/values-fi/translations.xml b/features/roomlist/impl/src/main/res/values-fi/translations.xml
index 27c4972452..910564ba32 100644
--- a/features/roomlist/impl/src/main/res/values-fi/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-fi/translations.xml
@@ -15,7 +15,6 @@
"Hylkää keskustelu"
"Ei kutsuja"
"%1$s (%2$s) kutsui sinut"
- "Liittymispyyntö lähetetty"
"Tämä on kertaluonteinen prosessi, kiitos odottamisesta."
"Tiliä määritetään."
"Luo uusi keskustelu tai huone"
@@ -37,6 +36,7 @@ Toistaiseksi voit poistaa suodattimien valinnan, jotta näet muut keskustelut."<
"Lukemattomat"
"Onnittelut!
Sinulla ei ole lukemattomia viestejä!"
+ "Liittymispyyntö lähetetty"
"Keskustelut"
"Merkitse luetuksi"
"Merkitse lukemattomaksi"
diff --git a/features/roomlist/impl/src/main/res/values-fr/translations.xml b/features/roomlist/impl/src/main/res/values-fr/translations.xml
index 0c6805086a..4ffd377d4f 100644
--- a/features/roomlist/impl/src/main/res/values-fr/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-fr/translations.xml
@@ -15,7 +15,6 @@
"Refuser l’invitation"
"Aucune invitation"
"%1$s (%2$s) vous a invité(e)"
- "Demande de rejoindre le salon envoyée"
"Il s’agit d’une opération ponctuelle, merci d’attendre quelques instants."
"Configuration de votre compte."
"Créer une nouvelle discussion ou un nouveau salon"
@@ -37,6 +36,7 @@ En attendant, vous pouvez désélectionner des filtres pour voir vos autres salo
"Non-lus"
"Félicitations !
Vous n’avez plus de messages non-lus !"
+ "Demande de rejoindre le salon envoyée"
"Conversations"
"Marquer comme lu"
"Marquer comme non lu"
diff --git a/features/roomlist/impl/src/main/res/values-hu/translations.xml b/features/roomlist/impl/src/main/res/values-hu/translations.xml
index 145919ffb7..4c1b882ef6 100644
--- a/features/roomlist/impl/src/main/res/values-hu/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-hu/translations.xml
@@ -15,7 +15,6 @@
"Csevegés elutasítása"
"Nincsenek meghívások"
"%1$s (%2$s) meghívta"
- "Csatlakozási kérés elküldve"
"Ez egy egyszeri folyamat, köszönjük a türelmét."
"A fiók beállítása."
"Új beszélgetés vagy szoba létrehozása"
@@ -37,6 +36,7 @@ Egyelőre törölheti a szűrőket a többi csevegés megtekintéséhez.""Olvasatlan"
"Gratulálunk!
Nincs olvasatlan üzenete!"
+ "Csatlakozási kérés elküldve"
"Összes csevegés"
"Megjelölés olvasottként"
"Megjelölés olvasatlanként"
diff --git a/features/roomlist/impl/src/main/res/values-in/translations.xml b/features/roomlist/impl/src/main/res/values-in/translations.xml
index 310e2a256c..2b390790e1 100644
--- a/features/roomlist/impl/src/main/res/values-in/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-in/translations.xml
@@ -15,7 +15,6 @@
"Tolak obrolan"
"Tidak ada undangan"
"%1$s (%2$s) mengundang Anda"
- "Permintaan untuk bergabung dikirim"
"Ini adalah proses satu kali, terima kasih telah menunggu."
"Menyiapkan akun Anda."
"Buat percakapan atau ruangan baru"
@@ -37,6 +36,7 @@ Untuk sementara, Anda dapat membatalkan pilihan saringan untuk melihat percakapa
"Belum dibaca"
"Selamat!
Anda tidak memiliki pesan yang belum dibaca!"
+ "Permintaan untuk bergabung dikirim"
"Semua Obrolan"
"Tandai sebagai dibaca"
"Tandai sebagai belum dibaca"
diff --git a/features/roomlist/impl/src/main/res/values-it/translations.xml b/features/roomlist/impl/src/main/res/values-it/translations.xml
index 464267ab27..981fb27d96 100644
--- a/features/roomlist/impl/src/main/res/values-it/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-it/translations.xml
@@ -15,7 +15,6 @@
"Rifiuta l\'invito alla conversazione"
"Nessun invito"
"%1$s (%2$s) ti ha invitato"
- "Richiesta di accesso inviata"
"Si tratta di una procedura che si effettua una sola volta, grazie per l\'attesa."
"Configurazione del tuo account."
"Crea una nuova conversazione o stanza"
@@ -37,6 +36,7 @@ Per il momento, puoi deselezionare i filtri per vedere le altre conversazioni."<
"Non letti"
"Congratulazioni!
Non hai messaggi non letti!"
+ "Richiesta di accesso inviata"
"Tutte le conversazioni"
"Segna come letto"
"Segna come non letto"
diff --git a/features/roomlist/impl/src/main/res/values-nb/translations.xml b/features/roomlist/impl/src/main/res/values-nb/translations.xml
index 7e4de08fae..b4fc0b1950 100644
--- a/features/roomlist/impl/src/main/res/values-nb/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-nb/translations.xml
@@ -15,7 +15,6 @@
"Avslå chat"
"Ingen invitasjoner"
"%1$s(%2$s) inviterte deg"
- "Forespørsel om å bli med sendt"
"Dette er en engangsprosess, takk for at du venter."
"Setter opp kontoen din."
"Opprett en ny samtale eller et nytt rom"
@@ -37,6 +36,7 @@ Inntil videre kan du velge bort filtre for å se de andre chattene dine""Uleste"
"Gratulerer!
Du har ingen uleste meldinger!"
+ "Forespørsel om å bli med sendt"
"Chatter"
"Marker som lest"
"Merk som ulest"
diff --git a/features/roomlist/impl/src/main/res/values-nl/translations.xml b/features/roomlist/impl/src/main/res/values-nl/translations.xml
index 425e21d5ed..fc207da016 100644
--- a/features/roomlist/impl/src/main/res/values-nl/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-nl/translations.xml
@@ -13,7 +13,6 @@
"Chat weigeren"
"Geen uitnodigingen"
"%1$s (%2$s) heeft je uitgenodigd"
- "Verzoek om toe te treden verzonden"
"Dit is een eenmalig proces, bedankt voor het wachten."
"Je account instellen."
"Begin een nieuw gesprek of maak een nieuwe kamer"
@@ -35,6 +34,7 @@ Voor nu kun je filters deselecteren om je andere chats te zien"
"Ongelezen"
"Gefeliciteerd!
Je hebt geen ongelezen berichten!"
+ "Verzoek om toe te treden verzonden"
"Chats"
"Markeren als gelezen"
"Markeren als ongelezen"
diff --git a/features/roomlist/impl/src/main/res/values-pl/translations.xml b/features/roomlist/impl/src/main/res/values-pl/translations.xml
index bc7f2cb189..8bb236e71a 100644
--- a/features/roomlist/impl/src/main/res/values-pl/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-pl/translations.xml
@@ -15,7 +15,6 @@
"Odrzuć czat"
"Brak zaproszeń"
"%1$s (%2$s) zaprosił Cię"
- "Wysłano prośbę o dołączenie"
"Jest to jednorazowy proces, dziękujemy za czekanie."
"Konfigurowanie Twojego konta."
"Utwórz nową rozmowę lub pokój"
@@ -37,6 +36,7 @@ Na razie możesz wyczyścić filtry, aby zobaczyć pozostałe czaty"
"Nieprzeczytane"
"Gratulacje!
Nie masz żadnych nieprzeczytanych wiadomości!"
+ "Wysłano prośbę o dołączenie"
"Wszystkie czaty"
"Oznacz jako przeczytane"
"Oznacz jako nieprzeczytane"
diff --git a/features/roomlist/impl/src/main/res/values-pt-rBR/translations.xml b/features/roomlist/impl/src/main/res/values-pt-rBR/translations.xml
index 00a47154c2..01b75db869 100644
--- a/features/roomlist/impl/src/main/res/values-pt-rBR/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-pt-rBR/translations.xml
@@ -15,7 +15,6 @@
"Recusar chat"
"Sem convites"
"%1$s(%2$s) convidou você"
- "Pedido de adesão enviado"
"Este é um processo único, obrigado por esperar."
"Configurando sua conta."
"Criar uma nova conversa ou sala"
@@ -37,6 +36,7 @@ Por enquanto, você pode desmarcar os filtros para ver seus outros bate-papos"
"Não lidos"
"Parabéns!
Você não tem nenhuma mensagem não lida!"
+ "Pedido de adesão enviado"
"Conversas"
"Marcar como lido"
"Marcar como não lido"
diff --git a/features/roomlist/impl/src/main/res/values-pt/translations.xml b/features/roomlist/impl/src/main/res/values-pt/translations.xml
index 4d87f54b8b..b332c4f1f8 100644
--- a/features/roomlist/impl/src/main/res/values-pt/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-pt/translations.xml
@@ -15,7 +15,6 @@
"Rejeitar conversa"
"Sem convites"
"%1$s (%2$s) convidou-te"
- "Pedido de adesão enviado"
"Este processo só acontece uma única vez, obrigado por esperares."
"A configurar a tua conta…"
"Criar uma nova conversa ou sala"
@@ -37,6 +36,7 @@ Por enquanto, podes anular a seleção dos filtros para veres as tuas outras con
"Por ler"
"Parabéns!
Não tens nenhuma mensagem por ler!"
+ "Pedido de adesão enviado"
"Conversas"
"Marcar como lida"
"Marcar como não lida"
diff --git a/features/roomlist/impl/src/main/res/values-ro/translations.xml b/features/roomlist/impl/src/main/res/values-ro/translations.xml
index b332101f2c..2d7bdd8a95 100644
--- a/features/roomlist/impl/src/main/res/values-ro/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-ro/translations.xml
@@ -13,7 +13,6 @@
"Refuzați conversația"
"Nicio invitație"
"%1$s (%2$s) v-a invitat."
- "Cererea de alăturare a fost trimisă"
"Acesta este un proces care se desfășoară o singură dată, vă mulțumim pentru așteptare."
"Contul dumneavoastră se configurează"
"Creați o conversație sau o cameră nouă"
@@ -35,6 +34,7 @@ Deocamdată, puteți deselecta filtrele pentru a vedea celelalte chat-uri""Necitite"
"Felicitari!
Nu aveți mesaje necitite!"
+ "Cererea de alăturare a fost trimisă"
"Toate conversatiile"
"Marcați ca citită"
"Marcați ca necitită"
diff --git a/features/roomlist/impl/src/main/res/values-ru/translations.xml b/features/roomlist/impl/src/main/res/values-ru/translations.xml
index c51fbc21d4..1ae52ac1a5 100644
--- a/features/roomlist/impl/src/main/res/values-ru/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-ru/translations.xml
@@ -15,7 +15,6 @@
"Отклонить чат"
"Нет приглашений"
"%1$s (%2$s) пригласил вас"
- "Запрос на присоединение отправлен"
"Это одноразовый процесс, спасибо, что подождали."
"Настройка учетной записи."
"Создайте новую беседу или комнату"
@@ -37,6 +36,7 @@
"Непрочитанные"
"Поздравляем!
У вас нет непрочитанных сообщений!"
+ "Запрос на присоединение отправлен"
"Все чаты"
"Пометить как прочитанное"
"Отметить как непрочитанное"
diff --git a/features/roomlist/impl/src/main/res/values-sk/translations.xml b/features/roomlist/impl/src/main/res/values-sk/translations.xml
index fb9da3707d..9898a0cbad 100644
--- a/features/roomlist/impl/src/main/res/values-sk/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-sk/translations.xml
@@ -15,7 +15,6 @@
"Odmietnuť konverzáciu"
"Žiadne pozvánky"
"%1$s (%2$s) vás pozval/a"
- "Žiadosť o pripojenie bola odoslaná"
"Ide o jednorazový proces, ďakujeme za trpezlivosť."
"Nastavenie vášho účtu."
"Vytvorte novú konverzáciu alebo miestnosť"
@@ -37,6 +36,7 @@ Zatiaľ môžete zrušiť výber filtrov, aby ste videli ostatné konverzácie"<
"Neprečítané"
"Gratulujeme!
Nemáte žiadne neprečítané správy!"
+ "Žiadosť o pripojenie bola odoslaná"
"Všetky konverzácie"
"Označiť ako prečítané"
"Označiť ako neprečítané"
diff --git a/features/roomlist/impl/src/main/res/values-sv/translations.xml b/features/roomlist/impl/src/main/res/values-sv/translations.xml
index 9c69cb1937..9cc2fe2f99 100644
--- a/features/roomlist/impl/src/main/res/values-sv/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-sv/translations.xml
@@ -15,7 +15,6 @@
"Avböj chatt"
"Inga inbjudningar"
"%1$s (%2$s) bjöd in dig"
- "Begäran om att gå med skickad"
"Detta är en engångsprocess, tack för att du väntar."
"Konfigurerar ditt konto"
"Skapa en ny konversation eller ett nytt rum"
@@ -37,6 +36,7 @@ För tillfället kan du avmarkera filter för att se dina andra chattar""Olästa"
"Grattis!
Du har inga olästa meddelanden!"
+ "Begäran om att gå med skickad"
"Alla chattar"
"Markera som läst"
"Markera som oläst"
diff --git a/features/roomlist/impl/src/main/res/values-tr/translations.xml b/features/roomlist/impl/src/main/res/values-tr/translations.xml
index 1502b4fcaf..6f42809ef3 100644
--- a/features/roomlist/impl/src/main/res/values-tr/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-tr/translations.xml
@@ -15,7 +15,6 @@
"Sohbeti reddet"
"Davet Yok"
"%1$s (%2$s) sizi davet etti"
- "Katılma isteği gönderildi"
"Bu tek seferlik bir işlemdir, beklediğiniz için teşekkürler."
"Hesabınızı ayarlanıyor."
"Yeni bir sohbet veya oda oluşturun"
@@ -37,6 +36,7 @@
"Okunmamış"
"Tebrikler!
Okunmamış mesajınız yok!"
+ "Katılma isteği gönderildi"
"Sohbetler"
"Okundu olarak işaretle"
"Okunmamış olarak işaretle"
diff --git a/features/roomlist/impl/src/main/res/values-uk/translations.xml b/features/roomlist/impl/src/main/res/values-uk/translations.xml
index 26875754d3..16836724df 100644
--- a/features/roomlist/impl/src/main/res/values-uk/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-uk/translations.xml
@@ -15,7 +15,6 @@
"Відхилити бесіду"
"Немає запрошень"
"%1$s (%2$s) запрошує вас"
- "Запит на приєднання надіслано"
"Це одноразовий процес, дякую за очікування."
"Налаштування облікового запису."
"Створити нову розмову або кімнату"
@@ -37,6 +36,7 @@
"Непрочитані"
"Вітаємо!
У вас немає непрочитаних повідомлень!"
+ "Запит на приєднання надіслано"
"Бесіди"
"Позначити прочитаним"
"Позначити непрочитаним"
diff --git a/features/roomlist/impl/src/main/res/values-zh-rTW/translations.xml b/features/roomlist/impl/src/main/res/values-zh-rTW/translations.xml
index 4a13d33c6c..1bc2ae181c 100644
--- a/features/roomlist/impl/src/main/res/values-zh-rTW/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-zh-rTW/translations.xml
@@ -15,7 +15,6 @@
"拒絕聊天"
"沒有邀請"
"%1$s(%2$s)邀請您"
- "已傳送加入請求"
"這是一次性的程序,感謝您耐心等候。"
"正在設定您的帳號。"
"建立新的對話或聊天室"
@@ -37,6 +36,7 @@
"未讀"
"恭喜!
您沒有任何未讀的訊息!"
+ "已傳送加入請求"
"所有聊天室"
"標為已讀"
"標為未讀"
diff --git a/features/roomlist/impl/src/main/res/values-zh/translations.xml b/features/roomlist/impl/src/main/res/values-zh/translations.xml
index 7c5d778ddf..e7e97040dd 100644
--- a/features/roomlist/impl/src/main/res/values-zh/translations.xml
+++ b/features/roomlist/impl/src/main/res/values-zh/translations.xml
@@ -15,7 +15,6 @@
"拒绝聊天"
"没有邀请"
"%1$s (%2$s)邀请了你"
- "加入请求已发送"
"这是一个一次性的过程,感谢您的等待。"
"设置您的账户。"
"创建新的对话或聊天室"
@@ -37,6 +36,7 @@
"未读"
"恭喜!
没有任何未读消息!"
+ "加入请求已发送"
"全部聊天"
"标记为已读"
"标记为未读"
diff --git a/features/roomlist/impl/src/main/res/values/localazy.xml b/features/roomlist/impl/src/main/res/values/localazy.xml
index d72af71f84..90432433c2 100644
--- a/features/roomlist/impl/src/main/res/values/localazy.xml
+++ b/features/roomlist/impl/src/main/res/values/localazy.xml
@@ -1,5 +1,8 @@
+ "Disable battery optimization for this app, to make sure all notifications are received."
+ "Disable optimization"
+ "Notifications not arriving?"
"Recover your cryptographic identity and message history with a recovery key if you have lost all your existing devices."
"Set up recovery"
"Set up recovery to protect your account"
@@ -15,7 +18,6 @@
"Decline chat"
"No Invites"
"%1$s (%2$s) invited you"
- "Request to join sent"
"This is a one time process, thanks for waiting."
"Setting up your account."
"Create a new conversation or room"
@@ -37,9 +39,11 @@ For now, you can deselect filters in order to see your other chats"
"Unreads"
"Congrats!
You don’t have any unread messages!"
+ "Request to join sent"
"Chats"
"Mark as read"
"Mark as unread"
+ "This room has been upgraded"
"Looks like you’re using a new device. Verify with another device to access your encrypted messages."
"Verify it’s you"
diff --git a/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListPresenterTest.kt b/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListPresenterTest.kt
index 446a864f0b..3184a44a1c 100644
--- a/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListPresenterTest.kt
+++ b/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListPresenterTest.kt
@@ -75,6 +75,7 @@ import io.element.android.libraries.preferences.api.store.AppPreferencesStore
import io.element.android.libraries.preferences.api.store.SessionPreferencesStore
import io.element.android.libraries.preferences.test.InMemoryAppPreferencesStore
import io.element.android.libraries.preferences.test.InMemorySessionPreferencesStore
+import io.element.android.libraries.push.api.battery.aBatteryOptimizationState
import io.element.android.libraries.push.api.notifications.NotificationCleaner
import io.element.android.libraries.push.test.notifications.FakeNotificationCleaner
import io.element.android.services.analytics.api.AnalyticsService
@@ -712,6 +713,7 @@ class RoomListPresenterTest {
analyticsService = analyticsService,
acceptDeclineInvitePresenter = acceptDeclineInvitePresenter,
fullScreenIntentPermissionsPresenter = { aFullScreenIntentPermissionsState() },
+ batteryOptimizationPresenter = { aBatteryOptimizationState() },
notificationCleaner = notificationCleaner,
logoutPresenter = { aDirectLogoutState() },
appPreferencesStore = appPreferencesStore,
diff --git a/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListViewTest.kt b/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListViewTest.kt
index 299ef07578..60da841e96 100644
--- a/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListViewTest.kt
+++ b/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/RoomListViewTest.kt
@@ -5,8 +5,6 @@
* Please see LICENSE files in the repository root for full details.
*/
-@file:OptIn(ExperimentalCoroutinesApi::class)
-
package io.element.android.features.roomlist.impl
import androidx.activity.ComponentActivity
@@ -30,7 +28,6 @@ import io.element.android.tests.testutils.clickOn
import io.element.android.tests.testutils.ensureCalledOnce
import io.element.android.tests.testutils.ensureCalledOnceWithParam
import io.element.android.tests.testutils.setSafeContent
-import kotlinx.coroutines.ExperimentalCoroutinesApi
import org.junit.Rule
import org.junit.Test
import org.junit.rules.TestRule
diff --git a/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/model/RoomListBaseRoomSummaryTest.kt b/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/model/RoomListBaseRoomSummaryTest.kt
index 4d5ef13d0b..e6bfb1a9cb 100644
--- a/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/model/RoomListBaseRoomSummaryTest.kt
+++ b/features/roomlist/impl/src/test/kotlin/io/element/android/features/roomlist/impl/model/RoomListBaseRoomSummaryTest.kt
@@ -84,6 +84,7 @@ internal fun createRoomListRoomSummary(
displayType: RoomSummaryDisplayType = RoomSummaryDisplayType.ROOM,
heroes: List = emptyList(),
timestamp: String? = null,
+ isTombstoned: Boolean = false,
) = RoomListRoomSummary(
id = A_ROOM_ID.value,
roomId = A_ROOM_ID,
@@ -104,4 +105,5 @@ internal fun createRoomListRoomSummary(
inviteSender = null,
isDm = false,
heroes = heroes.toPersistentList(),
+ isTombstoned = isTombstoned,
)
diff --git a/features/roommembermoderation/impl/src/main/res/values-fr/translations.xml b/features/roommembermoderation/impl/src/main/res/values-fr/translations.xml
index 9aabe07e11..5a09dddf4e 100644
--- a/features/roommembermoderation/impl/src/main/res/values-fr/translations.xml
+++ b/features/roommembermoderation/impl/src/main/res/values-fr/translations.xml
@@ -1,6 +1,6 @@
- "Retirer et bannir ce membre"
+ "Bannir du salon"
"Bannir"
"Il ne pourra pas rejoindre le salon à nouveau, même si il est invité."
"Êtes-vous certain de vouloir bannir ce membre ?"
diff --git a/features/roommembermoderation/impl/src/main/res/values-ru/translations.xml b/features/roommembermoderation/impl/src/main/res/values-ru/translations.xml
index ca4610dd31..6d89f42fe1 100644
--- a/features/roommembermoderation/impl/src/main/res/values-ru/translations.xml
+++ b/features/roommembermoderation/impl/src/main/res/values-ru/translations.xml
@@ -6,9 +6,15 @@
"Вы уверены, что хотите заблокировать этого участника?"
"Блокировка %1$s"
"Удалить"
+ "Они снова смогут присоединиться в эту комнату если их пригласят."
"Вы действительно хотите удалить этого участника?"
"Посмотреть профиль"
"Удалить участника из комнаты"
"Удалить участника и запретить присоединяться в будущем?"
"Удаление %1$s…"
+ "Разблокировать в комнате"
+ "Разблокировать"
+ "Они смогут снова войти в комнату, если их пригласят."
+ "Вы действительно хотите разблокировать этого участника?"
+ "Разблокировка %1$s"
diff --git a/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/enter/SecureBackupEnterRecoveryKeyView.kt b/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/enter/SecureBackupEnterRecoveryKeyView.kt
index ed5a381754..6a46431c35 100644
--- a/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/enter/SecureBackupEnterRecoveryKeyView.kt
+++ b/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/enter/SecureBackupEnterRecoveryKeyView.kt
@@ -7,7 +7,6 @@
package io.element.android.features.securebackup.impl.enter
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.layout.ColumnScope
import androidx.compose.foundation.layout.ExperimentalLayoutApi
import androidx.compose.foundation.layout.WindowInsets
@@ -71,7 +70,7 @@ fun SecureBackupEnterRecoveryKeyView(
}
}
-@OptIn(ExperimentalFoundationApi::class, ExperimentalLayoutApi::class)
+@OptIn(ExperimentalLayoutApi::class)
@Composable
private fun Content(
state: SecureBackupEnterRecoveryKeyState,
diff --git a/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/setup/views/RecoveryKeyView.kt b/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/setup/views/RecoveryKeyView.kt
index 9c24d463ba..fc05b6d316 100644
--- a/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/setup/views/RecoveryKeyView.kt
+++ b/features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/setup/views/RecoveryKeyView.kt
@@ -22,7 +22,6 @@ import androidx.compose.foundation.text.KeyboardOptions
import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
-import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.autofill.ContentType
import androidx.compose.ui.draw.alpha
@@ -169,7 +168,6 @@ private fun RecoveryKeyWithCopy(
}
}
-@OptIn(ExperimentalComposeUiApi::class)
@Composable
private fun RecoveryKeyFormContent(
state: RecoveryKeyViewState,
diff --git a/features/securebackup/impl/src/main/res/values-es/translations.xml b/features/securebackup/impl/src/main/res/values-es/translations.xml
index 4d4413690b..da6f4f2391 100644
--- a/features/securebackup/impl/src/main/res/values-es/translations.xml
+++ b/features/securebackup/impl/src/main/res/values-es/translations.xml
@@ -9,7 +9,7 @@
"Permitir almacenamiento de claves"
"Cambiar la clave de recuperación"
"Recupera tu identidad criptográfica y tu historial de mensajes con una clave de recuperación si has perdido todos tus dispositivos actuales."
- "Introduzca la clave de recuperación"
+ "Introduce la clave de recuperación"
"Tu almacén de claves no está sincronizado actualmente."
"Configurar la recuperación"
"Accede a tus mensajes cifrados si pierdes todos tus dispositivos o cierras sesión de %1$s en cualquier lugar."
diff --git a/features/userprofile/shared/src/main/res/values-in/translations.xml b/features/userprofile/shared/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..e368bc9692
--- /dev/null
+++ b/features/userprofile/shared/src/main/res/values-in/translations.xml
@@ -0,0 +1,19 @@
+
+
+ "Blokir"
+ "Pengguna yang diblokir tidak akan dapat mengirim Anda pesan dan semua pesan mereka akan disembunyikan. Anda dapat membuka blokirnya kapan saja."
+ "Blokir pengguna"
+ "Buka blokir"
+ "Anda akan dapat melihat semua pesan dari mereka lagi."
+ "Buka blokir pengguna"
+ "Blokir"
+ "Pengguna yang diblokir tidak akan dapat mengirim Anda pesan dan semua pesan mereka akan disembunyikan. Anda dapat membuka blokirnya kapan saja."
+ "Blokir pengguna"
+ "Profil"
+ "Buka blokir"
+ "Anda akan dapat melihat semua pesan dari mereka lagi."
+ "Buka blokir pengguna"
+ "Gunakan aplikasi web untuk memverifikasi pengguna ini."
+ "Verifikasi %1$s"
+ "Terjadi kesalahan saat mencoba memulai obrolan"
+
diff --git a/features/verifysession/impl/src/main/res/values-es/translations.xml b/features/verifysession/impl/src/main/res/values-es/translations.xml
index e22eb179b0..0f92e96395 100644
--- a/features/verifysession/impl/src/main/res/values-es/translations.xml
+++ b/features/verifysession/impl/src/main/res/values-es/translations.xml
@@ -18,7 +18,7 @@
"Comparar números"
"Tu nueva sesión ya está verificada. Tienes acceso a tus mensajes cifrados y otros usuarios lo considerarán de confianza."
"Ahora puedes confiar en la identidad de este usuario al enviar o recibir mensajes."
- "Introduzca la clave de recuperación"
+ "Introduce la clave de recuperación"
"O bien se agotó el tiempo de solicitud, se rechazó la solicitud o hubo una discrepancia en la verificación."
"Demuestra que eres tú para acceder a tu historial de mensajes cifrados."
"Abrir una sesión existente"
diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml
index d4db6807c4..296f70d939 100644
--- a/gradle/libs.versions.toml
+++ b/gradle/libs.versions.toml
@@ -6,7 +6,7 @@
android_gradle_plugin = "8.10.1"
kotlin = "2.1.21"
kotlinpoet = "2.2.0"
-ksp = "2.1.21-2.0.1"
+ksp = "2.1.21-2.0.2"
firebaseAppDistribution = "5.1.1"
# AndroidX
@@ -39,7 +39,7 @@ serialization_json = "1.8.1"
#other
detekt = "1.23.8"
coil = "3.2.0"
-showkase = "1.0.3"
+showkase = "1.0.4"
appyx = "1.7.1"
sqldelight = "2.1.0"
wysiwyg = "2.38.3"
@@ -147,7 +147,7 @@ test_junit = "junit:junit:4.13.2"
test_runner = "androidx.test:runner:1.6.2"
test_mockk = "io.mockk:mockk:1.14.2"
test_konsist = "com.lemonappdev:konsist:0.17.3"
-test_turbine = "app.cash.turbine:turbine:1.2.0"
+test_turbine = "app.cash.turbine:turbine:1.2.1"
test_truth = "com.google.truth:truth:1.4.4"
test_parameter_injector = "com.google.testparameterinjector:test-parameter-injector:1.18"
test_robolectric = "org.robolectric:robolectric:4.14.1"
@@ -172,7 +172,7 @@ jsoup = "org.jsoup:jsoup:1.20.1"
appyx_core = { module = "com.bumble.appyx:core", version.ref = "appyx" }
molecule-runtime = "app.cash.molecule:molecule-runtime:2.1.0"
timber = "com.jakewharton.timber:timber:5.0.1"
-matrix_sdk = "org.matrix.rustcomponents:sdk-android:25.6.10"
+matrix_sdk = "org.matrix.rustcomponents:sdk-android:25.6.18"
matrix_richtexteditor = { module = "io.element.android:wysiwyg", version.ref = "wysiwyg" }
matrix_richtexteditor_compose = { module = "io.element.android:wysiwyg-compose", version.ref = "wysiwyg" }
sqldelight-driver-android = { module = "app.cash.sqldelight:android-driver", version.ref = "sqldelight" }
@@ -186,15 +186,15 @@ vanniktech_blurhash = "com.vanniktech:blurhash:0.3.0"
telephoto_zoomableimage = { module = "me.saket.telephoto:zoomable-image-coil", version.ref = "telephoto" }
telephoto_flick = { module = "me.saket.telephoto:flick-android", version.ref = "telephoto" }
statemachine = "com.freeletics.flowredux:compose:1.2.2"
-maplibre = "org.maplibre.gl:android-sdk:11.10.1"
+maplibre = "org.maplibre.gl:android-sdk:11.10.3"
maplibre_ktx = "org.maplibre.gl:android-sdk-ktx-v7:3.0.2"
maplibre_annotation = "org.maplibre.gl:android-plugin-annotation-v9:3.0.2"
opusencoder = "io.element.android:opusencoder:1.2.0"
zxing_cpp = "io.github.zxing-cpp:android:2.3.0"
# Analytics
-posthog = "com.posthog:posthog-android:3.17.0"
-sentry = "io.sentry:sentry-android:8.13.2"
+posthog = "com.posthog:posthog-android:3.19.0"
+sentry = "io.sentry:sentry-android:8.13.3"
# main branch can be tested replacing the version with main-SNAPSHOT
matrix_analytics_events = "com.github.matrix-org:matrix-analytics-events:0.28.0"
@@ -237,7 +237,7 @@ anvil = { id = "dev.zacsweers.anvil", version.ref = "anvil" }
detekt = { id = "io.gitlab.arturbosch.detekt", version.ref = "detekt" }
ktlint = "org.jlleitschuh.gradle.ktlint:12.3.0"
dependencygraph = "com.savvasdalkitsis.module-dependency-graph:0.12"
-dependencycheck = "org.owasp.dependencycheck:12.1.2"
+dependencycheck = "org.owasp.dependencycheck:12.1.3"
dependencyanalysis = { id = "com.autonomousapps.dependency-analysis", version.ref = "dependencyAnalysis" }
paparazzi = "app.cash.paparazzi:1.3.5"
sqldelight = { id = "app.cash.sqldelight", version.ref = "sqldelight" }
diff --git a/libraries/dateformatter/impl/src/main/res/values-in/translations.xml b/libraries/dateformatter/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..4771c4e658
--- /dev/null
+++ b/libraries/dateformatter/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,5 @@
+
+
+ "%1$s pada %2$s"
+ "Bulan ini"
+
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/atomic/molecules/ComposerAlertMolecule.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/atomic/molecules/ComposerAlertMolecule.kt
index 33706239dc..0108779913 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/atomic/molecules/ComposerAlertMolecule.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/atomic/molecules/ComposerAlertMolecule.kt
@@ -39,7 +39,7 @@ import io.element.android.libraries.ui.strings.CommonStrings
@Composable
fun ComposerAlertMolecule(
- avatar: AvatarData,
+ avatar: AvatarData?,
content: AnnotatedString,
onSubmitClick: () -> Unit,
modifier: Modifier = Modifier,
@@ -71,9 +71,9 @@ fun ComposerAlertMolecule(
Row(
horizontalArrangement = Arrangement.spacedBy(16.dp)
) {
- Avatar(
- avatarData = avatar,
- )
+ if (avatar != null) {
+ Avatar(avatarData = avatar)
+ }
Text(
text = content,
modifier = Modifier.weight(1f),
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/Bloom.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/Bloom.kt
index a2b0049ad6..764a208a82 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/Bloom.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/Bloom.kt
@@ -370,7 +370,7 @@ fun Modifier.avatarBloom(
val initialsBitmap = initialsBitmap(
width = BloomDefaults.ENCODE_SIZE_PX.toDp(),
height = BloomDefaults.ENCODE_SIZE_PX.toDp(),
- text = avatarData.initial,
+ text = avatarData.initialLetter,
textColor = avatarColors.foreground,
backgroundColor = avatarColors.background,
)
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/Avatar.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/Avatar.kt
index 94ffd9c0fb..106e52d350 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/Avatar.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/Avatar.kt
@@ -7,9 +7,7 @@
package io.element.android.libraries.designsystem.components.avatar
-import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Arrangement
-import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.size
import androidx.compose.foundation.shape.CircleShape
@@ -21,21 +19,16 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.layout.ContentScale
-import androidx.compose.ui.semantics.clearAndSetSemantics
-import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.tooling.preview.PreviewParameter
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
-import androidx.compose.ui.unit.sp
import coil3.compose.AsyncImagePainter
import coil3.compose.SubcomposeAsyncImage
import coil3.compose.SubcomposeAsyncImageContent
-import io.element.android.compound.theme.ElementTheme
import io.element.android.libraries.designsystem.colors.AvatarColorsProvider
import io.element.android.libraries.designsystem.preview.ElementThemedPreview
import io.element.android.libraries.designsystem.preview.PreviewGroup
-import io.element.android.libraries.designsystem.text.toSp
import io.element.android.libraries.designsystem.theme.components.Text
import io.element.android.libraries.designsystem.utils.CommonDrawables
import timber.log.Timber
@@ -50,21 +43,18 @@ fun Avatar(
// If true, will show initials even if avatarData.url is not null
hideImage: Boolean = false,
) {
- val commonModifier = modifier
- .size(forcedAvatarSize ?: avatarData.size.dp)
- .clip(CircleShape)
if (avatarData.url.isNullOrBlank() || hideImage) {
- InitialsAvatar(
+ InitialLetterAvatar(
avatarData = avatarData,
forcedAvatarSize = forcedAvatarSize,
- modifier = commonModifier,
+ modifier = modifier,
contentDescription = contentDescription,
)
} else {
ImageAvatar(
avatarData = avatarData,
forcedAvatarSize = forcedAvatarSize,
- modifier = commonModifier,
+ modifier = modifier,
contentDescription = contentDescription,
)
}
@@ -77,11 +67,14 @@ private fun ImageAvatar(
modifier: Modifier = Modifier,
contentDescription: String? = null,
) {
+ val size = forcedAvatarSize ?: avatarData.size.dp
SubcomposeAsyncImage(
model = avatarData,
contentDescription = contentDescription,
contentScale = ContentScale.Crop,
modifier = modifier
+ .size(size)
+ .clip(CircleShape)
) {
val collectedState by painter.state.collectAsState()
when (val state = collectedState) {
@@ -90,13 +83,13 @@ private fun ImageAvatar(
SideEffect {
Timber.e(state.result.throwable, "Error loading avatar $state\n${state.result}")
}
- InitialsAvatar(
+ InitialLetterAvatar(
avatarData = avatarData,
forcedAvatarSize = forcedAvatarSize,
contentDescription = contentDescription,
)
}
- else -> InitialsAvatar(
+ else -> InitialLetterAvatar(
avatarData = avatarData,
forcedAvatarSize = forcedAvatarSize,
contentDescription = contentDescription,
@@ -106,33 +99,20 @@ private fun ImageAvatar(
}
@Composable
-private fun InitialsAvatar(
+private fun InitialLetterAvatar(
avatarData: AvatarData,
forcedAvatarSize: Dp?,
contentDescription: String?,
modifier: Modifier = Modifier,
) {
val avatarColors = AvatarColorsProvider.provide(avatarData.id)
- Box(
- modifier.background(color = avatarColors.background)
- ) {
- val fontSize = (forcedAvatarSize ?: avatarData.size.dp).toSp() / 2
- val originalFont = ElementTheme.typography.fontHeadingMdBold
- val ratio = fontSize.value / originalFont.fontSize.value
- val lineHeight = originalFont.lineHeight * ratio
- Text(
- modifier = Modifier
- .clearAndSetSemantics {
- contentDescription?.let {
- this.contentDescription = it
- }
- }
- .align(Alignment.Center),
- text = avatarData.initial,
- style = originalFont.copy(fontSize = fontSize, lineHeight = lineHeight, letterSpacing = 0.sp),
- color = avatarColors.foreground,
- )
- }
+ TextAvatar(
+ text = avatarData.initialLetter,
+ size = forcedAvatarSize ?: avatarData.size.dp,
+ colors = avatarColors,
+ contentDescription = contentDescription,
+ modifier = modifier
+ )
}
@Preview(group = PreviewGroup.Avatars)
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarCluster.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarCluster.kt
new file mode 100644
index 0000000000..9c7efa864d
--- /dev/null
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarCluster.kt
@@ -0,0 +1,127 @@
+/*
+ * Copyright 2024 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.designsystem.components.avatar
+
+import androidx.compose.foundation.layout.Arrangement
+import androidx.compose.foundation.layout.Box
+import androidx.compose.foundation.layout.Row
+import androidx.compose.foundation.layout.offset
+import androidx.compose.foundation.layout.size
+import androidx.compose.runtime.Composable
+import androidx.compose.ui.Alignment
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.semantics.contentDescription
+import androidx.compose.ui.semantics.semantics
+import androidx.compose.ui.tooling.preview.Preview
+import androidx.compose.ui.unit.dp
+import io.element.android.libraries.designsystem.preview.ElementThemedPreview
+import io.element.android.libraries.designsystem.preview.PreviewGroup
+import kotlinx.collections.immutable.ImmutableList
+import kotlinx.collections.immutable.toPersistentList
+import java.util.Collections
+import kotlin.math.PI
+import kotlin.math.cos
+import kotlin.math.sin
+
+private const val MAX_AVATAR_COUNT = 4
+
+@Composable
+fun AvatarCluster(
+ avatars: ImmutableList,
+ modifier: Modifier = Modifier,
+ hideAvatarImages: Boolean = false,
+ contentDescription: String? = null,
+) {
+ val limitedAvatars = avatars.take(MAX_AVATAR_COUNT)
+ val numberOfAvatars = limitedAvatars.size
+ if (numberOfAvatars == 4) {
+ // Swap 2 and 3 so that the 4th avatar is at the bottom right
+ Collections.swap(limitedAvatars, 2, 3)
+ }
+ when (numberOfAvatars) {
+ 0 -> {
+ error("Unsupported number of avatars: 0")
+ }
+ 1 -> {
+ Avatar(
+ avatarData = limitedAvatars[0],
+ modifier = modifier,
+ contentDescription = contentDescription,
+ hideImage = hideAvatarImages
+ )
+ }
+ else -> {
+ val size = limitedAvatars.first().size
+ val angle = 2 * Math.PI / numberOfAvatars
+ val offsetRadius = when (numberOfAvatars) {
+ 2 -> size.dp.value / 4.2
+ 3 -> size.dp.value / 4.0
+ 4 -> size.dp.value / 3.1
+ else -> error("Unsupported number of heroes: $numberOfAvatars")
+ }
+ val heroAvatarSize = when (numberOfAvatars) {
+ 2 -> size.dp / 2.2f
+ 3 -> size.dp / 2.4f
+ 4 -> size.dp / 2.2f
+ else -> error("Unsupported number of heroes: $numberOfAvatars")
+ }
+ val angleOffset = when (numberOfAvatars) {
+ 2 -> PI
+ 3 -> 7 * PI / 6
+ 4 -> 13 * PI / 4
+ else -> error("Unsupported number of heroes: $numberOfAvatars")
+ }
+ Box(
+ modifier = modifier
+ .size(size.dp)
+ .semantics {
+ this.contentDescription = contentDescription.orEmpty()
+ },
+ contentAlignment = Alignment.Center,
+ ) {
+ limitedAvatars.forEachIndexed { index, heroAvatar ->
+ val xOffset = (offsetRadius * cos(angle * index.toDouble() + angleOffset)).dp
+ val yOffset = (offsetRadius * sin(angle * index.toDouble() + angleOffset)).dp
+ Box(
+ modifier = Modifier
+ .size(heroAvatarSize)
+ .offset(
+ x = xOffset,
+ y = yOffset,
+ )
+ ) {
+ Avatar(
+ avatarData = heroAvatar,
+ forcedAvatarSize = heroAvatarSize,
+ hideImage = hideAvatarImages,
+ )
+ }
+ }
+ }
+ }
+ }
+}
+
+@Preview(group = PreviewGroup.Avatars)
+@Composable
+internal fun AvatarClusterPreview() = ElementThemedPreview {
+ Row(
+ horizontalArrangement = Arrangement.spacedBy(8.dp)
+ ) {
+ for (ngOfAvatars in 1..5) {
+ AvatarCluster(
+ avatars = List(ngOfAvatars) { anAvatarData(it) }.toPersistentList(),
+ )
+ }
+ }
+}
+
+private fun anAvatarData(i: Int) = anAvatarData(
+ id = ('A' + i).toString(),
+ name = ('A' + i).toString()
+)
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarData.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarData.kt
index 12b6fe05a3..2e711ee6eb 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarData.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarData.kt
@@ -18,7 +18,7 @@ data class AvatarData(
val url: String? = null,
val size: AvatarSize,
) {
- val initial by lazy {
+ val initialLetter by lazy {
// For roomIds, use "#" as initial
(name?.takeIf { it.isNotBlank() } ?: id.takeIf { !it.startsWith("!") } ?: "#")
.let { dn ->
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/CompositeAvatar.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/CompositeAvatar.kt
deleted file mode 100644
index c696050f23..0000000000
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/CompositeAvatar.kt
+++ /dev/null
@@ -1,140 +0,0 @@
-/*
- * Copyright 2024 New Vector Ltd.
- *
- * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
- * Please see LICENSE files in the repository root for full details.
- */
-
-package io.element.android.libraries.designsystem.components.avatar
-
-import androidx.compose.foundation.layout.Arrangement
-import androidx.compose.foundation.layout.Box
-import androidx.compose.foundation.layout.Row
-import androidx.compose.foundation.layout.offset
-import androidx.compose.foundation.layout.size
-import androidx.compose.runtime.Composable
-import androidx.compose.ui.Alignment
-import androidx.compose.ui.Modifier
-import androidx.compose.ui.semantics.contentDescription
-import androidx.compose.ui.semantics.semantics
-import androidx.compose.ui.tooling.preview.Preview
-import androidx.compose.ui.unit.dp
-import io.element.android.libraries.designsystem.preview.ElementThemedPreview
-import io.element.android.libraries.designsystem.preview.PreviewGroup
-import kotlinx.collections.immutable.ImmutableList
-import kotlinx.collections.immutable.toPersistentList
-import java.util.Collections
-import kotlin.math.PI
-import kotlin.math.cos
-import kotlin.math.sin
-
-@Composable
-fun CompositeAvatar(
- avatarData: AvatarData,
- heroes: ImmutableList,
- modifier: Modifier = Modifier,
- hideAvatarImages: Boolean = false,
- contentDescription: String? = null,
-) {
- if (avatarData.url != null || heroes.isEmpty()) {
- Avatar(
- avatarData = avatarData,
- modifier = modifier,
- contentDescription = contentDescription,
- hideImage = hideAvatarImages
- )
- } else {
- val limitedHeroes = heroes.take(4)
- val numberOfHeroes = limitedHeroes.size
- if (numberOfHeroes == 4) {
- // Swap 2 and 3 so that the 4th hero is at the bottom right
- Collections.swap(limitedHeroes, 2, 3)
- }
- when (numberOfHeroes) {
- 0 -> {
- error("Unsupported number of heroes: 0")
- }
- 1 -> {
- Avatar(
- avatarData = heroes[0],
- modifier = modifier,
- contentDescription = contentDescription,
- hideImage = hideAvatarImages
- )
- }
- else -> {
- val angle = 2 * Math.PI / numberOfHeroes
- val offsetRadius = when (numberOfHeroes) {
- 2 -> avatarData.size.dp.value / 4.2
- 3 -> avatarData.size.dp.value / 4.0
- 4 -> avatarData.size.dp.value / 3.1
- else -> error("Unsupported number of heroes: $numberOfHeroes")
- }
- val heroAvatarSize = when (numberOfHeroes) {
- 2 -> avatarData.size.dp / 2.2f
- 3 -> avatarData.size.dp / 2.4f
- 4 -> avatarData.size.dp / 2.2f
- else -> error("Unsupported number of heroes: $numberOfHeroes")
- }
- val angleOffset = when (numberOfHeroes) {
- 2 -> PI
- 3 -> 7 * PI / 6
- 4 -> 13 * PI / 4
- else -> error("Unsupported number of heroes: $numberOfHeroes")
- }
- Box(
- modifier = modifier
- .size(avatarData.size.dp)
- .semantics {
- this.contentDescription = contentDescription.orEmpty()
- },
- contentAlignment = Alignment.Center,
- ) {
- limitedHeroes.forEachIndexed { index, heroAvatar ->
- val xOffset = (offsetRadius * cos(angle * index.toDouble() + angleOffset)).dp
- val yOffset = (offsetRadius * sin(angle * index.toDouble() + angleOffset)).dp
- Box(
- modifier = Modifier
- .size(heroAvatarSize)
- .offset(
- x = xOffset,
- y = yOffset,
- )
- ) {
- Avatar(
- avatarData = heroAvatar,
- forcedAvatarSize = heroAvatarSize,
- hideImage = hideAvatarImages,
- )
- }
- }
- }
- }
- }
- }
-}
-
-@Preview(group = PreviewGroup.Avatars)
-@Composable
-internal fun CompositeAvatarPreview() = ElementThemedPreview {
- val mainAvatar = anAvatarData(
- id = "Zac",
- name = "Zac",
- size = AvatarSize.RoomListItem,
- )
- Row(
- horizontalArrangement = Arrangement.spacedBy(8.dp)
- ) {
- repeat(6) { nbOfHeroes ->
- CompositeAvatar(
- avatarData = mainAvatar,
- heroes = List(nbOfHeroes) { aHeroAvatarData(it) }.toPersistentList(),
- )
- }
- }
-}
-
-private fun aHeroAvatarData(i: Int) = anAvatarData(
- id = ('A' + i).toString(),
- name = ('A' + i).toString()
-)
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/RoomAvatar.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/RoomAvatar.kt
new file mode 100644
index 0000000000..44d1c9b491
--- /dev/null
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/RoomAvatar.kt
@@ -0,0 +1,48 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.designsystem.components.avatar
+
+import androidx.compose.runtime.Composable
+import androidx.compose.ui.Modifier
+import kotlinx.collections.immutable.ImmutableList
+
+@Composable
+fun RoomAvatar(
+ avatarData: AvatarData,
+ heroes: ImmutableList,
+ modifier: Modifier = Modifier,
+ isTombstoned: Boolean = false,
+ hideAvatarImage: Boolean = false,
+ contentDescription: String? = null,
+) {
+ when {
+ isTombstoned -> {
+ TombstonedRoomAvatar(
+ size = avatarData.size,
+ modifier = modifier,
+ contentDescription = contentDescription
+ )
+ }
+ avatarData.url != null || heroes.isEmpty() -> {
+ Avatar(
+ avatarData = avatarData,
+ modifier = modifier,
+ contentDescription = contentDescription,
+ hideImage = hideAvatarImage
+ )
+ }
+ else -> {
+ AvatarCluster(
+ avatars = heroes,
+ modifier = modifier,
+ hideAvatarImages = hideAvatarImage,
+ contentDescription = contentDescription
+ )
+ }
+ }
+}
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/TextAvatar.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/TextAvatar.kt
new file mode 100644
index 0000000000..65ebba3366
--- /dev/null
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/TextAvatar.kt
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.designsystem.components.avatar
+
+import androidx.compose.foundation.background
+import androidx.compose.foundation.layout.Box
+import androidx.compose.foundation.layout.size
+import androidx.compose.foundation.shape.CircleShape
+import androidx.compose.runtime.Composable
+import androidx.compose.ui.Alignment
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.draw.clip
+import androidx.compose.ui.semantics.clearAndSetSemantics
+import androidx.compose.ui.semantics.contentDescription
+import androidx.compose.ui.tooling.preview.Preview
+import androidx.compose.ui.unit.Dp
+import androidx.compose.ui.unit.dp
+import androidx.compose.ui.unit.sp
+import io.element.android.compound.theme.AvatarColors
+import io.element.android.compound.theme.ElementTheme
+import io.element.android.libraries.designsystem.preview.ElementPreview
+import io.element.android.libraries.designsystem.preview.PreviewGroup
+import io.element.android.libraries.designsystem.text.toSp
+import io.element.android.libraries.designsystem.theme.components.Text
+
+@Composable
+internal fun TextAvatar(
+ text: String,
+ size: Dp,
+ colors: AvatarColors,
+ contentDescription: String?,
+ modifier: Modifier = Modifier,
+) {
+ Box(
+ modifier
+ .size(size)
+ .clip(CircleShape)
+ .background(color = colors.background)
+ ) {
+ val fontSize = size.toSp() / 2
+ val originalFont = ElementTheme.typography.fontHeadingMdBold
+ val ratio = fontSize.value / originalFont.fontSize.value
+ val lineHeight = originalFont.lineHeight * ratio
+ Text(
+ modifier = Modifier
+ .clearAndSetSemantics {
+ contentDescription?.let {
+ this.contentDescription = it
+ }
+ }
+ .align(Alignment.Center),
+ text = text,
+ style = originalFont.copy(fontSize = fontSize, lineHeight = lineHeight, letterSpacing = 0.sp),
+ color = colors.foreground,
+ )
+ }
+}
+
+@Preview(group = PreviewGroup.Avatars)
+@Composable
+internal fun TextAvatarPreview() = ElementPreview {
+ TextAvatar(
+ text = "AB",
+ size = 40.dp,
+ colors = AvatarColors(
+ background = ElementTheme.colors.bgSubtlePrimary,
+ foreground = ElementTheme.colors.iconPrimary,
+ ),
+ contentDescription = null,
+ )
+ }
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/TombstonedRoomAvatar.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/TombstonedRoomAvatar.kt
new file mode 100644
index 0000000000..fe09be909d
--- /dev/null
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/avatar/TombstonedRoomAvatar.kt
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.designsystem.components.avatar
+
+import androidx.compose.runtime.Composable
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.tooling.preview.Preview
+import io.element.android.compound.theme.AvatarColors
+import io.element.android.compound.theme.ElementTheme
+import io.element.android.libraries.designsystem.preview.ElementPreview
+import io.element.android.libraries.designsystem.preview.PreviewGroup
+
+@Composable
+fun TombstonedRoomAvatar(
+ size: AvatarSize,
+ modifier: Modifier = Modifier,
+ contentDescription: String? = null,
+) {
+ TextAvatar(
+ text = "!",
+ size = size.dp,
+ colors = AvatarColors(
+ background = ElementTheme.colors.bgSubtlePrimary,
+ foreground = ElementTheme.colors.iconTertiary
+ ),
+ modifier = modifier,
+ contentDescription = contentDescription
+ )
+}
+
+@Preview(group = PreviewGroup.Avatars)
+@Composable
+internal fun TombstonedRoomAvatarPreview() = ElementPreview {
+ TombstonedRoomAvatar(
+ size = AvatarSize.RoomListItem,
+ contentDescription = null,
+ )
+}
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/media/WaveformPlaybackView.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/media/WaveformPlaybackView.kt
index 8986db82ee..767b56410f 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/media/WaveformPlaybackView.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/components/media/WaveformPlaybackView.kt
@@ -19,7 +19,6 @@ import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
-import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.geometry.CornerRadius
import androidx.compose.ui.geometry.Offset
@@ -60,7 +59,6 @@ private const val DEFAULT_GRAPHICS_LAYER_ALPHA: Float = 0.99F
* @param lineWidth The width of the waveform lines.
* @param linePadding The padding between waveform lines.
*/
-@OptIn(ExperimentalComposeUiApi::class)
@Composable
fun WaveformPlaybackView(
playbackProgress: Float,
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/DpScale.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/DpScale.kt
index 258d24cb99..856160d7bf 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/DpScale.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/DpScale.kt
@@ -11,6 +11,7 @@ import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.padding
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.tooling.preview.Preview
@@ -27,6 +28,7 @@ import io.element.android.libraries.designsystem.theme.components.Text
* will be smaller.
*/
@Composable
+@ReadOnlyComposable
fun Dp.applyScaleDown(): Dp = with(LocalDensity.current) {
return this@applyScaleDown * fontScale.coerceAtMost(1f)
}
@@ -37,6 +39,7 @@ fun Dp.applyScaleDown(): Dp = with(LocalDensity.current) {
* will be bigger.
*/
@Composable
+@ReadOnlyComposable
fun Dp.applyScaleUp(): Dp = with(LocalDensity.current) {
return this@applyScaleUp * fontScale.coerceAtLeast(1f)
}
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/UnitConverters.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/UnitConverters.kt
index c358517946..eaf6712830 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/UnitConverters.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/UnitConverters.kt
@@ -8,6 +8,7 @@
package io.element.android.libraries.designsystem.text
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.TextUnit
@@ -17,6 +18,7 @@ import androidx.compose.ui.unit.TextUnit
* Can be used for instance to use Dp unit for text.
*/
@Composable
+@ReadOnlyComposable
fun Dp.toSp(): TextUnit = with(LocalDensity.current) { toSp() }
/**
@@ -24,22 +26,26 @@ fun Dp.toSp(): TextUnit = with(LocalDensity.current) { toSp() }
* Can be used for instance to use Sp unit for size.
*/
@Composable
+@ReadOnlyComposable
fun TextUnit.toDp(): Dp = with(LocalDensity.current) { toDp() }
/**
* Convert Px value to Dp, regarding current density.
*/
@Composable
+@ReadOnlyComposable
fun Int.toDp(): Dp = with(LocalDensity.current) { toDp() }
/**
* Convert Dp value to pixels, regarding current density.
*/
@Composable
+@ReadOnlyComposable
fun Dp.toPx(): Float = with(LocalDensity.current) { toPx() }
/**
* Convert Dp value to pixels, regarding current density.
*/
@Composable
+@ReadOnlyComposable
fun Dp.roundToPx(): Int = with(LocalDensity.current) { roundToPx() }
diff --git a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/utils/WindowInsetsExtension.kt b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/utils/WindowInsetsExtension.kt
index f70cb5424e..a3a471875b 100644
--- a/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/utils/WindowInsetsExtension.kt
+++ b/libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/utils/WindowInsetsExtension.kt
@@ -9,10 +9,12 @@ package io.element.android.libraries.designsystem.utils
import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.platform.LocalLayoutDirection
@Composable
+@ReadOnlyComposable
fun WindowInsets.copy(
top: Int? = null,
right: Int? = null,
diff --git a/libraries/designsystem/src/test/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarDataTest.kt b/libraries/designsystem/src/test/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarDataTest.kt
index 6fe50e995b..01395eb9f1 100644
--- a/libraries/designsystem/src/test/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarDataTest.kt
+++ b/libraries/designsystem/src/test/kotlin/io/element/android/libraries/designsystem/components/avatar/AvatarDataTest.kt
@@ -14,30 +14,30 @@ class AvatarDataTest {
@Test
fun `initial with text should get the first char, uppercased`() {
val data = AvatarData("id", "test", null, AvatarSize.InviteSender)
- assertThat(data.initial).isEqualTo("T")
+ assertThat(data.initialLetter).isEqualTo("T")
}
@Test
fun `initial with leading whitespace should get the first non-whitespace char, uppercased`() {
val data = AvatarData("id", " test", null, AvatarSize.InviteSender)
- assertThat(data.initial).isEqualTo("T")
+ assertThat(data.initialLetter).isEqualTo("T")
}
@Test
fun `initial with long emoji should get the full emoji`() {
val data = AvatarData("id", "\uD83C\uDFF3\uFE0F\u200D\uD83C\uDF08 Test", null, AvatarSize.InviteSender)
- assertThat(data.initial).isEqualTo("\uD83C\uDFF3\uFE0F\u200D\uD83C\uDF08")
+ assertThat(data.initialLetter).isEqualTo("\uD83C\uDFF3\uFE0F\u200D\uD83C\uDF08")
}
@Test
fun `initial with short emoji should get the emoji`() {
val data = AvatarData("id", "✂ Test", null, AvatarSize.InviteSender)
- assertThat(data.initial).isEqualTo("✂")
+ assertThat(data.initialLetter).isEqualTo("✂")
}
@Test
fun `initial with a single letter should take that letter`() {
val data = AvatarData("id", "T", null, AvatarSize.InviteSender)
- assertThat(data.initial).isEqualTo("T")
+ assertThat(data.initialLetter).isEqualTo("T")
}
}
diff --git a/libraries/eventformatter/impl/src/main/res/values-es/translations.xml b/libraries/eventformatter/impl/src/main/res/values-es/translations.xml
index 65f16e35fe..186aad5455 100644
--- a/libraries/eventformatter/impl/src/main/res/values-es/translations.xml
+++ b/libraries/eventformatter/impl/src/main/res/values-es/translations.xml
@@ -19,6 +19,8 @@
"Eliminaste el avatar de la sala"
"%1$s expulsó permanentemente a %2$s"
"Expulsaste permanentemente a %1$s"
+ "Vetaste a %1$s: %2$s"
+ "%1$s vetó a %2$s: %3$s"
"%1$s creó la sala"
"Tú creaste la sala"
"%1$s invitó a %2$s"
@@ -55,6 +57,8 @@
"Rechazaste la invitación"
"%1$s echó a %2$s"
"Echaste a %1$s"
+ "Echaste a %1$s: %2$s"
+ "%1$s echó a %2$s: %3$s"
"%1$s envió una invitación a %2$s para unirse a la sala"
"Enviaste una invitación a %1$s para unirse a la sala"
"%1$s revocó la invitación a %2$s para unirse a la sala"
diff --git a/libraries/eventformatter/impl/src/main/res/values-ru/translations.xml b/libraries/eventformatter/impl/src/main/res/values-ru/translations.xml
index b2a86a6962..d0f4a39773 100644
--- a/libraries/eventformatter/impl/src/main/res/values-ru/translations.xml
+++ b/libraries/eventformatter/impl/src/main/res/values-ru/translations.xml
@@ -19,6 +19,8 @@
"Вы удалили изображение комнаты"
"%1$s заблокировал %2$s"
"Вы заблокировали %1$s"
+ "Вы заблокировали %1$s: %2$s"
+ "%1$s заблокирован %2$s: %3$s"
"%1$s создал комнату"
"Вы создали комнату"
"%1$s пригласил %2$s"
@@ -55,6 +57,8 @@
"Вы отклонили приглашение"
"%1$s удалил %2$s"
"Вы удалили %1$s"
+ "Вы удалили %1$s: %2$s"
+ "%1$s удален %2$s: %3$s"
"%1$s отправила приглашение %2$s присоединиться к комнате"
"Вы отправили приглашение присоединиться к комнате %1$s"
"%1$s отозвал приглашение %2$s присоединиться к комнате"
diff --git a/libraries/eventformatter/impl/src/main/res/values-uz/translations.xml b/libraries/eventformatter/impl/src/main/res/values-uz/translations.xml
index 91ac192205..aab758a1a1 100644
--- a/libraries/eventformatter/impl/src/main/res/values-uz/translations.xml
+++ b/libraries/eventformatter/impl/src/main/res/values-uz/translations.xml
@@ -24,7 +24,7 @@
"%1$ssizni taklif qildi"
"%1$sxonaga qo\'shildi"
"Siz xonaga qo\'shildingiz"
- "%1$s qo\'shilishni so\'radi"
+ "%1$s qoʻshilishni soʻradi"
"%1$s %2$sga qo\'shilishga ruxsat berdi"
"Siz %1$sga qo\'shilishaga ruxsat berdingiz"
"Siz qoʻshilishni soʻragansiz"
diff --git a/libraries/featureflag/api/src/main/kotlin/io/element/android/libraries/featureflag/api/FeatureFlags.kt b/libraries/featureflag/api/src/main/kotlin/io/element/android/libraries/featureflag/api/FeatureFlags.kt
index bcffe4daf0..00ab0fb57c 100644
--- a/libraries/featureflag/api/src/main/kotlin/io/element/android/libraries/featureflag/api/FeatureFlags.kt
+++ b/libraries/featureflag/api/src/main/kotlin/io/element/android/libraries/featureflag/api/FeatureFlags.kt
@@ -112,6 +112,17 @@ enum class FeatureFlags(
defaultValue = { false },
isFinished = false,
),
+ EnableKeyShareOnInvite(
+ key = "feature.enableKeyShareOnInvite",
+ title = "Share encrypted history with new members",
+ description = "When inviting a user to an encrypted room that has history visibility set to \"shared\"," +
+ " share encrypted history with that user, and accept encrypted history when you are invited to such a room." +
+ "\nRequires an app restart to take effect." +
+ "\n\nWARNING: this feature is EXPERIMENTAL and not all security precautions are implemented." +
+ " Do not enable on production accounts.",
+ defaultValue = { false },
+ isFinished = false,
+ ),
Knock(
key = "feature.knock",
title = "Ask to join",
diff --git a/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsEvents.kt b/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsEvents.kt
new file mode 100644
index 0000000000..e0b8433749
--- /dev/null
+++ b/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsEvents.kt
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.fullscreenintent.api
+
+sealed interface FullScreenIntentPermissionsEvents {
+ data object Dismiss : FullScreenIntentPermissionsEvents
+ data object OpenSettings : FullScreenIntentPermissionsEvents
+}
diff --git a/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsState.kt b/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsState.kt
index 3d77ebb4b5..5b3f84f977 100644
--- a/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsState.kt
+++ b/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsState.kt
@@ -10,6 +10,5 @@ package io.element.android.libraries.fullscreenintent.api
data class FullScreenIntentPermissionsState(
val permissionGranted: Boolean,
val shouldDisplayBanner: Boolean,
- val dismissFullScreenIntentBanner: () -> Unit,
- val openFullScreenIntentSettings: () -> Unit,
+ val eventSink: (FullScreenIntentPermissionsEvents) -> Unit,
)
diff --git a/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsStateProvider.kt b/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsStateProvider.kt
index 7dbe340c39..25ab2ab522 100644
--- a/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsStateProvider.kt
+++ b/libraries/fullscreenintent/api/src/main/kotlin/io/element/android/libraries/fullscreenintent/api/FullScreenIntentPermissionsStateProvider.kt
@@ -10,11 +10,9 @@ package io.element.android.libraries.fullscreenintent.api
fun aFullScreenIntentPermissionsState(
permissionGranted: Boolean = true,
shouldDisplay: Boolean = false,
- openFullScreenIntentSettings: () -> Unit = {},
- dismissFullScreenIntentBanner: () -> Unit = {},
+ eventSink: (FullScreenIntentPermissionsEvents) -> Unit = {},
) = FullScreenIntentPermissionsState(
permissionGranted = permissionGranted,
shouldDisplayBanner = shouldDisplay,
- openFullScreenIntentSettings = openFullScreenIntentSettings,
- dismissFullScreenIntentBanner = dismissFullScreenIntentBanner,
+ eventSink = eventSink,
)
diff --git a/libraries/fullscreenintent/impl/src/main/kotlin/io/element/android/libraries/fullscreenintent/impl/FullScreenIntentPermissionsPresenter.kt b/libraries/fullscreenintent/impl/src/main/kotlin/io/element/android/libraries/fullscreenintent/impl/FullScreenIntentPermissionsPresenter.kt
index 3e427b6fa6..14cc438f41 100644
--- a/libraries/fullscreenintent/impl/src/main/kotlin/io/element/android/libraries/fullscreenintent/impl/FullScreenIntentPermissionsPresenter.kt
+++ b/libraries/fullscreenintent/impl/src/main/kotlin/io/element/android/libraries/fullscreenintent/impl/FullScreenIntentPermissionsPresenter.kt
@@ -23,6 +23,7 @@ import io.element.android.libraries.architecture.Presenter
import io.element.android.libraries.core.meta.BuildMeta
import io.element.android.libraries.di.AppScope
import io.element.android.libraries.di.SingleIn
+import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsEvents
import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsState
import io.element.android.libraries.preferences.api.store.PreferenceDataStoreFactory
import io.element.android.services.toolbox.api.intent.ExternalIntentLauncher
@@ -60,15 +61,20 @@ class FullScreenIntentPermissionsPresenter @Inject constructor(
val coroutineScope = rememberCoroutineScope()
val isGranted = notificationManagerCompat.canUseFullScreenIntent()
val isBannerDismissed by isFullScreenIntentBannerDismissed.collectAsState(initial = true)
+
+ fun handleEvents(event: FullScreenIntentPermissionsEvents) {
+ when (event) {
+ FullScreenIntentPermissionsEvents.Dismiss -> coroutineScope.launch {
+ dismissFullScreenIntentBanner()
+ }
+ FullScreenIntentPermissionsEvents.OpenSettings -> openFullScreenIntentSettings()
+ }
+ }
+
return FullScreenIntentPermissionsState(
permissionGranted = isGranted,
shouldDisplayBanner = !isBannerDismissed && !isGranted,
- dismissFullScreenIntentBanner = {
- coroutineScope.launch {
- dismissFullScreenIntentBanner()
- }
- },
- openFullScreenIntentSettings = ::openFullScreenIntentSettings,
+ eventSink = ::handleEvents,
)
}
diff --git a/libraries/fullscreenintent/impl/src/test/kotlin/io/element/android/libraries/fullscreenintent/test/FullScreenIntentPermissionsPresenterTest.kt b/libraries/fullscreenintent/impl/src/test/kotlin/io/element/android/libraries/fullscreenintent/test/FullScreenIntentPermissionsPresenterTest.kt
index 8cf508562b..0d10032da0 100644
--- a/libraries/fullscreenintent/impl/src/test/kotlin/io/element/android/libraries/fullscreenintent/test/FullScreenIntentPermissionsPresenterTest.kt
+++ b/libraries/fullscreenintent/impl/src/test/kotlin/io/element/android/libraries/fullscreenintent/test/FullScreenIntentPermissionsPresenterTest.kt
@@ -15,6 +15,7 @@ import app.cash.molecule.moleculeFlow
import app.cash.turbine.test
import com.google.common.truth.Truth.assertThat
import io.element.android.libraries.core.meta.BuildMeta
+import io.element.android.libraries.fullscreenintent.api.FullScreenIntentPermissionsEvents
import io.element.android.libraries.fullscreenintent.impl.FullScreenIntentPermissionsPresenter
import io.element.android.libraries.matrix.test.core.aBuildMeta
import io.element.android.libraries.preferences.test.FakePreferenceDataStoreFactory
@@ -76,10 +77,8 @@ class FullScreenIntentPermissionsPresenterTest {
}.test {
skipItems(1)
val loadedItem = awaitItem()
- loadedItem.dismissFullScreenIntentBanner()
-
+ loadedItem.eventSink(FullScreenIntentPermissionsEvents.Dismiss)
runCurrent()
-
assertThat(awaitItem().shouldDisplayBanner).isFalse()
}
}
@@ -94,10 +93,8 @@ class FullScreenIntentPermissionsPresenterTest {
}.test {
skipItems(1)
val loadedItem = awaitItem()
- loadedItem.openFullScreenIntentSettings()
-
+ loadedItem.eventSink(FullScreenIntentPermissionsEvents.OpenSettings)
launchLambda.assertions().isCalledOnce()
-
cancelAndIgnoreRemainingEvents()
}
}
@@ -115,10 +112,8 @@ class FullScreenIntentPermissionsPresenterTest {
}.test {
skipItems(1)
val loadedItem = awaitItem()
- loadedItem.openFullScreenIntentSettings()
-
+ loadedItem.eventSink(FullScreenIntentPermissionsEvents.OpenSettings)
launchLambda.assertions().isNeverCalled()
-
cancelAndIgnoreRemainingEvents()
}
}
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/notification/NotificationData.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/notification/NotificationData.kt
index 338193ed44..f90b70171e 100644
--- a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/notification/NotificationData.kt
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/notification/NotificationData.kt
@@ -68,6 +68,7 @@ sealed interface NotificationContent {
) : MessageLike
data object RoomEncrypted : MessageLike
+ data object UnableToResolve : MessageLike
data class RoomMessage(
val senderId: UserId,
val messageType: MessageType
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/BaseRoom.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/BaseRoom.kt
index 120321bddf..f6152cf0c6 100644
--- a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/BaseRoom.kt
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/BaseRoom.kt
@@ -10,9 +10,11 @@ package io.element.android.libraries.matrix.api.room
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.SessionId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import io.element.android.libraries.matrix.api.room.powerlevels.RoomPowerLevels
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
import io.element.android.libraries.matrix.api.roomdirectory.RoomVisibility
import io.element.android.libraries.matrix.api.timeline.ReceiptType
import kotlinx.coroutines.CoroutineScope
@@ -55,6 +57,8 @@ interface BaseRoom : Closeable {
*/
fun info(): RoomInfo = roomInfoFlow.value
+ fun predecessorRoom(): PredecessorRoom?
+
/**
* A one-to-one is a room with exactly 2 members.
* See [the Matrix spec](https://spec.matrix.org/latest/client-server-api/#default-underride-rules).
@@ -216,17 +220,17 @@ interface BaseRoom : Closeable {
/**
* Store the given `ComposerDraft` in the state store of this room.
*/
- suspend fun saveComposerDraft(composerDraft: ComposerDraft): Result
+ suspend fun saveComposerDraft(composerDraft: ComposerDraft, threadRoot: ThreadId?): Result
/**
* Retrieve the `ComposerDraft` stored in the state store for this room.
*/
- suspend fun loadComposerDraft(): Result
+ suspend fun loadComposerDraft(threadRoot: ThreadId?): Result
/**
* Clear the `ComposerDraft` stored in the state store for this room.
*/
- suspend fun clearComposerDraft(): Result
+ suspend fun clearComposerDraft(threadRoot: ThreadId?): Result
/**
* Reports a room as inappropriate to the server.
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/RoomInfo.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/RoomInfo.kt
index 8702218150..13e2ed44da 100644
--- a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/RoomInfo.kt
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/RoomInfo.kt
@@ -14,6 +14,7 @@ import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.room.history.RoomHistoryVisibility
import io.element.android.libraries.matrix.api.room.join.JoinRule
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.matrix.api.user.MatrixUser
import kotlinx.collections.immutable.ImmutableList
import kotlinx.collections.immutable.ImmutableMap
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/tombstone/PredecessorRoom.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/tombstone/PredecessorRoom.kt
new file mode 100644
index 0000000000..cd54b5a07b
--- /dev/null
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/tombstone/PredecessorRoom.kt
@@ -0,0 +1,31 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.matrix.api.room.tombstone
+
+import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
+
+/**
+ *
+ * When a room A is tombstoned, it is replaced by a room B. The room A is the
+ * predecessor of B, and B is the successor of A. This type holds information
+ * about the predecessor room.
+ *
+ * A room is tombstoned if it has received a m.room.tombstone state event.
+ *
+ */
+data class PredecessorRoom(
+ /**
+ * The ID of the replaced room.
+ */
+ val roomId: RoomId,
+ /**
+ * The event ID of the last known event in the predecessor room.
+ */
+ val lastEventId: EventId,
+)
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/SuccessorRoom.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/tombstone/SuccessorRoom.kt
similarity index 92%
rename from libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/SuccessorRoom.kt
rename to libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/tombstone/SuccessorRoom.kt
index 4aaf3dd2d2..957585a464 100644
--- a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/SuccessorRoom.kt
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/tombstone/SuccessorRoom.kt
@@ -5,7 +5,7 @@
* Please see LICENSE files in the repository root for full details.
*/
-package io.element.android.libraries.matrix.api.room
+package io.element.android.libraries.matrix.api.room.tombstone
import io.element.android.libraries.matrix.api.core.RoomId
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/Timeline.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/Timeline.kt
index a940a0981f..00652a4fa9 100644
--- a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/Timeline.kt
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/Timeline.kt
@@ -131,6 +131,7 @@ interface Timeline : AutoCloseable {
* @param zoomLevel Optional zoom level to display the map at.
* @param assetType Optional type of the location asset.
* Set to SENDER if sharing own location. Set to PIN if sharing any location.
+ * @param replyParameters Optional reply parameters to use when sending the location.
*/
suspend fun sendLocation(
body: String,
@@ -138,6 +139,7 @@ interface Timeline : AutoCloseable {
description: String? = null,
zoomLevel: Int? = null,
assetType: AssetType? = null,
+ replyParameters: ReplyParameters?,
): Result
suspend fun sendVoiceMessage(
diff --git a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/item/event/MessageShield.kt b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/item/event/MessageShield.kt
index 1630f49301..2fd9ec699a 100644
--- a/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/item/event/MessageShield.kt
+++ b/libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/timeline/item/event/MessageShield.kt
@@ -28,6 +28,9 @@ sealed interface MessageShield {
/** The sender was previously verified but is not anymore. */
data class VerificationViolation(val isCritical: Boolean) : MessageShield
+
+ /** The sender of the event does not match the owner of the device that created the Megolm session. */
+ data class MismatchedSender(val isCritical: Boolean) : MessageShield
}
val MessageShield.isCritical: Boolean
@@ -38,4 +41,5 @@ val MessageShield.isCritical: Boolean
is MessageShield.UnverifiedIdentity -> isCritical
is MessageShield.SentInClear -> isCritical
is MessageShield.VerificationViolation -> isCritical
+ is MessageShield.MismatchedSender -> isCritical
}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustClientSessionDelegate.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustClientSessionDelegate.kt
index cb1a443ccb..7a3bfb3e6b 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustClientSessionDelegate.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustClientSessionDelegate.kt
@@ -8,12 +8,12 @@
package io.element.android.libraries.matrix.impl
import io.element.android.libraries.core.coroutine.CoroutineDispatchers
+import io.element.android.libraries.core.log.logger.LoggerTag
import io.element.android.libraries.matrix.impl.mapper.toSessionData
import io.element.android.libraries.matrix.impl.paths.getSessionPaths
import io.element.android.libraries.matrix.impl.util.anonymizedTokens
import io.element.android.libraries.sessionstorage.api.SessionStore
import kotlinx.coroutines.CoroutineScope
-import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.launch
import org.matrix.rustcomponents.sdk.ClientDelegate
import org.matrix.rustcomponents.sdk.ClientSessionDelegate
@@ -22,6 +22,8 @@ import timber.log.Timber
import java.lang.ref.WeakReference
import java.util.concurrent.atomic.AtomicBoolean
+private val loggerTag = LoggerTag("RustClientSessionDelegate")
+
/**
* This class is responsible for handling the session data for the Rust SDK.
*
@@ -29,14 +31,11 @@ import java.util.concurrent.atomic.AtomicBoolean
*
* IMPORTANT: you must set the [client] property as soon as possible so [didReceiveAuthError] can work properly.
*/
-@OptIn(ExperimentalCoroutinesApi::class)
class RustClientSessionDelegate(
private val sessionStore: SessionStore,
private val appCoroutineScope: CoroutineScope,
coroutineDispatchers: CoroutineDispatchers,
) : ClientSessionDelegate, ClientDelegate {
- private val clientLog = Timber.tag("$this")
-
// Used to ensure several calls to `didReceiveAuthError` don't trigger multiple logouts
private val isLoggingOut = AtomicBoolean(false)
@@ -64,7 +63,7 @@ class RustClientSessionDelegate(
appCoroutineScope.launch(updateTokensDispatcher) {
val existingData = sessionStore.getSession(session.userId) ?: return@launch
val (anonymizedAccessToken, anonymizedRefreshToken) = session.anonymizedTokens()
- clientLog.d(
+ Timber.tag(loggerTag.value).d(
"Saving new session data with token: access token '$anonymizedAccessToken' and refresh token '$anonymizedRefreshToken'. " +
"Was token valid: ${existingData.isTokenValid}"
)
@@ -75,29 +74,29 @@ class RustClientSessionDelegate(
sessionPaths = existingData.getSessionPaths(),
)
sessionStore.updateData(newData)
- clientLog.d("Saved new session data with access token: '$anonymizedAccessToken'.")
+ Timber.tag(loggerTag.value).d("Saved new session data with access token: '$anonymizedAccessToken'.")
}.invokeOnCompletion {
if (it != null) {
- clientLog.e(it, "Failed to save new session data.")
+ Timber.tag(loggerTag.value).e(it, "Failed to save new session data.")
}
}
}
override fun didReceiveAuthError(isSoftLogout: Boolean) {
- clientLog.w("didReceiveAuthError(isSoftLogout=$isSoftLogout)")
+ Timber.tag(loggerTag.value).w("didReceiveAuthError(isSoftLogout=$isSoftLogout)")
if (isLoggingOut.getAndSet(true).not()) {
- clientLog.v("didReceiveAuthError -> do the cleanup")
+ Timber.tag(loggerTag.value).v("didReceiveAuthError -> do the cleanup")
// TODO handle isSoftLogout parameter.
appCoroutineScope.launch(updateTokensDispatcher) {
val currentClient = client.get()
if (currentClient == null) {
- clientLog.w("didReceiveAuthError -> no client, exiting")
+ Timber.tag(loggerTag.value).w("didReceiveAuthError -> no client, exiting")
isLoggingOut.set(false)
return@launch
}
val existingData = sessionStore.getSession(currentClient.sessionId.value)
val (anonymizedAccessToken, anonymizedRefreshToken) = existingData.anonymizedTokens()
- clientLog.d(
+ Timber.tag(loggerTag.value).d(
"Removing session data with access token '$anonymizedAccessToken' " +
"and refresh token '$anonymizedRefreshToken'."
)
@@ -105,18 +104,18 @@ class RustClientSessionDelegate(
// Set isTokenValid to false
val newData = existingData.copy(isTokenValid = false)
sessionStore.updateData(newData)
- clientLog.d("Invalidated session data with access token: '$anonymizedAccessToken'.")
+ Timber.tag(loggerTag.value).d("Invalidated session data with access token: '$anonymizedAccessToken'.")
} else {
- clientLog.d("No session data found.")
+ Timber.tag(loggerTag.value).d("No session data found.")
}
currentClient.logout(userInitiated = false, ignoreSdkError = true)
}.invokeOnCompletion {
if (it != null) {
- clientLog.e(it, "Failed to remove session data.")
+ Timber.tag(loggerTag.value).e(it, "Failed to remove session data.")
}
}
} else {
- clientLog.v("didReceiveAuthError -> already cleaning up")
+ Timber.tag(loggerTag.value).v("didReceiveAuthError -> already cleaning up")
}
}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustMatrixClientFactory.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustMatrixClientFactory.kt
index bc8e337ada..8261969918 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustMatrixClientFactory.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/RustMatrixClientFactory.kt
@@ -127,6 +127,7 @@ class RustMatrixClientFactory @Inject constructor(
TrustRequirement.UNTRUSTED
}
)
+ .enableShareHistoryOnInvite(featureFlagService.isFeatureEnabled(FeatureFlags.EnableKeyShareOnInvite))
.run {
// Apply sliding sync version settings
when (slidingSyncType) {
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/media/RustMediaLoader.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/media/RustMediaLoader.kt
index d846321811..d7cd9c4092 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/media/RustMediaLoader.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/media/RustMediaLoader.kt
@@ -13,7 +13,6 @@ import io.element.android.libraries.core.mimetype.MimeTypes
import io.element.android.libraries.matrix.api.media.MatrixMediaLoader
import io.element.android.libraries.matrix.api.media.MediaFile
import io.element.android.libraries.matrix.api.media.MediaSource
-import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.withContext
import org.matrix.rustcomponents.sdk.Client
import org.matrix.rustcomponents.sdk.use
@@ -25,14 +24,12 @@ class RustMediaLoader(
dispatchers: CoroutineDispatchers,
private val innerClient: Client,
) : MatrixMediaLoader {
- @OptIn(ExperimentalCoroutinesApi::class)
private val mediaDispatcher = dispatchers.io.limitedParallelism(32)
private val cacheDirectory
get() = File(baseCacheDirectory, "temp/media").apply {
if (!exists()) mkdirs() // Must always ensure that this directory exists because "Clear cache" does not restart an app's process.
}
- @OptIn(ExperimentalUnsignedTypes::class)
override suspend fun loadMediaContent(source: MediaSource): Result =
withContext(mediaDispatcher) {
runCatchingExceptions {
@@ -42,7 +39,6 @@ class RustMediaLoader(
}
}
- @OptIn(ExperimentalUnsignedTypes::class)
override suspend fun loadMediaThumbnail(
source: MediaSource,
width: Long,
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationService.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationService.kt
index bab7cdea02..b88b53454a 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationService.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationService.kt
@@ -12,6 +12,7 @@ import io.element.android.libraries.core.extensions.runCatchingExceptions
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.SessionId
+import io.element.android.libraries.matrix.api.notification.NotificationContent
import io.element.android.libraries.matrix.api.notification.NotificationData
import io.element.android.libraries.matrix.api.notification.NotificationService
import io.element.android.services.toolbox.api.systemclock.SystemClock
@@ -24,7 +25,7 @@ class RustNotificationService(
private val sessionId: SessionId,
private val notificationClient: NotificationClient,
private val dispatchers: CoroutineDispatchers,
- clock: SystemClock,
+ private val clock: SystemClock,
) : NotificationService {
private val notificationMapper: NotificationMapper = NotificationMapper(clock)
@@ -43,11 +44,32 @@ class RustNotificationService(
val eventIds = requests.flatMap { it.eventIds }
for (eventId in eventIds) {
val item = items[eventId]
+ val roomId = RoomId(requests.find { it.eventIds.contains(eventId) }?.roomId!!)
if (item != null) {
- val roomId = RoomId(requests.find { it.eventIds.contains(eventId) }?.roomId!!)
put(EventId(eventId), notificationMapper.map(sessionId, EventId(eventId), roomId, item))
} else {
Timber.e("Could not retrieve event for notification with $eventId")
+ put(
+ EventId(eventId),
+ NotificationData(
+ sessionId = sessionId,
+ eventId = EventId(eventId),
+ threadId = null,
+ roomId = roomId,
+ senderAvatarUrl = null,
+ senderDisplayName = null,
+ senderIsNameAmbiguous = false,
+ roomAvatarUrl = null,
+ roomDisplayName = null,
+ isDirect = false,
+ isDm = false,
+ isEncrypted = false,
+ isNoisy = false,
+ timestamp = clock.epochMillis(),
+ content = NotificationContent.MessageLike.UnableToResolve,
+ hasMention = false
+ )
+ )
}
}
}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RoomInfoMapper.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RoomInfoMapper.kt
index 2717f6275e..e0dec91899 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RoomInfoMapper.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RoomInfoMapper.kt
@@ -14,11 +14,11 @@ import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.room.CurrentUserMembership
import io.element.android.libraries.matrix.api.room.RoomInfo
import io.element.android.libraries.matrix.api.room.RoomNotificationMode
-import io.element.android.libraries.matrix.api.room.SuccessorRoom
import io.element.android.libraries.matrix.api.user.MatrixUser
import io.element.android.libraries.matrix.impl.room.history.map
import io.element.android.libraries.matrix.impl.room.join.map
import io.element.android.libraries.matrix.impl.room.member.RoomMemberMapper
+import io.element.android.libraries.matrix.impl.room.tombstone.map
import kotlinx.collections.immutable.ImmutableMap
import kotlinx.collections.immutable.toImmutableList
import kotlinx.collections.immutable.toPersistentMap
@@ -28,7 +28,6 @@ import uniffi.matrix_sdk_base.EncryptionState
import org.matrix.rustcomponents.sdk.Membership as RustMembership
import org.matrix.rustcomponents.sdk.RoomInfo as RustRoomInfo
import org.matrix.rustcomponents.sdk.RoomNotificationMode as RustRoomNotificationMode
-import org.matrix.rustcomponents.sdk.SuccessorRoom as RustSuccessorRoom
class RoomInfoMapper {
fun map(rustRoomInfo: RustRoomInfo): RoomInfo = rustRoomInfo.let {
@@ -88,11 +87,6 @@ fun RustRoomNotificationMode.map(): RoomNotificationMode = when (this) {
RustRoomNotificationMode.MUTE -> RoomNotificationMode.MUTE
}
-fun RustSuccessorRoom.map(): SuccessorRoom = SuccessorRoom(
- roomId = RoomId(roomId),
- reason = reason,
-)
-
/**
* Map a RoomHero to a MatrixUser. There is not need to create a RoomHero type on the application side.
*/
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RustBaseRoom.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RustBaseRoom.kt
index f86a179af2..b6ff98baed 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RustBaseRoom.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/RustBaseRoom.kt
@@ -14,6 +14,7 @@ import io.element.android.libraries.matrix.api.core.DeviceId
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.SessionId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.room.BaseRoom
import io.element.android.libraries.matrix.api.room.MessageEventType
@@ -24,12 +25,14 @@ import io.element.android.libraries.matrix.api.room.RoomMembershipObserver
import io.element.android.libraries.matrix.api.room.StateEventType
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import io.element.android.libraries.matrix.api.room.powerlevels.RoomPowerLevels
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
import io.element.android.libraries.matrix.api.roomdirectory.RoomVisibility
import io.element.android.libraries.matrix.api.timeline.ReceiptType
import io.element.android.libraries.matrix.impl.room.draft.into
import io.element.android.libraries.matrix.impl.room.member.RoomMemberListFetcher
import io.element.android.libraries.matrix.impl.room.member.RoomMemberMapper
import io.element.android.libraries.matrix.impl.room.powerlevels.RoomPowerLevelsMapper
+import io.element.android.libraries.matrix.impl.room.tombstone.map
import io.element.android.libraries.matrix.impl.roomdirectory.map
import io.element.android.libraries.matrix.impl.timeline.toRustReceiptType
import io.element.android.libraries.matrix.impl.util.mxCallbackFlow
@@ -78,6 +81,10 @@ class RustBaseRoom(
})
}.stateIn(roomCoroutineScope, started = SharingStarted.Lazily, initialValue = initialRoomInfo)
+ override fun predecessorRoom(): PredecessorRoom? {
+ return innerRoom.predecessorRoom()?.map()
+ }
+
override suspend fun subscribeToSync() = roomSyncSubscriber.subscribe(roomId)
override suspend fun updateMembers() {
@@ -260,24 +267,24 @@ class RustBaseRoom(
}
}
- override suspend fun saveComposerDraft(composerDraft: ComposerDraft): Result = withContext(roomDispatcher) {
+ override suspend fun saveComposerDraft(composerDraft: ComposerDraft, threadRoot: ThreadId?): Result = withContext(roomDispatcher) {
runCatchingExceptions {
- Timber.d("saveComposerDraft: $composerDraft into $roomId")
- innerRoom.saveComposerDraft(composerDraft.into())
+ Timber.d("saveComposerDraft: $composerDraft into $roomId for thread root: $threadRoot")
+ innerRoom.saveComposerDraft(composerDraft.into(), threadRoot = threadRoot?.value)
}
}
- override suspend fun loadComposerDraft(): Result = withContext(roomDispatcher) {
+ override suspend fun loadComposerDraft(threadRoot: ThreadId?): Result = withContext(roomDispatcher) {
runCatchingExceptions {
- Timber.d("loadComposerDraft for $roomId")
- innerRoom.loadComposerDraft()?.into()
+ Timber.d("loadComposerDraft for $roomId with thread root: $threadRoot")
+ innerRoom.loadComposerDraft(threadRoot?.value)?.into()
}
}
- override suspend fun clearComposerDraft(): Result = withContext(roomDispatcher) {
+ override suspend fun clearComposerDraft(threadRoot: ThreadId?): Result = withContext(roomDispatcher) {
runCatchingExceptions {
- Timber.d("clearComposerDraft for $roomId")
- innerRoom.clearComposerDraft()
+ Timber.d("clearComposerDraft for $roomId with thread root: $threadRoot")
+ innerRoom.clearComposerDraft(threadRoot = threadRoot?.value)
}
}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/tombstone/PredecessorRoom.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/tombstone/PredecessorRoom.kt
new file mode 100644
index 0000000000..08daee4f19
--- /dev/null
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/tombstone/PredecessorRoom.kt
@@ -0,0 +1,20 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.matrix.impl.room.tombstone
+
+import io.element.android.libraries.matrix.api.core.EventId
+import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
+import org.matrix.rustcomponents.sdk.PredecessorRoom as RustPredecessorRoom
+
+fun RustPredecessorRoom.map(): PredecessorRoom {
+ return PredecessorRoom(
+ roomId = RoomId(roomId),
+ lastEventId = EventId(lastEventId),
+ )
+}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/tombstone/SuccessorRoom.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/tombstone/SuccessorRoom.kt
new file mode 100644
index 0000000000..afc0ee96af
--- /dev/null
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/room/tombstone/SuccessorRoom.kt
@@ -0,0 +1,19 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.matrix.impl.room.tombstone
+
+import io.element.android.libraries.matrix.api.core.RoomId
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
+import org.matrix.rustcomponents.sdk.SuccessorRoom as RustSuccessorRoom
+
+fun RustSuccessorRoom.map(): SuccessorRoom {
+ return SuccessorRoom(
+ roomId = RoomId(roomId),
+ reason = reason
+ )
+}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/roomlist/RoomListFactory.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/roomlist/RoomListFactory.kt
index 275c55ccc0..53b8127ab8 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/roomlist/RoomListFactory.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/roomlist/RoomListFactory.kt
@@ -27,6 +27,11 @@ import org.matrix.rustcomponents.sdk.RoomListService
import kotlin.coroutines.CoroutineContext
import org.matrix.rustcomponents.sdk.RoomList as InnerRoomList
+private val ROOM_LIST_RUST_FILTERS = listOf(
+ RoomListEntriesDynamicFilterKind.NonLeft,
+ RoomListEntriesDynamicFilterKind.DeduplicateVersions
+)
+
internal class RoomListFactory(
private val innerRoomListService: RoomListService,
private val sessionCoroutineScope: CoroutineScope,
@@ -55,11 +60,11 @@ internal class RoomListFactory(
coroutineScope.launch(coroutineContext) {
innerRoomList = innerProvider()
- innerRoomList?.let { innerRoomList ->
+ innerRoomList.let { innerRoomList ->
innerRoomList.entriesFlow(
pageSize = pageSize,
roomListDynamicEvents = dynamicEvents,
- initialFilterKind = RoomListEntriesDynamicFilterKind.NonLeft
+ initialFilterKind = RoomListEntriesDynamicFilterKind.All(ROOM_LIST_RUST_FILTERS),
).onEach { update ->
processor.postUpdate(update)
}.launchIn(this)
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/RustTimeline.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/RustTimeline.kt
index f2285b6aad..2f0154c208 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/RustTimeline.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/RustTimeline.kt
@@ -485,6 +485,7 @@ class RustTimeline(
description: String?,
zoomLevel: Int?,
assetType: AssetType?,
+ replyParameters: ReplyParameters?,
): Result = withContext(dispatcher) {
runCatchingExceptions {
inner.sendLocation(
@@ -493,6 +494,7 @@ class RustTimeline(
description = description,
zoomLevel = zoomLevel?.toUByte(),
assetType = assetType?.toInner(),
+ replyParams = replyParameters?.map(),
)
}
}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/item/event/EventTimelineItemMapper.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/item/event/EventTimelineItemMapper.kt
index 6d7ca02784..7cea0e29f4 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/item/event/EventTimelineItemMapper.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/item/event/EventTimelineItemMapper.kt
@@ -176,6 +176,7 @@ private fun ShieldState?.map(): MessageShield? {
ShieldStateCode.UNVERIFIED_IDENTITY -> MessageShield.UnverifiedIdentity(isCritical)
ShieldStateCode.SENT_IN_CLEAR -> MessageShield.SentInClear(isCritical)
ShieldStateCode.VERIFICATION_VIOLATION -> MessageShield.VerificationViolation(isCritical)
+ ShieldStateCode.MISMATCHED_SENDER -> MessageShield.MismatchedSender(isCritical)
}
}
diff --git a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessor.kt b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessor.kt
index 4dded4519d..8403f63188 100644
--- a/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessor.kt
+++ b/libraries/matrix/impl/src/main/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessor.kt
@@ -14,11 +14,10 @@ import io.element.android.libraries.matrix.api.timeline.item.event.MembershipCha
import io.element.android.libraries.matrix.api.timeline.item.event.OtherState
import io.element.android.libraries.matrix.api.timeline.item.event.RoomMembershipContent
import io.element.android.libraries.matrix.api.timeline.item.event.StateContent
-import io.element.android.libraries.matrix.api.timeline.item.virtual.VirtualTimelineItem
/**
* This timeline post-processor removes the room creation event and the self-join event from the timeline for DMs
- * or add the RoomBeginning item for non DM room.
+ * or add the RoomBeginning item.
*/
class RoomBeginningPostProcessor(private val mode: Timeline.Mode) {
fun process(
@@ -30,7 +29,7 @@ class RoomBeginningPostProcessor(private val mode: Timeline.Mode) {
return when {
items.isEmpty() -> items
mode == Timeline.Mode.PINNED_EVENTS -> items
- isDm -> processForDM(items, roomCreator, hasMoreToLoadBackwards)
+ isDm -> processForDM(items, roomCreator)
hasMoreToLoadBackwards -> items
else -> processForRoom(items)
}
@@ -41,13 +40,7 @@ class RoomBeginningPostProcessor(private val mode: Timeline.Mode) {
return items
}
- private fun processForDM(items: List, roomCreator: UserId?, hasMoreToLoadBackwards: Boolean): List {
- val roomBeginningItemIndex = if (!hasMoreToLoadBackwards) {
- items.indexOfFirst { it is MatrixTimelineItem.Virtual && it.virtual is VirtualTimelineItem.RoomBeginning }.takeIf { it >= 0 }
- } else {
- null
- }
-
+ private fun processForDM(items: List, roomCreator: UserId?): List {
// Find room creation event.
// This is usually the first MatrixTimelineItem.Event (so index 1, index 0 is a date)
val roomCreationEventIndex = items.indexOfFirst {
@@ -69,7 +62,6 @@ class RoomBeginningPostProcessor(private val mode: Timeline.Mode) {
}
val indicesToRemove = listOfNotNull(
- roomBeginningItemIndex,
roomCreationEventIndex,
selfUserJoinedEventIndex,
)
diff --git a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiClientBuilder.kt b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiClientBuilder.kt
index 9f64487448..68e9946cb4 100644
--- a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiClientBuilder.kt
+++ b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiClientBuilder.kt
@@ -41,6 +41,7 @@ class FakeFfiClientBuilder : ClientBuilder(NoPointer) {
override fun slidingSyncVersionBuilder(versionBuilder: SlidingSyncVersionBuilder) = this
override fun userAgent(userAgent: String) = this
override fun username(username: String) = this
+ override fun enableShareHistoryOnInvite(enableShareHistoryOnInvite: Boolean): ClientBuilder = this
override suspend fun buildWithQrCode(qrCodeData: QrCodeData, oidcConfiguration: OidcConfiguration, progressListener: QrLoginProgressListener): Client {
return FakeFfiClient()
diff --git a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiNotificationClient.kt b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiNotificationClient.kt
index ec244ede74..180da9cc89 100644
--- a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiNotificationClient.kt
+++ b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/fixtures/fakes/FakeFfiNotificationClient.kt
@@ -14,8 +14,11 @@ import org.matrix.rustcomponents.sdk.NotificationItemsRequest
class FakeFfiNotificationClient(
var notificationItemResult: Map = emptyMap(),
+ val closeResult: () -> Unit = { }
) : NotificationClient(NoPointer) {
override suspend fun getNotifications(requests: List): Map {
return notificationItemResult
}
+
+ override fun close() = closeResult()
}
diff --git a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationServiceTest.kt b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationServiceTest.kt
index c0d7ddf09b..3166acc891 100644
--- a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationServiceTest.kt
+++ b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/notification/RustNotificationServiceTest.kt
@@ -19,6 +19,7 @@ import io.element.android.libraries.matrix.test.A_SESSION_ID
import io.element.android.libraries.matrix.test.A_USER_ID_2
import io.element.android.services.toolbox.api.systemclock.SystemClock
import io.element.android.services.toolbox.test.systemclock.FakeSystemClock
+import io.element.android.tests.testutils.lambda.lambdaRecorder
import io.element.android.tests.testutils.testCoroutineDispatchers
import kotlinx.coroutines.test.TestScope
import kotlinx.coroutines.test.runTest
@@ -47,6 +48,33 @@ class RustNotificationServiceTest {
)
}
+ @Test
+ fun `test unable to resolve event`() = runTest {
+ val notificationClient = FakeFfiNotificationClient(
+ notificationItemResult = emptyMap(),
+ )
+ val sut = createRustNotificationService(
+ notificationClient = notificationClient,
+ )
+ val result = sut.getNotifications(mapOf(A_ROOM_ID to listOf(AN_EVENT_ID))).getOrThrow()[AN_EVENT_ID]!!
+ assertThat(result.content).isEqualTo(
+ NotificationContent.MessageLike.UnableToResolve
+ )
+ }
+
+ @Test
+ fun `close should invoke the close method of the service`() = runTest {
+ val closeResult = lambdaRecorder { }
+ val notificationClient = FakeFfiNotificationClient(
+ closeResult = closeResult,
+ )
+ val sut = createRustNotificationService(
+ notificationClient = notificationClient,
+ )
+ sut.close()
+ closeResult.assertions().isCalledOnce()
+ }
+
private fun TestScope.createRustNotificationService(
notificationClient: NotificationClient = FakeFfiNotificationClient(),
clock: SystemClock = FakeSystemClock(),
diff --git a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessorTest.kt b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessorTest.kt
index bb1e4581a1..ba0bef4266 100644
--- a/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessorTest.kt
+++ b/libraries/matrix/impl/src/test/kotlin/io/element/android/libraries/matrix/impl/timeline/postprocessor/RoomBeginningPostProcessorTest.kt
@@ -50,7 +50,7 @@ class RoomBeginningPostProcessorTest {
}
@Test
- fun `processor removes timeline start, room creation event and self-join event from DM timeline`() {
+ fun `processor removes room creation event and self-join event from DM timeline`() {
val timelineItems = listOf(
timelineStartEvent,
roomCreateEvent,
@@ -63,7 +63,7 @@ class RoomBeginningPostProcessorTest {
roomCreator = A_USER_ID,
hasMoreToLoadBackwards = false,
)
- assertThat(processedItems).isEmpty()
+ assertThat(processedItems).containsExactly(timelineStartEvent)
}
@Test
diff --git a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/FakeBaseRoom.kt b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/FakeBaseRoom.kt
index ae9aee8736..c620f5c886 100644
--- a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/FakeBaseRoom.kt
+++ b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/FakeBaseRoom.kt
@@ -11,6 +11,7 @@ import io.element.android.libraries.core.bool.orFalse
import io.element.android.libraries.matrix.api.core.EventId
import io.element.android.libraries.matrix.api.core.RoomId
import io.element.android.libraries.matrix.api.core.SessionId
+import io.element.android.libraries.matrix.api.core.ThreadId
import io.element.android.libraries.matrix.api.core.UserId
import io.element.android.libraries.matrix.api.room.BaseRoom
import io.element.android.libraries.matrix.api.room.MessageEventType
@@ -20,6 +21,7 @@ import io.element.android.libraries.matrix.api.room.RoomMembersState
import io.element.android.libraries.matrix.api.room.StateEventType
import io.element.android.libraries.matrix.api.room.draft.ComposerDraft
import io.element.android.libraries.matrix.api.room.powerlevels.RoomPowerLevels
+import io.element.android.libraries.matrix.api.room.tombstone.PredecessorRoom
import io.element.android.libraries.matrix.api.roomdirectory.RoomVisibility
import io.element.android.libraries.matrix.api.timeline.ReceiptType
import io.element.android.libraries.matrix.test.A_ROOM_ID
@@ -66,6 +68,7 @@ class FakeBaseRoom(
private val getRoomVisibilityResult: () -> Result = { lambdaError() },
private val forgetResult: () -> Result = { lambdaError() },
private val reportRoomResult: (String?) -> Result = { lambdaError() },
+ private val predecessorRoomResult: () -> PredecessorRoom? = { null },
) : BaseRoom {
private val _roomInfoFlow: MutableStateFlow = MutableStateFlow(initialRoomInfo)
override val roomInfoFlow: StateFlow = _roomInfoFlow
@@ -196,11 +199,14 @@ class FakeBaseRoom(
return Result.success(Unit)
}
- override suspend fun saveComposerDraft(composerDraft: ComposerDraft) = saveComposerDraftLambda(composerDraft)
+ override suspend fun saveComposerDraft(
+ composerDraft: ComposerDraft,
+ threadRoot: ThreadId?
+ ) = saveComposerDraftLambda(composerDraft)
- override suspend fun loadComposerDraft() = loadComposerDraftLambda()
+ override suspend fun loadComposerDraft(threadRoot: ThreadId?) = loadComposerDraftLambda()
- override suspend fun clearComposerDraft() = clearComposerDraftLambda()
+ override suspend fun clearComposerDraft(threadRoot: ThreadId?) = clearComposerDraftLambda()
override suspend fun getUpdatedIsEncrypted(): Result = simulateLongTask {
Result.success(info().isEncrypted.orFalse())
@@ -215,6 +221,8 @@ class FakeBaseRoom(
}
override suspend fun reportRoom(reason: String?) = reportRoomResult(reason)
+
+ override fun predecessorRoom(): PredecessorRoom? = predecessorRoomResult()
}
fun defaultRoomPowerLevels() = RoomPowerLevels(
diff --git a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomInfoFixture.kt b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomInfoFixture.kt
index 5b6040dee5..0fc88d1d81 100644
--- a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomInfoFixture.kt
+++ b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomInfoFixture.kt
@@ -15,9 +15,9 @@ import io.element.android.libraries.matrix.api.room.CurrentUserMembership
import io.element.android.libraries.matrix.api.room.RoomInfo
import io.element.android.libraries.matrix.api.room.RoomMember
import io.element.android.libraries.matrix.api.room.RoomNotificationMode
-import io.element.android.libraries.matrix.api.room.SuccessorRoom
import io.element.android.libraries.matrix.api.room.history.RoomHistoryVisibility
import io.element.android.libraries.matrix.api.room.join.JoinRule
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.matrix.api.user.MatrixUser
import io.element.android.libraries.matrix.test.AN_AVATAR_URL
import io.element.android.libraries.matrix.test.A_ROOM_ID
diff --git a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomSummaryFixture.kt b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomSummaryFixture.kt
index 11e462f977..27302a2d87 100644
--- a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomSummaryFixture.kt
+++ b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/room/RoomSummaryFixture.kt
@@ -15,10 +15,10 @@ import io.element.android.libraries.matrix.api.room.CurrentUserMembership
import io.element.android.libraries.matrix.api.room.RoomInfo
import io.element.android.libraries.matrix.api.room.RoomMember
import io.element.android.libraries.matrix.api.room.RoomNotificationMode
-import io.element.android.libraries.matrix.api.room.SuccessorRoom
import io.element.android.libraries.matrix.api.room.history.RoomHistoryVisibility
import io.element.android.libraries.matrix.api.room.join.JoinRule
import io.element.android.libraries.matrix.api.room.message.RoomMessage
+import io.element.android.libraries.matrix.api.room.tombstone.SuccessorRoom
import io.element.android.libraries.matrix.api.roomlist.RoomSummary
import io.element.android.libraries.matrix.api.timeline.item.event.EventTimelineItem
import io.element.android.libraries.matrix.api.user.MatrixUser
diff --git a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/timeline/FakeTimeline.kt b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/timeline/FakeTimeline.kt
index 3aa3a2e186..c4ab0160c4 100644
--- a/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/timeline/FakeTimeline.kt
+++ b/libraries/matrix/test/src/main/kotlin/io/element/android/libraries/matrix/test/timeline/FakeTimeline.kt
@@ -304,7 +304,8 @@ class FakeTimeline(
description: String?,
zoomLevel: Int?,
assetType: AssetType?,
- ) -> Result = { _, _, _, _, _ ->
+ replyParameters: ReplyParameters?,
+ ) -> Result = { _, _, _, _, _, _ ->
lambdaError()
}
@@ -314,6 +315,7 @@ class FakeTimeline(
description: String?,
zoomLevel: Int?,
assetType: AssetType?,
+ replyParameters: ReplyParameters?,
): Result = simulateLongTask {
sendLocationLambda(
body,
@@ -321,6 +323,7 @@ class FakeTimeline(
description,
zoomLevel,
assetType,
+ replyParameters,
)
}
diff --git a/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectRoomInfoProvider.kt b/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectRoomInfoProvider.kt
index 6d85cc28cb..f6ad30fae1 100644
--- a/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectRoomInfoProvider.kt
+++ b/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectRoomInfoProvider.kt
@@ -30,10 +30,12 @@ fun aSelectRoomInfo(
canonicalAlias: RoomAlias? = null,
avatarUrl: String? = null,
heroes: ImmutableList = persistentListOf(),
+ isTombstoned: Boolean = false,
) = SelectRoomInfo(
roomId = roomId,
name = name,
canonicalAlias = canonicalAlias,
avatarUrl = avatarUrl,
heroes = heroes,
+ isTombstoned = isTombstoned,
)
diff --git a/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectedRoom.kt b/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectedRoom.kt
index 11f6b74b95..06cead3526 100644
--- a/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectedRoom.kt
+++ b/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/components/SelectedRoom.kt
@@ -29,7 +29,7 @@ import androidx.compose.ui.unit.dp
import io.element.android.compound.theme.ElementTheme
import io.element.android.compound.tokens.generated.CompoundIcons
import io.element.android.libraries.designsystem.components.avatar.AvatarSize
-import io.element.android.libraries.designsystem.components.avatar.CompositeAvatar
+import io.element.android.libraries.designsystem.components.avatar.RoomAvatar
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.theme.components.Icon
@@ -53,9 +53,10 @@ fun SelectedRoom(
Column(
horizontalAlignment = Alignment.CenterHorizontally,
) {
- CompositeAvatar(
+ RoomAvatar(
avatarData = roomInfo.getAvatarData(AvatarSize.SelectedRoom),
heroes = roomInfo.heroes.map { it.getAvatarData(AvatarSize.SelectedRoom) }.toImmutableList(),
+ isTombstoned = roomInfo.isTombstoned,
)
Text(
// If name is null, we do not have space to render "No room name", so just use `#` here.
diff --git a/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/model/SelectRoomInfo.kt b/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/model/SelectRoomInfo.kt
index 8ca5dcd326..63a0b1cc77 100644
--- a/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/model/SelectRoomInfo.kt
+++ b/libraries/matrixui/src/main/kotlin/io/element/android/libraries/matrix/ui/model/SelectRoomInfo.kt
@@ -21,6 +21,7 @@ data class SelectRoomInfo(
val canonicalAlias: RoomAlias?,
val avatarUrl: String?,
val heroes: ImmutableList,
+ val isTombstoned: Boolean,
) {
fun getAvatarData(size: AvatarSize) = AvatarData(
id = roomId.value,
@@ -36,4 +37,5 @@ fun RoomSummary.toSelectRoomInfo() = SelectRoomInfo(
avatarUrl = info.avatarUrl,
heroes = info.heroes,
canonicalAlias = info.canonicalAlias,
+ isTombstoned = info.successorRoom != null,
)
diff --git a/libraries/matrixui/src/main/res/values-in/translations.xml b/libraries/matrixui/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..11b1de4d8a
--- /dev/null
+++ b/libraries/matrixui/src/main/res/values-in/translations.xml
@@ -0,0 +1,4 @@
+
+
+ "%1$s (%2$s) mengundang Anda"
+
diff --git a/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/AudioItemView.kt b/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/AudioItemView.kt
index 1bee0dffe3..73786e12a4 100644
--- a/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/AudioItemView.kt
+++ b/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/AudioItemView.kt
@@ -7,7 +7,6 @@
package io.element.android.libraries.mediaviewer.impl.gallery.ui
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.layout.Column
@@ -65,7 +64,6 @@ fun AudioItemView(
}
}
-@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun FilenameRow(
audio: MediaItem.Audio,
diff --git a/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/FileItemView.kt b/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/FileItemView.kt
index bdb6539ecc..cd73365cca 100644
--- a/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/FileItemView.kt
+++ b/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/FileItemView.kt
@@ -7,7 +7,6 @@
package io.element.android.libraries.mediaviewer.impl.gallery.ui
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.combinedClickable
import androidx.compose.foundation.layout.Column
@@ -65,7 +64,6 @@ fun FileItemView(
}
}
-@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun FilenameRow(
file: MediaItem.File,
diff --git a/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/VoiceItemView.kt b/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/VoiceItemView.kt
index 89f9a30f40..fdb236baa2 100644
--- a/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/VoiceItemView.kt
+++ b/libraries/mediaviewer/impl/src/main/kotlin/io/element/android/libraries/mediaviewer/impl/gallery/ui/VoiceItemView.kt
@@ -7,7 +7,6 @@
package io.element.android.libraries.mediaviewer.impl.gallery.ui
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.border
import androidx.compose.foundation.combinedClickable
@@ -84,7 +83,6 @@ fun VoiceItemView(
}
}
-@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun VoiceInfoRow(
state: VoiceMessageState,
diff --git a/libraries/mediaviewer/impl/src/main/res/values-in/translations.xml b/libraries/mediaviewer/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..2cdc0cf27c
--- /dev/null
+++ b/libraries/mediaviewer/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,19 @@
+
+
+ "Berkas ini akan dihapus dari ruangan dan anggota tidak akan memiliki akses ke sana."
+ "Hapus berkas?"
+ "Periksa koneksi internet Anda dan coba lagi."
+ "Dokumen, berkas audio, dan pesan suara yang diunggah ke ruangan ini akan ditampilkan di sini."
+ "Belum ada berkas yang diunggah"
+ "Memuat berkas…"
+ "Memuat media…"
+ "Berkas"
+ "Media"
+ "Gambar dan video yang diunggah ke ruangan ini akan ditampilkan di sini."
+ "Belum ada media yang diunggah"
+ "Media dan berkas"
+ "Format berkas"
+ "Nama berkas"
+ "Diunggah oleh"
+ "Diunggah pada"
+
diff --git a/libraries/permissions/api/src/main/kotlin/io/element/android/libraries/permissions/api/PermissionsView.kt b/libraries/permissions/api/src/main/kotlin/io/element/android/libraries/permissions/api/PermissionsView.kt
index 3823b1b8e1..1748a02db4 100644
--- a/libraries/permissions/api/src/main/kotlin/io/element/android/libraries/permissions/api/PermissionsView.kt
+++ b/libraries/permissions/api/src/main/kotlin/io/element/android/libraries/permissions/api/PermissionsView.kt
@@ -9,6 +9,7 @@ package io.element.android.libraries.permissions.api
import android.Manifest
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.tooling.preview.PreviewParameter
@@ -41,6 +42,7 @@ fun PermissionsView(
}
@Composable
+@ReadOnlyComposable
private fun String.toDialogContent(): String {
return when (this) {
Manifest.permission.POST_NOTIFICATIONS -> stringResource(id = R.string.dialog_permission_notification)
diff --git a/libraries/permissions/impl/src/main/res/values-in/translations.xml b/libraries/permissions/impl/src/main/res/values-in/translations.xml
new file mode 100644
index 0000000000..dff88d1314
--- /dev/null
+++ b/libraries/permissions/impl/src/main/res/values-in/translations.xml
@@ -0,0 +1,5 @@
+
+
+ "Pastikan aplikasi dapat menampilkan notifikasi."
+ "Periksa izin"
+
diff --git a/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/PushService.kt b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/PushService.kt
index f9a0496efb..fb1bd14404 100644
--- a/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/PushService.kt
+++ b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/PushService.kt
@@ -67,4 +67,9 @@ interface PushService {
* Reset the push history, including the push counter.
*/
suspend fun resetPushHistory()
+
+ /**
+ * Reset the battery optimization state.
+ */
+ suspend fun resetBatteryOptimizationState()
}
diff --git a/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationEvents.kt b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationEvents.kt
new file mode 100644
index 0000000000..ab8d9e92e5
--- /dev/null
+++ b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationEvents.kt
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.api.battery
+
+sealed interface BatteryOptimizationEvents {
+ data object Dismiss : BatteryOptimizationEvents
+ data object RequestDisableOptimizations : BatteryOptimizationEvents
+}
diff --git a/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationState.kt b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationState.kt
new file mode 100644
index 0000000000..7e7c2b2bd6
--- /dev/null
+++ b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationState.kt
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.api.battery
+
+data class BatteryOptimizationState(
+ val shouldDisplayBanner: Boolean,
+ val eventSink: (BatteryOptimizationEvents) -> Unit,
+)
diff --git a/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationStateProvider.kt b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationStateProvider.kt
new file mode 100644
index 0000000000..d6d4e5774b
--- /dev/null
+++ b/libraries/push/api/src/main/kotlin/io/element/android/libraries/push/api/battery/BatteryOptimizationStateProvider.kt
@@ -0,0 +1,16 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.api.battery
+
+fun aBatteryOptimizationState(
+ shouldDisplayBanner: Boolean = false,
+ eventSink: (BatteryOptimizationEvents) -> Unit = {},
+) = BatteryOptimizationState(
+ shouldDisplayBanner = shouldDisplayBanner,
+ eventSink = eventSink,
+)
diff --git a/libraries/push/impl/src/main/AndroidManifest.xml b/libraries/push/impl/src/main/AndroidManifest.xml
index 49ca55decc..c08c16ed5f 100644
--- a/libraries/push/impl/src/main/AndroidManifest.xml
+++ b/libraries/push/impl/src/main/AndroidManifest.xml
@@ -7,6 +7,9 @@
+
+
+
()
+ ?.isIgnoringBatteryOptimizations(context.packageName) == true
+ }
+
+ @SuppressLint("BatteryLife")
+ override fun requestDisablingBatteryOptimization(): Boolean {
+ val ignoreBatteryOptimizationsResult = launchAction(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS, withData = true)
+ if (ignoreBatteryOptimizationsResult) {
+ return true
+ }
+ // Open settings as a fallback if the first attempt fails
+ return launchAction(Settings.ACTION_IGNORE_BATTERY_OPTIMIZATION_SETTINGS, withData = false)
+ }
+
+ private fun launchAction(
+ action: String,
+ withData: Boolean,
+ ): Boolean {
+ val intent = Intent()
+ intent.action = action
+ if (withData) {
+ intent.data = ("package:" + context.packageName).toUri()
+ }
+ return try {
+ externalIntentLauncher.launch(intent)
+ true
+ } catch (exception: ActivityNotFoundException) {
+ Timber.w(exception, "Cannot launch intent with action $action.")
+ false
+ }
+ }
+}
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/battery/BatteryOptimizationPresenter.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/battery/BatteryOptimizationPresenter.kt
new file mode 100644
index 0000000000..9fa17f0544
--- /dev/null
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/battery/BatteryOptimizationPresenter.kt
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.impl.battery
+
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.collectAsState
+import androidx.compose.runtime.getValue
+import androidx.compose.runtime.mutableStateOf
+import androidx.compose.runtime.remember
+import androidx.compose.runtime.rememberCoroutineScope
+import androidx.compose.runtime.setValue
+import androidx.lifecycle.compose.LifecycleResumeEffect
+import io.element.android.libraries.architecture.Presenter
+import io.element.android.libraries.push.api.battery.BatteryOptimizationEvents
+import io.element.android.libraries.push.api.battery.BatteryOptimizationState
+import io.element.android.libraries.push.impl.push.MutableBatteryOptimizationStore
+import io.element.android.libraries.push.impl.store.PushDataStore
+import kotlinx.coroutines.launch
+import javax.inject.Inject
+
+class BatteryOptimizationPresenter @Inject constructor(
+ private val pushDataStore: PushDataStore,
+ private val mutableBatteryOptimizationStore: MutableBatteryOptimizationStore,
+ private val batteryOptimization: BatteryOptimization,
+) : Presenter {
+ @Composable
+ override fun present(): BatteryOptimizationState {
+ val coroutineScope = rememberCoroutineScope()
+ var isRequestSent by remember { mutableStateOf(false) }
+ var localShouldDisplayBanner by remember { mutableStateOf(true) }
+ val storeShouldDisplayBanner by pushDataStore.shouldDisplayBatteryOptimizationBannerFlow.collectAsState(initial = false)
+ var isSystemIgnoringBatteryOptimizations by remember {
+ mutableStateOf(batteryOptimization.isIgnoringBatteryOptimizations())
+ }
+
+ LifecycleResumeEffect(Unit) {
+ isSystemIgnoringBatteryOptimizations = batteryOptimization.isIgnoringBatteryOptimizations()
+ if (isRequestSent) {
+ localShouldDisplayBanner = false
+ }
+ onPauseOrDispose {}
+ }
+
+ fun handleEvents(event: BatteryOptimizationEvents) {
+ when (event) {
+ BatteryOptimizationEvents.Dismiss -> coroutineScope.launch {
+ mutableBatteryOptimizationStore.onOptimizationBannerDismissed()
+ }
+ BatteryOptimizationEvents.RequestDisableOptimizations -> {
+ isRequestSent = true
+ if (batteryOptimization.requestDisablingBatteryOptimization().not()) {
+ // If not able to perform the request, ensure that we do not display the banner again
+ coroutineScope.launch {
+ mutableBatteryOptimizationStore.onOptimizationBannerDismissed()
+ }
+ }
+ }
+ }
+ }
+
+ return BatteryOptimizationState(
+ shouldDisplayBanner = localShouldDisplayBanner && storeShouldDisplayBanner && !isSystemIgnoringBatteryOptimizations,
+ eventSink = ::handleEvents,
+ )
+ }
+}
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/di/PushModule.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/di/PushModule.kt
index 3e7c7ddae3..bb8b7e1624 100644
--- a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/di/PushModule.kt
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/di/PushModule.kt
@@ -10,16 +10,25 @@ package io.element.android.libraries.push.impl.di
import android.content.Context
import androidx.core.app.NotificationManagerCompat
import com.squareup.anvil.annotations.ContributesTo
+import dagger.Binds
import dagger.Module
import dagger.Provides
+import io.element.android.libraries.architecture.Presenter
import io.element.android.libraries.di.AppScope
import io.element.android.libraries.di.ApplicationContext
+import io.element.android.libraries.push.api.battery.BatteryOptimizationState
+import io.element.android.libraries.push.impl.battery.BatteryOptimizationPresenter
@Module
@ContributesTo(AppScope::class)
-object PushModule {
- @Provides
- fun provideNotificationCompatManager(@ApplicationContext context: Context): NotificationManagerCompat {
- return NotificationManagerCompat.from(context)
+interface PushModule {
+ companion object {
+ @Provides
+ fun provideNotificationCompatManager(@ApplicationContext context: Context): NotificationManagerCompat {
+ return NotificationManagerCompat.from(context)
+ }
}
+
+ @Binds
+ fun bindBatteryOptimizationPresenter(presenter: BatteryOptimizationPresenter): Presenter
}
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolver.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolver.kt
index d5eef83564..9a6b119a26 100644
--- a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolver.kt
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolver.kt
@@ -225,6 +225,11 @@ class DefaultNotifiableEventResolver @Inject constructor(
val fallbackNotifiableEvent = fallbackNotifiableEvent(userId, roomId, eventId)
ResolvedPushEvent.Event(fallbackNotifiableEvent)
}
+ NotificationContent.MessageLike.UnableToResolve -> {
+ Timber.tag(loggerTag.value).w("Unable to resolve notification -> fallback")
+ val fallbackNotifiableEvent = fallbackNotifiableEvent(userId, roomId, eventId)
+ ResolvedPushEvent.Event(fallbackNotifiableEvent)
+ }
is NotificationContent.MessageLike.RoomRedaction -> {
// Note: this case will be handled below
val redactedEventId = content.redactedEventId
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandler.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandler.kt
index a426cdcf42..4d9e390690 100644
--- a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandler.kt
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandler.kt
@@ -25,6 +25,7 @@ import io.element.android.libraries.push.impl.history.onUnableToRetrieveSession
import io.element.android.libraries.push.impl.notifications.NotificationEventRequest
import io.element.android.libraries.push.impl.notifications.NotificationResolverQueue
import io.element.android.libraries.push.impl.notifications.channels.NotificationChannels
+import io.element.android.libraries.push.impl.notifications.model.FallbackNotifiableEvent
import io.element.android.libraries.push.impl.notifications.model.NotifiableEvent
import io.element.android.libraries.push.impl.notifications.model.NotifiableRingingCallEvent
import io.element.android.libraries.push.impl.notifications.model.ResolvedPushEvent
@@ -50,6 +51,7 @@ class DefaultPushHandler @Inject constructor(
private val onNotifiableEventReceived: OnNotifiableEventReceived,
private val onRedactedEventReceived: OnRedactedEventReceived,
private val incrementPushDataStore: IncrementPushDataStore,
+ private val mutableBatteryOptimizationStore: MutableBatteryOptimizationStore,
private val userPushStoreFactory: UserPushStoreFactory,
private val pushClientSecret: PushClientSecret,
private val buildMeta: BuildMeta,
@@ -86,13 +88,24 @@ class DefaultPushHandler @Inject constructor(
} else {
result.fold(
onSuccess = {
- pushHistoryService.onSuccess(
- providerInfo = request.providerInfo,
- eventId = request.eventId,
- roomId = request.roomId,
- sessionId = request.sessionId,
- comment = "Push handled successfully",
- )
+ if (it is ResolvedPushEvent.Event && it.notifiableEvent is FallbackNotifiableEvent) {
+ pushHistoryService.onUnableToResolveEvent(
+ providerInfo = request.providerInfo,
+ eventId = request.eventId,
+ roomId = request.roomId,
+ sessionId = request.sessionId,
+ reason = "Showing fallback notification",
+ )
+ mutableBatteryOptimizationStore.showBatteryOptimizationBanner()
+ } else {
+ pushHistoryService.onSuccess(
+ providerInfo = request.providerInfo,
+ eventId = request.eventId,
+ roomId = request.roomId,
+ sessionId = request.sessionId,
+ comment = "Push handled successfully",
+ )
+ }
},
onFailure = { exception ->
pushHistoryService.onUnableToResolveEvent(
@@ -102,6 +115,7 @@ class DefaultPushHandler @Inject constructor(
sessionId = request.sessionId,
reason = exception.message ?: exception.javaClass.simpleName,
)
+ mutableBatteryOptimizationStore.showBatteryOptimizationBanner()
}
)
}
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/MutableBatteryOptimizationStore.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/MutableBatteryOptimizationStore.kt
new file mode 100644
index 0000000000..14e2cfd97b
--- /dev/null
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/push/MutableBatteryOptimizationStore.kt
@@ -0,0 +1,36 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.impl.push
+
+import com.squareup.anvil.annotations.ContributesBinding
+import io.element.android.libraries.di.AppScope
+import io.element.android.libraries.push.impl.store.DefaultPushDataStore
+import javax.inject.Inject
+
+interface MutableBatteryOptimizationStore {
+ suspend fun showBatteryOptimizationBanner()
+ suspend fun onOptimizationBannerDismissed()
+ suspend fun reset()
+}
+
+@ContributesBinding(AppScope::class)
+class DefaultMutableBatteryOptimizationStore @Inject constructor(
+ private val defaultPushDataStore: DefaultPushDataStore,
+) : MutableBatteryOptimizationStore {
+ override suspend fun showBatteryOptimizationBanner() {
+ defaultPushDataStore.setBatteryOptimizationBannerState(DefaultPushDataStore.BATTERY_OPTIMIZATION_BANNER_STATE_SHOW)
+ }
+
+ override suspend fun onOptimizationBannerDismissed() {
+ defaultPushDataStore.setBatteryOptimizationBannerState(DefaultPushDataStore.BATTERY_OPTIMIZATION_BANNER_STATE_DISMISSED)
+ }
+
+ override suspend fun reset() {
+ defaultPushDataStore.setBatteryOptimizationBannerState(DefaultPushDataStore.BATTERY_OPTIMIZATION_BANNER_STATE_INIT)
+ }
+}
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/DefaultPushDataStore.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/DefaultPushDataStore.kt
index 2130e91c72..a4d9413cb1 100644
--- a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/DefaultPushDataStore.kt
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/DefaultPushDataStore.kt
@@ -43,10 +43,24 @@ class DefaultPushDataStore @Inject constructor(
) : PushDataStore {
private val pushCounter = intPreferencesKey("push_counter")
+ /**
+ * Integer preference to track the state of the battery optimization banner.
+ * Possible values:
+ * [BATTERY_OPTIMIZATION_BANNER_STATE_INIT]: Should not show the banner
+ * [BATTERY_OPTIMIZATION_BANNER_STATE_SHOW]: Should show the banner
+ * [BATTERY_OPTIMIZATION_BANNER_STATE_DISMISSED]: Banner has been shown and user has dismissed it
+ */
+ private val batteryOptimizationBannerState = intPreferencesKey("battery_optimization_banner_state")
+
override val pushCounterFlow: Flow = context.dataStore.data.map { preferences ->
preferences[pushCounter] ?: 0
}
+ @Suppress("UnnecessaryParentheses")
+ override val shouldDisplayBatteryOptimizationBannerFlow: Flow = context.dataStore.data.map { preferences ->
+ (preferences[batteryOptimizationBannerState] ?: BATTERY_OPTIMIZATION_BANNER_STATE_INIT) == BATTERY_OPTIMIZATION_BANNER_STATE_SHOW
+ }
+
suspend fun incrementPushCounter() {
context.dataStore.edit { settings ->
val currentCounterValue = settings[pushCounter] ?: 0
@@ -54,6 +68,18 @@ class DefaultPushDataStore @Inject constructor(
}
}
+ suspend fun setBatteryOptimizationBannerState(newState: Int) {
+ context.dataStore.edit { settings ->
+ val currentValue = settings[batteryOptimizationBannerState] ?: BATTERY_OPTIMIZATION_BANNER_STATE_INIT
+ settings[batteryOptimizationBannerState] = when (currentValue) {
+ BATTERY_OPTIMIZATION_BANNER_STATE_INIT,
+ BATTERY_OPTIMIZATION_BANNER_STATE_SHOW -> newState
+ BATTERY_OPTIMIZATION_BANNER_STATE_DISMISSED -> currentValue
+ else -> error("Invalid value for showBatteryOptimizationBanner: $currentValue")
+ }
+ }
+ }
+
override fun getPushHistoryItemsFlow(): Flow> {
return pushDatabase.pushHistoryQueries.selectAll()
.asFlow()
@@ -84,4 +110,10 @@ class DefaultPushDataStore @Inject constructor(
it.clear()
}
}
+
+ companion object {
+ const val BATTERY_OPTIMIZATION_BANNER_STATE_INIT = 0
+ const val BATTERY_OPTIMIZATION_BANNER_STATE_SHOW = 1
+ const val BATTERY_OPTIMIZATION_BANNER_STATE_DISMISSED = 2
+ }
}
diff --git a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/PushDataStore.kt b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/PushDataStore.kt
index 13c4e06347..de8f6dbbc1 100644
--- a/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/PushDataStore.kt
+++ b/libraries/push/impl/src/main/kotlin/io/element/android/libraries/push/impl/store/PushDataStore.kt
@@ -11,6 +11,7 @@ import io.element.android.libraries.push.api.history.PushHistoryItem
import kotlinx.coroutines.flow.Flow
interface PushDataStore {
+ val shouldDisplayBatteryOptimizationBannerFlow: Flow
val pushCounterFlow: Flow
/**
diff --git a/libraries/push/impl/src/main/res/values-es/translations.xml b/libraries/push/impl/src/main/res/values-es/translations.xml
index 0fcab9de6d..0fcfe9994d 100644
--- a/libraries/push/impl/src/main/res/values-es/translations.xml
+++ b/libraries/push/impl/src/main/res/values-es/translations.xml
@@ -64,6 +64,7 @@
- "Se encontró %1$d proveedor de push: %2$s"
- "Se encontraron %1$d proveedores de push: %2$s"
+ "La aplicación se compiló con compatibilidad para: %1$s"
"Detectar proveedores de push"
"Verificar que la aplicación pueda mostrar notificaciones."
"No se ha hecho clic en la notificación."
diff --git a/libraries/push/impl/src/main/res/values/localazy.xml b/libraries/push/impl/src/main/res/values/localazy.xml
index 9860c8bef7..069183a3a2 100644
--- a/libraries/push/impl/src/main/res/values/localazy.xml
+++ b/libraries/push/impl/src/main/res/values/localazy.xml
@@ -13,7 +13,7 @@
- "%d notification"
- "%d notifications"
- "Notification"
+ "You have new messages."
"📹 Incoming call"
"** Failed to send - please open room"
"Join"
diff --git a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/DefaultPushServiceTest.kt b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/DefaultPushServiceTest.kt
index f3333e84f7..5ae8ab261e 100644
--- a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/DefaultPushServiceTest.kt
+++ b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/DefaultPushServiceTest.kt
@@ -7,13 +7,19 @@
package io.element.android.libraries.push.impl
+import app.cash.turbine.test
import com.google.common.truth.Truth.assertThat
import io.element.android.libraries.matrix.api.MatrixClient
import io.element.android.libraries.matrix.api.core.SessionId
+import io.element.android.libraries.matrix.test.AN_EVENT_ID
import io.element.android.libraries.matrix.test.AN_EXCEPTION
+import io.element.android.libraries.matrix.test.A_ROOM_ID
import io.element.android.libraries.matrix.test.A_SESSION_ID
import io.element.android.libraries.matrix.test.FakeMatrixClient
import io.element.android.libraries.push.api.GetCurrentPushProvider
+import io.element.android.libraries.push.api.history.PushHistoryItem
+import io.element.android.libraries.push.impl.push.FakeMutableBatteryOptimizationStore
+import io.element.android.libraries.push.impl.push.MutableBatteryOptimizationStore
import io.element.android.libraries.push.impl.store.InMemoryPushDataStore
import io.element.android.libraries.push.impl.store.PushDataStore
import io.element.android.libraries.push.impl.test.FakeTestPush
@@ -283,6 +289,53 @@ class DefaultPushServiceTest {
assertThat(userPushStore.getPushProviderName()).isEqualTo(aPushProvider.name)
}
+ @Test
+ fun `resetBatteryOptimizationState invokes the store method`() = runTest {
+ val resetResult = lambdaRecorder { }
+ val defaultPushService = createDefaultPushService(
+ mutableBatteryOptimizationStore = FakeMutableBatteryOptimizationStore(
+ resetResult = resetResult,
+ ),
+ )
+ defaultPushService.resetBatteryOptimizationState()
+ resetResult.assertions().isCalledOnce()
+ }
+
+ @Test
+ fun `resetPushHistory invokes the store method`() = runTest {
+ val resetResult = lambdaRecorder { }
+ val defaultPushService = createDefaultPushService(
+ pushDataStore = InMemoryPushDataStore(
+ resetResult = resetResult
+ ),
+ )
+ defaultPushService.resetPushHistory()
+ resetResult.assertions().isCalledOnce()
+ }
+
+ @Test
+ fun `getPushHistoryItemsFlow invokes the store method`() = runTest {
+ val store = InMemoryPushDataStore()
+ val aPushHistoryItem = PushHistoryItem(
+ pushDate = 0L,
+ formattedDate = "formattedDate",
+ providerInfo = "providerInfo",
+ eventId = AN_EVENT_ID,
+ roomId = A_ROOM_ID,
+ sessionId = A_SESSION_ID,
+ hasBeenResolved = false,
+ comment = null,
+ )
+ val defaultPushService = createDefaultPushService(
+ pushDataStore = store,
+ )
+ defaultPushService.getPushHistoryItemsFlow().test {
+ assertThat(awaitItem().isEmpty()).isTrue()
+ store.emitPushHistoryItems(listOf(aPushHistoryItem))
+ assertThat(awaitItem().first()).isEqualTo(aPushHistoryItem)
+ }
+ }
+
private fun createDefaultPushService(
testPush: TestPush = FakeTestPush(),
userPushStoreFactory: UserPushStoreFactory = FakeUserPushStoreFactory(),
@@ -291,6 +344,7 @@ class DefaultPushServiceTest {
sessionObserver: SessionObserver = NoOpSessionObserver(),
pushClientSecretStore: PushClientSecretStore = InMemoryPushClientSecretStore(),
pushDataStore: PushDataStore = InMemoryPushDataStore(),
+ mutableBatteryOptimizationStore: MutableBatteryOptimizationStore = FakeMutableBatteryOptimizationStore(),
): DefaultPushService {
return DefaultPushService(
testPush = testPush,
@@ -300,6 +354,7 @@ class DefaultPushServiceTest {
sessionObserver = sessionObserver,
pushClientSecretStore = pushClientSecretStore,
pushDataStore = pushDataStore,
+ mutableBatteryOptimizationStore = mutableBatteryOptimizationStore,
)
}
}
diff --git a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/AndroidBatteryOptimizationTest.kt b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/AndroidBatteryOptimizationTest.kt
new file mode 100644
index 0000000000..e3a28550ca
--- /dev/null
+++ b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/AndroidBatteryOptimizationTest.kt
@@ -0,0 +1,113 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.impl.battery
+
+import android.content.ActivityNotFoundException
+import android.content.Intent
+import android.provider.Settings
+import androidx.test.platform.app.InstrumentationRegistry
+import com.google.common.truth.Truth.assertThat
+import io.element.android.services.toolbox.api.intent.ExternalIntentLauncher
+import io.element.android.services.toolbox.test.intent.FakeExternalIntentLauncher
+import io.element.android.tests.testutils.lambda.lambdaRecorder
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.robolectric.RobolectricTestRunner
+
+@RunWith(RobolectricTestRunner::class)
+class AndroidBatteryOptimizationTest {
+ @Test
+ fun `isIgnoringBatteryOptimizations should return false`() {
+ val sut = createAndroidBatteryOptimization()
+ assertThat(sut.isIgnoringBatteryOptimizations()).isFalse()
+ }
+
+ @Test
+ fun `requestDisablingBatteryOptimization is called once with expected intent`() {
+ val launchLambda = lambdaRecorder { intent ->
+ assertThat(intent.action).isEqualTo(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS)
+ assertThat(intent.data.toString()).isEqualTo("package:${InstrumentationRegistry.getInstrumentation().context.packageName}")
+ }
+ val externalIntentLauncher = FakeExternalIntentLauncher(launchLambda)
+ val sut = createAndroidBatteryOptimization(
+ externalIntentLauncher = externalIntentLauncher,
+ )
+ val result = sut.requestDisablingBatteryOptimization()
+ launchLambda.assertions().isCalledOnce()
+ assertThat(result).isTrue()
+ }
+
+ @Test
+ fun `in case of 1 error, requestDisablingBatteryOptimization returns true`() {
+ var callNumber = 0
+ val launchLambda = lambdaRecorder { intent ->
+ callNumber++
+ when (callNumber) {
+ 1 -> {
+ assertThat(intent.action).isEqualTo(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS)
+ assertThat(intent.data.toString()).isEqualTo("package:${InstrumentationRegistry.getInstrumentation().context.packageName}")
+ throw ActivityNotFoundException("Test exception")
+ }
+ 2 -> {
+ assertThat(intent.action).isEqualTo(Settings.ACTION_IGNORE_BATTERY_OPTIMIZATION_SETTINGS)
+ assertThat(intent.data).isNull()
+ // No error
+ }
+ else -> {
+ throw AssertionError("Unexpected call number: $callNumber")
+ }
+ }
+ }
+ val externalIntentLauncher = FakeExternalIntentLauncher(launchLambda)
+ val sut = createAndroidBatteryOptimization(
+ externalIntentLauncher = externalIntentLauncher,
+ )
+ val result = sut.requestDisablingBatteryOptimization()
+ launchLambda.assertions().isCalledExactly(2)
+ assertThat(result).isTrue()
+ }
+
+ @Test
+ fun `in case of 2 errors, requestDisablingBatteryOptimization returns false`() {
+ var callNumber = 0
+ val launchLambda = lambdaRecorder { intent ->
+ callNumber++
+ when (callNumber) {
+ 1 -> {
+ assertThat(intent.action).isEqualTo(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS)
+ assertThat(intent.data.toString()).isEqualTo("package:${InstrumentationRegistry.getInstrumentation().context.packageName}")
+ throw ActivityNotFoundException("Test exception")
+ }
+ 2 -> {
+ assertThat(intent.action).isEqualTo(Settings.ACTION_IGNORE_BATTERY_OPTIMIZATION_SETTINGS)
+ assertThat(intent.data).isNull()
+ throw ActivityNotFoundException("Test exception")
+ }
+ else -> {
+ throw AssertionError("Unexpected call number: $callNumber")
+ }
+ }
+ }
+ val externalIntentLauncher = FakeExternalIntentLauncher(launchLambda)
+ val sut = createAndroidBatteryOptimization(
+ externalIntentLauncher = externalIntentLauncher,
+ )
+ val result = sut.requestDisablingBatteryOptimization()
+ launchLambda.assertions().isCalledExactly(2)
+ assertThat(result).isFalse()
+ }
+
+ private fun createAndroidBatteryOptimization(
+ externalIntentLauncher: ExternalIntentLauncher = FakeExternalIntentLauncher(),
+ ): AndroidBatteryOptimization {
+ return AndroidBatteryOptimization(
+ context = InstrumentationRegistry.getInstrumentation().context,
+ externalIntentLauncher = externalIntentLauncher,
+ )
+ }
+}
diff --git a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/BatteryOptimizationPresenterTest.kt b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/BatteryOptimizationPresenterTest.kt
new file mode 100644
index 0000000000..d5dd7c48d4
--- /dev/null
+++ b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/BatteryOptimizationPresenterTest.kt
@@ -0,0 +1,170 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.impl.battery
+
+import androidx.lifecycle.Lifecycle
+import com.google.common.truth.Truth.assertThat
+import io.element.android.libraries.push.api.battery.BatteryOptimizationEvents
+import io.element.android.libraries.push.impl.push.FakeMutableBatteryOptimizationStore
+import io.element.android.libraries.push.impl.push.MutableBatteryOptimizationStore
+import io.element.android.libraries.push.impl.store.InMemoryPushDataStore
+import io.element.android.libraries.push.impl.store.PushDataStore
+import io.element.android.tests.testutils.FakeLifecycleOwner
+import io.element.android.tests.testutils.WarmUpRule
+import io.element.android.tests.testutils.lambda.lambdaRecorder
+import io.element.android.tests.testutils.testWithLifecycleOwner
+import kotlinx.coroutines.test.runTest
+import org.junit.Rule
+import org.junit.Test
+
+class BatteryOptimizationPresenterTest {
+ @get:Rule
+ val warmUpRule = WarmUpRule()
+
+ @Test
+ fun `present - initial state`() = runTest {
+ val presenter = createPresenter(
+ pushDataStore = InMemoryPushDataStore(
+ initialShouldDisplayBatteryOptimizationBanner = false,
+ ),
+ batteryOptimization = FakeBatteryOptimization(
+ isIgnoringBatteryOptimizationsResult = false,
+ ),
+ )
+ val lifeCycleOwner = FakeLifecycleOwner()
+ presenter.testWithLifecycleOwner(lifeCycleOwner) {
+ val initialState = awaitItem()
+ assertThat(initialState.shouldDisplayBanner).isFalse()
+ lifeCycleOwner.givenState(Lifecycle.State.RESUMED)
+ }
+ }
+
+ @Test
+ fun `present - should display banner`() = runTest {
+ val presenter = createPresenter(
+ pushDataStore = InMemoryPushDataStore(
+ initialShouldDisplayBatteryOptimizationBanner = true,
+ ),
+ batteryOptimization = FakeBatteryOptimization(
+ isIgnoringBatteryOptimizationsResult = false,
+ ),
+ )
+ presenter.testWithLifecycleOwner {
+ val initialState = awaitItem()
+ assertThat(initialState.shouldDisplayBanner).isFalse()
+ assertThat(awaitItem().shouldDisplayBanner).isTrue()
+ }
+ }
+
+ @Test
+ fun `present - should display banner, but setting already performed`() = runTest {
+ val presenter = createPresenter(
+ pushDataStore = InMemoryPushDataStore(
+ initialShouldDisplayBatteryOptimizationBanner = true,
+ ),
+ batteryOptimization = FakeBatteryOptimization(
+ isIgnoringBatteryOptimizationsResult = true,
+ ),
+ )
+ presenter.testWithLifecycleOwner {
+ val initialState = awaitItem()
+ assertThat(initialState.shouldDisplayBanner).isFalse()
+ assertThat(awaitItem().shouldDisplayBanner).isFalse()
+ }
+ }
+
+ @Test
+ fun `present - should display banner, user dismisses`() = runTest {
+ val onOptimizationBannerDismissedResult = lambdaRecorder { }
+ val presenter = createPresenter(
+ pushDataStore = InMemoryPushDataStore(
+ initialShouldDisplayBatteryOptimizationBanner = true,
+ ),
+ batteryOptimization = FakeBatteryOptimization(
+ isIgnoringBatteryOptimizationsResult = false,
+ ),
+ mutableBatteryOptimizationStore = FakeMutableBatteryOptimizationStore(
+ onOptimizationBannerDismissedResult = onOptimizationBannerDismissedResult,
+ ),
+ )
+ presenter.testWithLifecycleOwner {
+ val initialState = awaitItem()
+ assertThat(initialState.shouldDisplayBanner).isFalse()
+ val displayedItem = awaitItem()
+ assertThat(displayedItem.shouldDisplayBanner).isTrue()
+ displayedItem.eventSink(BatteryOptimizationEvents.Dismiss)
+ onOptimizationBannerDismissedResult.assertions().isCalledOnce()
+ }
+ }
+
+ @Test
+ fun `present - should display banner, user continue, error case`() = runTest {
+ val onOptimizationBannerDismissedResult = lambdaRecorder { }
+ val requestDisablingBatteryOptimizationResult = lambdaRecorder { false }
+ val presenter = createPresenter(
+ pushDataStore = InMemoryPushDataStore(
+ initialShouldDisplayBatteryOptimizationBanner = true,
+ ),
+ batteryOptimization = FakeBatteryOptimization(
+ isIgnoringBatteryOptimizationsResult = false,
+ requestDisablingBatteryOptimizationResult = requestDisablingBatteryOptimizationResult
+ ),
+ mutableBatteryOptimizationStore = FakeMutableBatteryOptimizationStore(
+ onOptimizationBannerDismissedResult = onOptimizationBannerDismissedResult,
+ ),
+ )
+ presenter.testWithLifecycleOwner {
+ val initialState = awaitItem()
+ assertThat(initialState.shouldDisplayBanner).isFalse()
+ val displayedItem = awaitItem()
+ assertThat(displayedItem.shouldDisplayBanner).isTrue()
+ displayedItem.eventSink(BatteryOptimizationEvents.RequestDisableOptimizations)
+ requestDisablingBatteryOptimizationResult.assertions().isCalledOnce()
+ onOptimizationBannerDismissedResult.assertions().isCalledOnce()
+ }
+ }
+
+ @Test
+ fun `present - should display banner, user continue, nominal case`() = runTest {
+ val requestDisablingBatteryOptimizationResult = lambdaRecorder { true }
+ val batteryOptimization = FakeBatteryOptimization(
+ isIgnoringBatteryOptimizationsResult = false,
+ requestDisablingBatteryOptimizationResult = requestDisablingBatteryOptimizationResult
+ )
+ val presenter = createPresenter(
+ pushDataStore = InMemoryPushDataStore(
+ initialShouldDisplayBatteryOptimizationBanner = true,
+ ),
+ batteryOptimization = batteryOptimization,
+ mutableBatteryOptimizationStore = FakeMutableBatteryOptimizationStore(),
+ )
+ val lifeCycleOwner = FakeLifecycleOwner()
+ presenter.testWithLifecycleOwner(lifeCycleOwner) {
+ val initialState = awaitItem()
+ assertThat(initialState.shouldDisplayBanner).isFalse()
+ val displayedItem = awaitItem()
+ assertThat(displayedItem.shouldDisplayBanner).isTrue()
+ displayedItem.eventSink(BatteryOptimizationEvents.RequestDisableOptimizations)
+ requestDisablingBatteryOptimizationResult.assertions().isCalledOnce()
+ batteryOptimization.isIgnoringBatteryOptimizationsResult = true
+ lifeCycleOwner.givenState(Lifecycle.State.RESUMED)
+ assertThat(awaitItem().shouldDisplayBanner).isFalse()
+ assertThat(awaitItem().shouldDisplayBanner).isFalse()
+ }
+ }
+
+ private fun createPresenter(
+ pushDataStore: PushDataStore = InMemoryPushDataStore(),
+ mutableBatteryOptimizationStore: MutableBatteryOptimizationStore = FakeMutableBatteryOptimizationStore(),
+ batteryOptimization: BatteryOptimization = FakeBatteryOptimization(),
+ ) = BatteryOptimizationPresenter(
+ pushDataStore = pushDataStore,
+ mutableBatteryOptimizationStore = mutableBatteryOptimizationStore,
+ batteryOptimization = batteryOptimization
+ )
+}
diff --git a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/FakeBatteryOptimization.kt b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/FakeBatteryOptimization.kt
new file mode 100644
index 0000000000..0adb3d2520
--- /dev/null
+++ b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/battery/FakeBatteryOptimization.kt
@@ -0,0 +1,23 @@
+/*
+ * Copyright 2025 New Vector Ltd.
+ *
+ * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
+ * Please see LICENSE files in the repository root for full details.
+ */
+
+package io.element.android.libraries.push.impl.battery
+
+import io.element.android.tests.testutils.lambda.lambdaError
+
+class FakeBatteryOptimization(
+ var isIgnoringBatteryOptimizationsResult: Boolean = false,
+ private val requestDisablingBatteryOptimizationResult: () -> Boolean = { lambdaError() }
+) : BatteryOptimization {
+ override fun isIgnoringBatteryOptimizations(): Boolean {
+ return isIgnoringBatteryOptimizationsResult
+ }
+
+ override fun requestDisablingBatteryOptimization(): Boolean {
+ return requestDisablingBatteryOptimizationResult()
+ }
+}
diff --git a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolverTest.kt b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolverTest.kt
index 2ba00156c7..5b93e90064 100644
--- a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolverTest.kt
+++ b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/notifications/DefaultNotifiableEventResolverTest.kt
@@ -608,7 +608,32 @@ class DefaultNotifiableEventResolverTest {
roomId = A_ROOM_ID,
eventId = AN_EVENT_ID,
editedEventId = null,
- description = "Notification",
+ description = "You have new messages.",
+ canBeReplaced = true,
+ isRedacted = false,
+ isUpdated = false,
+ timestamp = A_FAKE_TIMESTAMP,
+ )
+ )
+ assertThat(result.getEvent(request)).isEqualTo(Result.success(expectedResult))
+ }
+
+ @Test
+ fun `resolve UnableToResolve`() = runTest {
+ val sut = createDefaultNotifiableEventResolver(
+ notificationResult = Result.success(
+ mapOf(AN_EVENT_ID to aNotificationData(content = NotificationContent.MessageLike.UnableToResolve))
+ )
+ )
+ val request = NotificationEventRequest(A_SESSION_ID, A_ROOM_ID, AN_EVENT_ID, "firebase")
+ val result = sut.resolveEvents(A_SESSION_ID, listOf(request))
+ val expectedResult = ResolvedPushEvent.Event(
+ FallbackNotifiableEvent(
+ sessionId = A_SESSION_ID,
+ roomId = A_ROOM_ID,
+ eventId = AN_EVENT_ID,
+ editedEventId = null,
+ description = "You have new messages.",
canBeReplaced = true,
isRedacted = false,
isUpdated = false,
diff --git a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandlerTest.kt b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandlerTest.kt
index 933c830525..64a3b87aa7 100644
--- a/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandlerTest.kt
+++ b/libraries/push/impl/src/test/kotlin/io/element/android/libraries/push/impl/push/DefaultPushHandlerTest.kt
@@ -86,7 +86,7 @@ class DefaultPushHandlerTest {
fun `when classical PushData is received, the notification drawer is informed`() = runTest {
val aNotifiableMessageEvent = aNotifiableMessageEvent()
val notifiableEventResult =
- lambdaRecorder, Result
"Některé znaky nejsou povoleny. Podporovány jsou pouze písmena, číslice a následující symboly ! $ & ‘ ( ) * + / ; = ? @ [ ] - . _"
"Některé zprávy nebyly odeslány"
"Omlouváme se, došlo k chybě"
+ "Odesílatel události se neshoduje s vlastníkem zařízení, které ji odeslalo."
"Autenticitu této zašifrované zprávy nelze na tomto zařízení zaručit."
"Zašifrováno dříve ověřeným uživatelem."
"Není zašifrováno."
@@ -377,8 +381,13 @@ Opravdu chcete pokračovat?"
"%1$s Připnuté zprávy"
"Načítání zprávy…"
"Zobrazit vše"
+ "Přejít do nové místnosti"
+ "Tato místnost byla nahrazena a již není aktivní"
+ "Zobrazit staré zprávy"
+ "Tato místnost je pokračováním jiné místnosti"
"Chat"
"Žádost o vstup odeslána"
+ "Tato místnost byla aktualizována"
"Sdílet polohu"
"Sdílet moji polohu"
"Otevřít v Mapách Apple"
diff --git a/libraries/ui-strings/src/main/res/values-cy/translations.xml b/libraries/ui-strings/src/main/res/values-cy/translations.xml
index c6747aca86..52c1046030 100644
--- a/libraries/ui-strings/src/main/res/values-cy/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-cy/translations.xml
@@ -396,7 +396,6 @@ Ydych chi\'n siŵr eich bod am barhau?"
"Wrthi\'n llwytho neges…"
"Dangos y Cyfan"
"Sgwrs"
- "Anfonwyd y cais i ymuno"
"Rhannu lleoliad"
"Rhannu fy lleoliad"
"Agor yn Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-de/translations.xml b/libraries/ui-strings/src/main/res/values-de/translations.xml
index afcc1f784f..94f6dc40fc 100644
--- a/libraries/ui-strings/src/main/res/values-de/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-de/translations.xml
@@ -372,7 +372,6 @@ Möchten Sie wirklich fortfahren?"
"Nachricht wird geladen…"
"Alle anzeigen"
"Chat"
- "Beitrittsanfrage geschickt"
"Standort teilen"
"Meinen Standort teilen"
"In Apple Maps öffnen"
diff --git a/libraries/ui-strings/src/main/res/values-el/translations.xml b/libraries/ui-strings/src/main/res/values-el/translations.xml
index efadb6753d..795acf8c29 100644
--- a/libraries/ui-strings/src/main/res/values-el/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-el/translations.xml
@@ -372,7 +372,6 @@
"Φόρτωση μηνύματος…"
"Προβολή Όλων"
"Συνομιλία"
- "Το αίτημα συμμετοχής στάλθηκε"
"Κοινή χρήση τοποθεσίας"
"Κοινή χρήση της τοποθεσίας μου"
"Άνοιγμα στο Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-es/translations.xml b/libraries/ui-strings/src/main/res/values-es/translations.xml
index 50fbc4479d..2b0c7b84d4 100644
--- a/libraries/ui-strings/src/main/res/values-es/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-es/translations.xml
@@ -1,16 +1,19 @@
+ "Avatar"
"Borrar"
- "%1$d dígito introducido"
- "%1$d dígitos introducidos"
"Ocultar contraseña"
+ "Unirse a la llamada"
"Ir al final"
"Sólo menciones"
"Silenciado"
"Página %1$d"
"Pausar"
+ "Mensaje de voz, duración: %1$s, posición actual: %2$s"
"Campo PIN"
"Reproducir"
"Encuesta"
@@ -30,6 +33,7 @@
"Iniciar llamada"
"Menú de usuario"
"Mostrar detalles"
+ "Mensaje de voz, duración: %1$s"
"Grabar mensaje de voz"
"Detener grabación"
"Aceptar"
@@ -56,9 +60,11 @@
"Desactivar"
"Desactivar cuenta"
"Rechazar"
+ "Rechazar y bloquear"
"Eliminar encuesta"
"Desactivar"
"Descartar"
+ "Descartar"
"Hecho"
"Editar"
"Editar leyenda"
@@ -100,8 +106,11 @@
"Eliminar mensaje"
"Responder"
"Responder en el hilo"
+ "Denunciar"
"Informar de un error"
- "Reportar contenido"
+ "Denunciar contenido"
+ "Denunciar conversación"
+ "Denunciar sala"
"Restablecer"
"Restablecer identidad"
"Reintentar"
@@ -125,7 +134,7 @@
"Toca para ver opciones"
"Intentar de nuevo"
"Desprender"
- "Ver en la línea de tiempo"
+ "Ver en la cronología"
"Ver fuente"
"Sí"
"Sí, intentar de nuevo"
@@ -145,7 +154,9 @@
"Copiado al portapapeles"
"Derechos de autor"
"Creando sala…"
+ "Solicitud cancelada"
"Saliste de la sala"
+ "Invitación rechazada"
"Oscuro"
"Error de descifrado"
"Opciones de desarrollador"
@@ -158,6 +169,7 @@
"Edición"
"Editando leyenda"
"* %1$s %2$s"
+ "Archivo vacío"
"Cifrado"
"Cifrado activado"
"Introduce tu PIN"
@@ -180,8 +192,9 @@ Motivo: %1$s."
"En respuesta a %1$s"
"Instalar APK"
"No se encontró este ID de Matrix, por lo que es posible que no se reciba la invitación."
- "Abandonando la sala"
+ "Saliendo de la sala"
"Claro"
+ "Línea copiada al portapapeles"
"Enlace copiado al portapapeles"
"Cargando…"
"Cargando más…"
@@ -202,6 +215,7 @@ Motivo: %1$s."
"%1$s (%2$s)"
"No hay resultados"
"Sala sin nombre"
+ "No cifrado"
"Sin conexión"
"Licencias de código abierto"
"o"
@@ -210,6 +224,7 @@ Motivo: %1$s."
"Enlace permanente"
"Permiso"
"Fijado"
+ "Comprueba tu conexión a Internet"
"Espera, por favor…"
"¿Estás seguro de que quieres finalizar esta encuesta?"
"Encuesta: %1$s"
@@ -222,6 +237,7 @@ Motivo: %1$s."
"Política de privacidad"
"Reacción"
"Reacciones"
+ "Motivo"
"Clave de recuperación"
"Recargando…"
"Respondiendo a %1$s"
@@ -249,6 +265,7 @@ Motivo: %1$s."
"Ubicación compartida"
"Cerrando sesión"
"Algo salió mal"
+ "Hemos encontrado un problema. Inténtalo de nuevo."
"Iniciando chat…"
"Sticker"
"Terminado"
@@ -263,7 +280,7 @@ Motivo: %1$s."
"No se puede descifrar"
"Enviado desde un dispositivo no seguro"
"No tienes acceso a este mensaje"
- "La identidad verificada del remitente ha cambiado"
+ "Se restableció la identidad verificada del remitente"
"Las invitaciones no se pudieron enviar a uno o más usuarios."
"No se pudo enviar la(s) invitación(es)"
"Desbloquear"
@@ -283,12 +300,18 @@ Motivo: %1$s."
"Esperando…"
"Esperando este mensaje"
"Tú"
- "La identidad de %1$s parece haber cambiado. %2$s"
- "La identidad %2$s de %1$s parece haber cambiado. %3$s"
+ "Se restableció la identidad de %1$s. %2$s"
+ "Se restableció la identidad de %1$s %2$s. %3$s"
"(%1$s)"
- "La identidad verificada de %1$s ha cambiado."
- "La identidad verificada %2$s de %1$s ha cambiado. %3$s"
+ "Se restableció la identidad de %1$s."
+ "Se restableció la identidad de %1$s %2$s. %3$s"
"Retirar la verificación"
+ "El enlace %1$s te está llevando a otro sitio %2$s
+
+¿Estás seguro de que quieres continuar?"
+ "Revisa este enlace"
+ "Sala denunciada"
+ "Denunciaste y saliste de la sala"
"Confirmar"
"Error"
"Terminado"
@@ -335,7 +358,7 @@ Motivo: %1$s."
"¿No puedes confirmar? Ve a tu cuenta para restablecer tu identidad."
"Retirar la verificación y enviar"
"Puedes retirar tu verificación y enviar este mensaje de todos modos, o puedes cancelarlo por ahora e intentarlo de nuevo más tarde después de volver a verificar a %1$s."
- "Tu mensaje no se envió porque la identidad verificada de %1$s ha cambiado"
+ "Tu mensaje no se envió porque la identidad verificada de %1$s fue restablecida"
"Enviar mensaje de todos modos"
"%1$s utiliza uno o más dispositivos no verificados. Puedes enviar el mensaje de todos modos, o puedes cancelarlo por ahora y volver a intentarlo más tarde, una vez %2$s haya verificado todos sus dispositivos."
"Tu mensaje no se envió porque %1$s no ha verificado todos los dispositivos"
@@ -349,14 +372,13 @@ Motivo: %1$s."
"Cargando mensaje…"
"Ver todos"
"Chat"
- "Solicitud de unión enviada"
"Compartir ubicación"
"Compartir mi ubicación"
"Abrir en Apple Maps"
"Abrir en Google Maps"
"Abrir en OpenStreetMap"
"Compartir esta ubicación"
- "Mensaje no enviado porque la identidad verificada de %1$s ha cambiado."
+ "Mensaje no enviado porque la identidad verificada de %1$s fue restablecida."
"Mensaje no enviado porque %1$s no ha verificado todos los dispositivos."
"Mensaje no enviado porque no has verificado uno o más de tus dispositivos."
"Ubicación"
diff --git a/libraries/ui-strings/src/main/res/values-et/translations.xml b/libraries/ui-strings/src/main/res/values-et/translations.xml
index 9547e7663a..1ed332da5f 100644
--- a/libraries/ui-strings/src/main/res/values-et/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-et/translations.xml
@@ -371,8 +371,13 @@ Kas sa oled kindel, et soovid jätkata?"
"%1$s esiletõstetud sõnumit"
"Laadime sõnumit…"
"Näita kõiki"
+ "Hüppa uude jututuppa"
+ "See jututuba on asendatud uuega ning pole enam aktiivne"
+ "Vaata vanu sõnumeid"
+ "See jututuba on varasema jututoa jätk"
"Vestlus"
"Liitumispalve on saadetud"
+ "See jututuba on uuendatud"
"Jaga asukohta"
"Jaga minu asukohta"
"Ava Apple Mapsis"
diff --git a/libraries/ui-strings/src/main/res/values-eu/translations.xml b/libraries/ui-strings/src/main/res/values-eu/translations.xml
index c3c2c12a1c..f3bbd83167 100644
--- a/libraries/ui-strings/src/main/res/values-eu/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-eu/translations.xml
@@ -330,7 +330,6 @@ Arrazoia: %1$s."
"Mezua kargatzen…"
"Ikusi guztia"
"Txata"
- "Sartzeko eskaera bidali da"
"Partekatu kokapena"
"Partekatu nire kokapena"
"Ireki Apple Maps-en"
diff --git a/libraries/ui-strings/src/main/res/values-fa/translations.xml b/libraries/ui-strings/src/main/res/values-fa/translations.xml
index 4fb5ceea2d..a6cc73c1f6 100644
--- a/libraries/ui-strings/src/main/res/values-fa/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-fa/translations.xml
@@ -323,7 +323,6 @@
"بار کردن پشامها…"
"نمایش همه"
"گپ"
- "درخواست پیوستن فرستاده شد"
"همرسانی موقعیت"
"همرسانی مکانم"
"گشودن در نقشههای اپل"
diff --git a/libraries/ui-strings/src/main/res/values-fi/translations.xml b/libraries/ui-strings/src/main/res/values-fi/translations.xml
index 4c3be6c5c3..aba5d6756e 100644
--- a/libraries/ui-strings/src/main/res/values-fi/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-fi/translations.xml
@@ -371,8 +371,13 @@ Haluatko varmasti jatkaa?"
"Kiinnitetty viesti %1$s"
"Viestiä ladataan…"
"Näytä kaikki"
+ "Siirry uuteen huoneeseen"
+ "Tämä huone on korvattu, eikä se ole enää aktiivinen"
+ "Katso vanhoja viestejä"
+ "Tämä huone on jatkoa toiselle huoneelle"
"Keskustelu"
"Liittymispyyntö lähetetty"
+ "Tämä huone on päivitetty"
"Jaa sijainti"
"Jaa sijaintini"
"Avaa Apple Mapsissa"
diff --git a/libraries/ui-strings/src/main/res/values-fr/translations.xml b/libraries/ui-strings/src/main/res/values-fr/translations.xml
index d15958d55a..154710c593 100644
--- a/libraries/ui-strings/src/main/res/values-fr/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-fr/translations.xml
@@ -138,12 +138,16 @@
"Afficher la source"
"Oui"
"Oui, réessayez"
+ "Désactivez l’optimisation de la batterie pour cette application afin de vous assurer que toutes les notifications sont reçues."
+ "Désactiver l’optimisation"
+ "Ils vous manque des notifications?"
"Votre serveur prend désormais en charge un nouveau protocole plus rapide. Déconnectez-vous, puis reconnectez-vous pour effectuer la mise à niveau dès maintenant. En le faisant tout de suite, vous éviterez une déconnexion forcée lorsque l’ancien protocole sera supprimé."
"Mise à niveau disponible"
"À propos"
"Politique d’utilisation acceptable"
"Ajout d’une légende"
"Paramètres avancés"
+ "une image"
"Statistiques d’utilisation"
"Apparence"
"Audio"
@@ -259,6 +263,7 @@ Raison : %1$s."
"Envoi en cours…"
"Échec de l’envoi"
"Envoyé"
+ ". "
"Serveur non pris en charge"
"URL du serveur"
"Paramètres"
@@ -333,6 +338,7 @@ Raison : %1$s."
"Certains caractères ne sont pas autorisés. Seuls les lettres, les chiffres et les symboles suivants sont utilisables ! $ & ‘ ( ) * + / ; = ? @ [ ] - . _"
"Certains messages n’ont pas été envoyés"
"Désolé, une erreur s’est produite"
+ "L’expéditeur de ce message ne correspond pas au propriétaire de l’appareil qui l’a envoyé."
"L’authenticité de ce message chiffré ne peut être garantie sur cet appareil."
"Chiffré par un utilisateur précédemment vérifié."
"Non chiffré."
@@ -371,8 +377,13 @@ Raison : %1$s."
"%1$s Messages épinglés"
"Chargement du message…"
"Voir tout"
+ "Aller dans le nouveau salon"
+ "Ce salon a été remplacé et n’est plus actif"
+ "Voir les anciens messages"
+ "Ce salon est la continuation du salon précédent"
"Discussion"
"Demande de rejoindre le salon envoyée"
+ "Ce salon a été mis à niveau."
"Partage de position"
"Partager ma position"
"Ouvrir dans Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-hu/translations.xml b/libraries/ui-strings/src/main/res/values-hu/translations.xml
index ab14bca3b7..a58cb9db00 100644
--- a/libraries/ui-strings/src/main/res/values-hu/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-hu/translations.xml
@@ -138,6 +138,9 @@
"Forrás megtekintése"
"Igen"
"Igen, újrapróbálkozás"
+ "Kapcsolja ki az alkalmazás akkumulátor-optimalizálását, hogy biztosan megkapja az összes értesítést."
+ "Optimalizálás letiltása"
+ "Nem érkeznek meg az értesítések?"
"A kiszolgálója mostantól egy új, gyorsabb protokollt támogat. A frissítéshez jelentkezzen ki, majd jelentkezzen be újra. Ha ezt most megteszi, elkerülheti a kényszerített kijelentkeztetést a régi protokollt eltávolításakor."
"Frissítés érhető el"
"Névjegy"
@@ -333,6 +336,7 @@ Biztos, hogy folytatja?"
"Egyes karakterek nem engedélyezettek. Csak a betűk, a számjegyek és a következő szimbólumok támogatottak: $ & \'() * +/; =? @ [] - . _"
"Néhány üzenet nem került elküldésre"
"Elnézést, hiba történt"
+ "Az esemény feladója nem egyezik az eseményt küldő eszköz tulajdonosával."
"A titkosított üzenetek valódiságát ezen az eszközön nem lehet garantálni."
"Egy korábban ellenőrzött felhasználó által titkosítva."
"Nincs titkosítva."
@@ -371,8 +375,13 @@ Biztos, hogy folytatja?"
"%1$s kitűzött üzenet"
"Üzenet betöltése…"
"Összes megtekintése"
+ "Ugrás az új szobába"
+ "Ezt a szobát lecserélték, és már nem aktív."
+ "Régi üzenetek megtekintése"
+ "Ez a szoba egy másik szoba folytatása"
"Csevegés"
"Csatlakozási kérés elküldve"
+ "A szoba verzióját frissítették"
"Hely megosztása"
"Saját hely megosztása"
"Megnyitás az Apple Mapsben"
diff --git a/libraries/ui-strings/src/main/res/values-in/translations.xml b/libraries/ui-strings/src/main/res/values-in/translations.xml
index 722bf149ac..c27f8ef33b 100644
--- a/libraries/ui-strings/src/main/res/values-in/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-in/translations.xml
@@ -334,7 +334,6 @@ Alasan: %1$s."
"Memuat pesan…"
"Lihat Semua"
"Obrolan"
- "Permintaan untuk bergabung dikirim"
"Bagikan lokasi"
"Bagikan lokasi saya"
"Buka di Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-it/translations.xml b/libraries/ui-strings/src/main/res/values-it/translations.xml
index c78465247f..4f4446050b 100644
--- a/libraries/ui-strings/src/main/res/values-it/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-it/translations.xml
@@ -359,7 +359,6 @@ Sei sicuro di voler continuare?"
"Caricamento messaggio…"
"Mostra tutti"
"Conversazione"
- "Richiesta di accesso inviata"
"Condividi posizione"
"Condividi la mia posizione"
"Apri in Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-nb/translations.xml b/libraries/ui-strings/src/main/res/values-nb/translations.xml
index 573107cc01..5536fb3a7e 100644
--- a/libraries/ui-strings/src/main/res/values-nb/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-nb/translations.xml
@@ -73,7 +73,7 @@
"Avslutt avstemning"
"Skriv inn PIN-koden"
"Glemt passordet?"
- "Fremover"
+ "Videresend"
"Gå tilbake"
"Ignorer"
"Inviter"
@@ -138,12 +138,16 @@
"Vis kilde"
"Ja"
"Ja, prøv igjen"
+ "Deaktiver batterioptimalisering for denne appen for å sikre at alle varsler mottas."
+ "Deaktiver optimalisering"
+ "Kommer ikke varslene frem?"
"Serveren din støtter nå en ny, raskere protokoll. Logg ut og logg inn igjen for å oppgradere nå. Ved å gjøre dette nå, unngår du å bli tvunget til å logge ut når den gamle protokollen fjernes senere."
"Oppgradering tilgjengelig"
"Om"
"Retningslinjer for akseptabel bruk"
"Legger til bildetekst"
"Avanserte innstillinger"
+ "et bilde"
"Analyse"
"Utseende"
"Lyd"
@@ -333,6 +337,7 @@ Er du sikker på at du vil fortsette?"
"Noen tegn er ikke tillatt. Bare bokstaver, sifre og følgende symboler støttes! $ & \'() * +/; =? @ [] - . _"
"Noen meldinger er ikke sendt"
"Beklager, det oppstod en feil"
+ "Avsenderen av hendelsen samsvarer ikke med eieren av enheten som sendte den."
"Ektheten til denne krypterte meldingen kan ikke garanteres på denne enheten."
"Kryptert av en tidligere verifisert bruker."
"Ikke kryptert."
@@ -343,6 +348,10 @@ Er du sikker på at du vil fortsette?"
"Hei, snakk med meg på %1$s: %2$s"
"%1$s Android"
"Rageshake for å rapportere feil"
+ "%1$s: %2$s"
+ "Alternativer"
+ "Fjern %1$s"
+ "Innstillinger"
"Kunne ikke velge medium, prøv igjen."
"Teksting er kanskje ikke synlig for personer som bruker eldre apper."
"Kunne ikke behandle medier for opplasting, vennligst prøv igjen."
@@ -371,8 +380,13 @@ Er du sikker på at du vil fortsette?"
"%1$s Festede meldinger"
"Laster inn melding…"
"Vis alle"
+ "Gå til nytt rom"
+ "Dette rommet har blitt erstattet og er ikke lenger aktivt"
+ "Se gamle meldinger"
+ "Dette rommet er en fortsettelse av et annet rom"
"Chat"
"Forespørsel om å bli med sendt"
+ "Dette rommet har blitt oppgradert"
"Del lokasjon"
"Del min lokasjon"
"Åpne i Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-nl/translations.xml b/libraries/ui-strings/src/main/res/values-nl/translations.xml
index 1066ee7e79..fcb11918db 100644
--- a/libraries/ui-strings/src/main/res/values-nl/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-nl/translations.xml
@@ -323,7 +323,6 @@ Reden: %1$s."
"Bericht laden…"
"Bekijk alles"
"Chat"
- "Verzoek om toe te treden verzonden"
"Locatie delen"
"Deel mijn locatie"
"Openen in Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-pl/translations.xml b/libraries/ui-strings/src/main/res/values-pl/translations.xml
index 76b3177b6a..bb8e162f30 100644
--- a/libraries/ui-strings/src/main/res/values-pl/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-pl/translations.xml
@@ -378,7 +378,6 @@ Czy na pewno chcesz kontynuować?"
"Wczytywanie wiadomości…"
"Wyświetl wszystkie"
"Czat"
- "Wysłano prośbę o dołączenie"
"Udostępnij lokalizację"
"Udostępnij moją lokalizację"
"Otwórz w Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-pt-rBR/translations.xml b/libraries/ui-strings/src/main/res/values-pt-rBR/translations.xml
index d8fddecca2..f5952be07e 100644
--- a/libraries/ui-strings/src/main/res/values-pt-rBR/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-pt-rBR/translations.xml
@@ -372,7 +372,6 @@ Você tem certeza de que deseja continuar?"
"Carregando mensagem…"
"Ver tudo"
"Bate-papo"
- "Pedido de adesão enviado"
"Compartilhar localização"
"Compartilhar minha localização"
"Abrir no Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-pt/translations.xml b/libraries/ui-strings/src/main/res/values-pt/translations.xml
index d8931a4a99..721755f9f1 100644
--- a/libraries/ui-strings/src/main/res/values-pt/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-pt/translations.xml
@@ -372,7 +372,6 @@ Tens a certeza de que queres continuar?"
"A carregar mensagem…"
"Ver todas"
"Conversa"
- "Pedido de adesão enviado"
"Partilhar localização"
"Partilhar a minha localização"
"Abrir no Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-ro/translations.xml b/libraries/ui-strings/src/main/res/values-ro/translations.xml
index 76771a4c9f..aad4fc5981 100644
--- a/libraries/ui-strings/src/main/res/values-ro/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-ro/translations.xml
@@ -327,7 +327,6 @@ Motiv:%1$s."
"Se încarcă mesajul…"
"Vedeți toate"
"Chat"
- "Cererea de alăturare a fost trimisă"
"Partajați locația"
"Distribuiți locația mea"
"Deschideți în Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-ru/translations.xml b/libraries/ui-strings/src/main/res/values-ru/translations.xml
index 67a9e3b03a..7d2f9ba66a 100644
--- a/libraries/ui-strings/src/main/res/values-ru/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-ru/translations.xml
@@ -308,7 +308,7 @@
"Идентификатор %1$s изменился. %2$s"
"Пользователь %1$s сменил имя пользователя на %2$s. %3$s"
"(%1$s)"
- "Проверенная личность пользователя %1$s изменилась."
+ "%1$s была сброшена."
"%1$s’s %2$s подтвержденная личность изменилась. %3$s"
"Вывод верификации"
"Ссылка %1$s ведет вас на другой сайт %2$s
@@ -364,7 +364,7 @@
"Не можете подтвердить? Перейдите в свою учетную запись, чтобы сбросить свою идентификацию."
"Отозвать статус и отправить"
"Вы можете либо отозвать свой статус подтверждения и всё равно отправить это сообщение, либо отменить его сейчас и повторить попытку после повторного подтверждения %1$s."
- "Ваше сообщение не было отправлено, потому что изменилась подтвержденная личность %1$s"
+ "Ваше сообщение не было отправлено, потому что подтвержденная личность %1$s была сброшена"
"Отправь сообщение в любом случае"
"%1$s использует одно или несколько непроверенных устройств. Вы все равно можете отправить сообщение или отменить его пока и повторить попытку позже %2$s, проверив все устройства пользователя."
"Ваше сообщение не было отправлено, потому что %1$s не проверил одно или несколько устройств"
@@ -377,15 +377,20 @@
"%1$s Закрепленные сообщения"
"Загрузка сообщения…"
"Посмотреть все"
+ "Перейти в новую комнату"
+ "Эта комната была заменена и больше не активна"
+ "Посмотреть старые сообщения"
+ "Эта комната является продолжением другой комнаты"
"Чат"
"Запрос на присоединение отправлен"
+ "Эта комната была обновлена"
"Поделиться местоположением"
"Поделиться моим местоположением"
"Открыть в Apple Maps"
"Открыть в Google Maps"
"Открыть в OpenStreetMap"
"Поделиться этим местоположением"
- "Сообщение не отправлено, потому что верифицированная личность %1$s изменилась."
+ "Сообщение не отправлено, потому что подтвержденная личность %1$s была сброшена."
"Сообщение не отправлено, потому что %1$s не проверил одно или несколько устройств."
"Сообщение не отправлено, поскольку вы не подтвердили одно или несколько своих устройств."
"Местоположение"
diff --git a/libraries/ui-strings/src/main/res/values-sk/translations.xml b/libraries/ui-strings/src/main/res/values-sk/translations.xml
index fa2ccf4b58..14dea09167 100644
--- a/libraries/ui-strings/src/main/res/values-sk/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-sk/translations.xml
@@ -378,7 +378,6 @@ Naozaj chcete pokračovať?"
"Načítava sa správa…"
"Zobraziť všetko"
"Konverzácia"
- "Žiadosť o pripojenie bola odoslaná"
"Zdieľať polohu"
"Zdieľať moju polohu"
"Otvoriť v Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-sv/translations.xml b/libraries/ui-strings/src/main/res/values-sv/translations.xml
index 2733eed812..aa8b4e231e 100644
--- a/libraries/ui-strings/src/main/res/values-sv/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-sv/translations.xml
@@ -371,8 +371,13 @@ Anledning:%1$s."
"%1$s Fästa meddelanden"
"Laddar meddelande …"
"Visa alla"
+ "Hoppa till nytt rum"
+ "Det här rummet har ersatts och är inte längre aktivt"
+ "Se gamla meddelanden"
+ "Det här rummet är en fortsättning på ett annat rum"
"Chatt"
"Begäran om att gå med skickad"
+ "Det här rummet har uppgraderats"
"Dela plats"
"Dela min plats"
"Öppna i Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-tr/translations.xml b/libraries/ui-strings/src/main/res/values-tr/translations.xml
index 40bb3fe7e4..fee4cbe5dd 100644
--- a/libraries/ui-strings/src/main/res/values-tr/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-tr/translations.xml
@@ -348,7 +348,6 @@ Neden: %1$s."
"Mesaj yükleniyor…"
"Tümünü görüntüle"
"Sohbet"
- "Katılma isteği gönderildi"
"Konum paylaş"
"Konumumu paylaş"
"Apple Maps\'de aç"
diff --git a/libraries/ui-strings/src/main/res/values-uk/translations.xml b/libraries/ui-strings/src/main/res/values-uk/translations.xml
index b317dd24d4..985a951d93 100644
--- a/libraries/ui-strings/src/main/res/values-uk/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-uk/translations.xml
@@ -378,7 +378,6 @@
"Завантаження повідомлення…"
"Переглянути всі"
"Бесіда"
- "Запит на приєднання надіслано"
"Поділитися розташуванням"
"Поділитися моїм розташуванням"
"Відкрити в Apple Maps"
diff --git a/libraries/ui-strings/src/main/res/values-uz/translations.xml b/libraries/ui-strings/src/main/res/values-uz/translations.xml
index 2f15a5ccd8..f2498383d7 100644
--- a/libraries/ui-strings/src/main/res/values-uz/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-uz/translations.xml
@@ -1,5 +1,6 @@
+ "Avatar"
"Oʻchirish"
"Parolni yashirish"
"Faqat eslatmalar"
diff --git a/libraries/ui-strings/src/main/res/values-zh-rTW/translations.xml b/libraries/ui-strings/src/main/res/values-zh-rTW/translations.xml
index 835b89bc19..f83e689b17 100644
--- a/libraries/ui-strings/src/main/res/values-zh-rTW/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-zh-rTW/translations.xml
@@ -366,7 +366,6 @@
"正在載入訊息……"
"檢視全部"
"聊天"
- "已傳送加入請求"
"分享位置"
"分享我的位置"
"在 Apple Maps 中開啟"
diff --git a/libraries/ui-strings/src/main/res/values-zh/translations.xml b/libraries/ui-strings/src/main/res/values-zh/translations.xml
index c43a8bf1da..c5a29e7f61 100644
--- a/libraries/ui-strings/src/main/res/values-zh/translations.xml
+++ b/libraries/ui-strings/src/main/res/values-zh/translations.xml
@@ -357,7 +357,6 @@
"正在加载消息…"
"查看全部"
"聊天"
- "加入请求已发送"
"分享位置"
"分享我的位置"
"在 Apple Maps 中打开"
diff --git a/libraries/ui-strings/src/main/res/values/localazy.xml b/libraries/ui-strings/src/main/res/values/localazy.xml
index 1548788ce4..323b762a43 100644
--- a/libraries/ui-strings/src/main/res/values/localazy.xml
+++ b/libraries/ui-strings/src/main/res/values/localazy.xml
@@ -138,12 +138,16 @@
"View source"
"Yes"
"Yes, try again"
+ "Disable battery optimization for this app, to make sure all notifications are received."
+ "Disable optimization"
+ "Notifications not arriving?"
"Your server now supports a new, faster protocol. Log out and log back in to upgrade now. Doing this now will help you avoid a forced logout when the old protocol is removed later."
"Upgrade available"
"About"
"Acceptable use policy"
"Adding caption"
"Advanced settings"
+ "an image"
"Analytics"
"Appearance"
"Audio"
@@ -240,6 +244,10 @@ Reason: %1$s."
"Reason"
"Recovery key"
"Refreshing…"
+
+ - "%1$d reply"
+ - "%1$d replies"
+
"Replying to %1$s"
"Report a bug"
"Report a problem"
@@ -259,6 +267,7 @@ Reason: %1$s."
"Sending…"
"Sending failed"
"Sent"
+ ". "
"Server not supported"
"Server URL"
"Settings"
@@ -333,6 +342,7 @@ Are you sure you want to continue?"
"Some characters are not allowed. Only letters, digits and the following symbols are supported ! $ & ‘ ( ) * + / ; = ? @ [ ] - . _"
"Some messages have not been sent"
"Sorry, an error occurred"
+ "The sender of the event does not match the owner of the device that sent it."
"The authenticity of this encrypted message can\'t be guaranteed on this device."
"Encrypted by a previously-verified user."
"Not encrypted."
@@ -343,6 +353,10 @@ Are you sure you want to continue?"
"Hey, talk to me on %1$s: %2$s"
"%1$s Android"
"Rageshake to report bug"
+ "%1$s: %2$s"
+ "Options"
+ "Remove %1$s"
+ "Settings"
"Failed selecting media, please try again."
"Captions might not be visible to people using older apps."
"Failed processing media to upload, please try again."
@@ -367,12 +381,18 @@ Are you sure you want to continue?"
"Failed processing media to upload, please try again."
"Could not retrieve user details"
"Message in %1$s"
+ "Already viewing this room!"
"%1$s of %2$s"
"%1$s Pinned messages"
"Loading message…"
"View All"
+ "Jump to new room"
+ "This room has been replaced and is no longer active"
+ "See old messages"
+ "This room is a continuation of another room"
"Chat"
"Request to join sent"
+ "This room has been upgraded"
"Share location"
"Share my location"
"Open in Apple Maps"
diff --git a/plugins/src/main/kotlin/Versions.kt b/plugins/src/main/kotlin/Versions.kt
index ef5abdf881..fa05b0780a 100644
--- a/plugins/src/main/kotlin/Versions.kt
+++ b/plugins/src/main/kotlin/Versions.kt
@@ -32,7 +32,7 @@ private const val versionYear = 25
private const val versionMonth = 6
// Note: must be in [0,99]
-private const val versionReleaseNumber = 2
+private const val versionReleaseNumber = 3
object Versions {
const val VERSION_CODE = (2000 + versionYear) * 10_000 + versionMonth * 100 + versionReleaseNumber
diff --git a/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_0_de.png b/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_0_de.png
index 7f499e1a1f..222d7385b2 100644
--- a/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_0_de.png
+++ b/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:68d4a226ac51845b139f18e51bba0dfc2b9a6bd713a8cb72d379eb9ea9b72818
-size 84909
+oid sha256:b6b99f8f732aacb6a77bf856bbb5e23fb1478bf7ce90eafef9e7ba7b67da215f
+size 86774
diff --git a/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_1_de.png b/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_1_de.png
index 800f0f03bf..9aff4b7a4a 100644
--- a/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_1_de.png
+++ b/screenshots/de/features.analytics.impl_AnalyticsOptInView_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:60cd358c1a76e51a9b4b9a7580a758519aa03618e0f13e3cf6ded80e433a3d1a
-size 84184
+oid sha256:11155727ceed9e3c6f22b149d90dd92b58af5e4be729e6920e7071d9f9734530
+size 84388
diff --git a/screenshots/de/features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_de.png b/screenshots/de/features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_de.png
new file mode 100644
index 0000000000..3b7e11cf70
--- /dev/null
+++ b/screenshots/de/features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_de.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:5b5cab99263ef7a2ca101b3292221ce1c04f2f0e3a4e96b59cdcd0060bf5f613
+size 25598
diff --git a/screenshots/de/features.ftue.impl.notifications_NotificationsOptInView_Day_0_de.png b/screenshots/de/features.ftue.impl.notifications_NotificationsOptInView_Day_0_de.png
index 6caf3c9a0f..6b0618101f 100644
--- a/screenshots/de/features.ftue.impl.notifications_NotificationsOptInView_Day_0_de.png
+++ b/screenshots/de/features.ftue.impl.notifications_NotificationsOptInView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:cbc979b60abb037029d820842169a8c441ab70ed3332c5103bd9b348c2b70d1f
-size 70501
+oid sha256:bea6b7dc353227e8954d60ac072e29cc3321883f4a59fff6d1506a810232726e
+size 71375
diff --git a/screenshots/de/features.joinroom.impl_JoinRoomView_Day_13_de.png b/screenshots/de/features.joinroom.impl_JoinRoomView_Day_13_de.png
index c77391fe87..ddd6ccd07a 100644
--- a/screenshots/de/features.joinroom.impl_JoinRoomView_Day_13_de.png
+++ b/screenshots/de/features.joinroom.impl_JoinRoomView_Day_13_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:e2f99bc7839aae2d19d389cc642405e4bc8475b2ccb771540e7182576d986160
-size 33413
+oid sha256:7502335594b906de16b65eab01e5b53ddb88cedd6429ae9b60355552041a1893
+size 33348
diff --git a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_0_de.png b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_0_de.png
index 3c692a69bb..1acc22f4aa 100644
--- a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_0_de.png
+++ b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:9e92456cb9af2df38afb714417227008e7d20038cb265b4b4693abf028371c55
-size 14675
+oid sha256:1551c365ef7522b0ee850f2064585b86c047cce8a28337739d09e71b2458852a
+size 14502
diff --git a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_1_de.png b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_1_de.png
index 258af19174..f3cccea8c7 100644
--- a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_1_de.png
+++ b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:4627a0d09d046b1277036329ef6dbfeac3e4d25f90439ab2dab0f50dc44ae855
-size 19452
+oid sha256:7c18bb43dea68bded70fe2fe21f2f14140b49106ccbbf988c06506a84e1aa6ba
+size 19265
diff --git a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_2_de.png b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_2_de.png
index c85ffd8d44..2abaefddfb 100644
--- a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_2_de.png
+++ b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_2_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:31fa1df9955825deaf920cd23d3d17d3861e461d5b9cdb3d8f21673886bcb938
-size 30652
+oid sha256:25b5b715c1fc4cc67152c6b29e90fbf718eea81c1b75550292a5a4297d8a9449
+size 30479
diff --git a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_3_de.png b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_3_de.png
index 356494b08c..65d6ddcfa6 100644
--- a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_3_de.png
+++ b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_3_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:3b3b589020f23cfba6d50094e54beca90f8d407e256962cc0d8fb136e7a1a14a
-size 39233
+oid sha256:2ef41a8c3b3e672299f77eb236f2dd335d26399bb58842788813b90824d6860a
+size 39081
diff --git a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_4_de.png b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_4_de.png
index 59b4cf56ff..b2d0ff9590 100644
--- a/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_4_de.png
+++ b/screenshots/de/features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_4_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:5a9fca64040da057e303f4c9da0c19c52a0cb9ffc4bf1e29d2b0e8f151322e96
-size 34494
+oid sha256:22df7ef05574f86e7090b91fa2b74103a778aed7029f262f57d54e9d6a886647
+size 34350
diff --git a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_0_de.png b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_0_de.png
index a80ddaa421..f183602a07 100644
--- a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_0_de.png
+++ b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:b2a9305f6faaf67eaac59f762e21c77070fbb572561df1cf92ec8d6bca0d0dce
-size 151343
+oid sha256:cb8a3fad1817764b52e0db7c3f5c6b7e103438928399f4344713272a53374662
+size 364750
diff --git a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_1_de.png b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_1_de.png
index 94127b5426..6cedac977c 100644
--- a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_1_de.png
+++ b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:8032ef23e046995a32eb8ac61a735fc0960da6b4904464c3dee027c3bd1b4f9b
-size 157194
+oid sha256:51df75495180e7665befca85e0e986d26481660cf6f6f6e1cc95b4caecd36955
+size 370225
diff --git a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_4_de.png b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_4_de.png
index 8c2d51c040..951b754bfd 100644
--- a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_4_de.png
+++ b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_4_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:0e7beb51d718e2a5e0532fbe8d6e2118f50e742194366da48df3dba6d6545d72
-size 150535
+oid sha256:84f9227018c9ece9ca911e33b50073f3674cf5c3d2473b109b35c8e3af597fce
+size 363930
diff --git a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_8_de.png b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_8_de.png
index 5c9e4cd489..4e388fe750 100644
--- a/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_8_de.png
+++ b/screenshots/de/features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_8_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d40a925f1672f1c1c6287b9b9b16c34564a5c40d56a28135fa84e1fec748e39b
-size 152711
+oid sha256:fdc57799e07bcddd56f9edde75113bc4cffa1ba8c02370ae3fe0d07b1106da51
+size 365987
diff --git a/screenshots/de/features.messages.impl_MessagesView_Day_6_de.png b/screenshots/de/features.messages.impl_MessagesView_Day_6_de.png
index ff5440ae92..60f44fd73a 100644
--- a/screenshots/de/features.messages.impl_MessagesView_Day_6_de.png
+++ b/screenshots/de/features.messages.impl_MessagesView_Day_6_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:fa561a80f58818de91d0daa8fdb5b5324b1b94de7f2dc61d4568b51825142d93
-size 54183
+oid sha256:cb29742520c9662f7eee364c28129f4f76ae5ab8fd9ce02dbf657a3429a3e7aa
+size 51530
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_0_de.png b/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_0_de.png
deleted file mode 100644
index 6f4be1aa17..0000000000
--- a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_0_de.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:efb039797d56b8a0caba770235a618793ec505702981a1c608237fd7bf582f49
-size 18155
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_1_de.png b/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_1_de.png
deleted file mode 100644
index cc9557a270..0000000000
--- a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_1_de.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:00c631e0245b249bef9533f3904441acd1279ee23f5ae0d930283d22035f8f53
-size 22738
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_2_de.png b/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_2_de.png
deleted file mode 100644
index cd7a349d51..0000000000
--- a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_2_de.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:ea5a3696b6d8eaa5674b417944d9110cc85a0e37dd223d0495b259caf414ffec
-size 28416
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_8_de.png b/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_8_de.png
deleted file mode 100644
index e15d3745bb..0000000000
--- a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_8_de.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:cc604387773fc50481303c325a57813f354ea14724a2f0ea2d46f059ef9e5204
-size 9294
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_9_de.png b/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_9_de.png
deleted file mode 100644
index 9fc16502c1..0000000000
--- a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_9_de.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:909d70e02e2d76ff69bdbea2f98d891e0bd0257e883aaa7df5a45c2ddde4707b
-size 28074
diff --git a/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_0_de.png b/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_0_de.png
index 305047698a..2b58644d33 100644
--- a/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_0_de.png
+++ b/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:060b934a586c09671d8d9a8cf836f509cc69119b458a7ab11be295374c3de9a5
-size 33881
+oid sha256:6e1b139382c574ef78bcedd2107378ee3e4e395a07bc888e11192bac270aafee
+size 12284
diff --git a/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_1_de.png b/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_1_de.png
index eba88dc95e..c7ee196df8 100644
--- a/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_1_de.png
+++ b/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:dd5c940af37b03268f32d57e43d35eec59261fa9674d89ba09d2a234d5427e7b
-size 34176
+oid sha256:c263b0b8fd4c6bdf53118aa5ed06ef919ae5973ed370580cd3d6290c455f9c39
+size 12524
diff --git a/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_2_de.png b/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_2_de.png
index 7ac6f8ca09..2b58644d33 100644
--- a/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_2_de.png
+++ b/screenshots/de/features.roomdetails.impl.members_RoomMemberListViewBanned_Day_2_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:7a2963041eda1c927be2d82c11ac738b3f44bf0687f8dbd504bdbda6069ec8cb
-size 26246
+oid sha256:6e1b139382c574ef78bcedd2107378ee3e4e395a07bc888e11192bac270aafee
+size 12284
diff --git a/screenshots/de/features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Day_0_de.png b/screenshots/de/features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Day_0_de.png
index 58a80ad74d..191c360673 100644
--- a/screenshots/de/features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Day_0_de.png
+++ b/screenshots/de/features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:cee74685fe9d76a5a1389f500fbcb22517ca092625ff0f033bd870713e053537
-size 15121
+oid sha256:dda7469b3c6a9940d7dc9e6c29a52707788af32ca4c17960eb0a29aab0eff4c7
+size 15134
diff --git a/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_0_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_0_de.png
new file mode 100644
index 0000000000..5cab90546a
--- /dev/null
+++ b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_0_de.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:8edf8f2d1b29db9dfe47756dcd3fcc01fc908736b0c009320cf8bac535881416
+size 18252
diff --git a/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_1_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_1_de.png
new file mode 100644
index 0000000000..8596d7d68c
--- /dev/null
+++ b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_1_de.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:7203569b41833fe19935273838d59086031b10660f2e12ab5982432e867e5c1c
+size 22128
diff --git a/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_2_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_2_de.png
new file mode 100644
index 0000000000..c3d7c681a1
--- /dev/null
+++ b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_2_de.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:ec50fa44bf08be308a39eb0d607803b079875c12dfd608f2a70ea4b53e164c39
+size 27566
diff --git a/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_3_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_3_de.png
new file mode 100644
index 0000000000..f2b320ec01
--- /dev/null
+++ b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_3_de.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:a577c026a1502e2fe3bef1ff5f39e3857c06a0ab314c2ef4c384bceb7b9088b1
+size 28630
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_3_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_4_de.png
similarity index 100%
rename from screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_3_de.png
rename to screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_4_de.png
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_4_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_5_de.png
similarity index 100%
rename from screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_4_de.png
rename to screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_5_de.png
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_5_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_6_de.png
similarity index 100%
rename from screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_5_de.png
rename to screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_6_de.png
diff --git a/screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_6_de.png b/screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_7_de.png
similarity index 100%
rename from screenshots/de/features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_6_de.png
rename to screenshots/de/features.roommembermoderation.impl_RoomMemberModerationView_Day_7_de.png
diff --git a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_0_de.png b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_0_de.png
index fb3d275ea7..f2f91815ce 100644
--- a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_0_de.png
+++ b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:e8bc4d690dd194e80f222aa0f80072c8d15fbe0bf74fc70fb8dc0d90a27d18b9
-size 75795
+oid sha256:01b5e7fd76bd27d28420d6dcae61cc6381a9240e3bca78f4b1191a015eb395e2
+size 73458
diff --git a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_1_de.png b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_1_de.png
index fb3d275ea7..f2f91815ce 100644
--- a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_1_de.png
+++ b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:e8bc4d690dd194e80f222aa0f80072c8d15fbe0bf74fc70fb8dc0d90a27d18b9
-size 75795
+oid sha256:01b5e7fd76bd27d28420d6dcae61cc6381a9240e3bca78f4b1191a015eb395e2
+size 73458
diff --git a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_2_de.png b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_2_de.png
index 45efba4987..24f0ee5f73 100644
--- a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_2_de.png
+++ b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_2_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:c31627e40bf94976fb4cdcd2fe3809c73b6e922ebba3cda9e2bf03d3ba2bb939
-size 76317
+oid sha256:362fa3a6e8da97f67c0c3502be9d53929cf2cec1f7bd6c15ccaa95070d65b24e
+size 74006
diff --git a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_3_de.png b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_3_de.png
index fd97700af2..bd4e5a26b3 100644
--- a/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_3_de.png
+++ b/screenshots/de/features.securebackup.impl.disable_SecureBackupDisableView_Day_3_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:56b13e7d7fb1e8890e97750568e78d4c67d947a3a54d87e5ff5d254394072b2c
-size 48664
+oid sha256:e80fa798011e89eb0cd931dbd384b7c800120dd2df8b2227d6e5d8ec93ef238f
+size 46816
diff --git a/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_0_de.png b/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_0_de.png
index 4daeb50e88..37a6a0a0e9 100644
--- a/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_0_de.png
+++ b/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:a94bbe83945a488ce4bf4b753d9b06825bd4e7f18943f8e642562273bdc0a5e9
-size 62927
+oid sha256:54862a355da93704e0e6eb779d6a6011296ca2a968117d36cc4eae8fd96173ac
+size 69526
diff --git a/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_1_de.png b/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_1_de.png
index 43aac0230d..a3886a1e3d 100644
--- a/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_1_de.png
+++ b/screenshots/de/features.securebackup.impl.reset.root_ResetIdentityRootView_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:5d097c185b721aecced3cf9d6d49a70f8b3cd09130fef0061059034ce149cc26
-size 47988
+oid sha256:f953a19a979cdee1503766531545b4683bc8b672a26903af8283820768e4a637
+size 53428
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_2_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_2_de.png
index de2db10cbe..933993102a 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_2_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_2_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d5b792fa5dbd2067080d5972a81881be30df6f5a9335c9aece6245da488b05cf
-size 65583
+oid sha256:a3766ba621a245967c15b7b83fa72bd9e4d7546a37f5ea4caf83c6788a1aa5b6
+size 61181
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_3_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_3_de.png
index de2db10cbe..933993102a 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_3_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_3_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d5b792fa5dbd2067080d5972a81881be30df6f5a9335c9aece6245da488b05cf
-size 65583
+oid sha256:a3766ba621a245967c15b7b83fa72bd9e4d7546a37f5ea4caf83c6788a1aa5b6
+size 61181
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_4_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_4_de.png
index e7072458cc..45fee6dd26 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_4_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_4_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:c78753ad8b299377a12eb844182bb9e86346f66d89eca03dcbc5cda10ef6ff44
-size 55083
+oid sha256:2fe92f15ed85ca629e56dad8c30487aee018a51fc4e9eaf6eab29a2eb4c27d42
+size 51695
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_0_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_0_de.png
index 623f2b9bb3..ac9e47eac1 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_0_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:e439033d1bd70cfa0d9574cd4388d6387ffb5181d3b8e4a55a37c224b380e91d
-size 65262
+oid sha256:f4915dcc73c8761e491613c91542f65ea0e549bac1852b10770b9087b1f90a48
+size 61415
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_1_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_1_de.png
index a0542ada23..6f657e67f8 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_1_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_1_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:bd9c3d54b3c95358bc988ffbaed518d6e79ea61aeba475d63d76a623e931b70d
-size 61756
+oid sha256:e1fe049a477258416fb2964230845ebf009e35d0a7baabefa624842cf1e8ff89
+size 57768
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_2_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_2_de.png
index de2db10cbe..933993102a 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_2_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_2_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d5b792fa5dbd2067080d5972a81881be30df6f5a9335c9aece6245da488b05cf
-size 65583
+oid sha256:a3766ba621a245967c15b7b83fa72bd9e4d7546a37f5ea4caf83c6788a1aa5b6
+size 61181
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_3_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_3_de.png
index de2db10cbe..933993102a 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_3_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_3_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d5b792fa5dbd2067080d5972a81881be30df6f5a9335c9aece6245da488b05cf
-size 65583
+oid sha256:a3766ba621a245967c15b7b83fa72bd9e4d7546a37f5ea4caf83c6788a1aa5b6
+size 61181
diff --git a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_4_de.png b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_4_de.png
index e7072458cc..45fee6dd26 100644
--- a/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_4_de.png
+++ b/screenshots/de/features.securebackup.impl.setup_SecureBackupSetupView_Day_4_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:c78753ad8b299377a12eb844182bb9e86346f66d89eca03dcbc5cda10ef6ff44
-size 55083
+oid sha256:2fe92f15ed85ca629e56dad8c30487aee018a51fc4e9eaf6eab29a2eb4c27d42
+size 51695
diff --git a/screenshots/de/features.signedout.impl_SignedOutView_Day_0_de.png b/screenshots/de/features.signedout.impl_SignedOutView_Day_0_de.png
index 723a6c8bc5..9c6f85a915 100644
--- a/screenshots/de/features.signedout.impl_SignedOutView_Day_0_de.png
+++ b/screenshots/de/features.signedout.impl_SignedOutView_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:4c89ba76087d550a18167f2358ccdd6bd3366c67f6d6d3b01c991b52f35e36b8
-size 63564
+oid sha256:5e794da71cadd6f1e9f0662a359325c9cae1e8ebc9877537a1fdba6d1c006ce6
+size 63399
diff --git a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_5_de.png b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_5_de.png
index 092bef5a65..3df05cb2c1 100644
--- a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_5_de.png
+++ b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_5_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d13f4c555210dea41c0bad3abd6c02cfc43fa93b2bb88b30f2490c61fdb56476
-size 53798
+oid sha256:232c8a93fff37940b058795447f43388cd8d61de1a3ca5aab1545885b3bc566d
+size 53704
diff --git a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_6_de.png b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_6_de.png
index 96438c9b8b..10f61efd98 100644
--- a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_6_de.png
+++ b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_6_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:533a08c37bdd563f993d68b4cd5d5b1a010d57d5fa7da2e0306c66b8e7839bbe
-size 56238
+oid sha256:9150cab47a9a9560df48ffefb09e7481f23f675a80877dfaf29168a535f4fee2
+size 55496
diff --git a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_7_de.png b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_7_de.png
index 5904cf8f98..fddbf4418c 100644
--- a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_7_de.png
+++ b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_7_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:208347b868ef5ddc16b2c06ac5e6a59eaceb6008fc276149683365025778f684
-size 44800
+oid sha256:0a2c484e54b7b0a051c99a472d78efa6d5b9171e23b07fbfd37e66b56df96898
+size 44713
diff --git a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_8_de.png b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_8_de.png
index 1635026b33..d772ada026 100644
--- a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_8_de.png
+++ b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_8_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:ce54a0e068a3f68f6fefaa33152ff919b698e743b6e3ec6a1e78568ee8b16fb1
-size 47381
+oid sha256:eea647e460084d645b91ade9261677ceef281d410d6463e5e0688b41c9754aed
+size 46617
diff --git a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_9_de.png b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_9_de.png
index d43b2e090e..d63a010d55 100644
--- a/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_9_de.png
+++ b/screenshots/de/features.verifysession.impl.incoming_IncomingVerificationView_Day_9_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:f1ce5390b1db7f940a913ea9ba923bf919424a05649f1b39a033a7f5bea9a2fc
-size 35670
+oid sha256:b0ae7bbbde765a903beb419aff127b795bb4d49921b93dc60dd1d5218055fbd8
+size 35666
diff --git a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_4_de.png b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_4_de.png
index 092bef5a65..3df05cb2c1 100644
--- a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_4_de.png
+++ b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_4_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d13f4c555210dea41c0bad3abd6c02cfc43fa93b2bb88b30f2490c61fdb56476
-size 53798
+oid sha256:232c8a93fff37940b058795447f43388cd8d61de1a3ca5aab1545885b3bc566d
+size 53704
diff --git a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_5_de.png b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_5_de.png
index 96438c9b8b..10f61efd98 100644
--- a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_5_de.png
+++ b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_5_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:533a08c37bdd563f993d68b4cd5d5b1a010d57d5fa7da2e0306c66b8e7839bbe
-size 56238
+oid sha256:9150cab47a9a9560df48ffefb09e7481f23f675a80877dfaf29168a535f4fee2
+size 55496
diff --git a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_6_de.png b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_6_de.png
index 5904cf8f98..fddbf4418c 100644
--- a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_6_de.png
+++ b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_6_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:208347b868ef5ddc16b2c06ac5e6a59eaceb6008fc276149683365025778f684
-size 44800
+oid sha256:0a2c484e54b7b0a051c99a472d78efa6d5b9171e23b07fbfd37e66b56df96898
+size 44713
diff --git a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_9_de.png b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_9_de.png
index d43b2e090e..d63a010d55 100644
--- a/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_9_de.png
+++ b/screenshots/de/features.verifysession.impl.outgoing_OutgoingVerificationView_Day_9_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:f1ce5390b1db7f940a913ea9ba923bf919424a05649f1b39a033a7f5bea9a2fc
-size 35670
+oid sha256:b0ae7bbbde765a903beb419aff127b795bb4d49921b93dc60dd1d5218055fbd8
+size 35666
diff --git a/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerDark_DateTime_pickers_de.png b/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerDark_DateTime_pickers_de.png
index b1bb373b78..dbad303a62 100644
--- a/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerDark_DateTime_pickers_de.png
+++ b/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerDark_DateTime_pickers_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:26f21bdb866ee13fbcfd0edca7b57425bc14a79c878e31330ac41b375fd18222
-size 31092
+oid sha256:9a552260805265802772756fc44a4e6944f2fa6b3b715c77958753cb52f48a18
+size 31452
diff --git a/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerLight_DateTime_pickers_de.png b/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerLight_DateTime_pickers_de.png
index afc79d353a..fbe511f864 100644
--- a/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerLight_DateTime_pickers_de.png
+++ b/screenshots/de/libraries.designsystem.theme.components.previews_DatePickerLight_DateTime_pickers_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:efa139e3f0ab0c8978a5d22909ede6e3da4c5772ae9c3af578bbca824ccb1735
-size 31581
+oid sha256:dd9ce1166232db781b60f870a249789e8e723fe3ff9feeed64214774b4a049de
+size 31986
diff --git a/screenshots/de/libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_3_de.png b/screenshots/de/libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_3_de.png
index 19e7937d63..9f825ec840 100644
--- a/screenshots/de/libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_3_de.png
+++ b/screenshots/de/libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_3_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:45a56e54b7b6ed617c7c2a3413b35a4d699ded6d933789dc4b3d471ed404405b
-size 22205
+oid sha256:31ba33141179bb2249d0ed3821e630289fe3bb7a85cf4f1b99795c85a507fb52
+size 529081
diff --git a/screenshots/de/libraries.textcomposer_TextComposerFormattingNotEncrypted_Day_0_de.png b/screenshots/de/libraries.textcomposer_TextComposerFormattingNotEncrypted_Day_0_de.png
index ed4394b6fa..6ea8c4a052 100644
--- a/screenshots/de/libraries.textcomposer_TextComposerFormattingNotEncrypted_Day_0_de.png
+++ b/screenshots/de/libraries.textcomposer_TextComposerFormattingNotEncrypted_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:5bccb7232766f51b2166b9d9621f53f893cf133861f1e77331789a5e2cbc96c1
-size 66072
+oid sha256:5b45550a4e0579982bda9d9f8ceba223a46111baac3aa91cde7fc55c2d4d63ca
+size 66196
diff --git a/screenshots/de/libraries.textcomposer_TextComposerFormatting_Day_0_de.png b/screenshots/de/libraries.textcomposer_TextComposerFormatting_Day_0_de.png
index ec74e4e56d..4944157b9c 100644
--- a/screenshots/de/libraries.textcomposer_TextComposerFormatting_Day_0_de.png
+++ b/screenshots/de/libraries.textcomposer_TextComposerFormatting_Day_0_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:b860e3abcf9d5a4265ab3dd17316a00d96d46da5e6ed6f7bb60eaf5e5d0122da
-size 53402
+oid sha256:8f521b3c6970fad597fab5a24e4b608bfd9a6d1596c1a4675f402a0ac49d7654
+size 53491
diff --git a/screenshots/de/libraries.textcomposer_TextComposerReplyNotEncrypted_Day_5_de.png b/screenshots/de/libraries.textcomposer_TextComposerReplyNotEncrypted_Day_5_de.png
index 2a405463e7..d2c54e26bb 100644
--- a/screenshots/de/libraries.textcomposer_TextComposerReplyNotEncrypted_Day_5_de.png
+++ b/screenshots/de/libraries.textcomposer_TextComposerReplyNotEncrypted_Day_5_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:3bbb1d73be9f2f9dd999a42e2e75f95e16a8ca610759bd37ef0ba80c5f564b3b
-size 61663
+oid sha256:fe97833d8fb608ade441753fad18ad6e0cce2510b5451e1c5d9b10c18a7e97d4
+size 92039
diff --git a/screenshots/de/libraries.textcomposer_TextComposerReply_Day_5_de.png b/screenshots/de/libraries.textcomposer_TextComposerReply_Day_5_de.png
index 3794879115..735caca5a4 100644
--- a/screenshots/de/libraries.textcomposer_TextComposerReply_Day_5_de.png
+++ b/screenshots/de/libraries.textcomposer_TextComposerReply_Day_5_de.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:4c213578bdbc2495a4a26251264d803c51f6c4c4cd6547d46f0738a52fd3af3b
-size 59895
+oid sha256:7aa44ff345d0b2bb9a4f2c2c94f4cf5acfe1518c33608a4673f748d5f25ac886
+size 104285
diff --git a/screenshots/html/data.js b/screenshots/html/data.js
index 17e97c6284..5edac704cf 100644
--- a/screenshots/html/data.js
+++ b/screenshots/html/data.js
@@ -1,70 +1,70 @@
// Generated file, do not edit
export const screenshots = [
["en","en-dark","de",],
-["features.preferences.impl.about_AboutView_Day_0_en","features.preferences.impl.about_AboutView_Night_0_en",20238,],
+["features.preferences.impl.about_AboutView_Day_0_en","features.preferences.impl.about_AboutView_Night_0_en",20252,],
["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_0_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_0_en",0,],
-["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_1_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_1_en",20238,],
-["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_2_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_2_en",20238,],
-["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_3_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_3_en",20238,],
-["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_4_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_4_en",20238,],
-["features.logout.impl_AccountDeactivationView_Day_0_en","features.logout.impl_AccountDeactivationView_Night_0_en",20238,],
-["features.logout.impl_AccountDeactivationView_Day_1_en","features.logout.impl_AccountDeactivationView_Night_1_en",20238,],
-["features.logout.impl_AccountDeactivationView_Day_2_en","features.logout.impl_AccountDeactivationView_Night_2_en",20238,],
-["features.logout.impl_AccountDeactivationView_Day_3_en","features.logout.impl_AccountDeactivationView_Night_3_en",20238,],
-["features.logout.impl_AccountDeactivationView_Day_4_en","features.logout.impl_AccountDeactivationView_Night_4_en",20238,],
-["features.login.impl.accountprovider_AccountProviderOtherView_Day_0_en","features.login.impl.accountprovider_AccountProviderOtherView_Night_0_en",20238,],
+["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_1_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_1_en",20252,],
+["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_2_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_2_en",20252,],
+["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_3_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_3_en",20252,],
+["features.invite.impl.acceptdecline_AcceptDeclineInviteView_Day_4_en","features.invite.impl.acceptdecline_AcceptDeclineInviteView_Night_4_en",20252,],
+["features.logout.impl_AccountDeactivationView_Day_0_en","features.logout.impl_AccountDeactivationView_Night_0_en",20252,],
+["features.logout.impl_AccountDeactivationView_Day_1_en","features.logout.impl_AccountDeactivationView_Night_1_en",20252,],
+["features.logout.impl_AccountDeactivationView_Day_2_en","features.logout.impl_AccountDeactivationView_Night_2_en",20252,],
+["features.logout.impl_AccountDeactivationView_Day_3_en","features.logout.impl_AccountDeactivationView_Night_3_en",20252,],
+["features.logout.impl_AccountDeactivationView_Day_4_en","features.logout.impl_AccountDeactivationView_Night_4_en",20252,],
+["features.login.impl.accountprovider_AccountProviderOtherView_Day_0_en","features.login.impl.accountprovider_AccountProviderOtherView_Night_0_en",20252,],
["features.login.impl.accountprovider_AccountProviderView_Day_0_en","features.login.impl.accountprovider_AccountProviderView_Night_0_en",0,],
["features.login.impl.accountprovider_AccountProviderView_Day_1_en","features.login.impl.accountprovider_AccountProviderView_Night_1_en",0,],
["features.login.impl.accountprovider_AccountProviderView_Day_2_en","features.login.impl.accountprovider_AccountProviderView_Night_2_en",0,],
["features.login.impl.accountprovider_AccountProviderView_Day_3_en","features.login.impl.accountprovider_AccountProviderView_Night_3_en",0,],
["features.messages.impl.actionlist_ActionListViewContent_Day_0_en","features.messages.impl.actionlist_ActionListViewContent_Night_0_en",0,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_10_en","features.messages.impl.actionlist_ActionListViewContent_Night_10_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_11_en","features.messages.impl.actionlist_ActionListViewContent_Night_11_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_12_en","features.messages.impl.actionlist_ActionListViewContent_Night_12_en",20238,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_10_en","features.messages.impl.actionlist_ActionListViewContent_Night_10_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_11_en","features.messages.impl.actionlist_ActionListViewContent_Night_11_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_12_en","features.messages.impl.actionlist_ActionListViewContent_Night_12_en",20252,],
["features.messages.impl.actionlist_ActionListViewContent_Day_1_en","features.messages.impl.actionlist_ActionListViewContent_Night_1_en",0,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_2_en","features.messages.impl.actionlist_ActionListViewContent_Night_2_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_3_en","features.messages.impl.actionlist_ActionListViewContent_Night_3_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_4_en","features.messages.impl.actionlist_ActionListViewContent_Night_4_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_5_en","features.messages.impl.actionlist_ActionListViewContent_Night_5_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_6_en","features.messages.impl.actionlist_ActionListViewContent_Night_6_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_7_en","features.messages.impl.actionlist_ActionListViewContent_Night_7_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_8_en","features.messages.impl.actionlist_ActionListViewContent_Night_8_en",20238,],
-["features.messages.impl.actionlist_ActionListViewContent_Day_9_en","features.messages.impl.actionlist_ActionListViewContent_Night_9_en",20238,],
-["features.createroom.impl.addpeople_AddPeopleView_Day_0_en","features.createroom.impl.addpeople_AddPeopleView_Night_0_en",20238,],
-["features.createroom.impl.addpeople_AddPeopleView_Day_1_en","features.createroom.impl.addpeople_AddPeopleView_Night_1_en",20238,],
-["features.createroom.impl.addpeople_AddPeopleView_Day_2_en","features.createroom.impl.addpeople_AddPeopleView_Night_2_en",20238,],
-["features.createroom.impl.addpeople_AddPeopleView_Day_3_en","features.createroom.impl.addpeople_AddPeopleView_Night_3_en",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewDark_0_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewDark_1_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewDark_2_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewDark_3_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewDark_4_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewDark_5_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewLight_0_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewLight_1_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewLight_2_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewLight_3_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewLight_4_en","",20238,],
-["features.preferences.impl.advanced_AdvancedSettingsViewLight_5_en","",20238,],
-["libraries.designsystem.components.dialogs_AlertDialogContent_Dialogs_en","",20238,],
-["libraries.designsystem.components.dialogs_AlertDialog_Day_0_en","libraries.designsystem.components.dialogs_AlertDialog_Night_0_en",20238,],
-["features.analytics.impl_AnalyticsOptInView_Day_0_en","features.analytics.impl_AnalyticsOptInView_Night_0_en",20238,],
-["features.analytics.impl_AnalyticsOptInView_Day_1_en","features.analytics.impl_AnalyticsOptInView_Night_1_en",20238,],
-["features.analytics.api.preferences_AnalyticsPreferencesView_Day_0_en","features.analytics.api.preferences_AnalyticsPreferencesView_Night_0_en",20238,],
-["features.analytics.api.preferences_AnalyticsPreferencesView_Day_1_en","features.analytics.api.preferences_AnalyticsPreferencesView_Night_1_en",20238,],
-["features.preferences.impl.analytics_AnalyticsSettingsView_Day_0_en","features.preferences.impl.analytics_AnalyticsSettingsView_Night_0_en",20238,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_2_en","features.messages.impl.actionlist_ActionListViewContent_Night_2_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_3_en","features.messages.impl.actionlist_ActionListViewContent_Night_3_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_4_en","features.messages.impl.actionlist_ActionListViewContent_Night_4_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_5_en","features.messages.impl.actionlist_ActionListViewContent_Night_5_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_6_en","features.messages.impl.actionlist_ActionListViewContent_Night_6_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_7_en","features.messages.impl.actionlist_ActionListViewContent_Night_7_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_8_en","features.messages.impl.actionlist_ActionListViewContent_Night_8_en",20252,],
+["features.messages.impl.actionlist_ActionListViewContent_Day_9_en","features.messages.impl.actionlist_ActionListViewContent_Night_9_en",20252,],
+["features.createroom.impl.addpeople_AddPeopleView_Day_0_en","features.createroom.impl.addpeople_AddPeopleView_Night_0_en",20252,],
+["features.createroom.impl.addpeople_AddPeopleView_Day_1_en","features.createroom.impl.addpeople_AddPeopleView_Night_1_en",20252,],
+["features.createroom.impl.addpeople_AddPeopleView_Day_2_en","features.createroom.impl.addpeople_AddPeopleView_Night_2_en",20252,],
+["features.createroom.impl.addpeople_AddPeopleView_Day_3_en","features.createroom.impl.addpeople_AddPeopleView_Night_3_en",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewDark_0_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewDark_1_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewDark_2_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewDark_3_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewDark_4_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewDark_5_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewLight_0_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewLight_1_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewLight_2_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewLight_3_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewLight_4_en","",20252,],
+["features.preferences.impl.advanced_AdvancedSettingsViewLight_5_en","",20252,],
+["libraries.designsystem.components.dialogs_AlertDialogContent_Dialogs_en","",20252,],
+["libraries.designsystem.components.dialogs_AlertDialog_Day_0_en","libraries.designsystem.components.dialogs_AlertDialog_Night_0_en",20252,],
+["features.analytics.impl_AnalyticsOptInView_Day_0_en","features.analytics.impl_AnalyticsOptInView_Night_0_en",20252,],
+["features.analytics.impl_AnalyticsOptInView_Day_1_en","features.analytics.impl_AnalyticsOptInView_Night_1_en",20252,],
+["features.analytics.api.preferences_AnalyticsPreferencesView_Day_0_en","features.analytics.api.preferences_AnalyticsPreferencesView_Night_0_en",20252,],
+["features.analytics.api.preferences_AnalyticsPreferencesView_Day_1_en","features.analytics.api.preferences_AnalyticsPreferencesView_Night_1_en",20252,],
+["features.preferences.impl.analytics_AnalyticsSettingsView_Day_0_en","features.preferences.impl.analytics_AnalyticsSettingsView_Night_0_en",20252,],
["libraries.designsystem.components_Announcement_Day_0_en","libraries.designsystem.components_Announcement_Night_0_en",0,],
-["services.apperror.impl_AppErrorView_Day_0_en","services.apperror.impl_AppErrorView_Night_0_en",20238,],
+["services.apperror.impl_AppErrorView_Day_0_en","services.apperror.impl_AppErrorView_Night_0_en",20252,],
["libraries.designsystem.components.async_AsyncActionView_Day_0_en","libraries.designsystem.components.async_AsyncActionView_Night_0_en",0,],
-["libraries.designsystem.components.async_AsyncActionView_Day_1_en","libraries.designsystem.components.async_AsyncActionView_Night_1_en",20238,],
+["libraries.designsystem.components.async_AsyncActionView_Day_1_en","libraries.designsystem.components.async_AsyncActionView_Night_1_en",20252,],
["libraries.designsystem.components.async_AsyncActionView_Day_2_en","libraries.designsystem.components.async_AsyncActionView_Night_2_en",0,],
-["libraries.designsystem.components.async_AsyncActionView_Day_3_en","libraries.designsystem.components.async_AsyncActionView_Night_3_en",20238,],
+["libraries.designsystem.components.async_AsyncActionView_Day_3_en","libraries.designsystem.components.async_AsyncActionView_Night_3_en",20252,],
["libraries.designsystem.components.async_AsyncActionView_Day_4_en","libraries.designsystem.components.async_AsyncActionView_Night_4_en",0,],
-["libraries.designsystem.components.async_AsyncFailure_Day_0_en","libraries.designsystem.components.async_AsyncFailure_Night_0_en",20238,],
+["libraries.designsystem.components.async_AsyncFailure_Day_0_en","libraries.designsystem.components.async_AsyncFailure_Night_0_en",20252,],
["libraries.designsystem.components.async_AsyncIndicatorFailure_Day_0_en","libraries.designsystem.components.async_AsyncIndicatorFailure_Night_0_en",0,],
["libraries.designsystem.components.async_AsyncIndicatorLoading_Day_0_en","libraries.designsystem.components.async_AsyncIndicatorLoading_Night_0_en",0,],
["libraries.designsystem.components.async_AsyncLoading_Day_0_en","libraries.designsystem.components.async_AsyncLoading_Night_0_en",0,],
-["features.messages.impl.messagecomposer_AttachmentSourcePickerMenu_Day_0_en","features.messages.impl.messagecomposer_AttachmentSourcePickerMenu_Night_0_en",20238,],
+["features.messages.impl.messagecomposer_AttachmentSourcePickerMenu_Day_0_en","features.messages.impl.messagecomposer_AttachmentSourcePickerMenu_Night_0_en",20252,],
["libraries.matrix.ui.components_AttachmentThumbnail_Day_0_en","libraries.matrix.ui.components_AttachmentThumbnail_Night_0_en",0,],
["libraries.matrix.ui.components_AttachmentThumbnail_Day_1_en","libraries.matrix.ui.components_AttachmentThumbnail_Night_1_en",0,],
["libraries.matrix.ui.components_AttachmentThumbnail_Day_2_en","libraries.matrix.ui.components_AttachmentThumbnail_Night_2_en",0,],
@@ -74,18 +74,18 @@ export const screenshots = [
["libraries.matrix.ui.components_AttachmentThumbnail_Day_6_en","libraries.matrix.ui.components_AttachmentThumbnail_Night_6_en",0,],
["libraries.matrix.ui.components_AttachmentThumbnail_Day_7_en","libraries.matrix.ui.components_AttachmentThumbnail_Night_7_en",0,],
["libraries.matrix.ui.components_AttachmentThumbnail_Day_8_en","libraries.matrix.ui.components_AttachmentThumbnail_Night_8_en",0,],
-["features.messages.impl.attachments.preview_AttachmentsView_0_en","",20238,],
-["features.messages.impl.attachments.preview_AttachmentsView_1_en","",20238,],
-["features.messages.impl.attachments.preview_AttachmentsView_2_en","",20238,],
-["features.messages.impl.attachments.preview_AttachmentsView_3_en","",20238,],
-["features.messages.impl.attachments.preview_AttachmentsView_4_en","",20238,],
-["features.messages.impl.attachments.preview_AttachmentsView_5_en","",20238,],
+["features.messages.impl.attachments.preview_AttachmentsView_0_en","",20252,],
+["features.messages.impl.attachments.preview_AttachmentsView_1_en","",20252,],
+["features.messages.impl.attachments.preview_AttachmentsView_2_en","",20252,],
+["features.messages.impl.attachments.preview_AttachmentsView_3_en","",20252,],
+["features.messages.impl.attachments.preview_AttachmentsView_4_en","",20252,],
+["features.messages.impl.attachments.preview_AttachmentsView_5_en","",20252,],
["features.messages.impl.attachments.preview_AttachmentsView_6_en","",0,],
-["features.messages.impl.attachments.preview_AttachmentsView_7_en","",20238,],
+["features.messages.impl.attachments.preview_AttachmentsView_7_en","",20252,],
["libraries.mediaviewer.impl.gallery.ui_AudioItemView_Day_0_en","libraries.mediaviewer.impl.gallery.ui_AudioItemView_Night_0_en",0,],
["libraries.mediaviewer.impl.gallery.ui_AudioItemView_Day_1_en","libraries.mediaviewer.impl.gallery.ui_AudioItemView_Night_1_en",0,],
["libraries.mediaviewer.impl.gallery.ui_AudioItemView_Day_2_en","libraries.mediaviewer.impl.gallery.ui_AudioItemView_Night_2_en",0,],
-["libraries.matrix.ui.components_AvatarActionBottomSheet_Day_0_en","libraries.matrix.ui.components_AvatarActionBottomSheet_Night_0_en",20238,],
+["libraries.matrix.ui.components_AvatarActionBottomSheet_Day_0_en","libraries.matrix.ui.components_AvatarActionBottomSheet_Night_0_en",20252,],
["features.knockrequests.impl.banner_AvatarRowRtl_Day_0_en","features.knockrequests.impl.banner_AvatarRowRtl_Night_0_en",0,],
["features.knockrequests.impl.banner_AvatarRowRtl_Day_1_en","features.knockrequests.impl.banner_AvatarRowRtl_Night_1_en",0,],
["features.knockrequests.impl.banner_AvatarRowRtl_Day_2_en","features.knockrequests.impl.banner_AvatarRowRtl_Night_2_en",0,],
@@ -193,13 +193,13 @@ export const screenshots = [
["libraries.designsystem.components_Badge_Day_0_en","libraries.designsystem.components_Badge_Night_0_en",0,],
["libraries.designsystem.components_BigCheckmark_Day_0_en","libraries.designsystem.components_BigCheckmark_Night_0_en",0,],
["libraries.designsystem.components_BigIcon_Day_0_en","libraries.designsystem.components_BigIcon_Night_0_en",0,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_0_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_0_en",20238,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_1_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_1_en",20238,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_2_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_2_en",20238,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_3_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_3_en",20238,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_4_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_4_en",20238,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_5_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_5_en",20238,],
-["features.preferences.impl.blockedusers_BlockedUsersView_Day_6_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_6_en",20238,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_0_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_0_en",20252,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_1_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_1_en",20252,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_2_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_2_en",20252,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_3_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_3_en",20252,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_4_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_4_en",20252,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_5_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_5_en",20252,],
+["features.preferences.impl.blockedusers_BlockedUsersView_Day_6_en","features.preferences.impl.blockedusers_BlockedUsersView_Night_6_en",20252,],
["libraries.designsystem.components_BloomInitials_Day_0_en","libraries.designsystem.components_BloomInitials_Night_0_en",0,],
["libraries.designsystem.components_BloomInitials_Day_1_en","libraries.designsystem.components_BloomInitials_Night_1_en",0,],
["libraries.designsystem.components_BloomInitials_Day_2_en","libraries.designsystem.components_BloomInitials_Night_2_en",0,],
@@ -210,141 +210,141 @@ export const screenshots = [
["libraries.designsystem.components_BloomInitials_Day_7_en","libraries.designsystem.components_BloomInitials_Night_7_en",0,],
["libraries.designsystem.components_Bloom_Day_0_en","libraries.designsystem.components_Bloom_Night_0_en",0,],
["libraries.designsystem.theme.components_BottomSheetDragHandle_Day_0_en","libraries.designsystem.theme.components_BottomSheetDragHandle_Night_0_en",0,],
-["features.rageshake.impl.bugreport_BugReportView_Day_0_en","features.rageshake.impl.bugreport_BugReportView_Night_0_en",20238,],
-["features.rageshake.impl.bugreport_BugReportView_Day_1_en","features.rageshake.impl.bugreport_BugReportView_Night_1_en",20238,],
-["features.rageshake.impl.bugreport_BugReportView_Day_2_en","features.rageshake.impl.bugreport_BugReportView_Night_2_en",20238,],
-["features.rageshake.impl.bugreport_BugReportView_Day_3_en","features.rageshake.impl.bugreport_BugReportView_Night_3_en",20238,],
-["features.rageshake.impl.bugreport_BugReportView_Day_4_en","features.rageshake.impl.bugreport_BugReportView_Night_4_en",20238,],
+["features.rageshake.impl.bugreport_BugReportView_Day_0_en","features.rageshake.impl.bugreport_BugReportView_Night_0_en",20252,],
+["features.rageshake.impl.bugreport_BugReportView_Day_1_en","features.rageshake.impl.bugreport_BugReportView_Night_1_en",20252,],
+["features.rageshake.impl.bugreport_BugReportView_Day_2_en","features.rageshake.impl.bugreport_BugReportView_Night_2_en",20252,],
+["features.rageshake.impl.bugreport_BugReportView_Day_3_en","features.rageshake.impl.bugreport_BugReportView_Night_3_en",20252,],
+["features.rageshake.impl.bugreport_BugReportView_Day_4_en","features.rageshake.impl.bugreport_BugReportView_Night_4_en",20252,],
["libraries.designsystem.atomic.molecules_ButtonColumnMolecule_Day_0_en","libraries.designsystem.atomic.molecules_ButtonColumnMolecule_Night_0_en",0,],
["libraries.designsystem.atomic.molecules_ButtonRowMolecule_Day_0_en","libraries.designsystem.atomic.molecules_ButtonRowMolecule_Night_0_en",0,],
["features.messages.impl.timeline.components_CallMenuItem_Day_0_en","features.messages.impl.timeline.components_CallMenuItem_Night_0_en",0,],
["features.messages.impl.timeline.components_CallMenuItem_Day_1_en","features.messages.impl.timeline.components_CallMenuItem_Night_1_en",0,],
-["features.messages.impl.timeline.components_CallMenuItem_Day_2_en","features.messages.impl.timeline.components_CallMenuItem_Night_2_en",20238,],
-["features.messages.impl.timeline.components_CallMenuItem_Day_3_en","features.messages.impl.timeline.components_CallMenuItem_Night_3_en",20238,],
+["features.messages.impl.timeline.components_CallMenuItem_Day_2_en","features.messages.impl.timeline.components_CallMenuItem_Night_2_en",20252,],
+["features.messages.impl.timeline.components_CallMenuItem_Day_3_en","features.messages.impl.timeline.components_CallMenuItem_Night_3_en",20252,],
["features.messages.impl.timeline.components_CallMenuItem_Day_4_en","features.messages.impl.timeline.components_CallMenuItem_Night_4_en",0,],
["features.messages.impl.timeline.components_CallMenuItem_Day_5_en","features.messages.impl.timeline.components_CallMenuItem_Night_5_en",0,],
["features.call.impl.ui_CallScreenPipView_Day_0_en","features.call.impl.ui_CallScreenPipView_Night_0_en",0,],
["features.call.impl.ui_CallScreenPipView_Day_1_en","features.call.impl.ui_CallScreenPipView_Night_1_en",0,],
["features.call.impl.ui_CallScreenView_Day_0_en","features.call.impl.ui_CallScreenView_Night_0_en",0,],
-["features.call.impl.ui_CallScreenView_Day_1_en","features.call.impl.ui_CallScreenView_Night_1_en",20238,],
-["features.call.impl.ui_CallScreenView_Day_2_en","features.call.impl.ui_CallScreenView_Night_2_en",20238,],
-["features.call.impl.ui_CallScreenView_Day_3_en","features.call.impl.ui_CallScreenView_Night_3_en",20238,],
-["libraries.textcomposer_CaptionWarningBottomSheet_Day_0_en","libraries.textcomposer_CaptionWarningBottomSheet_Night_0_en",20238,],
-["features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Day_0_en","features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Night_0_en",20238,],
-["features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Day_1_en","features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Night_1_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_0_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_0_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_10_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_10_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_1_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_1_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_2_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_2_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_3_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_3_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_4_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_4_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_5_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_5_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_6_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_6_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_7_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_7_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_8_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_8_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_9_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_9_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_0_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_0_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_1_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_1_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_2_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_2_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_3_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_3_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_4_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_4_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_5_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_5_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_6_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_6_en",20238,],
+["features.call.impl.ui_CallScreenView_Day_1_en","features.call.impl.ui_CallScreenView_Night_1_en",20252,],
+["features.call.impl.ui_CallScreenView_Day_2_en","features.call.impl.ui_CallScreenView_Night_2_en",20252,],
+["features.call.impl.ui_CallScreenView_Day_3_en","features.call.impl.ui_CallScreenView_Night_3_en",20252,],
+["libraries.textcomposer_CaptionWarningBottomSheet_Day_0_en","libraries.textcomposer_CaptionWarningBottomSheet_Night_0_en",20252,],
+["features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Day_0_en","features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Night_0_en",20252,],
+["features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Day_1_en","features.login.impl.screens.changeaccountprovider_ChangeAccountProviderView_Night_1_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_0_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_0_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_10_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_10_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_1_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_1_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_2_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_2_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_3_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_3_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_4_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_4_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_5_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_5_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_6_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_6_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_7_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_7_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_8_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_8_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Day_9_en","features.roomdetails.impl.rolesandpermissions.changeroles_ChangeRolesView_Night_9_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_0_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_0_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_1_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_1_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_2_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_2_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_3_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_3_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_4_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_4_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_5_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_5_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Day_6_en","features.roomdetails.impl.rolesandpermissions.permissions_ChangeRoomPermissionsView_Night_6_en",20252,],
["features.login.impl.changeserver_ChangeServerView_Day_0_en","features.login.impl.changeserver_ChangeServerView_Night_0_en",0,],
-["features.login.impl.changeserver_ChangeServerView_Day_1_en","features.login.impl.changeserver_ChangeServerView_Night_1_en",20238,],
-["features.login.impl.changeserver_ChangeServerView_Day_2_en","features.login.impl.changeserver_ChangeServerView_Night_2_en",20238,],
-["features.login.impl.changeserver_ChangeServerView_Day_3_en","features.login.impl.changeserver_ChangeServerView_Night_3_en",20238,],
+["features.login.impl.changeserver_ChangeServerView_Day_1_en","features.login.impl.changeserver_ChangeServerView_Night_1_en",20252,],
+["features.login.impl.changeserver_ChangeServerView_Day_2_en","features.login.impl.changeserver_ChangeServerView_Night_2_en",20252,],
+["features.login.impl.changeserver_ChangeServerView_Day_3_en","features.login.impl.changeserver_ChangeServerView_Night_3_en",20252,],
["libraries.matrix.ui.components_CheckableResolvedUserRow_en","",0,],
-["libraries.matrix.ui.components_CheckableUnresolvedUserRow_en","",20238,],
+["libraries.matrix.ui.components_CheckableUnresolvedUserRow_en","",20252,],
["libraries.designsystem.theme.components_Checkboxes_Toggles_en","",0,],
-["features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Day_0_en","features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Night_0_en",20238,],
-["features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Day_1_en","features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Night_1_en",20238,],
-["features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Day_2_en","features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Night_2_en",20238,],
-["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_0_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_0_en",20238,],
-["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_1_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_1_en",20238,],
-["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_2_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_2_en",20238,],
-["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_3_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_3_en",20238,],
+["features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Day_0_en","features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Night_0_en",20252,],
+["features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Day_1_en","features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Night_1_en",20252,],
+["features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Day_2_en","features.login.impl.screens.chooseaccountprovider_ChooseAccountProviderView_Night_2_en",20252,],
+["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_0_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_0_en",20252,],
+["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_1_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_1_en",20252,],
+["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_2_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_2_en",20252,],
+["features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Day_3_en","features.ftue.impl.sessionverification.choosemode_ChooseSelfVerificationModeView_Night_3_en",20252,],
["libraries.designsystem.theme.components_CircularProgressIndicator_Progress_Indicators_en","",0,],
["libraries.designsystem.components_ClickableLinkText_Text_en","",0,],
["libraries.designsystem.theme_ColorAliases_Day_0_en","libraries.designsystem.theme_ColorAliases_Night_0_en",0,],
-["libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Day_0_en","libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Night_0_en",20238,],
-["libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Day_1_en","libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Night_1_en",20238,],
-["libraries.textcomposer_ComposerModeView_Day_0_en","libraries.textcomposer_ComposerModeView_Night_0_en",20238,],
+["libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Day_0_en","libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Night_0_en",20252,],
+["libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Day_1_en","libraries.designsystem.atomic.molecules_ComposerAlertMolecule_Night_1_en",20252,],
+["libraries.textcomposer_ComposerModeView_Day_0_en","libraries.textcomposer_ComposerModeView_Night_0_en",20252,],
["libraries.textcomposer_ComposerModeView_Day_1_en","libraries.textcomposer_ComposerModeView_Night_1_en",0,],
["libraries.textcomposer_ComposerModeView_Day_2_en","libraries.textcomposer_ComposerModeView_Night_2_en",0,],
["libraries.textcomposer_ComposerModeView_Day_3_en","libraries.textcomposer_ComposerModeView_Night_3_en",0,],
["libraries.designsystem.components.avatar_CompositeAvatar_Avatars_en","",0,],
-["features.createroom.impl.configureroom_ConfigureRoomViewDark_0_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewDark_1_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewDark_2_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewDark_3_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewDark_4_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewDark_5_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewLight_0_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewLight_1_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewLight_2_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewLight_3_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewLight_4_en","",20238,],
-["features.createroom.impl.configureroom_ConfigureRoomViewLight_5_en","",20238,],
-["features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Day_0_en","features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Night_0_en",20238,],
-["features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Day_1_en","features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Night_1_en",20238,],
-["features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Day_2_en","features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Night_2_en",20238,],
-["features.roomlist.impl.components_ConfirmRecoveryKeyBanner_Day_0_en","features.roomlist.impl.components_ConfirmRecoveryKeyBanner_Night_0_en",20238,],
+["features.createroom.impl.configureroom_ConfigureRoomViewDark_0_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewDark_1_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewDark_2_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewDark_3_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewDark_4_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewDark_5_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewLight_0_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewLight_1_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewLight_2_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewLight_3_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewLight_4_en","",20252,],
+["features.createroom.impl.configureroom_ConfigureRoomViewLight_5_en","",20252,],
+["features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Day_0_en","features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Night_0_en",20252,],
+["features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Day_1_en","features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Night_1_en",20252,],
+["features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Day_2_en","features.login.impl.screens.confirmaccountprovider_ConfirmAccountProviderView_Night_2_en",20252,],
+["features.roomlist.impl.components_ConfirmRecoveryKeyBanner_Day_0_en","features.roomlist.impl.components_ConfirmRecoveryKeyBanner_Night_0_en",20252,],
["libraries.designsystem.components.dialogs_ConfirmationDialogContent_Dialogs_en","",0,],
["libraries.designsystem.components.dialogs_ConfirmationDialog_Day_0_en","libraries.designsystem.components.dialogs_ConfirmationDialog_Night_0_en",0,],
["features.networkmonitor.api.ui_ConnectivityIndicatorView_Day_0_en","features.networkmonitor.api.ui_ConnectivityIndicatorView_Night_0_en",0,],
["libraries.designsystem.atomic.atoms_CounterAtom_Day_0_en","libraries.designsystem.atomic.atoms_CounterAtom_Night_0_en",0,],
-["features.rageshake.api.crash_CrashDetectionView_Day_0_en","features.rageshake.api.crash_CrashDetectionView_Night_0_en",20238,],
-["features.login.impl.screens.createaccount_CreateAccountView_Day_0_en","features.login.impl.screens.createaccount_CreateAccountView_Night_0_en",20238,],
-["features.login.impl.screens.createaccount_CreateAccountView_Day_1_en","features.login.impl.screens.createaccount_CreateAccountView_Night_1_en",20238,],
-["features.login.impl.screens.createaccount_CreateAccountView_Day_2_en","features.login.impl.screens.createaccount_CreateAccountView_Night_2_en",20238,],
-["features.login.impl.screens.createaccount_CreateAccountView_Day_3_en","features.login.impl.screens.createaccount_CreateAccountView_Night_3_en",20238,],
-["libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Day_0_en","libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Night_0_en",20238,],
-["libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Day_1_en","libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Night_1_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_0_en","features.poll.impl.create_CreatePollView_Night_0_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_1_en","features.poll.impl.create_CreatePollView_Night_1_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_2_en","features.poll.impl.create_CreatePollView_Night_2_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_3_en","features.poll.impl.create_CreatePollView_Night_3_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_4_en","features.poll.impl.create_CreatePollView_Night_4_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_5_en","features.poll.impl.create_CreatePollView_Night_5_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_6_en","features.poll.impl.create_CreatePollView_Night_6_en",20238,],
-["features.poll.impl.create_CreatePollView_Day_7_en","features.poll.impl.create_CreatePollView_Night_7_en",20238,],
-["features.createroom.impl.root_CreateRoomRootView_Day_0_en","features.createroom.impl.root_CreateRoomRootView_Night_0_en",20238,],
-["features.createroom.impl.root_CreateRoomRootView_Day_1_en","features.createroom.impl.root_CreateRoomRootView_Night_1_en",20238,],
-["features.createroom.impl.root_CreateRoomRootView_Day_2_en","features.createroom.impl.root_CreateRoomRootView_Night_2_en",20238,],
-["features.createroom.impl.root_CreateRoomRootView_Day_3_en","features.createroom.impl.root_CreateRoomRootView_Night_3_en",20238,],
-["features.createroom.impl.root_CreateRoomRootView_Day_4_en","features.createroom.impl.root_CreateRoomRootView_Night_4_en",20238,],
-["features.createroom.impl.root_CreateRoomRootView_Day_5_en","features.createroom.impl.root_CreateRoomRootView_Night_5_en",20238,],
-["libraries.dateformatter.impl.previews_DateFormatterModeView_0_en","",20238,],
-["libraries.dateformatter.impl.previews_DateFormatterModeView_1_en","",20238,],
-["libraries.dateformatter.impl.previews_DateFormatterModeView_2_en","",20238,],
-["libraries.dateformatter.impl.previews_DateFormatterModeView_3_en","",20238,],
-["libraries.dateformatter.impl.previews_DateFormatterModeView_4_en","",20238,],
+["features.rageshake.api.crash_CrashDetectionView_Day_0_en","features.rageshake.api.crash_CrashDetectionView_Night_0_en",20252,],
+["features.login.impl.screens.createaccount_CreateAccountView_Day_0_en","features.login.impl.screens.createaccount_CreateAccountView_Night_0_en",20252,],
+["features.login.impl.screens.createaccount_CreateAccountView_Day_1_en","features.login.impl.screens.createaccount_CreateAccountView_Night_1_en",20252,],
+["features.login.impl.screens.createaccount_CreateAccountView_Day_2_en","features.login.impl.screens.createaccount_CreateAccountView_Night_2_en",20252,],
+["features.login.impl.screens.createaccount_CreateAccountView_Day_3_en","features.login.impl.screens.createaccount_CreateAccountView_Night_3_en",20252,],
+["libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Day_0_en","libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Night_0_en",20252,],
+["libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Day_1_en","libraries.matrix.ui.components_CreateDmConfirmationBottomSheet_Night_1_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_0_en","features.poll.impl.create_CreatePollView_Night_0_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_1_en","features.poll.impl.create_CreatePollView_Night_1_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_2_en","features.poll.impl.create_CreatePollView_Night_2_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_3_en","features.poll.impl.create_CreatePollView_Night_3_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_4_en","features.poll.impl.create_CreatePollView_Night_4_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_5_en","features.poll.impl.create_CreatePollView_Night_5_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_6_en","features.poll.impl.create_CreatePollView_Night_6_en",20252,],
+["features.poll.impl.create_CreatePollView_Day_7_en","features.poll.impl.create_CreatePollView_Night_7_en",20252,],
+["features.createroom.impl.root_CreateRoomRootView_Day_0_en","features.createroom.impl.root_CreateRoomRootView_Night_0_en",20252,],
+["features.createroom.impl.root_CreateRoomRootView_Day_1_en","features.createroom.impl.root_CreateRoomRootView_Night_1_en",20252,],
+["features.createroom.impl.root_CreateRoomRootView_Day_2_en","features.createroom.impl.root_CreateRoomRootView_Night_2_en",20252,],
+["features.createroom.impl.root_CreateRoomRootView_Day_3_en","features.createroom.impl.root_CreateRoomRootView_Night_3_en",20252,],
+["features.createroom.impl.root_CreateRoomRootView_Day_4_en","features.createroom.impl.root_CreateRoomRootView_Night_4_en",20252,],
+["features.createroom.impl.root_CreateRoomRootView_Day_5_en","features.createroom.impl.root_CreateRoomRootView_Night_5_en",20252,],
+["libraries.dateformatter.impl.previews_DateFormatterModeView_0_en","",20252,],
+["libraries.dateformatter.impl.previews_DateFormatterModeView_1_en","",20252,],
+["libraries.dateformatter.impl.previews_DateFormatterModeView_2_en","",20252,],
+["libraries.dateformatter.impl.previews_DateFormatterModeView_3_en","",20252,],
+["libraries.dateformatter.impl.previews_DateFormatterModeView_4_en","",20252,],
["libraries.mediaviewer.impl.gallery.ui_DateItemView_Day_0_en","libraries.mediaviewer.impl.gallery.ui_DateItemView_Night_0_en",0,],
["libraries.mediaviewer.impl.gallery.ui_DateItemView_Day_1_en","libraries.mediaviewer.impl.gallery.ui_DateItemView_Night_1_en",0,],
-["libraries.designsystem.theme.components.previews_DatePickerDark_DateTime_pickers_en","",20238,],
-["libraries.designsystem.theme.components.previews_DatePickerLight_DateTime_pickers_en","",20238,],
-["features.invite.impl.declineandblock_DeclineAndBlockView_Day_0_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_0_en",20238,],
-["features.invite.impl.declineandblock_DeclineAndBlockView_Day_1_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_1_en",20238,],
-["features.invite.impl.declineandblock_DeclineAndBlockView_Day_2_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_2_en",20238,],
-["features.invite.impl.declineandblock_DeclineAndBlockView_Day_3_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_3_en",20238,],
-["features.invite.impl.declineandblock_DeclineAndBlockView_Day_4_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_4_en",20238,],
+["libraries.designsystem.theme.components.previews_DatePickerDark_DateTime_pickers_en","",20252,],
+["libraries.designsystem.theme.components.previews_DatePickerLight_DateTime_pickers_en","",20252,],
+["features.invite.impl.declineandblock_DeclineAndBlockView_Day_0_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_0_en",20252,],
+["features.invite.impl.declineandblock_DeclineAndBlockView_Day_1_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_1_en",20252,],
+["features.invite.impl.declineandblock_DeclineAndBlockView_Day_2_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_2_en",20252,],
+["features.invite.impl.declineandblock_DeclineAndBlockView_Day_3_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_3_en",20252,],
+["features.invite.impl.declineandblock_DeclineAndBlockView_Day_4_en","features.invite.impl.declineandblock_DeclineAndBlockView_Night_4_en",20252,],
["features.logout.impl.direct_DefaultDirectLogoutView_Day_0_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_0_en",0,],
-["features.logout.impl.direct_DefaultDirectLogoutView_Day_1_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_1_en",20238,],
-["features.logout.impl.direct_DefaultDirectLogoutView_Day_2_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_2_en",20238,],
-["features.logout.impl.direct_DefaultDirectLogoutView_Day_3_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_3_en",20238,],
+["features.logout.impl.direct_DefaultDirectLogoutView_Day_1_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_1_en",20252,],
+["features.logout.impl.direct_DefaultDirectLogoutView_Day_2_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_2_en",20252,],
+["features.logout.impl.direct_DefaultDirectLogoutView_Day_3_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_3_en",20252,],
["features.logout.impl.direct_DefaultDirectLogoutView_Day_4_en","features.logout.impl.direct_DefaultDirectLogoutView_Night_4_en",0,],
-["features.preferences.impl.notifications.edit_DefaultNotificationSettingOption_Day_0_en","features.preferences.impl.notifications.edit_DefaultNotificationSettingOption_Night_0_en",20238,],
-["features.roomlist.impl.components_DefaultRoomListTopBarWithIndicator_Day_0_en","features.roomlist.impl.components_DefaultRoomListTopBarWithIndicator_Night_0_en",20238,],
-["features.roomlist.impl.components_DefaultRoomListTopBar_Day_0_en","features.roomlist.impl.components_DefaultRoomListTopBar_Night_0_en",20238,],
+["features.preferences.impl.notifications.edit_DefaultNotificationSettingOption_Day_0_en","features.preferences.impl.notifications.edit_DefaultNotificationSettingOption_Night_0_en",20252,],
+["features.roomlist.impl.components_DefaultRoomListTopBarWithIndicator_Day_0_en","features.roomlist.impl.components_DefaultRoomListTopBarWithIndicator_Night_0_en",20252,],
+["features.roomlist.impl.components_DefaultRoomListTopBar_Day_0_en","features.roomlist.impl.components_DefaultRoomListTopBar_Night_0_en",20252,],
["features.licenses.impl.details_DependenciesDetailsView_Day_0_en","features.licenses.impl.details_DependenciesDetailsView_Night_0_en",0,],
-["features.licenses.impl.list_DependencyLicensesListView_Day_0_en","features.licenses.impl.list_DependencyLicensesListView_Night_0_en",20238,],
-["features.licenses.impl.list_DependencyLicensesListView_Day_1_en","features.licenses.impl.list_DependencyLicensesListView_Night_1_en",20238,],
-["features.licenses.impl.list_DependencyLicensesListView_Day_2_en","features.licenses.impl.list_DependencyLicensesListView_Night_2_en",20238,],
-["features.licenses.impl.list_DependencyLicensesListView_Day_3_en","features.licenses.impl.list_DependencyLicensesListView_Night_3_en",20238,],
-["features.preferences.impl.developer_DeveloperSettingsView_Day_0_en","features.preferences.impl.developer_DeveloperSettingsView_Night_0_en",20238,],
-["features.preferences.impl.developer_DeveloperSettingsView_Day_1_en","features.preferences.impl.developer_DeveloperSettingsView_Night_1_en",20238,],
-["features.preferences.impl.developer_DeveloperSettingsView_Day_2_en","features.preferences.impl.developer_DeveloperSettingsView_Night_2_en",20238,],
+["features.licenses.impl.list_DependencyLicensesListView_Day_0_en","features.licenses.impl.list_DependencyLicensesListView_Night_0_en",20252,],
+["features.licenses.impl.list_DependencyLicensesListView_Day_1_en","features.licenses.impl.list_DependencyLicensesListView_Night_1_en",20252,],
+["features.licenses.impl.list_DependencyLicensesListView_Day_2_en","features.licenses.impl.list_DependencyLicensesListView_Night_2_en",20252,],
+["features.licenses.impl.list_DependencyLicensesListView_Day_3_en","features.licenses.impl.list_DependencyLicensesListView_Night_3_en",20252,],
+["features.preferences.impl.developer_DeveloperSettingsView_Day_0_en","features.preferences.impl.developer_DeveloperSettingsView_Night_0_en",20252,],
+["features.preferences.impl.developer_DeveloperSettingsView_Day_1_en","features.preferences.impl.developer_DeveloperSettingsView_Night_1_en",20252,],
+["features.preferences.impl.developer_DeveloperSettingsView_Day_2_en","features.preferences.impl.developer_DeveloperSettingsView_Night_2_en",20252,],
["libraries.designsystem.theme.components_DialogWithDestructiveButton_Dialog_with_destructive_button_Dialogs_en","",0,],
["libraries.designsystem.theme.components_DialogWithOnlyMessageAndOkButton_Dialog_with_only_message_and_ok_button_Dialogs_en","",0,],
["libraries.designsystem.theme.components_DialogWithThirdButton_Dialog_with_third_button_Dialogs_en","",0,],
@@ -357,17 +357,17 @@ export const screenshots = [
["libraries.designsystem.text_DpScale_1_0f__en","",0,],
["libraries.designsystem.text_DpScale_1_5f__en","",0,],
["libraries.designsystem.theme.components_DropdownMenuItem_Menus_en","",0,],
-["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_0_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_0_en",20238,],
-["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_1_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_1_en",20238,],
-["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_2_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_2_en",20238,],
-["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_3_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_3_en",20238,],
-["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_4_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_4_en",20238,],
-["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_0_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_0_en",20238,],
-["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_1_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_1_en",20238,],
-["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_2_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_2_en",20238,],
-["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_3_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_3_en",20238,],
-["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_4_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_4_en",20238,],
-["features.preferences.impl.user.editprofile_EditUserProfileView_Day_0_en","features.preferences.impl.user.editprofile_EditUserProfileView_Night_0_en",20238,],
+["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_0_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_0_en",20252,],
+["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_1_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_1_en",20252,],
+["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_2_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_2_en",20252,],
+["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_3_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_3_en",20252,],
+["features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Day_4_en","features.preferences.impl.notifications.edit_EditDefaultNotificationSettingView_Night_4_en",20252,],
+["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_0_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_0_en",20252,],
+["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_1_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_1_en",20252,],
+["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_2_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_2_en",20252,],
+["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_3_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_3_en",20252,],
+["features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Day_4_en","features.roomdetails.impl.securityandprivacy.editroomaddress_EditRoomAddressView_Night_4_en",20252,],
+["features.preferences.impl.user.editprofile_EditUserProfileView_Day_0_en","features.preferences.impl.user.editprofile_EditUserProfileView_Night_0_en",20252,],
["libraries.matrix.ui.components_EditableAvatarView_Day_0_en","libraries.matrix.ui.components_EditableAvatarView_Night_0_en",0,],
["libraries.matrix.ui.components_EditableAvatarView_Day_1_en","libraries.matrix.ui.components_EditableAvatarView_Night_1_en",0,],
["libraries.matrix.ui.components_EditableAvatarView_Day_2_en","libraries.matrix.ui.components_EditableAvatarView_Night_2_en",0,],
@@ -377,9 +377,9 @@ export const screenshots = [
["libraries.designsystem.atomic.atoms_ElementLogoAtomMedium_Day_0_en","libraries.designsystem.atomic.atoms_ElementLogoAtomMedium_Night_0_en",0,],
["features.messages.impl.timeline.components.customreaction_EmojiItem_Day_0_en","features.messages.impl.timeline.components.customreaction_EmojiItem_Night_0_en",0,],
["features.messages.impl.timeline.components.customreaction_EmojiPicker_Day_0_en","features.messages.impl.timeline.components.customreaction_EmojiPicker_Night_0_en",0,],
-["libraries.designsystem.components.dialogs_ErrorDialogContent_Dialogs_en","",20238,],
-["libraries.designsystem.components.dialogs_ErrorDialogWithDoNotShowAgain_Day_0_en","libraries.designsystem.components.dialogs_ErrorDialogWithDoNotShowAgain_Night_0_en",20238,],
-["libraries.designsystem.components.dialogs_ErrorDialog_Day_0_en","libraries.designsystem.components.dialogs_ErrorDialog_Night_0_en",20238,],
+["libraries.designsystem.components.dialogs_ErrorDialogContent_Dialogs_en","",20252,],
+["libraries.designsystem.components.dialogs_ErrorDialogWithDoNotShowAgain_Day_0_en","libraries.designsystem.components.dialogs_ErrorDialogWithDoNotShowAgain_Night_0_en",20252,],
+["libraries.designsystem.components.dialogs_ErrorDialog_Day_0_en","libraries.designsystem.components.dialogs_ErrorDialog_Night_0_en",20252,],
["features.messages.impl.timeline.debug_EventDebugInfoView_Day_0_en","features.messages.impl.timeline.debug_EventDebugInfoView_Night_0_en",0,],
["libraries.featureflag.ui_FeatureListView_Day_0_en","libraries.featureflag.ui_FeatureListView_Night_0_en",0,],
["libraries.mediaviewer.impl.gallery.ui_FileItemView_Day_0_en","libraries.mediaviewer.impl.gallery.ui_FileItemView_Night_0_en",0,],
@@ -397,16 +397,16 @@ export const screenshots = [
["libraries.designsystem.theme.components_FloatingActionButton_Floating_Action_Buttons_en","",0,],
["libraries.designsystem.atomic.pages_FlowStepPage_Day_0_en","libraries.designsystem.atomic.pages_FlowStepPage_Night_0_en",0,],
["features.messages.impl.timeline.focus_FocusRequestStateView_Day_0_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_0_en",0,],
-["features.messages.impl.timeline.focus_FocusRequestStateView_Day_1_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_1_en",20238,],
-["features.messages.impl.timeline.focus_FocusRequestStateView_Day_2_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_2_en",20238,],
-["features.messages.impl.timeline.focus_FocusRequestStateView_Day_3_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_3_en",20238,],
+["features.messages.impl.timeline.focus_FocusRequestStateView_Day_1_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_1_en",20252,],
+["features.messages.impl.timeline.focus_FocusRequestStateView_Day_2_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_2_en",20252,],
+["features.messages.impl.timeline.focus_FocusRequestStateView_Day_3_en","features.messages.impl.timeline.focus_FocusRequestStateView_Night_3_en",20252,],
["features.messages.impl.timeline.components_FocusedEvent_Day_0_en","features.messages.impl.timeline.components_FocusedEvent_Night_0_en",0,],
["libraries.textcomposer.components_FormattingOption_Day_0_en","libraries.textcomposer.components_FormattingOption_Night_0_en",0,],
["features.messages.impl.forward_ForwardMessagesView_Day_0_en","features.messages.impl.forward_ForwardMessagesView_Night_0_en",0,],
["features.messages.impl.forward_ForwardMessagesView_Day_1_en","features.messages.impl.forward_ForwardMessagesView_Night_1_en",0,],
["features.messages.impl.forward_ForwardMessagesView_Day_2_en","features.messages.impl.forward_ForwardMessagesView_Night_2_en",0,],
-["features.messages.impl.forward_ForwardMessagesView_Day_3_en","features.messages.impl.forward_ForwardMessagesView_Night_3_en",20238,],
-["features.roomlist.impl.components_FullScreenIntentPermissionBanner_Day_0_en","features.roomlist.impl.components_FullScreenIntentPermissionBanner_Night_0_en",20238,],
+["features.messages.impl.forward_ForwardMessagesView_Day_3_en","features.messages.impl.forward_ForwardMessagesView_Night_3_en",20252,],
+["features.roomlist.impl.components_FullScreenIntentPermissionBanner_Day_0_en","features.roomlist.impl.components_FullScreenIntentPermissionBanner_Night_0_en",20252,],
["libraries.designsystem.components.button_GradientFloatingActionButtonCircleShape_Day_0_en","libraries.designsystem.components.button_GradientFloatingActionButtonCircleShape_Night_0_en",0,],
["libraries.designsystem.components.button_GradientFloatingActionButton_Day_0_en","libraries.designsystem.components.button_GradientFloatingActionButton_Night_0_en",0,],
["features.messages.impl.timeline.components.group_GroupHeaderView_Day_0_en","features.messages.impl.timeline.components.group_GroupHeaderView_Night_0_en",0,],
@@ -420,8 +420,8 @@ export const screenshots = [
["libraries.designsystem.atomic.molecules_IconTitlePlaceholdersRowMolecule_Day_0_en","libraries.designsystem.atomic.molecules_IconTitlePlaceholdersRowMolecule_Night_0_en",0,],
["libraries.designsystem.atomic.molecules_IconTitleSubtitleMolecule_Day_0_en","libraries.designsystem.atomic.molecules_IconTitleSubtitleMolecule_Night_0_en",0,],
["libraries.designsystem.theme.components_IconToggleButton_Toggles_en","",0,],
-["appicon.enterprise_Icon_en","",0,],
["appicon.element_Icon_en","",0,],
+["appicon.enterprise_Icon_en","",0,],
["libraries.designsystem.icons_IconsCompound_Day_0_en","libraries.designsystem.icons_IconsCompound_Night_0_en",0,],
["libraries.designsystem.icons_IconsCompound_Day_1_en","libraries.designsystem.icons_IconsCompound_Night_1_en",0,],
["libraries.designsystem.icons_IconsCompound_Day_2_en","libraries.designsystem.icons_IconsCompound_Night_2_en",0,],
@@ -430,8 +430,8 @@ export const screenshots = [
["libraries.designsystem.icons_IconsCompound_Day_5_en","libraries.designsystem.icons_IconsCompound_Night_5_en",0,],
["libraries.designsystem.icons_IconsOther_Day_0_en","libraries.designsystem.icons_IconsOther_Night_0_en",0,],
["features.messages.impl.crypto.identity_IdentityChangeStateView_Day_0_en","features.messages.impl.crypto.identity_IdentityChangeStateView_Night_0_en",0,],
-["features.messages.impl.crypto.identity_IdentityChangeStateView_Day_1_en","features.messages.impl.crypto.identity_IdentityChangeStateView_Night_1_en",20238,],
-["features.messages.impl.crypto.identity_IdentityChangeStateView_Day_2_en","features.messages.impl.crypto.identity_IdentityChangeStateView_Night_2_en",20238,],
+["features.messages.impl.crypto.identity_IdentityChangeStateView_Day_1_en","features.messages.impl.crypto.identity_IdentityChangeStateView_Night_1_en",20252,],
+["features.messages.impl.crypto.identity_IdentityChangeStateView_Day_2_en","features.messages.impl.crypto.identity_IdentityChangeStateView_Night_2_en",20252,],
["libraries.mediaviewer.impl.gallery.ui_ImageItemView_Day_0_en","libraries.mediaviewer.impl.gallery.ui_ImageItemView_Night_0_en",0,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_0_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_0_en",0,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_10_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_10_en",0,],
@@ -439,84 +439,85 @@ export const screenshots = [
["libraries.matrix.ui.messages.reply_InReplyToView_Day_1_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_1_en",0,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_2_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_2_en",0,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_3_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_3_en",0,],
-["libraries.matrix.ui.messages.reply_InReplyToView_Day_4_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_4_en",20238,],
+["libraries.matrix.ui.messages.reply_InReplyToView_Day_4_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_4_en",20252,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_5_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_5_en",0,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_6_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_6_en",0,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_7_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_7_en",0,],
-["libraries.matrix.ui.messages.reply_InReplyToView_Day_8_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_8_en",20238,],
+["libraries.matrix.ui.messages.reply_InReplyToView_Day_8_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_8_en",20252,],
["libraries.matrix.ui.messages.reply_InReplyToView_Day_9_en","libraries.matrix.ui.messages.reply_InReplyToView_Night_9_en",0,],
-["features.call.impl.ui_IncomingCallScreen_Day_0_en","features.call.impl.ui_IncomingCallScreen_Night_0_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_0_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_0_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_10_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_10_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_11_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_11_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_12_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_12_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_13_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_13_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_1_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_1_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_2_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_2_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_3_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_3_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_4_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_4_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_5_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_5_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_6_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_6_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_7_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_7_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_8_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_8_en",20238,],
-["features.verifysession.impl.incoming_IncomingVerificationView_Day_9_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_9_en",20238,],
+["features.call.impl.ui_IncomingCallScreen_Day_0_en","features.call.impl.ui_IncomingCallScreen_Night_0_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_0_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_0_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_10_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_10_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_11_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_11_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_12_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_12_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_13_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_13_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_1_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_1_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_2_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_2_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_3_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_3_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_4_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_4_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_5_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_5_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_6_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_6_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_7_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_7_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_8_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_8_en",20252,],
+["features.verifysession.impl.incoming_IncomingVerificationView_Day_9_en","features.verifysession.impl.incoming_IncomingVerificationView_Night_9_en",20252,],
["features.networkmonitor.api.ui_Indicator_Day_0_en","features.networkmonitor.api.ui_Indicator_Night_0_en",0,],
["libraries.designsystem.atomic.molecules_InfoListItemMolecule_Day_0_en","libraries.designsystem.atomic.molecules_InfoListItemMolecule_Night_0_en",0,],
["libraries.designsystem.atomic.organisms_InfoListOrganism_Day_0_en","libraries.designsystem.atomic.organisms_InfoListOrganism_Night_0_en",0,],
-["libraries.matrix.ui.components_InviteSenderView_Day_0_en","libraries.matrix.ui.components_InviteSenderView_Night_0_en",20238,],
-["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_0_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_0_en",20238,],
-["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_1_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_1_en",20238,],
-["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_2_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_2_en",20238,],
-["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_3_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_3_en",20238,],
-["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_4_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_4_en",20238,],
-["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_5_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_5_en",20238,],
+["features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_en","features.call.impl.ui_InvalidAudioDeviceDialog_Night_0_en",20255,],
+["libraries.matrix.ui.components_InviteSenderView_Day_0_en","libraries.matrix.ui.components_InviteSenderView_Night_0_en",20252,],
+["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_0_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_0_en",20252,],
+["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_1_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_1_en",20252,],
+["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_2_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_2_en",20252,],
+["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_3_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_3_en",20252,],
+["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_4_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_4_en",20252,],
+["features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Day_5_en","features.createroom.impl.joinbyaddress_JoinRoomByAddressView_Night_5_en",20252,],
["features.joinroom.impl_JoinRoomView_Day_0_en","features.joinroom.impl_JoinRoomView_Night_0_en",0,],
-["features.joinroom.impl_JoinRoomView_Day_10_en","features.joinroom.impl_JoinRoomView_Night_10_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_11_en","features.joinroom.impl_JoinRoomView_Night_11_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_12_en","features.joinroom.impl_JoinRoomView_Night_12_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_13_en","features.joinroom.impl_JoinRoomView_Night_13_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_14_en","features.joinroom.impl_JoinRoomView_Night_14_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_15_en","features.joinroom.impl_JoinRoomView_Night_15_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_16_en","features.joinroom.impl_JoinRoomView_Night_16_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_1_en","features.joinroom.impl_JoinRoomView_Night_1_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_2_en","features.joinroom.impl_JoinRoomView_Night_2_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_3_en","features.joinroom.impl_JoinRoomView_Night_3_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_4_en","features.joinroom.impl_JoinRoomView_Night_4_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_5_en","features.joinroom.impl_JoinRoomView_Night_5_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_6_en","features.joinroom.impl_JoinRoomView_Night_6_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_7_en","features.joinroom.impl_JoinRoomView_Night_7_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_8_en","features.joinroom.impl_JoinRoomView_Night_8_en",20238,],
-["features.joinroom.impl_JoinRoomView_Day_9_en","features.joinroom.impl_JoinRoomView_Night_9_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_0_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_0_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_1_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_1_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_2_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_2_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_3_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_3_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_4_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_4_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_5_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_5_en",20238,],
-["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_6_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_6_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_0_en","features.knockrequests.impl.list_KnockRequestsListView_Night_0_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_10_en","features.knockrequests.impl.list_KnockRequestsListView_Night_10_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_1_en","features.knockrequests.impl.list_KnockRequestsListView_Night_1_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_2_en","features.knockrequests.impl.list_KnockRequestsListView_Night_2_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_3_en","features.knockrequests.impl.list_KnockRequestsListView_Night_3_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_4_en","features.knockrequests.impl.list_KnockRequestsListView_Night_4_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_5_en","features.knockrequests.impl.list_KnockRequestsListView_Night_5_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_6_en","features.knockrequests.impl.list_KnockRequestsListView_Night_6_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_7_en","features.knockrequests.impl.list_KnockRequestsListView_Night_7_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_8_en","features.knockrequests.impl.list_KnockRequestsListView_Night_8_en",20238,],
-["features.knockrequests.impl.list_KnockRequestsListView_Day_9_en","features.knockrequests.impl.list_KnockRequestsListView_Night_9_en",20238,],
+["features.joinroom.impl_JoinRoomView_Day_10_en","features.joinroom.impl_JoinRoomView_Night_10_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_11_en","features.joinroom.impl_JoinRoomView_Night_11_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_12_en","features.joinroom.impl_JoinRoomView_Night_12_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_13_en","features.joinroom.impl_JoinRoomView_Night_13_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_14_en","features.joinroom.impl_JoinRoomView_Night_14_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_15_en","features.joinroom.impl_JoinRoomView_Night_15_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_16_en","features.joinroom.impl_JoinRoomView_Night_16_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_1_en","features.joinroom.impl_JoinRoomView_Night_1_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_2_en","features.joinroom.impl_JoinRoomView_Night_2_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_3_en","features.joinroom.impl_JoinRoomView_Night_3_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_4_en","features.joinroom.impl_JoinRoomView_Night_4_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_5_en","features.joinroom.impl_JoinRoomView_Night_5_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_6_en","features.joinroom.impl_JoinRoomView_Night_6_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_7_en","features.joinroom.impl_JoinRoomView_Night_7_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_8_en","features.joinroom.impl_JoinRoomView_Night_8_en",20252,],
+["features.joinroom.impl_JoinRoomView_Day_9_en","features.joinroom.impl_JoinRoomView_Night_9_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_0_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_0_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_1_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_1_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_2_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_2_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_3_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_3_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_4_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_4_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_5_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_5_en",20252,],
+["features.knockrequests.impl.banner_KnockRequestsBannerView_Day_6_en","features.knockrequests.impl.banner_KnockRequestsBannerView_Night_6_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_0_en","features.knockrequests.impl.list_KnockRequestsListView_Night_0_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_10_en","features.knockrequests.impl.list_KnockRequestsListView_Night_10_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_1_en","features.knockrequests.impl.list_KnockRequestsListView_Night_1_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_2_en","features.knockrequests.impl.list_KnockRequestsListView_Night_2_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_3_en","features.knockrequests.impl.list_KnockRequestsListView_Night_3_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_4_en","features.knockrequests.impl.list_KnockRequestsListView_Night_4_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_5_en","features.knockrequests.impl.list_KnockRequestsListView_Night_5_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_6_en","features.knockrequests.impl.list_KnockRequestsListView_Night_6_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_7_en","features.knockrequests.impl.list_KnockRequestsListView_Night_7_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_8_en","features.knockrequests.impl.list_KnockRequestsListView_Night_8_en",20252,],
+["features.knockrequests.impl.list_KnockRequestsListView_Day_9_en","features.knockrequests.impl.list_KnockRequestsListView_Night_9_en",20252,],
["libraries.designsystem.components_LabelledCheckbox_Toggles_en","",0,],
["features.leaveroom.api_LeaveRoomView_Day_0_en","features.leaveroom.api_LeaveRoomView_Night_0_en",0,],
-["features.leaveroom.api_LeaveRoomView_Day_1_en","features.leaveroom.api_LeaveRoomView_Night_1_en",20238,],
-["features.leaveroom.api_LeaveRoomView_Day_2_en","features.leaveroom.api_LeaveRoomView_Night_2_en",20238,],
-["features.leaveroom.api_LeaveRoomView_Day_3_en","features.leaveroom.api_LeaveRoomView_Night_3_en",20238,],
-["features.leaveroom.api_LeaveRoomView_Day_4_en","features.leaveroom.api_LeaveRoomView_Night_4_en",20238,],
-["features.leaveroom.api_LeaveRoomView_Day_5_en","features.leaveroom.api_LeaveRoomView_Night_5_en",20238,],
-["features.leaveroom.api_LeaveRoomView_Day_6_en","features.leaveroom.api_LeaveRoomView_Night_6_en",20238,],
+["features.leaveroom.api_LeaveRoomView_Day_1_en","features.leaveroom.api_LeaveRoomView_Night_1_en",20252,],
+["features.leaveroom.api_LeaveRoomView_Day_2_en","features.leaveroom.api_LeaveRoomView_Night_2_en",20252,],
+["features.leaveroom.api_LeaveRoomView_Day_3_en","features.leaveroom.api_LeaveRoomView_Night_3_en",20252,],
+["features.leaveroom.api_LeaveRoomView_Day_4_en","features.leaveroom.api_LeaveRoomView_Night_4_en",20252,],
+["features.leaveroom.api_LeaveRoomView_Day_5_en","features.leaveroom.api_LeaveRoomView_Night_5_en",20252,],
+["features.leaveroom.api_LeaveRoomView_Day_6_en","features.leaveroom.api_LeaveRoomView_Night_6_en",20252,],
["libraries.designsystem.background_LightGradientBackground_Day_0_en","libraries.designsystem.background_LightGradientBackground_Night_0_en",0,],
["libraries.designsystem.theme.components_LinearProgressIndicator_Progress_Indicators_en","",0,],
["features.messages.impl.link_LinkView_Day_0_en","features.messages.impl.link_LinkView_Night_0_en",0,],
-["features.messages.impl.link_LinkView_Day_1_en","features.messages.impl.link_LinkView_Night_1_en",20238,],
+["features.messages.impl.link_LinkView_Day_1_en","features.messages.impl.link_LinkView_Night_1_en",20252,],
["libraries.designsystem.components.dialogs_ListDialogContent_Dialogs_en","",0,],
["libraries.designsystem.components.dialogs_ListDialog_Day_0_en","libraries.designsystem.components.dialogs_ListDialog_Night_0_en",0,],
["libraries.designsystem.theme.components_ListItemPrimaryActionWithIcon_List_item_-_Primary_action_&_Icon_List_items_en","",0,],
@@ -571,31 +572,31 @@ export const screenshots = [
["libraries.designsystem.theme.components_ListSupportingTextSmallPadding_List_supporting_text_-_small_padding_List_sections_en","",0,],
["libraries.textcomposer.components_LiveWaveformView_Day_0_en","libraries.textcomposer.components_LiveWaveformView_Night_0_en",0,],
["appnav.room.joined_LoadingRoomNodeView_Day_0_en","appnav.room.joined_LoadingRoomNodeView_Night_0_en",0,],
-["appnav.room.joined_LoadingRoomNodeView_Day_1_en","appnav.room.joined_LoadingRoomNodeView_Night_1_en",20238,],
-["features.lockscreen.impl.settings_LockScreenSettingsView_Day_0_en","features.lockscreen.impl.settings_LockScreenSettingsView_Night_0_en",20238,],
-["features.lockscreen.impl.settings_LockScreenSettingsView_Day_1_en","features.lockscreen.impl.settings_LockScreenSettingsView_Night_1_en",20238,],
-["features.lockscreen.impl.settings_LockScreenSettingsView_Day_2_en","features.lockscreen.impl.settings_LockScreenSettingsView_Night_2_en",20238,],
+["appnav.room.joined_LoadingRoomNodeView_Day_1_en","appnav.room.joined_LoadingRoomNodeView_Night_1_en",20252,],
+["features.lockscreen.impl.settings_LockScreenSettingsView_Day_0_en","features.lockscreen.impl.settings_LockScreenSettingsView_Night_0_en",20252,],
+["features.lockscreen.impl.settings_LockScreenSettingsView_Day_1_en","features.lockscreen.impl.settings_LockScreenSettingsView_Night_1_en",20252,],
+["features.lockscreen.impl.settings_LockScreenSettingsView_Day_2_en","features.lockscreen.impl.settings_LockScreenSettingsView_Night_2_en",20252,],
["appnav.loggedin_LoggedInView_Day_0_en","appnav.loggedin_LoggedInView_Night_0_en",0,],
-["appnav.loggedin_LoggedInView_Day_1_en","appnav.loggedin_LoggedInView_Night_1_en",20238,],
-["appnav.loggedin_LoggedInView_Day_2_en","appnav.loggedin_LoggedInView_Night_2_en",20238,],
-["appnav.loggedin_LoggedInView_Day_3_en","appnav.loggedin_LoggedInView_Night_3_en",20238,],
-["features.login.impl.screens.loginpassword_LoginPasswordView_Day_0_en","features.login.impl.screens.loginpassword_LoginPasswordView_Night_0_en",20238,],
-["features.login.impl.screens.loginpassword_LoginPasswordView_Day_1_en","features.login.impl.screens.loginpassword_LoginPasswordView_Night_1_en",20238,],
-["features.login.impl.screens.loginpassword_LoginPasswordView_Day_2_en","features.login.impl.screens.loginpassword_LoginPasswordView_Night_2_en",20238,],
-["features.logout.impl_LogoutView_Day_0_en","features.logout.impl_LogoutView_Night_0_en",20238,],
-["features.logout.impl_LogoutView_Day_10_en","features.logout.impl_LogoutView_Night_10_en",20238,],
-["features.logout.impl_LogoutView_Day_11_en","features.logout.impl_LogoutView_Night_11_en",20238,],
-["features.logout.impl_LogoutView_Day_1_en","features.logout.impl_LogoutView_Night_1_en",20238,],
-["features.logout.impl_LogoutView_Day_2_en","features.logout.impl_LogoutView_Night_2_en",20238,],
-["features.logout.impl_LogoutView_Day_3_en","features.logout.impl_LogoutView_Night_3_en",20238,],
-["features.logout.impl_LogoutView_Day_4_en","features.logout.impl_LogoutView_Night_4_en",20238,],
-["features.logout.impl_LogoutView_Day_5_en","features.logout.impl_LogoutView_Night_5_en",20238,],
-["features.logout.impl_LogoutView_Day_6_en","features.logout.impl_LogoutView_Night_6_en",20238,],
-["features.logout.impl_LogoutView_Day_7_en","features.logout.impl_LogoutView_Night_7_en",20238,],
-["features.logout.impl_LogoutView_Day_8_en","features.logout.impl_LogoutView_Night_8_en",20238,],
-["features.logout.impl_LogoutView_Day_9_en","features.logout.impl_LogoutView_Night_9_en",20238,],
+["appnav.loggedin_LoggedInView_Day_1_en","appnav.loggedin_LoggedInView_Night_1_en",20252,],
+["appnav.loggedin_LoggedInView_Day_2_en","appnav.loggedin_LoggedInView_Night_2_en",20252,],
+["appnav.loggedin_LoggedInView_Day_3_en","appnav.loggedin_LoggedInView_Night_3_en",20252,],
+["features.login.impl.screens.loginpassword_LoginPasswordView_Day_0_en","features.login.impl.screens.loginpassword_LoginPasswordView_Night_0_en",20252,],
+["features.login.impl.screens.loginpassword_LoginPasswordView_Day_1_en","features.login.impl.screens.loginpassword_LoginPasswordView_Night_1_en",20252,],
+["features.login.impl.screens.loginpassword_LoginPasswordView_Day_2_en","features.login.impl.screens.loginpassword_LoginPasswordView_Night_2_en",20252,],
+["features.logout.impl_LogoutView_Day_0_en","features.logout.impl_LogoutView_Night_0_en",20252,],
+["features.logout.impl_LogoutView_Day_10_en","features.logout.impl_LogoutView_Night_10_en",20252,],
+["features.logout.impl_LogoutView_Day_11_en","features.logout.impl_LogoutView_Night_11_en",20252,],
+["features.logout.impl_LogoutView_Day_1_en","features.logout.impl_LogoutView_Night_1_en",20252,],
+["features.logout.impl_LogoutView_Day_2_en","features.logout.impl_LogoutView_Night_2_en",20252,],
+["features.logout.impl_LogoutView_Day_3_en","features.logout.impl_LogoutView_Night_3_en",20252,],
+["features.logout.impl_LogoutView_Day_4_en","features.logout.impl_LogoutView_Night_4_en",20252,],
+["features.logout.impl_LogoutView_Day_5_en","features.logout.impl_LogoutView_Night_5_en",20252,],
+["features.logout.impl_LogoutView_Day_6_en","features.logout.impl_LogoutView_Night_6_en",20252,],
+["features.logout.impl_LogoutView_Day_7_en","features.logout.impl_LogoutView_Night_7_en",20252,],
+["features.logout.impl_LogoutView_Day_8_en","features.logout.impl_LogoutView_Night_8_en",20252,],
+["features.logout.impl_LogoutView_Day_9_en","features.logout.impl_LogoutView_Night_9_en",20252,],
["libraries.designsystem.components.button_MainActionButton_Buttons_en","",0,],
-["libraries.textcomposer_MarkdownTextComposerEdit_Day_0_en","libraries.textcomposer_MarkdownTextComposerEdit_Night_0_en",20238,],
+["libraries.textcomposer_MarkdownTextComposerEdit_Day_0_en","libraries.textcomposer_MarkdownTextComposerEdit_Night_0_en",20252,],
["libraries.textcomposer.components.markdown_MarkdownTextInput_Day_0_en","libraries.textcomposer.components.markdown_MarkdownTextInput_Night_0_en",0,],
["libraries.designsystem.atomic.atoms_MatrixBadgeAtomInfo_Day_0_en","libraries.designsystem.atomic.atoms_MatrixBadgeAtomInfo_Night_0_en",0,],
["libraries.designsystem.atomic.atoms_MatrixBadgeAtomNegative_Day_0_en","libraries.designsystem.atomic.atoms_MatrixBadgeAtomNegative_Night_0_en",0,],
@@ -608,22 +609,22 @@ export const screenshots = [
["libraries.matrix.ui.components_MatrixUserRow_Day_1_en","libraries.matrix.ui.components_MatrixUserRow_Night_1_en",0,],
["libraries.mediaviewer.impl.local.audio_MediaAudioView_Day_0_en","libraries.mediaviewer.impl.local.audio_MediaAudioView_Night_0_en",0,],
["libraries.mediaviewer.impl.local.audio_MediaAudioView_Day_1_en","libraries.mediaviewer.impl.local.audio_MediaAudioView_Night_1_en",0,],
-["libraries.mediaviewer.impl.details_MediaDeleteConfirmationBottomSheet_Day_0_en","libraries.mediaviewer.impl.details_MediaDeleteConfirmationBottomSheet_Night_0_en",20238,],
-["libraries.mediaviewer.impl.details_MediaDetailsBottomSheet_Day_0_en","libraries.mediaviewer.impl.details_MediaDetailsBottomSheet_Night_0_en",20238,],
+["libraries.mediaviewer.impl.details_MediaDeleteConfirmationBottomSheet_Day_0_en","libraries.mediaviewer.impl.details_MediaDeleteConfirmationBottomSheet_Night_0_en",20252,],
+["libraries.mediaviewer.impl.details_MediaDetailsBottomSheet_Day_0_en","libraries.mediaviewer.impl.details_MediaDetailsBottomSheet_Night_0_en",20252,],
["libraries.mediaviewer.impl.local.file_MediaFileView_Day_0_en","libraries.mediaviewer.impl.local.file_MediaFileView_Night_0_en",0,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_0_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_0_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_10_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_10_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_11_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_11_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_12_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_12_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_1_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_1_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_2_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_2_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_3_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_3_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_4_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_4_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_5_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_5_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_6_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_6_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_7_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_7_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_8_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_8_en",20238,],
-["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_9_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_9_en",20238,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_0_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_0_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_10_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_10_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_11_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_11_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_12_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_12_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_1_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_1_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_2_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_2_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_3_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_3_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_4_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_4_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_5_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_5_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_6_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_6_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_7_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_7_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_8_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_8_en",20252,],
+["libraries.mediaviewer.impl.gallery_MediaGalleryView_Day_9_en","libraries.mediaviewer.impl.gallery_MediaGalleryView_Night_9_en",20252,],
["libraries.mediaviewer.impl.local.image_MediaImageView_Day_0_en","libraries.mediaviewer.impl.local.image_MediaImageView_Night_0_en",0,],
["libraries.mediaviewer.impl.local.player_MediaPlayerControllerView_Day_0_en","libraries.mediaviewer.impl.local.player_MediaPlayerControllerView_Night_0_en",0,],
["libraries.mediaviewer.impl.local.player_MediaPlayerControllerView_Day_1_en","libraries.mediaviewer.impl.local.player_MediaPlayerControllerView_Night_1_en",0,],
@@ -631,14 +632,14 @@ export const screenshots = [
["libraries.mediaviewer.impl.local.video_MediaVideoView_Day_0_en","libraries.mediaviewer.impl.local.video_MediaVideoView_Night_0_en",0,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_0_en","",0,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_10_en","",0,],
-["libraries.mediaviewer.impl.viewer_MediaViewerView_11_en","",20238,],
-["libraries.mediaviewer.impl.viewer_MediaViewerView_12_en","",20238,],
+["libraries.mediaviewer.impl.viewer_MediaViewerView_11_en","",20252,],
+["libraries.mediaviewer.impl.viewer_MediaViewerView_12_en","",20252,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_13_en","",0,],
-["libraries.mediaviewer.impl.viewer_MediaViewerView_14_en","",20238,],
+["libraries.mediaviewer.impl.viewer_MediaViewerView_14_en","",20252,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_15_en","",0,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_16_en","",0,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_1_en","",0,],
-["libraries.mediaviewer.impl.viewer_MediaViewerView_2_en","",20238,],
+["libraries.mediaviewer.impl.viewer_MediaViewerView_2_en","",20252,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_3_en","",0,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_4_en","",0,],
["libraries.mediaviewer.impl.viewer_MediaViewerView_5_en","",0,],
@@ -650,14 +651,8 @@ export const screenshots = [
["libraries.textcomposer.mentions_MentionSpanTheme_Day_0_en","libraries.textcomposer.mentions_MentionSpanTheme_Night_0_en",0,],
["libraries.designsystem.theme.components.previews_Menu_Menus_en","",0,],
["features.messages.impl.messagecomposer_MessageComposerViewVoice_Day_0_en","features.messages.impl.messagecomposer_MessageComposerViewVoice_Night_0_en",0,],
-["features.messages.impl.messagecomposer_MessageComposerView_Day_0_en","features.messages.impl.messagecomposer_MessageComposerView_Night_0_en",20238,],
+["features.messages.impl.messagecomposer_MessageComposerView_Day_0_en","features.messages.impl.messagecomposer_MessageComposerView_Night_0_en",20252,],
["features.messages.impl.timeline.components_MessageEventBubble_Day_0_en","features.messages.impl.timeline.components_MessageEventBubble_Night_0_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_10_en","features.messages.impl.timeline.components_MessageEventBubble_Night_10_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_11_en","features.messages.impl.timeline.components_MessageEventBubble_Night_11_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_12_en","features.messages.impl.timeline.components_MessageEventBubble_Night_12_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_13_en","features.messages.impl.timeline.components_MessageEventBubble_Night_13_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_14_en","features.messages.impl.timeline.components_MessageEventBubble_Night_14_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_15_en","features.messages.impl.timeline.components_MessageEventBubble_Night_15_en",0,],
["features.messages.impl.timeline.components_MessageEventBubble_Day_1_en","features.messages.impl.timeline.components_MessageEventBubble_Night_1_en",0,],
["features.messages.impl.timeline.components_MessageEventBubble_Day_2_en","features.messages.impl.timeline.components_MessageEventBubble_Night_2_en",0,],
["features.messages.impl.timeline.components_MessageEventBubble_Day_3_en","features.messages.impl.timeline.components_MessageEventBubble_Night_3_en",0,],
@@ -665,9 +660,7 @@ export const screenshots = [
["features.messages.impl.timeline.components_MessageEventBubble_Day_5_en","features.messages.impl.timeline.components_MessageEventBubble_Night_5_en",0,],
["features.messages.impl.timeline.components_MessageEventBubble_Day_6_en","features.messages.impl.timeline.components_MessageEventBubble_Night_6_en",0,],
["features.messages.impl.timeline.components_MessageEventBubble_Day_7_en","features.messages.impl.timeline.components_MessageEventBubble_Night_7_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_8_en","features.messages.impl.timeline.components_MessageEventBubble_Night_8_en",0,],
-["features.messages.impl.timeline.components_MessageEventBubble_Day_9_en","features.messages.impl.timeline.components_MessageEventBubble_Night_9_en",0,],
-["features.messages.impl.timeline.components_MessageShieldView_Day_0_en","features.messages.impl.timeline.components_MessageShieldView_Night_0_en",20238,],
+["features.messages.impl.timeline.components_MessageShieldView_Day_0_en","features.messages.impl.timeline.components_MessageShieldView_Night_0_en",20252,],
["features.messages.impl.timeline.components_MessageStateEventContainer_Day_0_en","features.messages.impl.timeline.components_MessageStateEventContainer_Night_0_en",0,],
["features.messages.impl.timeline.components_MessagesReactionButtonAdd_Day_0_en","features.messages.impl.timeline.components_MessagesReactionButtonAdd_Night_0_en",0,],
["features.messages.impl.timeline.components_MessagesReactionButtonExtra_Day_0_en","features.messages.impl.timeline.components_MessagesReactionButtonExtra_Night_0_en",0,],
@@ -675,25 +668,25 @@ export const screenshots = [
["features.messages.impl.timeline.components_MessagesReactionButton_Day_1_en","features.messages.impl.timeline.components_MessagesReactionButton_Night_1_en",0,],
["features.messages.impl.timeline.components_MessagesReactionButton_Day_2_en","features.messages.impl.timeline.components_MessagesReactionButton_Night_2_en",0,],
["features.messages.impl.timeline.components_MessagesReactionButton_Day_3_en","features.messages.impl.timeline.components_MessagesReactionButton_Night_3_en",0,],
-["features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Day_0_en","features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Night_0_en",20238,],
-["features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Day_1_en","features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Night_1_en",20238,],
-["features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Day_2_en","features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Night_2_en",20238,],
-["features.messages.impl_MessagesView_Day_0_en","features.messages.impl_MessagesView_Night_0_en",20238,],
-["features.messages.impl_MessagesView_Day_10_en","features.messages.impl_MessagesView_Night_10_en",20238,],
-["features.messages.impl_MessagesView_Day_11_en","features.messages.impl_MessagesView_Night_11_en",20238,],
-["features.messages.impl_MessagesView_Day_12_en","features.messages.impl_MessagesView_Night_12_en",20238,],
-["features.messages.impl_MessagesView_Day_13_en","features.messages.impl_MessagesView_Night_13_en",20238,],
-["features.messages.impl_MessagesView_Day_1_en","features.messages.impl_MessagesView_Night_1_en",20238,],
-["features.messages.impl_MessagesView_Day_2_en","features.messages.impl_MessagesView_Night_2_en",20238,],
-["features.messages.impl_MessagesView_Day_3_en","features.messages.impl_MessagesView_Night_3_en",20238,],
-["features.messages.impl_MessagesView_Day_4_en","features.messages.impl_MessagesView_Night_4_en",20238,],
-["features.messages.impl_MessagesView_Day_5_en","features.messages.impl_MessagesView_Night_5_en",20238,],
-["features.messages.impl_MessagesView_Day_6_en","features.messages.impl_MessagesView_Night_6_en",20238,],
-["features.messages.impl_MessagesView_Day_7_en","features.messages.impl_MessagesView_Night_7_en",20238,],
-["features.messages.impl_MessagesView_Day_8_en","features.messages.impl_MessagesView_Night_8_en",20238,],
-["features.messages.impl_MessagesView_Day_9_en","features.messages.impl_MessagesView_Night_9_en",20238,],
+["features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Day_0_en","features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Night_0_en",20252,],
+["features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Day_1_en","features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Night_1_en",20252,],
+["features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Day_2_en","features.messages.impl.crypto.identity_MessagesViewWithIdentityChange_Night_2_en",20252,],
+["features.messages.impl_MessagesView_Day_0_en","features.messages.impl_MessagesView_Night_0_en",20252,],
+["features.messages.impl_MessagesView_Day_10_en","features.messages.impl_MessagesView_Night_10_en",20252,],
+["features.messages.impl_MessagesView_Day_11_en","features.messages.impl_MessagesView_Night_11_en",20252,],
+["features.messages.impl_MessagesView_Day_12_en","features.messages.impl_MessagesView_Night_12_en",20252,],
+["features.messages.impl_MessagesView_Day_13_en","features.messages.impl_MessagesView_Night_13_en",20252,],
+["features.messages.impl_MessagesView_Day_1_en","features.messages.impl_MessagesView_Night_1_en",20252,],
+["features.messages.impl_MessagesView_Day_2_en","features.messages.impl_MessagesView_Night_2_en",20252,],
+["features.messages.impl_MessagesView_Day_3_en","features.messages.impl_MessagesView_Night_3_en",20252,],
+["features.messages.impl_MessagesView_Day_4_en","features.messages.impl_MessagesView_Night_4_en",20252,],
+["features.messages.impl_MessagesView_Day_5_en","features.messages.impl_MessagesView_Night_5_en",20252,],
+["features.messages.impl_MessagesView_Day_6_en","features.messages.impl_MessagesView_Night_6_en",20252,],
+["features.messages.impl_MessagesView_Day_7_en","features.messages.impl_MessagesView_Night_7_en",20252,],
+["features.messages.impl_MessagesView_Day_8_en","features.messages.impl_MessagesView_Night_8_en",20252,],
+["features.messages.impl_MessagesView_Day_9_en","features.messages.impl_MessagesView_Night_9_en",20252,],
["features.migration.impl_MigrationView_Day_0_en","features.migration.impl_MigrationView_Night_0_en",0,],
-["features.migration.impl_MigrationView_Day_1_en","features.migration.impl_MigrationView_Night_1_en",20238,],
+["features.migration.impl_MigrationView_Day_1_en","features.migration.impl_MigrationView_Night_1_en",20252,],
["libraries.designsystem.theme.components_ModalBottomSheetDark_Bottom_Sheets_en","",0,],
["libraries.designsystem.theme.components_ModalBottomSheetLight_Bottom_Sheets_en","",0,],
["appicon.element_MonochromeIcon_en","",0,],
@@ -702,45 +695,43 @@ export const screenshots = [
["libraries.designsystem.components.list_MutipleSelectionListItemSelectedTrailingContent_Multiple_selection_List_item_-_selection_in_trailing_content_List_items_en","",0,],
["libraries.designsystem.components.list_MutipleSelectionListItemSelected_Multiple_selection_List_item_-_selection_in_supporting_text_List_items_en","",0,],
["libraries.designsystem.components.list_MutipleSelectionListItem_Multiple_selection_List_item_-_no_selection_List_items_en","",0,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_0_en","features.preferences.impl.notifications_NotificationSettingsView_Night_0_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_10_en","features.preferences.impl.notifications_NotificationSettingsView_Night_10_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_11_en","features.preferences.impl.notifications_NotificationSettingsView_Night_11_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_12_en","features.preferences.impl.notifications_NotificationSettingsView_Night_12_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_13_en","features.preferences.impl.notifications_NotificationSettingsView_Night_13_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_1_en","features.preferences.impl.notifications_NotificationSettingsView_Night_1_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_2_en","features.preferences.impl.notifications_NotificationSettingsView_Night_2_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_3_en","features.preferences.impl.notifications_NotificationSettingsView_Night_3_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_4_en","features.preferences.impl.notifications_NotificationSettingsView_Night_4_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_5_en","features.preferences.impl.notifications_NotificationSettingsView_Night_5_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_6_en","features.preferences.impl.notifications_NotificationSettingsView_Night_6_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_7_en","features.preferences.impl.notifications_NotificationSettingsView_Night_7_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_8_en","features.preferences.impl.notifications_NotificationSettingsView_Night_8_en",20238,],
-["features.preferences.impl.notifications_NotificationSettingsView_Day_9_en","features.preferences.impl.notifications_NotificationSettingsView_Night_9_en",20238,],
-["features.ftue.impl.notifications_NotificationsOptInView_Day_0_en","features.ftue.impl.notifications_NotificationsOptInView_Night_0_en",20238,],
-["libraries.oidc.impl.webview_OidcView_Day_0_en","libraries.oidc.impl.webview_OidcView_Night_0_en",0,],
-["libraries.oidc.impl.webview_OidcView_Day_1_en","libraries.oidc.impl.webview_OidcView_Night_1_en",0,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_0_en","features.preferences.impl.notifications_NotificationSettingsView_Night_0_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_10_en","features.preferences.impl.notifications_NotificationSettingsView_Night_10_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_11_en","features.preferences.impl.notifications_NotificationSettingsView_Night_11_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_12_en","features.preferences.impl.notifications_NotificationSettingsView_Night_12_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_13_en","features.preferences.impl.notifications_NotificationSettingsView_Night_13_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_1_en","features.preferences.impl.notifications_NotificationSettingsView_Night_1_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_2_en","features.preferences.impl.notifications_NotificationSettingsView_Night_2_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_3_en","features.preferences.impl.notifications_NotificationSettingsView_Night_3_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_4_en","features.preferences.impl.notifications_NotificationSettingsView_Night_4_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_5_en","features.preferences.impl.notifications_NotificationSettingsView_Night_5_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_6_en","features.preferences.impl.notifications_NotificationSettingsView_Night_6_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_7_en","features.preferences.impl.notifications_NotificationSettingsView_Night_7_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_8_en","features.preferences.impl.notifications_NotificationSettingsView_Night_8_en",20252,],
+["features.preferences.impl.notifications_NotificationSettingsView_Day_9_en","features.preferences.impl.notifications_NotificationSettingsView_Night_9_en",20252,],
+["features.ftue.impl.notifications_NotificationsOptInView_Day_0_en","features.ftue.impl.notifications_NotificationsOptInView_Night_0_en",20252,],
["libraries.designsystem.atomic.pages_OnBoardingPage_Day_0_en","libraries.designsystem.atomic.pages_OnBoardingPage_Night_0_en",0,],
-["features.login.impl.screens.onboarding_OnBoardingView_Day_0_en","features.login.impl.screens.onboarding_OnBoardingView_Night_0_en",20238,],
-["features.login.impl.screens.onboarding_OnBoardingView_Day_1_en","features.login.impl.screens.onboarding_OnBoardingView_Night_1_en",20238,],
-["features.login.impl.screens.onboarding_OnBoardingView_Day_2_en","features.login.impl.screens.onboarding_OnBoardingView_Night_2_en",20238,],
-["features.login.impl.screens.onboarding_OnBoardingView_Day_3_en","features.login.impl.screens.onboarding_OnBoardingView_Night_3_en",20238,],
-["features.login.impl.screens.onboarding_OnBoardingView_Day_4_en","features.login.impl.screens.onboarding_OnBoardingView_Night_4_en",20238,],
-["features.login.impl.screens.onboarding_OnBoardingView_Day_5_en","features.login.impl.screens.onboarding_OnBoardingView_Night_5_en",20238,],
+["features.login.impl.screens.onboarding_OnBoardingView_Day_0_en","features.login.impl.screens.onboarding_OnBoardingView_Night_0_en",20252,],
+["features.login.impl.screens.onboarding_OnBoardingView_Day_1_en","features.login.impl.screens.onboarding_OnBoardingView_Night_1_en",20252,],
+["features.login.impl.screens.onboarding_OnBoardingView_Day_2_en","features.login.impl.screens.onboarding_OnBoardingView_Night_2_en",20252,],
+["features.login.impl.screens.onboarding_OnBoardingView_Day_3_en","features.login.impl.screens.onboarding_OnBoardingView_Night_3_en",20252,],
+["features.login.impl.screens.onboarding_OnBoardingView_Day_4_en","features.login.impl.screens.onboarding_OnBoardingView_Night_4_en",20252,],
+["features.login.impl.screens.onboarding_OnBoardingView_Day_5_en","features.login.impl.screens.onboarding_OnBoardingView_Night_5_en",20252,],
["libraries.designsystem.background_OnboardingBackground_Day_0_en","libraries.designsystem.background_OnboardingBackground_Night_0_en",0,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_0_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_0_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_10_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_10_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_11_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_11_en",20238,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_0_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_0_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_10_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_10_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_11_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_11_en",20252,],
["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_12_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_12_en",0,],
["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_13_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_13_en",0,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_1_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_1_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_2_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_2_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_3_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_3_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_4_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_4_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_5_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_5_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_6_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_6_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_7_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_7_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_8_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_8_en",20238,],
-["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_9_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_9_en",20238,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_1_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_1_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_2_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_2_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_3_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_3_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_4_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_4_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_5_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_5_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_6_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_6_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_7_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_7_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_8_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_8_en",20252,],
+["features.verifysession.impl.outgoing_OutgoingVerificationView_Day_9_en","features.verifysession.impl.outgoing_OutgoingVerificationView_Night_9_en",20252,],
["libraries.designsystem.theme.components_OutlinedButtonLargeLowPadding_Buttons_en","",0,],
["libraries.designsystem.theme.components_OutlinedButtonLarge_Buttons_en","",0,],
["libraries.designsystem.theme.components_OutlinedButtonMediumLowPadding_Buttons_en","",0,],
@@ -754,65 +745,65 @@ export const screenshots = [
["libraries.designsystem.components_PageTitleWithIconFull_Day_5_en","libraries.designsystem.components_PageTitleWithIconFull_Night_5_en",0,],
["libraries.designsystem.components_PageTitleWithIconFull_Day_6_en","libraries.designsystem.components_PageTitleWithIconFull_Night_6_en",0,],
["libraries.designsystem.components_PageTitleWithIconMinimal_Day_0_en","libraries.designsystem.components_PageTitleWithIconMinimal_Night_0_en",0,],
-["libraries.mediaviewer.impl.local.pdf_PdfPagesErrorView_Day_0_en","libraries.mediaviewer.impl.local.pdf_PdfPagesErrorView_Night_0_en",20238,],
-["features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Day_0_en","features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Night_0_en",20238,],
-["libraries.permissions.api_PermissionsView_Day_0_en","libraries.permissions.api_PermissionsView_Night_0_en",20238,],
-["libraries.permissions.api_PermissionsView_Day_1_en","libraries.permissions.api_PermissionsView_Night_1_en",20238,],
-["libraries.permissions.api_PermissionsView_Day_2_en","libraries.permissions.api_PermissionsView_Night_2_en",20238,],
-["libraries.permissions.api_PermissionsView_Day_3_en","libraries.permissions.api_PermissionsView_Night_3_en",20238,],
+["libraries.mediaviewer.impl.local.pdf_PdfPagesErrorView_Day_0_en","libraries.mediaviewer.impl.local.pdf_PdfPagesErrorView_Night_0_en",20252,],
+["features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Day_0_en","features.roomdetails.impl.rolesandpermissions.changeroles_PendingMemberRowWithLongName_Night_0_en",20252,],
+["libraries.permissions.api_PermissionsView_Day_0_en","libraries.permissions.api_PermissionsView_Night_0_en",20252,],
+["libraries.permissions.api_PermissionsView_Day_1_en","libraries.permissions.api_PermissionsView_Night_1_en",20252,],
+["libraries.permissions.api_PermissionsView_Day_2_en","libraries.permissions.api_PermissionsView_Night_2_en",20252,],
+["libraries.permissions.api_PermissionsView_Day_3_en","libraries.permissions.api_PermissionsView_Night_3_en",20252,],
["features.lockscreen.impl.components_PinEntryTextField_Day_0_en","features.lockscreen.impl.components_PinEntryTextField_Night_0_en",0,],
["libraries.designsystem.components_PinIcon_Day_0_en","libraries.designsystem.components_PinIcon_Night_0_en",0,],
["features.lockscreen.impl.unlock.keypad_PinKeypad_Day_0_en","features.lockscreen.impl.unlock.keypad_PinKeypad_Night_0_en",0,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_0_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_0_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_1_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_1_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_2_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_2_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_3_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_3_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_4_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_4_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_5_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_5_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_6_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_6_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_7_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_7_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_0_en","features.lockscreen.impl.unlock_PinUnlockView_Night_0_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_1_en","features.lockscreen.impl.unlock_PinUnlockView_Night_1_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_2_en","features.lockscreen.impl.unlock_PinUnlockView_Night_2_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_3_en","features.lockscreen.impl.unlock_PinUnlockView_Night_3_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_4_en","features.lockscreen.impl.unlock_PinUnlockView_Night_4_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_5_en","features.lockscreen.impl.unlock_PinUnlockView_Night_5_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_6_en","features.lockscreen.impl.unlock_PinUnlockView_Night_6_en",20238,],
-["features.lockscreen.impl.unlock_PinUnlockView_Day_7_en","features.lockscreen.impl.unlock_PinUnlockView_Night_7_en",20238,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_0_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_0_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_1_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_1_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_2_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_2_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_3_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_3_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_4_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_4_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_5_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_5_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_6_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_6_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockViewInApp_Day_7_en","features.lockscreen.impl.unlock_PinUnlockViewInApp_Night_7_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_0_en","features.lockscreen.impl.unlock_PinUnlockView_Night_0_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_1_en","features.lockscreen.impl.unlock_PinUnlockView_Night_1_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_2_en","features.lockscreen.impl.unlock_PinUnlockView_Night_2_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_3_en","features.lockscreen.impl.unlock_PinUnlockView_Night_3_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_4_en","features.lockscreen.impl.unlock_PinUnlockView_Night_4_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_5_en","features.lockscreen.impl.unlock_PinUnlockView_Night_5_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_6_en","features.lockscreen.impl.unlock_PinUnlockView_Night_6_en",20252,],
+["features.lockscreen.impl.unlock_PinUnlockView_Day_7_en","features.lockscreen.impl.unlock_PinUnlockView_Night_7_en",20252,],
["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_0_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_0_en",0,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_10_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_10_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_1_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_1_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_2_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_2_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_3_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_3_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_4_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_4_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_5_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_5_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_6_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_6_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_7_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_7_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_8_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_8_en",20238,],
-["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_9_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_9_en",20238,],
-["features.messages.impl.pinned.list_PinnedMessagesListView_Day_0_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_0_en",20238,],
-["features.messages.impl.pinned.list_PinnedMessagesListView_Day_1_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_1_en",20238,],
-["features.messages.impl.pinned.list_PinnedMessagesListView_Day_2_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_2_en",20238,],
-["features.messages.impl.pinned.list_PinnedMessagesListView_Day_3_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_3_en",20238,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_10_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_10_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_1_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_1_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_2_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_2_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_3_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_3_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_4_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_4_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_5_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_5_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_6_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_6_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_7_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_7_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_8_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_8_en",20252,],
+["features.messages.impl.pinned.banner_PinnedMessagesBannerView_Day_9_en","features.messages.impl.pinned.banner_PinnedMessagesBannerView_Night_9_en",20252,],
+["features.messages.impl.pinned.list_PinnedMessagesListView_Day_0_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_0_en",20252,],
+["features.messages.impl.pinned.list_PinnedMessagesListView_Day_1_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_1_en",20252,],
+["features.messages.impl.pinned.list_PinnedMessagesListView_Day_2_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_2_en",20252,],
+["features.messages.impl.pinned.list_PinnedMessagesListView_Day_3_en","features.messages.impl.pinned.list_PinnedMessagesListView_Night_3_en",20252,],
["libraries.designsystem.atomic.atoms_PlaceholderAtom_Day_0_en","libraries.designsystem.atomic.atoms_PlaceholderAtom_Night_0_en",0,],
-["features.poll.api.pollcontent_PollAnswerViewDisclosedNotSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewDisclosedNotSelected_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollAnswerViewDisclosedSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewDisclosedSelected_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollAnswerViewEndedSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewEndedSelected_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollAnswerViewEndedWinnerNotSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewEndedWinnerNotSelected_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollAnswerViewEndedWinnerSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewEndedWinnerSelected_Night_0_en",20238,],
+["features.poll.api.pollcontent_PollAnswerViewDisclosedNotSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewDisclosedNotSelected_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollAnswerViewDisclosedSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewDisclosedSelected_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollAnswerViewEndedSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewEndedSelected_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollAnswerViewEndedWinnerNotSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewEndedWinnerNotSelected_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollAnswerViewEndedWinnerSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewEndedWinnerSelected_Night_0_en",20252,],
["features.poll.api.pollcontent_PollAnswerViewUndisclosedNotSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewUndisclosedNotSelected_Night_0_en",0,],
["features.poll.api.pollcontent_PollAnswerViewUndisclosedSelected_Day_0_en","features.poll.api.pollcontent_PollAnswerViewUndisclosedSelected_Night_0_en",0,],
-["features.poll.api.pollcontent_PollContentViewCreatorEditable_Day_0_en","features.poll.api.pollcontent_PollContentViewCreatorEditable_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollContentViewCreatorEnded_Day_0_en","features.poll.api.pollcontent_PollContentViewCreatorEnded_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollContentViewCreator_Day_0_en","features.poll.api.pollcontent_PollContentViewCreator_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollContentViewDisclosed_Day_0_en","features.poll.api.pollcontent_PollContentViewDisclosed_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollContentViewEnded_Day_0_en","features.poll.api.pollcontent_PollContentViewEnded_Night_0_en",20238,],
-["features.poll.api.pollcontent_PollContentViewUndisclosed_Day_0_en","features.poll.api.pollcontent_PollContentViewUndisclosed_Night_0_en",20238,],
-["features.poll.impl.history_PollHistoryView_Day_0_en","features.poll.impl.history_PollHistoryView_Night_0_en",20238,],
-["features.poll.impl.history_PollHistoryView_Day_1_en","features.poll.impl.history_PollHistoryView_Night_1_en",20238,],
-["features.poll.impl.history_PollHistoryView_Day_2_en","features.poll.impl.history_PollHistoryView_Night_2_en",20238,],
-["features.poll.impl.history_PollHistoryView_Day_3_en","features.poll.impl.history_PollHistoryView_Night_3_en",20238,],
-["features.poll.impl.history_PollHistoryView_Day_4_en","features.poll.impl.history_PollHistoryView_Night_4_en",20238,],
+["features.poll.api.pollcontent_PollContentViewCreatorEditable_Day_0_en","features.poll.api.pollcontent_PollContentViewCreatorEditable_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollContentViewCreatorEnded_Day_0_en","features.poll.api.pollcontent_PollContentViewCreatorEnded_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollContentViewCreator_Day_0_en","features.poll.api.pollcontent_PollContentViewCreator_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollContentViewDisclosed_Day_0_en","features.poll.api.pollcontent_PollContentViewDisclosed_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollContentViewEnded_Day_0_en","features.poll.api.pollcontent_PollContentViewEnded_Night_0_en",20252,],
+["features.poll.api.pollcontent_PollContentViewUndisclosed_Day_0_en","features.poll.api.pollcontent_PollContentViewUndisclosed_Night_0_en",20252,],
+["features.poll.impl.history_PollHistoryView_Day_0_en","features.poll.impl.history_PollHistoryView_Night_0_en",20252,],
+["features.poll.impl.history_PollHistoryView_Day_1_en","features.poll.impl.history_PollHistoryView_Night_1_en",20252,],
+["features.poll.impl.history_PollHistoryView_Day_2_en","features.poll.impl.history_PollHistoryView_Night_2_en",20252,],
+["features.poll.impl.history_PollHistoryView_Day_3_en","features.poll.impl.history_PollHistoryView_Night_3_en",20252,],
+["features.poll.impl.history_PollHistoryView_Day_4_en","features.poll.impl.history_PollHistoryView_Night_4_en",20252,],
["features.poll.api.pollcontent_PollTitleView_Day_0_en","features.poll.api.pollcontent_PollTitleView_Night_0_en",0,],
["libraries.designsystem.components.preferences_PreferenceCategory_Preferences_en","",0,],
["libraries.designsystem.components.preferences_PreferenceCheckbox_Preferences_en","",0,],
@@ -826,218 +817,215 @@ export const screenshots = [
["libraries.designsystem.components.preferences_PreferenceRow_Preferences_en","",0,],
["libraries.designsystem.components.preferences_PreferenceSlide_Preferences_en","",0,],
["libraries.designsystem.components.preferences_PreferenceSwitch_Preferences_en","",0,],
-["features.preferences.impl.root_PreferencesRootViewDark_0_en","",20238,],
-["features.preferences.impl.root_PreferencesRootViewDark_1_en","",20238,],
-["features.preferences.impl.root_PreferencesRootViewLight_0_en","",20238,],
-["features.preferences.impl.root_PreferencesRootViewLight_1_en","",20238,],
+["features.preferences.impl.root_PreferencesRootViewDark_0_en","",20252,],
+["features.preferences.impl.root_PreferencesRootViewDark_1_en","",20252,],
+["features.preferences.impl.root_PreferencesRootViewLight_0_en","",20252,],
+["features.preferences.impl.root_PreferencesRootViewLight_1_en","",20252,],
["features.messages.impl.timeline.components.event_ProgressButton_Day_0_en","features.messages.impl.timeline.components.event_ProgressButton_Night_0_en",0,],
-["libraries.designsystem.components_ProgressDialogContent_Dialogs_en","",20238,],
-["libraries.designsystem.components_ProgressDialog_Day_0_en","libraries.designsystem.components_ProgressDialog_Night_0_en",20238,],
-["features.messages.impl.timeline.protection_ProtectedView_Day_0_en","features.messages.impl.timeline.protection_ProtectedView_Night_0_en",20238,],
-["features.messages.impl.timeline.protection_ProtectedView_Day_1_en","features.messages.impl.timeline.protection_ProtectedView_Night_1_en",20238,],
-["features.messages.impl.timeline.protection_ProtectedView_Day_2_en","features.messages.impl.timeline.protection_ProtectedView_Night_2_en",20238,],
-["features.messages.impl.timeline.protection_ProtectedView_Day_3_en","features.messages.impl.timeline.protection_ProtectedView_Night_3_en",20238,],
-["libraries.troubleshoot.impl.history_PushHistoryView_Day_0_en","libraries.troubleshoot.impl.history_PushHistoryView_Night_0_en",20238,],
-["libraries.troubleshoot.impl.history_PushHistoryView_Day_1_en","libraries.troubleshoot.impl.history_PushHistoryView_Night_1_en",20238,],
-["libraries.troubleshoot.impl.history_PushHistoryView_Day_2_en","libraries.troubleshoot.impl.history_PushHistoryView_Night_2_en",20238,],
-["features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Day_0_en","features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Night_0_en",20238,],
-["features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Day_1_en","features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Night_1_en",20238,],
-["features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Day_2_en","features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Night_2_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_0_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_0_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_1_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_1_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_2_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_2_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_3_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_3_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_4_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_4_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_5_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_5_en",20238,],
-["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_6_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_6_en",20238,],
-["features.login.impl.screens.qrcode.intro_QrCodeIntroView_Day_0_en","features.login.impl.screens.qrcode.intro_QrCodeIntroView_Night_0_en",20238,],
-["features.login.impl.screens.qrcode.intro_QrCodeIntroView_Day_1_en","features.login.impl.screens.qrcode.intro_QrCodeIntroView_Night_1_en",20238,],
-["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_0_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_0_en",20238,],
-["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_1_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_1_en",20238,],
-["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_2_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_2_en",20238,],
-["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_3_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_3_en",20238,],
-["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_4_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_4_en",20238,],
+["libraries.designsystem.components_ProgressDialogContent_Dialogs_en","",20252,],
+["libraries.designsystem.components_ProgressDialog_Day_0_en","libraries.designsystem.components_ProgressDialog_Night_0_en",20252,],
+["features.messages.impl.timeline.protection_ProtectedView_Day_0_en","features.messages.impl.timeline.protection_ProtectedView_Night_0_en",20252,],
+["features.messages.impl.timeline.protection_ProtectedView_Day_1_en","features.messages.impl.timeline.protection_ProtectedView_Night_1_en",20252,],
+["features.messages.impl.timeline.protection_ProtectedView_Day_2_en","features.messages.impl.timeline.protection_ProtectedView_Night_2_en",20252,],
+["features.messages.impl.timeline.protection_ProtectedView_Day_3_en","features.messages.impl.timeline.protection_ProtectedView_Night_3_en",20252,],
+["libraries.troubleshoot.impl.history_PushHistoryView_Day_0_en","libraries.troubleshoot.impl.history_PushHistoryView_Night_0_en",20252,],
+["libraries.troubleshoot.impl.history_PushHistoryView_Day_1_en","libraries.troubleshoot.impl.history_PushHistoryView_Night_1_en",20252,],
+["libraries.troubleshoot.impl.history_PushHistoryView_Day_2_en","libraries.troubleshoot.impl.history_PushHistoryView_Night_2_en",20252,],
+["features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Day_0_en","features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Night_0_en",20252,],
+["features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Day_1_en","features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Night_1_en",20252,],
+["features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Day_2_en","features.login.impl.screens.qrcode.confirmation_QrCodeConfirmationView_Night_2_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_0_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_0_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_1_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_1_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_2_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_2_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_3_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_3_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_4_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_4_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_5_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_5_en",20252,],
+["features.login.impl.screens.qrcode.error_QrCodeErrorView_Day_6_en","features.login.impl.screens.qrcode.error_QrCodeErrorView_Night_6_en",20252,],
+["features.login.impl.screens.qrcode.intro_QrCodeIntroView_Day_0_en","features.login.impl.screens.qrcode.intro_QrCodeIntroView_Night_0_en",20252,],
+["features.login.impl.screens.qrcode.intro_QrCodeIntroView_Day_1_en","features.login.impl.screens.qrcode.intro_QrCodeIntroView_Night_1_en",20252,],
+["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_0_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_0_en",20252,],
+["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_1_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_1_en",20252,],
+["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_2_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_2_en",20252,],
+["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_3_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_3_en",20252,],
+["features.login.impl.screens.qrcode.scan_QrCodeScanView_Day_4_en","features.login.impl.screens.qrcode.scan_QrCodeScanView_Night_4_en",20252,],
["libraries.designsystem.theme.components_RadioButton_Toggles_en","",0,],
-["features.rageshake.api.detection_RageshakeDialogContent_Day_0_en","features.rageshake.api.detection_RageshakeDialogContent_Night_0_en",20238,],
-["features.rageshake.api.preferences_RageshakePreferencesView_Day_0_en","features.rageshake.api.preferences_RageshakePreferencesView_Night_0_en",20238,],
+["features.rageshake.api.detection_RageshakeDialogContent_Day_0_en","features.rageshake.api.detection_RageshakeDialogContent_Night_0_en",20252,],
+["features.rageshake.api.preferences_RageshakePreferencesView_Day_0_en","features.rageshake.api.preferences_RageshakePreferencesView_Night_0_en",20252,],
["features.rageshake.api.preferences_RageshakePreferencesView_Day_1_en","features.rageshake.api.preferences_RageshakePreferencesView_Night_1_en",0,],
["features.messages.impl.timeline.components.reactionsummary_ReactionSummaryViewContent_Day_0_en","features.messages.impl.timeline.components.reactionsummary_ReactionSummaryViewContent_Night_0_en",0,],
-["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_0_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_0_en",20238,],
-["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_1_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_1_en",20238,],
-["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_2_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_2_en",20238,],
-["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_3_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_3_en",20238,],
-["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_4_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_4_en",20238,],
-["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_5_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_5_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_0_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_0_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_10_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_10_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_11_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_11_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_12_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_12_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_13_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_13_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_1_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_1_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_2_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_2_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_3_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_3_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_4_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_4_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_5_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_5_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_6_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_6_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_7_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_7_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_8_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_8_en",20238,],
-["features.securebackup.impl.setup.views_RecoveryKeyView_Day_9_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_9_en",20238,],
+["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_0_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_0_en",20252,],
+["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_1_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_1_en",20252,],
+["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_2_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_2_en",20252,],
+["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_3_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_3_en",20252,],
+["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_4_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_4_en",20252,],
+["features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Day_5_en","features.messages.impl.timeline.components.receipt.bottomsheet_ReadReceiptBottomSheet_Night_5_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_0_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_0_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_10_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_10_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_11_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_11_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_12_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_12_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_13_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_13_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_1_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_1_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_2_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_2_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_3_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_3_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_4_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_4_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_5_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_5_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_6_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_6_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_7_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_7_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_8_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_8_en",20252,],
+["features.securebackup.impl.setup.views_RecoveryKeyView_Day_9_en","features.securebackup.impl.setup.views_RecoveryKeyView_Night_9_en",20252,],
["libraries.designsystem.atomic.atoms_RedIndicatorAtom_Day_0_en","libraries.designsystem.atomic.atoms_RedIndicatorAtom_Night_0_en",0,],
["features.messages.impl.timeline.components_ReplySwipeIndicator_Day_0_en","features.messages.impl.timeline.components_ReplySwipeIndicator_Night_0_en",0,],
-["features.messages.impl.report_ReportMessageView_Day_0_en","features.messages.impl.report_ReportMessageView_Night_0_en",20238,],
-["features.messages.impl.report_ReportMessageView_Day_1_en","features.messages.impl.report_ReportMessageView_Night_1_en",20238,],
-["features.messages.impl.report_ReportMessageView_Day_2_en","features.messages.impl.report_ReportMessageView_Night_2_en",20238,],
-["features.messages.impl.report_ReportMessageView_Day_3_en","features.messages.impl.report_ReportMessageView_Night_3_en",20238,],
-["features.messages.impl.report_ReportMessageView_Day_4_en","features.messages.impl.report_ReportMessageView_Night_4_en",20238,],
-["features.messages.impl.report_ReportMessageView_Day_5_en","features.messages.impl.report_ReportMessageView_Night_5_en",20238,],
-["features.reportroom.impl_ReportRoomView_Day_0_en","features.reportroom.impl_ReportRoomView_Night_0_en",20238,],
-["features.reportroom.impl_ReportRoomView_Day_1_en","features.reportroom.impl_ReportRoomView_Night_1_en",20238,],
-["features.reportroom.impl_ReportRoomView_Day_2_en","features.reportroom.impl_ReportRoomView_Night_2_en",20238,],
-["features.reportroom.impl_ReportRoomView_Day_3_en","features.reportroom.impl_ReportRoomView_Night_3_en",20238,],
-["features.reportroom.impl_ReportRoomView_Day_4_en","features.reportroom.impl_ReportRoomView_Night_4_en",20238,],
-["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_0_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_0_en",20238,],
-["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_1_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_1_en",20238,],
-["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_2_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_2_en",20238,],
-["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_3_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_3_en",20238,],
-["features.securebackup.impl.reset.root_ResetIdentityRootView_Day_0_en","features.securebackup.impl.reset.root_ResetIdentityRootView_Night_0_en",20238,],
-["features.securebackup.impl.reset.root_ResetIdentityRootView_Day_1_en","features.securebackup.impl.reset.root_ResetIdentityRootView_Night_1_en",20238,],
+["features.messages.impl.report_ReportMessageView_Day_0_en","features.messages.impl.report_ReportMessageView_Night_0_en",20252,],
+["features.messages.impl.report_ReportMessageView_Day_1_en","features.messages.impl.report_ReportMessageView_Night_1_en",20252,],
+["features.messages.impl.report_ReportMessageView_Day_2_en","features.messages.impl.report_ReportMessageView_Night_2_en",20252,],
+["features.messages.impl.report_ReportMessageView_Day_3_en","features.messages.impl.report_ReportMessageView_Night_3_en",20252,],
+["features.messages.impl.report_ReportMessageView_Day_4_en","features.messages.impl.report_ReportMessageView_Night_4_en",20252,],
+["features.messages.impl.report_ReportMessageView_Day_5_en","features.messages.impl.report_ReportMessageView_Night_5_en",20252,],
+["features.reportroom.impl_ReportRoomView_Day_0_en","features.reportroom.impl_ReportRoomView_Night_0_en",20252,],
+["features.reportroom.impl_ReportRoomView_Day_1_en","features.reportroom.impl_ReportRoomView_Night_1_en",20252,],
+["features.reportroom.impl_ReportRoomView_Day_2_en","features.reportroom.impl_ReportRoomView_Night_2_en",20252,],
+["features.reportroom.impl_ReportRoomView_Day_3_en","features.reportroom.impl_ReportRoomView_Night_3_en",20252,],
+["features.reportroom.impl_ReportRoomView_Day_4_en","features.reportroom.impl_ReportRoomView_Night_4_en",20252,],
+["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_0_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_0_en",20252,],
+["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_1_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_1_en",20252,],
+["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_2_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_2_en",20252,],
+["features.securebackup.impl.reset.password_ResetIdentityPasswordView_Day_3_en","features.securebackup.impl.reset.password_ResetIdentityPasswordView_Night_3_en",20252,],
+["features.securebackup.impl.reset.root_ResetIdentityRootView_Day_0_en","features.securebackup.impl.reset.root_ResetIdentityRootView_Night_0_en",20252,],
+["features.securebackup.impl.reset.root_ResetIdentityRootView_Day_1_en","features.securebackup.impl.reset.root_ResetIdentityRootView_Night_1_en",20252,],
["features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Day_0_en","features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Night_0_en",0,],
-["features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Day_1_en","features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Night_1_en",20238,],
-["features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Day_2_en","features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Night_2_en",20238,],
-["libraries.designsystem.components.dialogs_RetryDialogContent_Dialogs_en","",20238,],
-["libraries.designsystem.components.dialogs_RetryDialog_Day_0_en","libraries.designsystem.components.dialogs_RetryDialog_Night_0_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_0_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_0_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_1_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_1_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_2_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_2_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_3_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_3_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_4_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_4_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_5_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_5_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_6_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_6_en",20238,],
-["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_7_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_7_en",20238,],
+["features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Day_1_en","features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Night_1_en",20252,],
+["features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Day_2_en","features.messages.impl.crypto.sendfailure.resolve_ResolveVerifiedUserSendFailureView_Night_2_en",20252,],
+["libraries.designsystem.components.dialogs_RetryDialogContent_Dialogs_en","",20252,],
+["libraries.designsystem.components.dialogs_RetryDialog_Day_0_en","libraries.designsystem.components.dialogs_RetryDialog_Night_0_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_0_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_0_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_1_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_1_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_2_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_2_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_3_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_3_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_4_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_4_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_5_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_5_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_6_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_6_en",20252,],
+["features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Day_7_en","features.roomdetails.impl.rolesandpermissions_RolesAndPermissionsView_Night_7_en",20252,],
["libraries.matrix.ui.room.address_RoomAddressField_Day_0_en","libraries.matrix.ui.room.address_RoomAddressField_Night_0_en",0,],
["features.roomaliasresolver.impl_RoomAliasResolverView_Day_0_en","features.roomaliasresolver.impl_RoomAliasResolverView_Night_0_en",0,],
-["features.roomaliasresolver.impl_RoomAliasResolverView_Day_1_en","features.roomaliasresolver.impl_RoomAliasResolverView_Night_1_en",20238,],
-["features.roomaliasresolver.impl_RoomAliasResolverView_Day_2_en","features.roomaliasresolver.impl_RoomAliasResolverView_Night_2_en",20238,],
-["features.roomdetails.impl_RoomDetailsDark_0_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_10_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_11_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_12_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_13_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_14_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_15_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_16_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_17_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_18_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_1_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_2_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_3_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_4_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_5_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_6_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_7_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_8_en","",20238,],
-["features.roomdetails.impl_RoomDetailsDark_9_en","",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_0_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_0_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_1_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_1_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_2_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_2_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_3_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_3_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_4_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_4_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_5_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_5_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_6_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_6_en",20238,],
-["features.roomdetails.impl.edit_RoomDetailsEditView_Day_7_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_7_en",20238,],
-["features.roomdetails.impl_RoomDetails_0_en","",20238,],
-["features.roomdetails.impl_RoomDetails_10_en","",20238,],
-["features.roomdetails.impl_RoomDetails_11_en","",20238,],
-["features.roomdetails.impl_RoomDetails_12_en","",20238,],
-["features.roomdetails.impl_RoomDetails_13_en","",20238,],
-["features.roomdetails.impl_RoomDetails_14_en","",20238,],
-["features.roomdetails.impl_RoomDetails_15_en","",20238,],
-["features.roomdetails.impl_RoomDetails_16_en","",20238,],
-["features.roomdetails.impl_RoomDetails_17_en","",20238,],
-["features.roomdetails.impl_RoomDetails_18_en","",20238,],
-["features.roomdetails.impl_RoomDetails_1_en","",20238,],
-["features.roomdetails.impl_RoomDetails_2_en","",20238,],
-["features.roomdetails.impl_RoomDetails_3_en","",20238,],
-["features.roomdetails.impl_RoomDetails_4_en","",20238,],
-["features.roomdetails.impl_RoomDetails_5_en","",20238,],
-["features.roomdetails.impl_RoomDetails_6_en","",20238,],
-["features.roomdetails.impl_RoomDetails_7_en","",20238,],
-["features.roomdetails.impl_RoomDetails_8_en","",20238,],
-["features.roomdetails.impl_RoomDetails_9_en","",20238,],
-["features.roomdirectory.impl.root_RoomDirectoryView_Day_0_en","features.roomdirectory.impl.root_RoomDirectoryView_Night_0_en",20238,],
-["features.roomdirectory.impl.root_RoomDirectoryView_Day_1_en","features.roomdirectory.impl.root_RoomDirectoryView_Night_1_en",20238,],
-["features.roomdirectory.impl.root_RoomDirectoryView_Day_2_en","features.roomdirectory.impl.root_RoomDirectoryView_Night_2_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_0_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_0_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_1_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_1_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_2_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_2_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_3_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_3_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_4_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_4_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_5_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_5_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_6_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_6_en",20238,],
-["features.roomdetails.impl.invite_RoomInviteMembersView_Day_7_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_7_en",20238,],
-["features.roomlist.impl.components_RoomListContentView_Day_0_en","features.roomlist.impl.components_RoomListContentView_Night_0_en",20238,],
-["features.roomlist.impl.components_RoomListContentView_Day_1_en","features.roomlist.impl.components_RoomListContentView_Night_1_en",20238,],
+["features.roomaliasresolver.impl_RoomAliasResolverView_Day_1_en","features.roomaliasresolver.impl_RoomAliasResolverView_Night_1_en",20252,],
+["features.roomaliasresolver.impl_RoomAliasResolverView_Day_2_en","features.roomaliasresolver.impl_RoomAliasResolverView_Night_2_en",20252,],
+["features.roomdetails.impl_RoomDetailsDark_0_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_10_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_11_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_12_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_13_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_14_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_15_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_16_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_17_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_18_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_1_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_2_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_3_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_4_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_5_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_6_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_7_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_8_en","",20252,],
+["features.roomdetails.impl_RoomDetailsDark_9_en","",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_0_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_0_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_1_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_1_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_2_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_2_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_3_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_3_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_4_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_4_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_5_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_5_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_6_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_6_en",20252,],
+["features.roomdetails.impl.edit_RoomDetailsEditView_Day_7_en","features.roomdetails.impl.edit_RoomDetailsEditView_Night_7_en",20252,],
+["features.roomdetails.impl_RoomDetails_0_en","",20252,],
+["features.roomdetails.impl_RoomDetails_10_en","",20252,],
+["features.roomdetails.impl_RoomDetails_11_en","",20252,],
+["features.roomdetails.impl_RoomDetails_12_en","",20252,],
+["features.roomdetails.impl_RoomDetails_13_en","",20252,],
+["features.roomdetails.impl_RoomDetails_14_en","",20252,],
+["features.roomdetails.impl_RoomDetails_15_en","",20252,],
+["features.roomdetails.impl_RoomDetails_16_en","",20252,],
+["features.roomdetails.impl_RoomDetails_17_en","",20252,],
+["features.roomdetails.impl_RoomDetails_18_en","",20252,],
+["features.roomdetails.impl_RoomDetails_1_en","",20252,],
+["features.roomdetails.impl_RoomDetails_2_en","",20252,],
+["features.roomdetails.impl_RoomDetails_3_en","",20252,],
+["features.roomdetails.impl_RoomDetails_4_en","",20252,],
+["features.roomdetails.impl_RoomDetails_5_en","",20252,],
+["features.roomdetails.impl_RoomDetails_6_en","",20252,],
+["features.roomdetails.impl_RoomDetails_7_en","",20252,],
+["features.roomdetails.impl_RoomDetails_8_en","",20252,],
+["features.roomdetails.impl_RoomDetails_9_en","",20252,],
+["features.roomdirectory.impl.root_RoomDirectoryView_Day_0_en","features.roomdirectory.impl.root_RoomDirectoryView_Night_0_en",20252,],
+["features.roomdirectory.impl.root_RoomDirectoryView_Day_1_en","features.roomdirectory.impl.root_RoomDirectoryView_Night_1_en",20252,],
+["features.roomdirectory.impl.root_RoomDirectoryView_Day_2_en","features.roomdirectory.impl.root_RoomDirectoryView_Night_2_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_0_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_0_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_1_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_1_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_2_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_2_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_3_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_3_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_4_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_4_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_5_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_5_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_6_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_6_en",20252,],
+["features.roomdetails.impl.invite_RoomInviteMembersView_Day_7_en","features.roomdetails.impl.invite_RoomInviteMembersView_Night_7_en",20252,],
+["features.roomlist.impl.components_RoomListContentView_Day_0_en","features.roomlist.impl.components_RoomListContentView_Night_0_en",20252,],
+["features.roomlist.impl.components_RoomListContentView_Day_1_en","features.roomlist.impl.components_RoomListContentView_Night_1_en",20252,],
["features.roomlist.impl.components_RoomListContentView_Day_2_en","features.roomlist.impl.components_RoomListContentView_Night_2_en",0,],
-["features.roomlist.impl.components_RoomListContentView_Day_3_en","features.roomlist.impl.components_RoomListContentView_Night_3_en",20238,],
-["features.roomlist.impl.components_RoomListContentView_Day_4_en","features.roomlist.impl.components_RoomListContentView_Night_4_en",20238,],
-["features.roomlist.impl_RoomListDeclineInviteMenuContent_Day_0_en","features.roomlist.impl_RoomListDeclineInviteMenuContent_Night_0_en",20238,],
-["features.roomlist.impl.filters_RoomListFiltersView_Day_0_en","features.roomlist.impl.filters_RoomListFiltersView_Night_0_en",20238,],
-["features.roomlist.impl.filters_RoomListFiltersView_Day_1_en","features.roomlist.impl.filters_RoomListFiltersView_Night_1_en",20238,],
-["features.roomlist.impl_RoomListModalBottomSheetContent_Day_0_en","features.roomlist.impl_RoomListModalBottomSheetContent_Night_0_en",20238,],
-["features.roomlist.impl_RoomListModalBottomSheetContent_Day_1_en","features.roomlist.impl_RoomListModalBottomSheetContent_Night_1_en",20238,],
-["features.roomlist.impl_RoomListModalBottomSheetContent_Day_2_en","features.roomlist.impl_RoomListModalBottomSheetContent_Night_2_en",20238,],
+["features.roomlist.impl.components_RoomListContentView_Day_3_en","features.roomlist.impl.components_RoomListContentView_Night_3_en",20252,],
+["features.roomlist.impl.components_RoomListContentView_Day_4_en","features.roomlist.impl.components_RoomListContentView_Night_4_en",20252,],
+["features.roomlist.impl_RoomListDeclineInviteMenuContent_Day_0_en","features.roomlist.impl_RoomListDeclineInviteMenuContent_Night_0_en",20252,],
+["features.roomlist.impl.filters_RoomListFiltersView_Day_0_en","features.roomlist.impl.filters_RoomListFiltersView_Night_0_en",20252,],
+["features.roomlist.impl.filters_RoomListFiltersView_Day_1_en","features.roomlist.impl.filters_RoomListFiltersView_Night_1_en",20252,],
+["features.roomlist.impl_RoomListModalBottomSheetContent_Day_0_en","features.roomlist.impl_RoomListModalBottomSheetContent_Night_0_en",20252,],
+["features.roomlist.impl_RoomListModalBottomSheetContent_Day_1_en","features.roomlist.impl_RoomListModalBottomSheetContent_Night_1_en",20252,],
+["features.roomlist.impl_RoomListModalBottomSheetContent_Day_2_en","features.roomlist.impl_RoomListModalBottomSheetContent_Night_2_en",20252,],
["features.roomlist.impl.search_RoomListSearchContent_Day_0_en","features.roomlist.impl.search_RoomListSearchContent_Night_0_en",0,],
-["features.roomlist.impl.search_RoomListSearchContent_Day_1_en","features.roomlist.impl.search_RoomListSearchContent_Night_1_en",20238,],
-["features.roomlist.impl_RoomListView_Day_0_en","features.roomlist.impl_RoomListView_Night_0_en",20238,],
-["features.roomlist.impl_RoomListView_Day_10_en","features.roomlist.impl_RoomListView_Night_10_en",20238,],
-["features.roomlist.impl_RoomListView_Day_1_en","features.roomlist.impl_RoomListView_Night_1_en",20238,],
-["features.roomlist.impl_RoomListView_Day_2_en","features.roomlist.impl_RoomListView_Night_2_en",20238,],
-["features.roomlist.impl_RoomListView_Day_3_en","features.roomlist.impl_RoomListView_Night_3_en",20238,],
-["features.roomlist.impl_RoomListView_Day_4_en","features.roomlist.impl_RoomListView_Night_4_en",20238,],
-["features.roomlist.impl_RoomListView_Day_5_en","features.roomlist.impl_RoomListView_Night_5_en",20238,],
-["features.roomlist.impl_RoomListView_Day_6_en","features.roomlist.impl_RoomListView_Night_6_en",20238,],
-["features.roomlist.impl_RoomListView_Day_7_en","features.roomlist.impl_RoomListView_Night_7_en",20238,],
+["features.roomlist.impl.search_RoomListSearchContent_Day_1_en","features.roomlist.impl.search_RoomListSearchContent_Night_1_en",20252,],
+["features.roomlist.impl_RoomListView_Day_0_en","features.roomlist.impl_RoomListView_Night_0_en",20252,],
+["features.roomlist.impl_RoomListView_Day_10_en","features.roomlist.impl_RoomListView_Night_10_en",20252,],
+["features.roomlist.impl_RoomListView_Day_1_en","features.roomlist.impl_RoomListView_Night_1_en",20252,],
+["features.roomlist.impl_RoomListView_Day_2_en","features.roomlist.impl_RoomListView_Night_2_en",20252,],
+["features.roomlist.impl_RoomListView_Day_3_en","features.roomlist.impl_RoomListView_Night_3_en",20252,],
+["features.roomlist.impl_RoomListView_Day_4_en","features.roomlist.impl_RoomListView_Night_4_en",20252,],
+["features.roomlist.impl_RoomListView_Day_5_en","features.roomlist.impl_RoomListView_Night_5_en",20252,],
+["features.roomlist.impl_RoomListView_Day_6_en","features.roomlist.impl_RoomListView_Night_6_en",20252,],
+["features.roomlist.impl_RoomListView_Day_7_en","features.roomlist.impl_RoomListView_Night_7_en",20252,],
["features.roomlist.impl_RoomListView_Day_8_en","features.roomlist.impl_RoomListView_Night_8_en",0,],
["features.roomlist.impl_RoomListView_Day_9_en","features.roomlist.impl_RoomListView_Night_9_en",0,],
-["features.roomdetails.impl.members_RoomMemberListViewBanned_Day_0_en","features.roomdetails.impl.members_RoomMemberListViewBanned_Night_0_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListViewBanned_Day_1_en","features.roomdetails.impl.members_RoomMemberListViewBanned_Night_1_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListViewBanned_Day_2_en","features.roomdetails.impl.members_RoomMemberListViewBanned_Night_2_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_0_en","features.roomdetails.impl.members_RoomMemberListView_Night_0_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_1_en","features.roomdetails.impl.members_RoomMemberListView_Night_1_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_2_en","features.roomdetails.impl.members_RoomMemberListView_Night_2_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_3_en","features.roomdetails.impl.members_RoomMemberListView_Night_3_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_4_en","features.roomdetails.impl.members_RoomMemberListView_Night_4_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_5_en","features.roomdetails.impl.members_RoomMemberListView_Night_5_en",20238,],
+["features.roomdetails.impl.members_RoomMemberListViewBanned_Day_0_en","features.roomdetails.impl.members_RoomMemberListViewBanned_Night_0_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListViewBanned_Day_1_en","features.roomdetails.impl.members_RoomMemberListViewBanned_Night_1_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListViewBanned_Day_2_en","features.roomdetails.impl.members_RoomMemberListViewBanned_Night_2_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_0_en","features.roomdetails.impl.members_RoomMemberListView_Night_0_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_1_en","features.roomdetails.impl.members_RoomMemberListView_Night_1_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_2_en","features.roomdetails.impl.members_RoomMemberListView_Night_2_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_3_en","features.roomdetails.impl.members_RoomMemberListView_Night_3_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_4_en","features.roomdetails.impl.members_RoomMemberListView_Night_4_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_5_en","features.roomdetails.impl.members_RoomMemberListView_Night_5_en",20252,],
["features.roomdetails.impl.members_RoomMemberListView_Day_6_en","features.roomdetails.impl.members_RoomMemberListView_Night_6_en",0,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_7_en","features.roomdetails.impl.members_RoomMemberListView_Night_7_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_8_en","features.roomdetails.impl.members_RoomMemberListView_Night_8_en",20238,],
-["features.roomdetails.impl.members_RoomMemberListView_Day_9_en","features.roomdetails.impl.members_RoomMemberListView_Night_9_en",20238,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_7_en","features.roomdetails.impl.members_RoomMemberListView_Night_7_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_8_en","features.roomdetails.impl.members_RoomMemberListView_Night_8_en",20252,],
+["features.roomdetails.impl.members_RoomMemberListView_Day_9_en","features.roomdetails.impl.members_RoomMemberListView_Night_9_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_0_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_0_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_1_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_1_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_2_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_2_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_3_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_3_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_4_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_4_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_5_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_5_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_6_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_6_en",20252,],
+["features.roommembermoderation.impl_RoomMemberModerationView_Day_7_en","features.roommembermoderation.impl_RoomMemberModerationView_Night_7_en",20252,],
["libraries.designsystem.atomic.molecules_RoomMembersCountMolecule_Day_0_en","libraries.designsystem.atomic.molecules_RoomMembersCountMolecule_Night_0_en",0,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_0_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_0_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_10_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_10_en",0,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_1_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_1_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_2_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_2_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_3_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_3_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_4_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_4_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_5_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_5_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_6_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_6_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_7_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_7_en",0,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_8_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_8_en",20238,],
-["features.roomdetails.impl.members.moderation_RoomMembersModerationView_Day_9_en","features.roomdetails.impl.members.moderation_RoomMembersModerationView_Night_9_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsOption_Day_0_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsOption_Night_0_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_0_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_0_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_1_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_1_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_2_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_2_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_3_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_3_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_4_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_4_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_5_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_5_en",20238,],
-["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_6_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_6_en",20238,],
-["libraries.roomselect.impl_RoomSelectView_Day_0_en","libraries.roomselect.impl_RoomSelectView_Night_0_en",20238,],
-["libraries.roomselect.impl_RoomSelectView_Day_1_en","libraries.roomselect.impl_RoomSelectView_Night_1_en",20238,],
-["libraries.roomselect.impl_RoomSelectView_Day_2_en","libraries.roomselect.impl_RoomSelectView_Night_2_en",20238,],
-["libraries.roomselect.impl_RoomSelectView_Day_3_en","libraries.roomselect.impl_RoomSelectView_Night_3_en",20238,],
-["libraries.roomselect.impl_RoomSelectView_Day_4_en","libraries.roomselect.impl_RoomSelectView_Night_4_en",20238,],
-["libraries.roomselect.impl_RoomSelectView_Day_5_en","libraries.roomselect.impl_RoomSelectView_Night_5_en",20238,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsOption_Day_0_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsOption_Night_0_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_0_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_0_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_1_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_1_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_2_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_2_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_3_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_3_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_4_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_4_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_5_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_5_en",20252,],
+["features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Day_6_en","features.roomdetails.impl.notificationsettings_RoomNotificationSettingsView_Night_6_en",20252,],
+["libraries.roomselect.impl_RoomSelectView_Day_0_en","libraries.roomselect.impl_RoomSelectView_Night_0_en",20252,],
+["libraries.roomselect.impl_RoomSelectView_Day_1_en","libraries.roomselect.impl_RoomSelectView_Night_1_en",20252,],
+["libraries.roomselect.impl_RoomSelectView_Day_2_en","libraries.roomselect.impl_RoomSelectView_Night_2_en",20252,],
+["libraries.roomselect.impl_RoomSelectView_Day_3_en","libraries.roomselect.impl_RoomSelectView_Night_3_en",20252,],
+["libraries.roomselect.impl_RoomSelectView_Day_4_en","libraries.roomselect.impl_RoomSelectView_Night_4_en",20252,],
+["libraries.roomselect.impl_RoomSelectView_Day_5_en","libraries.roomselect.impl_RoomSelectView_Night_5_en",20252,],
["features.roomlist.impl.components_RoomSummaryPlaceholderRow_Day_0_en","features.roomlist.impl.components_RoomSummaryPlaceholderRow_Night_0_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_0_en","features.roomlist.impl.components_RoomSummaryRow_Night_0_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_10_en","features.roomlist.impl.components_RoomSummaryRow_Night_10_en",0,],
@@ -1060,12 +1048,12 @@ export const screenshots = [
["features.roomlist.impl.components_RoomSummaryRow_Day_26_en","features.roomlist.impl.components_RoomSummaryRow_Night_26_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_27_en","features.roomlist.impl.components_RoomSummaryRow_Night_27_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_28_en","features.roomlist.impl.components_RoomSummaryRow_Night_28_en",0,],
-["features.roomlist.impl.components_RoomSummaryRow_Day_29_en","features.roomlist.impl.components_RoomSummaryRow_Night_29_en",20238,],
-["features.roomlist.impl.components_RoomSummaryRow_Day_2_en","features.roomlist.impl.components_RoomSummaryRow_Night_2_en",20238,],
-["features.roomlist.impl.components_RoomSummaryRow_Day_30_en","features.roomlist.impl.components_RoomSummaryRow_Night_30_en",20238,],
-["features.roomlist.impl.components_RoomSummaryRow_Day_31_en","features.roomlist.impl.components_RoomSummaryRow_Night_31_en",20238,],
-["features.roomlist.impl.components_RoomSummaryRow_Day_32_en","features.roomlist.impl.components_RoomSummaryRow_Night_32_en",20238,],
-["features.roomlist.impl.components_RoomSummaryRow_Day_33_en","features.roomlist.impl.components_RoomSummaryRow_Night_33_en",20238,],
+["features.roomlist.impl.components_RoomSummaryRow_Day_29_en","features.roomlist.impl.components_RoomSummaryRow_Night_29_en",20252,],
+["features.roomlist.impl.components_RoomSummaryRow_Day_2_en","features.roomlist.impl.components_RoomSummaryRow_Night_2_en",20252,],
+["features.roomlist.impl.components_RoomSummaryRow_Day_30_en","features.roomlist.impl.components_RoomSummaryRow_Night_30_en",20252,],
+["features.roomlist.impl.components_RoomSummaryRow_Day_31_en","features.roomlist.impl.components_RoomSummaryRow_Night_31_en",20252,],
+["features.roomlist.impl.components_RoomSummaryRow_Day_32_en","features.roomlist.impl.components_RoomSummaryRow_Night_32_en",20252,],
+["features.roomlist.impl.components_RoomSummaryRow_Day_33_en","features.roomlist.impl.components_RoomSummaryRow_Night_33_en",20252,],
["features.roomlist.impl.components_RoomSummaryRow_Day_3_en","features.roomlist.impl.components_RoomSummaryRow_Night_3_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_4_en","features.roomlist.impl.components_RoomSummaryRow_Night_4_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_5_en","features.roomlist.impl.components_RoomSummaryRow_Night_5_en",0,],
@@ -1073,77 +1061,77 @@ export const screenshots = [
["features.roomlist.impl.components_RoomSummaryRow_Day_7_en","features.roomlist.impl.components_RoomSummaryRow_Night_7_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_8_en","features.roomlist.impl.components_RoomSummaryRow_Night_8_en",0,],
["features.roomlist.impl.components_RoomSummaryRow_Day_9_en","features.roomlist.impl.components_RoomSummaryRow_Night_9_en",0,],
-["appnav.root_RootView_Day_0_en","appnav.root_RootView_Night_0_en",20238,],
-["appnav.root_RootView_Day_1_en","appnav.root_RootView_Night_1_en",20238,],
-["appnav.root_RootView_Day_2_en","appnav.root_RootView_Night_2_en",20238,],
-["appicon.element_RoundIcon_en","",0,],
+["appnav.root_RootView_Day_0_en","appnav.root_RootView_Night_0_en",20252,],
+["appnav.root_RootView_Day_1_en","appnav.root_RootView_Night_1_en",20252,],
+["appnav.root_RootView_Day_2_en","appnav.root_RootView_Night_2_en",20252,],
["appicon.enterprise_RoundIcon_en","",0,],
+["appicon.element_RoundIcon_en","",0,],
["libraries.designsystem.atomic.atoms_RoundedIconAtom_Day_0_en","libraries.designsystem.atomic.atoms_RoundedIconAtom_Night_0_en",0,],
-["features.verifysession.impl.emoji_SasEmojis_Day_0_en","features.verifysession.impl.emoji_SasEmojis_Night_0_en",20238,],
-["features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Day_0_en","features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Night_0_en",20238,],
-["features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Day_1_en","features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Night_1_en",20238,],
+["features.verifysession.impl.emoji_SasEmojis_Day_0_en","features.verifysession.impl.emoji_SasEmojis_Night_0_en",20252,],
+["features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Day_0_en","features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Night_0_en",20252,],
+["features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Day_1_en","features.login.impl.screens.searchaccountprovider_SearchAccountProviderView_Night_1_en",20252,],
["libraries.designsystem.theme.components_SearchBarActiveNoneQuery_Search_views_en","",0,],
["libraries.designsystem.theme.components_SearchBarActiveWithContent_Search_views_en","",0,],
-["libraries.designsystem.theme.components_SearchBarActiveWithNoResults_Search_views_en","",20238,],
+["libraries.designsystem.theme.components_SearchBarActiveWithNoResults_Search_views_en","",20252,],
["libraries.designsystem.theme.components_SearchBarActiveWithQueryNoBackButton_Search_views_en","",0,],
["libraries.designsystem.theme.components_SearchBarActiveWithQuery_Search_views_en","",0,],
["libraries.designsystem.theme.components_SearchBarInactive_Search_views_en","",0,],
-["features.createroom.impl.components_SearchMultipleUsersResultItem_en","",20238,],
-["features.createroom.impl.components_SearchSingleUserResultItem_en","",20238,],
-["features.securebackup.impl.disable_SecureBackupDisableView_Day_0_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_0_en",20238,],
-["features.securebackup.impl.disable_SecureBackupDisableView_Day_1_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_1_en",20238,],
-["features.securebackup.impl.disable_SecureBackupDisableView_Day_2_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_2_en",20238,],
-["features.securebackup.impl.disable_SecureBackupDisableView_Day_3_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_3_en",20238,],
-["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_0_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_0_en",20238,],
-["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_1_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_1_en",20238,],
-["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_2_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_2_en",20238,],
-["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_3_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_3_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_0_en","features.securebackup.impl.root_SecureBackupRootView_Night_0_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_10_en","features.securebackup.impl.root_SecureBackupRootView_Night_10_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_11_en","features.securebackup.impl.root_SecureBackupRootView_Night_11_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_12_en","features.securebackup.impl.root_SecureBackupRootView_Night_12_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_13_en","features.securebackup.impl.root_SecureBackupRootView_Night_13_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_14_en","features.securebackup.impl.root_SecureBackupRootView_Night_14_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_15_en","features.securebackup.impl.root_SecureBackupRootView_Night_15_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_16_en","features.securebackup.impl.root_SecureBackupRootView_Night_16_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_17_en","features.securebackup.impl.root_SecureBackupRootView_Night_17_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_1_en","features.securebackup.impl.root_SecureBackupRootView_Night_1_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_2_en","features.securebackup.impl.root_SecureBackupRootView_Night_2_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_3_en","features.securebackup.impl.root_SecureBackupRootView_Night_3_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_4_en","features.securebackup.impl.root_SecureBackupRootView_Night_4_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_5_en","features.securebackup.impl.root_SecureBackupRootView_Night_5_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_6_en","features.securebackup.impl.root_SecureBackupRootView_Night_6_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_7_en","features.securebackup.impl.root_SecureBackupRootView_Night_7_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_8_en","features.securebackup.impl.root_SecureBackupRootView_Night_8_en",20238,],
-["features.securebackup.impl.root_SecureBackupRootView_Day_9_en","features.securebackup.impl.root_SecureBackupRootView_Night_9_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_0_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_0_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_1_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_1_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_2_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_2_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_3_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_3_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_4_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_4_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupView_Day_0_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_0_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupView_Day_1_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_1_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupView_Day_2_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_2_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupView_Day_3_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_3_en",20238,],
-["features.securebackup.impl.setup_SecureBackupSetupView_Day_4_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_4_en",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_0_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_1_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_2_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_3_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_4_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_5_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_6_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_7_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_8_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_0_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_1_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_2_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_3_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_4_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_5_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_6_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_7_en","",20238,],
-["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_8_en","",20238,],
+["features.createroom.impl.components_SearchMultipleUsersResultItem_en","",20252,],
+["features.createroom.impl.components_SearchSingleUserResultItem_en","",20252,],
+["features.securebackup.impl.disable_SecureBackupDisableView_Day_0_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_0_en",20252,],
+["features.securebackup.impl.disable_SecureBackupDisableView_Day_1_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_1_en",20252,],
+["features.securebackup.impl.disable_SecureBackupDisableView_Day_2_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_2_en",20252,],
+["features.securebackup.impl.disable_SecureBackupDisableView_Day_3_en","features.securebackup.impl.disable_SecureBackupDisableView_Night_3_en",20252,],
+["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_0_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_0_en",20252,],
+["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_1_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_1_en",20252,],
+["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_2_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_2_en",20252,],
+["features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Day_3_en","features.securebackup.impl.enter_SecureBackupEnterRecoveryKeyView_Night_3_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_0_en","features.securebackup.impl.root_SecureBackupRootView_Night_0_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_10_en","features.securebackup.impl.root_SecureBackupRootView_Night_10_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_11_en","features.securebackup.impl.root_SecureBackupRootView_Night_11_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_12_en","features.securebackup.impl.root_SecureBackupRootView_Night_12_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_13_en","features.securebackup.impl.root_SecureBackupRootView_Night_13_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_14_en","features.securebackup.impl.root_SecureBackupRootView_Night_14_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_15_en","features.securebackup.impl.root_SecureBackupRootView_Night_15_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_16_en","features.securebackup.impl.root_SecureBackupRootView_Night_16_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_17_en","features.securebackup.impl.root_SecureBackupRootView_Night_17_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_1_en","features.securebackup.impl.root_SecureBackupRootView_Night_1_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_2_en","features.securebackup.impl.root_SecureBackupRootView_Night_2_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_3_en","features.securebackup.impl.root_SecureBackupRootView_Night_3_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_4_en","features.securebackup.impl.root_SecureBackupRootView_Night_4_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_5_en","features.securebackup.impl.root_SecureBackupRootView_Night_5_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_6_en","features.securebackup.impl.root_SecureBackupRootView_Night_6_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_7_en","features.securebackup.impl.root_SecureBackupRootView_Night_7_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_8_en","features.securebackup.impl.root_SecureBackupRootView_Night_8_en",20252,],
+["features.securebackup.impl.root_SecureBackupRootView_Day_9_en","features.securebackup.impl.root_SecureBackupRootView_Night_9_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_0_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_0_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_1_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_1_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_2_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_2_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_3_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_3_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupViewChange_Day_4_en","features.securebackup.impl.setup_SecureBackupSetupViewChange_Night_4_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupView_Day_0_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_0_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupView_Day_1_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_1_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupView_Day_2_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_2_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupView_Day_3_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_3_en",20252,],
+["features.securebackup.impl.setup_SecureBackupSetupView_Day_4_en","features.securebackup.impl.setup_SecureBackupSetupView_Night_4_en",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_0_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_1_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_2_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_3_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_4_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_5_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_6_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_7_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewDark_8_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_0_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_1_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_2_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_3_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_4_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_5_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_6_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_7_en","",20252,],
+["features.roomdetails.impl.securityandprivacy_SecurityAndPrivacyViewLight_8_en","",20252,],
["libraries.matrix.ui.components_SelectedRoom_Day_0_en","libraries.matrix.ui.components_SelectedRoom_Night_0_en",0,],
["libraries.matrix.ui.components_SelectedRoom_Day_1_en","libraries.matrix.ui.components_SelectedRoom_Night_1_en",0,],
["libraries.matrix.ui.components_SelectedRoom_Day_2_en","libraries.matrix.ui.components_SelectedRoom_Night_2_en",0,],
@@ -1151,11 +1139,11 @@ export const screenshots = [
["libraries.matrix.ui.components_SelectedUser_Day_0_en","libraries.matrix.ui.components_SelectedUser_Night_0_en",0,],
["libraries.matrix.ui.components_SelectedUsersRowList_Day_0_en","libraries.matrix.ui.components_SelectedUsersRowList_Night_0_en",0,],
["libraries.textcomposer.components_SendButton_Day_0_en","libraries.textcomposer.components_SendButton_Night_0_en",0,],
-["features.location.impl.send_SendLocationView_Day_0_en","features.location.impl.send_SendLocationView_Night_0_en",20238,],
-["features.location.impl.send_SendLocationView_Day_1_en","features.location.impl.send_SendLocationView_Night_1_en",20238,],
-["features.location.impl.send_SendLocationView_Day_2_en","features.location.impl.send_SendLocationView_Night_2_en",20238,],
-["features.location.impl.send_SendLocationView_Day_3_en","features.location.impl.send_SendLocationView_Night_3_en",20238,],
-["features.location.impl.send_SendLocationView_Day_4_en","features.location.impl.send_SendLocationView_Night_4_en",20238,],
+["features.location.impl.send_SendLocationView_Day_0_en","features.location.impl.send_SendLocationView_Night_0_en",20252,],
+["features.location.impl.send_SendLocationView_Day_1_en","features.location.impl.send_SendLocationView_Night_1_en",20252,],
+["features.location.impl.send_SendLocationView_Day_2_en","features.location.impl.send_SendLocationView_Night_2_en",20252,],
+["features.location.impl.send_SendLocationView_Day_3_en","features.location.impl.send_SendLocationView_Night_3_en",20252,],
+["features.location.impl.send_SendLocationView_Day_4_en","features.location.impl.send_SendLocationView_Night_4_en",20252,],
["libraries.matrix.ui.messages.sender_SenderName_Day_0_en","libraries.matrix.ui.messages.sender_SenderName_Night_0_en",0,],
["libraries.matrix.ui.messages.sender_SenderName_Day_1_en","libraries.matrix.ui.messages.sender_SenderName_Night_1_en",0,],
["libraries.matrix.ui.messages.sender_SenderName_Day_2_en","libraries.matrix.ui.messages.sender_SenderName_Night_2_en",0,],
@@ -1165,27 +1153,27 @@ export const screenshots = [
["libraries.matrix.ui.messages.sender_SenderName_Day_6_en","libraries.matrix.ui.messages.sender_SenderName_Night_6_en",0,],
["libraries.matrix.ui.messages.sender_SenderName_Day_7_en","libraries.matrix.ui.messages.sender_SenderName_Night_7_en",0,],
["libraries.matrix.ui.messages.sender_SenderName_Day_8_en","libraries.matrix.ui.messages.sender_SenderName_Night_8_en",0,],
-["features.verifysession.impl.incoming.ui_SessionDetailsView_Day_0_en","features.verifysession.impl.incoming.ui_SessionDetailsView_Night_0_en",20238,],
-["features.roomlist.impl.components_SetUpRecoveryKeyBanner_Day_0_en","features.roomlist.impl.components_SetUpRecoveryKeyBanner_Night_0_en",20238,],
-["features.lockscreen.impl.setup.biometric_SetupBiometricView_Day_0_en","features.lockscreen.impl.setup.biometric_SetupBiometricView_Night_0_en",20238,],
-["features.lockscreen.impl.setup.pin_SetupPinView_Day_0_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_0_en",20238,],
-["features.lockscreen.impl.setup.pin_SetupPinView_Day_1_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_1_en",20238,],
-["features.lockscreen.impl.setup.pin_SetupPinView_Day_2_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_2_en",20238,],
-["features.lockscreen.impl.setup.pin_SetupPinView_Day_3_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_3_en",20238,],
-["features.lockscreen.impl.setup.pin_SetupPinView_Day_4_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_4_en",20238,],
+["features.verifysession.impl.incoming.ui_SessionDetailsView_Day_0_en","features.verifysession.impl.incoming.ui_SessionDetailsView_Night_0_en",20252,],
+["features.roomlist.impl.components_SetUpRecoveryKeyBanner_Day_0_en","features.roomlist.impl.components_SetUpRecoveryKeyBanner_Night_0_en",20252,],
+["features.lockscreen.impl.setup.biometric_SetupBiometricView_Day_0_en","features.lockscreen.impl.setup.biometric_SetupBiometricView_Night_0_en",20252,],
+["features.lockscreen.impl.setup.pin_SetupPinView_Day_0_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_0_en",20252,],
+["features.lockscreen.impl.setup.pin_SetupPinView_Day_1_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_1_en",20252,],
+["features.lockscreen.impl.setup.pin_SetupPinView_Day_2_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_2_en",20252,],
+["features.lockscreen.impl.setup.pin_SetupPinView_Day_3_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_3_en",20252,],
+["features.lockscreen.impl.setup.pin_SetupPinView_Day_4_en","features.lockscreen.impl.setup.pin_SetupPinView_Night_4_en",20252,],
["features.share.impl_ShareView_Day_0_en","features.share.impl_ShareView_Night_0_en",0,],
["features.share.impl_ShareView_Day_1_en","features.share.impl_ShareView_Night_1_en",0,],
["features.share.impl_ShareView_Day_2_en","features.share.impl_ShareView_Night_2_en",0,],
-["features.share.impl_ShareView_Day_3_en","features.share.impl_ShareView_Night_3_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_0_en","features.location.impl.show_ShowLocationView_Night_0_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_1_en","features.location.impl.show_ShowLocationView_Night_1_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_2_en","features.location.impl.show_ShowLocationView_Night_2_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_3_en","features.location.impl.show_ShowLocationView_Night_3_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_4_en","features.location.impl.show_ShowLocationView_Night_4_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_5_en","features.location.impl.show_ShowLocationView_Night_5_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_6_en","features.location.impl.show_ShowLocationView_Night_6_en",20238,],
-["features.location.impl.show_ShowLocationView_Day_7_en","features.location.impl.show_ShowLocationView_Night_7_en",20238,],
-["features.signedout.impl_SignedOutView_Day_0_en","features.signedout.impl_SignedOutView_Night_0_en",20238,],
+["features.share.impl_ShareView_Day_3_en","features.share.impl_ShareView_Night_3_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_0_en","features.location.impl.show_ShowLocationView_Night_0_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_1_en","features.location.impl.show_ShowLocationView_Night_1_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_2_en","features.location.impl.show_ShowLocationView_Night_2_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_3_en","features.location.impl.show_ShowLocationView_Night_3_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_4_en","features.location.impl.show_ShowLocationView_Night_4_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_5_en","features.location.impl.show_ShowLocationView_Night_5_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_6_en","features.location.impl.show_ShowLocationView_Night_6_en",20252,],
+["features.location.impl.show_ShowLocationView_Day_7_en","features.location.impl.show_ShowLocationView_Night_7_en",20252,],
+["features.signedout.impl_SignedOutView_Day_0_en","features.signedout.impl_SignedOutView_Night_0_en",20252,],
["libraries.designsystem.components.dialogs_SingleSelectionDialogContent_Dialogs_en","",0,],
["libraries.designsystem.components.dialogs_SingleSelectionDialog_Day_0_en","libraries.designsystem.components.dialogs_SingleSelectionDialog_Night_0_en",0,],
["libraries.designsystem.components.list_SingleSelectionListItemCustomFormattert_Single_selection_List_item_-_custom_formatter_List_items_en","",0,],
@@ -1194,7 +1182,7 @@ export const screenshots = [
["libraries.designsystem.components.list_SingleSelectionListItemUnselectedWithSupportingText_Single_selection_List_item_-_no_selection,_supporting_text_List_items_en","",0,],
["libraries.designsystem.components.list_SingleSelectionListItem_Single_selection_List_item_-_no_selection_List_items_en","",0,],
["libraries.designsystem.theme.components_Sliders_Sliders_en","",0,],
-["features.login.impl.dialogs_SlidingSyncNotSupportedDialog_Day_0_en","features.login.impl.dialogs_SlidingSyncNotSupportedDialog_Night_0_en",20238,],
+["features.login.impl.dialogs_SlidingSyncNotSupportedDialog_Day_0_en","features.login.impl.dialogs_SlidingSyncNotSupportedDialog_Night_0_en",20252,],
["libraries.designsystem.theme.components_SnackbarWithActionAndCloseButton_Snackbar_with_action_and_close_button_Snackbars_en","",0,],
["libraries.designsystem.theme.components_SnackbarWithActionOnNewLineAndCloseButton_Snackbar_with_action_and_close_button_on_new_line_Snackbars_en","",0,],
["libraries.designsystem.theme.components_SnackbarWithActionOnNewLine_Snackbar_with_action_on_new_line_Snackbars_en","",0,],
@@ -1203,60 +1191,60 @@ export const screenshots = [
["libraries.designsystem.modifiers_SquareSizeModifierInsideSquare_en","",0,],
["libraries.designsystem.modifiers_SquareSizeModifierLargeHeight_en","",0,],
["libraries.designsystem.modifiers_SquareSizeModifierLargeWidth_en","",0,],
-["features.location.api.internal_StaticMapPlaceholder_Day_0_en","features.location.api.internal_StaticMapPlaceholder_Night_0_en",20238,],
+["features.location.api.internal_StaticMapPlaceholder_Day_0_en","features.location.api.internal_StaticMapPlaceholder_Night_0_en",20252,],
["features.location.api_StaticMapView_Day_0_en","features.location.api_StaticMapView_Night_0_en",0,],
-["features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Day_0_en","features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Night_0_en",20238,],
+["features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Day_0_en","features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Night_0_en",20252,],
["libraries.designsystem.atomic.pages_SunsetPage_Day_0_en","libraries.designsystem.atomic.pages_SunsetPage_Night_0_en",0,],
["libraries.designsystem.components.button_SuperButton_Day_0_en","libraries.designsystem.components.button_SuperButton_Night_0_en",0,],
["libraries.designsystem.theme.components_Surface_en","",0,],
["libraries.designsystem.theme.components_Switch_Toggles_en","",0,],
-["appnav.loggedin_SyncStateView_Day_0_en","appnav.loggedin_SyncStateView_Night_0_en",20238,],
+["appnav.loggedin_SyncStateView_Day_0_en","appnav.loggedin_SyncStateView_Night_0_en",20252,],
["libraries.designsystem.theme.components_TextButtonLargeLowPadding_Buttons_en","",0,],
["libraries.designsystem.theme.components_TextButtonLarge_Buttons_en","",0,],
["libraries.designsystem.theme.components_TextButtonMediumLowPadding_Buttons_en","",0,],
["libraries.designsystem.theme.components_TextButtonMedium_Buttons_en","",0,],
["libraries.designsystem.theme.components_TextButtonSmall_Buttons_en","",0,],
-["libraries.textcomposer_TextComposerAddCaption_Day_0_en","libraries.textcomposer_TextComposerAddCaption_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerCaption_Day_0_en","libraries.textcomposer_TextComposerCaption_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerEditCaption_Day_0_en","libraries.textcomposer_TextComposerEditCaption_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerEditNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerEditNotEncrypted_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerEdit_Day_0_en","libraries.textcomposer_TextComposerEdit_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerFormattingNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerFormattingNotEncrypted_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerFormatting_Day_0_en","libraries.textcomposer_TextComposerFormatting_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerLinkDialogCreateLinkWithoutText_Day_0_en","libraries.textcomposer_TextComposerLinkDialogCreateLinkWithoutText_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerLinkDialogCreateLink_Day_0_en","libraries.textcomposer_TextComposerLinkDialogCreateLink_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerLinkDialogEditLink_Day_0_en","libraries.textcomposer_TextComposerLinkDialogEditLink_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_10_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_10_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_11_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_11_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_1_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_1_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_2_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_2_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_3_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_3_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_4_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_4_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_5_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_5_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_6_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_6_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_7_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_7_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_8_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_8_en",20238,],
-["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_9_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_9_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_0_en","libraries.textcomposer_TextComposerReply_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_10_en","libraries.textcomposer_TextComposerReply_Night_10_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_11_en","libraries.textcomposer_TextComposerReply_Night_11_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_1_en","libraries.textcomposer_TextComposerReply_Night_1_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_2_en","libraries.textcomposer_TextComposerReply_Night_2_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_3_en","libraries.textcomposer_TextComposerReply_Night_3_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_4_en","libraries.textcomposer_TextComposerReply_Night_4_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_5_en","libraries.textcomposer_TextComposerReply_Night_5_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_6_en","libraries.textcomposer_TextComposerReply_Night_6_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_7_en","libraries.textcomposer_TextComposerReply_Night_7_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_8_en","libraries.textcomposer_TextComposerReply_Night_8_en",20238,],
-["libraries.textcomposer_TextComposerReply_Day_9_en","libraries.textcomposer_TextComposerReply_Night_9_en",20238,],
-["libraries.textcomposer_TextComposerSimpleNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerSimpleNotEncrypted_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerSimple_Day_0_en","libraries.textcomposer_TextComposerSimple_Night_0_en",20238,],
-["libraries.textcomposer_TextComposerVoiceNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerVoiceNotEncrypted_Night_0_en",20238,],
+["libraries.textcomposer_TextComposerAddCaption_Day_0_en","libraries.textcomposer_TextComposerAddCaption_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerCaption_Day_0_en","libraries.textcomposer_TextComposerCaption_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerEditCaption_Day_0_en","libraries.textcomposer_TextComposerEditCaption_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerEditNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerEditNotEncrypted_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerEdit_Day_0_en","libraries.textcomposer_TextComposerEdit_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerFormattingNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerFormattingNotEncrypted_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerFormatting_Day_0_en","libraries.textcomposer_TextComposerFormatting_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerLinkDialogCreateLinkWithoutText_Day_0_en","libraries.textcomposer_TextComposerLinkDialogCreateLinkWithoutText_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerLinkDialogCreateLink_Day_0_en","libraries.textcomposer_TextComposerLinkDialogCreateLink_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerLinkDialogEditLink_Day_0_en","libraries.textcomposer_TextComposerLinkDialogEditLink_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_10_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_10_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_11_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_11_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_1_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_1_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_2_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_2_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_3_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_3_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_4_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_4_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_5_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_5_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_6_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_6_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_7_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_7_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_8_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_8_en",20252,],
+["libraries.textcomposer_TextComposerReplyNotEncrypted_Day_9_en","libraries.textcomposer_TextComposerReplyNotEncrypted_Night_9_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_0_en","libraries.textcomposer_TextComposerReply_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_10_en","libraries.textcomposer_TextComposerReply_Night_10_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_11_en","libraries.textcomposer_TextComposerReply_Night_11_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_1_en","libraries.textcomposer_TextComposerReply_Night_1_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_2_en","libraries.textcomposer_TextComposerReply_Night_2_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_3_en","libraries.textcomposer_TextComposerReply_Night_3_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_4_en","libraries.textcomposer_TextComposerReply_Night_4_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_5_en","libraries.textcomposer_TextComposerReply_Night_5_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_6_en","libraries.textcomposer_TextComposerReply_Night_6_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_7_en","libraries.textcomposer_TextComposerReply_Night_7_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_8_en","libraries.textcomposer_TextComposerReply_Night_8_en",20252,],
+["libraries.textcomposer_TextComposerReply_Day_9_en","libraries.textcomposer_TextComposerReply_Night_9_en",20252,],
+["libraries.textcomposer_TextComposerSimpleNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerSimpleNotEncrypted_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerSimple_Day_0_en","libraries.textcomposer_TextComposerSimple_Night_0_en",20252,],
+["libraries.textcomposer_TextComposerVoiceNotEncrypted_Day_0_en","libraries.textcomposer_TextComposerVoiceNotEncrypted_Night_0_en",20252,],
["libraries.textcomposer_TextComposerVoice_Day_0_en","libraries.textcomposer_TextComposerVoice_Night_0_en",0,],
["libraries.designsystem.theme.components_TextDark_Text_en","",0,],
-["libraries.designsystem.components.dialogs_TextFieldDialogWithError_Day_0_en","libraries.designsystem.components.dialogs_TextFieldDialogWithError_Night_0_en",20238,],
-["libraries.designsystem.components.dialogs_TextFieldDialog_Day_0_en","libraries.designsystem.components.dialogs_TextFieldDialog_Night_0_en",20238,],
+["libraries.designsystem.components.dialogs_TextFieldDialogWithError_Day_0_en","libraries.designsystem.components.dialogs_TextFieldDialogWithError_Night_0_en",20252,],
+["libraries.designsystem.components.dialogs_TextFieldDialog_Day_0_en","libraries.designsystem.components.dialogs_TextFieldDialog_Night_0_en",20252,],
["libraries.designsystem.components.list_TextFieldListItemEmpty_Text_field_List_item_-_empty_List_items_en","",0,],
["libraries.designsystem.components.list_TextFieldListItemTextFieldValue_Text_field_List_item_-_textfieldvalue_List_items_en","",0,],
["libraries.designsystem.components.list_TextFieldListItem_Text_field_List_item_-_text_List_items_en","",0,],
@@ -1268,14 +1256,14 @@ export const screenshots = [
["libraries.mediaviewer.impl.local.txt_TextFileContentView_Day_3_en","libraries.mediaviewer.impl.local.txt_TextFileContentView_Night_3_en",0,],
["libraries.textcomposer.components_TextFormatting_Day_0_en","libraries.textcomposer.components_TextFormatting_Night_0_en",0,],
["libraries.designsystem.theme.components_TextLight_Text_en","",0,],
-["libraries.designsystem.theme.components.previews_TimePickerHorizontal_DateTime_pickers_en","",20238,],
-["libraries.designsystem.theme.components.previews_TimePickerVerticalDark_DateTime_pickers_en","",20238,],
-["libraries.designsystem.theme.components.previews_TimePickerVerticalLight_DateTime_pickers_en","",20238,],
+["libraries.designsystem.theme.components.previews_TimePickerHorizontal_DateTime_pickers_en","",20252,],
+["libraries.designsystem.theme.components.previews_TimePickerVerticalDark_DateTime_pickers_en","",20252,],
+["libraries.designsystem.theme.components.previews_TimePickerVerticalLight_DateTime_pickers_en","",20252,],
["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_0_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_0_en",0,],
["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_1_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_1_en",0,],
["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_2_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_2_en",0,],
-["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_3_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_3_en",20238,],
-["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_4_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_4_en",20238,],
+["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_3_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_3_en",20252,],
+["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_4_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_4_en",20252,],
["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_5_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_5_en",0,],
["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_6_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_6_en",0,],
["features.messages.impl.timeline.components_TimelineEventTimestampView_Day_7_en","features.messages.impl.timeline.components_TimelineEventTimestampView_Night_7_en",0,],
@@ -1285,18 +1273,18 @@ export const screenshots = [
["features.messages.impl.timeline.components.event_TimelineItemAudioView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemAudioView_Night_2_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemAudioView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemAudioView_Night_3_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemAudioView_Day_4_en","features.messages.impl.timeline.components.event_TimelineItemAudioView_Night_4_en",0,],
-["features.messages.impl.timeline.components_TimelineItemCallNotifyView_Day_0_en","features.messages.impl.timeline.components_TimelineItemCallNotifyView_Night_0_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemCallNotifyView_Day_0_en","features.messages.impl.timeline.components_TimelineItemCallNotifyView_Night_0_en",20252,],
["features.messages.impl.timeline.components.virtual_TimelineItemDaySeparatorView_Day_0_en","features.messages.impl.timeline.components.virtual_TimelineItemDaySeparatorView_Night_0_en",0,],
["features.messages.impl.timeline.components.virtual_TimelineItemDaySeparatorView_Day_1_en","features.messages.impl.timeline.components.virtual_TimelineItemDaySeparatorView_Night_1_en",0,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_0_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_1_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_2_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_3_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_4_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_4_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_5_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_5_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_6_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_6_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_7_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_7_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_8_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_8_en",20238,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_0_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_1_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_2_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_3_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_4_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_4_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_5_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_5_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_6_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_6_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_7_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_7_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Day_8_en","features.messages.impl.timeline.components.event_TimelineItemEncryptedView_Night_8_en",20252,],
["features.messages.impl.timeline.components_TimelineItemEventRowDisambiguated_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowDisambiguated_Night_0_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowForDirectRoom_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowForDirectRoom_Night_0_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowLongSenderName_en","",0,],
@@ -1304,18 +1292,18 @@ export const screenshots = [
["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_0_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_1_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_1_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_2_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_2_en",0,],
-["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_3_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_3_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_4_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_4_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_3_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_3_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_4_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_4_en",20252,],
["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_5_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_5_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_6_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_6_en",0,],
-["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_7_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_7_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemEventRowUtd_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowUtd_Night_0_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemEventRowWithManyReactions_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithManyReactions_Night_0_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Day_7_en","features.messages.impl.timeline.components_TimelineItemEventRowTimestamp_Night_7_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemEventRowUtd_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowUtd_Night_0_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemEventRowWithManyReactions_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithManyReactions_Night_0_en",20252,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithRR_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithRR_Night_0_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithRR_Day_1_en","features.messages.impl.timeline.components_TimelineItemEventRowWithRR_Night_1_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithRR_Day_2_en","features.messages.impl.timeline.components_TimelineItemEventRowWithRR_Night_2_en",0,],
-["features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Night_0_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_1_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Night_1_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Night_0_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Day_1_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReplyInformative_Night_1_en",20252,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReplyOther_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReplyOther_Night_0_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReplyOther_Day_1_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReplyOther_Night_1_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_0_en",0,],
@@ -1324,40 +1312,40 @@ export const screenshots = [
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_1_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_1_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_2_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_2_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_3_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_3_en",0,],
-["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_4_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_4_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_4_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_4_en",20252,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_5_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_5_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_6_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_6_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_7_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_7_en",0,],
-["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_8_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_8_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_8_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_8_en",20252,],
["features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Day_9_en","features.messages.impl.timeline.components_TimelineItemEventRowWithReply_Night_9_en",0,],
["features.messages.impl.timeline.components_TimelineItemEventRow_Day_0_en","features.messages.impl.timeline.components_TimelineItemEventRow_Night_0_en",0,],
-["features.messages.impl.timeline.components_TimelineItemEventTimestampBelow_en","",20238,],
+["features.messages.impl.timeline.components_TimelineItemEventTimestampBelow_en","",20252,],
["features.messages.impl.timeline.components.event_TimelineItemFileView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemFileView_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemFileView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemFileView_Night_1_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemFileView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemFileView_Night_2_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemFileView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemFileView_Night_3_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemFileView_Day_4_en","features.messages.impl.timeline.components.event_TimelineItemFileView_Night_4_en",0,],
-["features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentCollapse_Day_0_en","features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentCollapse_Night_0_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentExpanded_Day_0_en","features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentExpanded_Night_0_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemImageViewHideMediaContent_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemImageViewHideMediaContent_Night_0_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentCollapse_Day_0_en","features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentCollapse_Night_0_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentExpanded_Day_0_en","features.messages.impl.timeline.components_TimelineItemGroupedEventsRowContentExpanded_Night_0_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemImageViewHideMediaContent_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemImageViewHideMediaContent_Night_0_en",20252,],
["features.messages.impl.timeline.components.event_TimelineItemImageView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemImageView_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemImageView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemImageView_Night_1_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemImageView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemImageView_Night_2_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemImageView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemImageView_Night_3_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemInformativeView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemInformativeView_Night_0_en",0,],
-["features.messages.impl.timeline.components.event_TimelineItemLegacyCallInviteView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemLegacyCallInviteView_Night_0_en",20238,],
+["features.messages.impl.timeline.components.event_TimelineItemLegacyCallInviteView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemLegacyCallInviteView_Night_0_en",20252,],
["features.messages.impl.timeline.components.event_TimelineItemLocationView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemLocationView_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemLocationView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemLocationView_Night_1_en",0,],
-["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_0_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_1_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_2_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_3_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemReactionsLayout_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsLayout_Night_0_en",20238,],
+["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_0_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_1_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_2_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemPollView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemPollView_Night_3_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemReactionsLayout_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsLayout_Night_0_en",20252,],
["features.messages.impl.timeline.components_TimelineItemReactionsViewFew_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsViewFew_Night_0_en",0,],
-["features.messages.impl.timeline.components_TimelineItemReactionsViewIncoming_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsViewIncoming_Night_0_en",20238,],
-["features.messages.impl.timeline.components_TimelineItemReactionsViewOutgoing_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsViewOutgoing_Night_0_en",20238,],
+["features.messages.impl.timeline.components_TimelineItemReactionsViewIncoming_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsViewIncoming_Night_0_en",20252,],
+["features.messages.impl.timeline.components_TimelineItemReactionsViewOutgoing_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsViewOutgoing_Night_0_en",20252,],
["features.messages.impl.timeline.components_TimelineItemReactionsView_Day_0_en","features.messages.impl.timeline.components_TimelineItemReactionsView_Night_0_en",0,],
-["features.messages.impl.timeline.components.virtual_TimelineItemReadMarkerView_Day_0_en","features.messages.impl.timeline.components.virtual_TimelineItemReadMarkerView_Night_0_en",20238,],
+["features.messages.impl.timeline.components.virtual_TimelineItemReadMarkerView_Day_0_en","features.messages.impl.timeline.components.virtual_TimelineItemReadMarkerView_Night_0_en",20252,],
["features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Day_0_en","features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Night_0_en",0,],
["features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Day_1_en","features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Night_1_en",0,],
["features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Day_2_en","features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Night_2_en",0,],
@@ -1366,8 +1354,8 @@ export const screenshots = [
["features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Day_5_en","features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Night_5_en",0,],
["features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Day_6_en","features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Night_6_en",0,],
["features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Day_7_en","features.messages.impl.timeline.components.receipt_TimelineItemReadReceiptView_Night_7_en",0,],
-["features.messages.impl.timeline.components.event_TimelineItemRedactedView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemRedactedView_Night_0_en",20238,],
-["features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Day_0_en","features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Night_0_en",20238,],
+["features.messages.impl.timeline.components.event_TimelineItemRedactedView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemRedactedView_Night_0_en",20252,],
+["features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Day_0_en","features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Night_0_en",20252,],
["features.messages.impl.timeline.components_TimelineItemStateEventRow_Day_0_en","features.messages.impl.timeline.components_TimelineItemStateEventRow_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemStateView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemStateView_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemStickerView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemStickerView_Night_0_en",0,],
@@ -1382,8 +1370,8 @@ export const screenshots = [
["features.messages.impl.timeline.components.event_TimelineItemTextView_Day_3_en","features.messages.impl.timeline.components.event_TimelineItemTextView_Night_3_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemTextView_Day_4_en","features.messages.impl.timeline.components.event_TimelineItemTextView_Night_4_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemTextView_Day_5_en","features.messages.impl.timeline.components.event_TimelineItemTextView_Night_5_en",0,],
-["features.messages.impl.timeline.components.event_TimelineItemUnknownView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemUnknownView_Night_0_en",20238,],
-["features.messages.impl.timeline.components.event_TimelineItemVideoViewHideMediaContent_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemVideoViewHideMediaContent_Night_0_en",20238,],
+["features.messages.impl.timeline.components.event_TimelineItemUnknownView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemUnknownView_Night_0_en",20252,],
+["features.messages.impl.timeline.components.event_TimelineItemVideoViewHideMediaContent_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemVideoViewHideMediaContent_Night_0_en",20252,],
["features.messages.impl.timeline.components.event_TimelineItemVideoView_Day_0_en","features.messages.impl.timeline.components.event_TimelineItemVideoView_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemVideoView_Day_1_en","features.messages.impl.timeline.components.event_TimelineItemVideoView_Night_1_en",0,],
["features.messages.impl.timeline.components.event_TimelineItemVideoView_Day_2_en","features.messages.impl.timeline.components.event_TimelineItemVideoView_Night_2_en",0,],
@@ -1406,73 +1394,73 @@ export const screenshots = [
["features.messages.impl.timeline.components.event_TimelineItemVoiceView_Day_9_en","features.messages.impl.timeline.components.event_TimelineItemVoiceView_Night_9_en",0,],
["features.messages.impl.timeline.components.virtual_TimelineLoadingMoreIndicator_Day_0_en","features.messages.impl.timeline.components.virtual_TimelineLoadingMoreIndicator_Night_0_en",0,],
["features.messages.impl.timeline.components.event_TimelineVideoWithCaptionRow_Day_0_en","features.messages.impl.timeline.components.event_TimelineVideoWithCaptionRow_Night_0_en",0,],
-["features.messages.impl.timeline_TimelineViewMessageShield_Day_0_en","features.messages.impl.timeline_TimelineViewMessageShield_Night_0_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_0_en","features.messages.impl.timeline_TimelineView_Night_0_en",20238,],
+["features.messages.impl.timeline_TimelineViewMessageShield_Day_0_en","features.messages.impl.timeline_TimelineViewMessageShield_Night_0_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_0_en","features.messages.impl.timeline_TimelineView_Night_0_en",20252,],
["features.messages.impl.timeline_TimelineView_Day_10_en","features.messages.impl.timeline_TimelineView_Night_10_en",0,],
-["features.messages.impl.timeline_TimelineView_Day_11_en","features.messages.impl.timeline_TimelineView_Night_11_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_12_en","features.messages.impl.timeline_TimelineView_Night_12_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_13_en","features.messages.impl.timeline_TimelineView_Night_13_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_14_en","features.messages.impl.timeline_TimelineView_Night_14_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_15_en","features.messages.impl.timeline_TimelineView_Night_15_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_16_en","features.messages.impl.timeline_TimelineView_Night_16_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_17_en","features.messages.impl.timeline_TimelineView_Night_17_en",20238,],
-["features.messages.impl.timeline_TimelineView_Day_1_en","features.messages.impl.timeline_TimelineView_Night_1_en",20238,],
+["features.messages.impl.timeline_TimelineView_Day_11_en","features.messages.impl.timeline_TimelineView_Night_11_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_12_en","features.messages.impl.timeline_TimelineView_Night_12_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_13_en","features.messages.impl.timeline_TimelineView_Night_13_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_14_en","features.messages.impl.timeline_TimelineView_Night_14_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_15_en","features.messages.impl.timeline_TimelineView_Night_15_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_16_en","features.messages.impl.timeline_TimelineView_Night_16_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_17_en","features.messages.impl.timeline_TimelineView_Night_17_en",20252,],
+["features.messages.impl.timeline_TimelineView_Day_1_en","features.messages.impl.timeline_TimelineView_Night_1_en",20252,],
["features.messages.impl.timeline_TimelineView_Day_2_en","features.messages.impl.timeline_TimelineView_Night_2_en",0,],
["features.messages.impl.timeline_TimelineView_Day_3_en","features.messages.impl.timeline_TimelineView_Night_3_en",0,],
-["features.messages.impl.timeline_TimelineView_Day_4_en","features.messages.impl.timeline_TimelineView_Night_4_en",20238,],
+["features.messages.impl.timeline_TimelineView_Day_4_en","features.messages.impl.timeline_TimelineView_Night_4_en",20252,],
["features.messages.impl.timeline_TimelineView_Day_5_en","features.messages.impl.timeline_TimelineView_Night_5_en",0,],
-["features.messages.impl.timeline_TimelineView_Day_6_en","features.messages.impl.timeline_TimelineView_Night_6_en",20238,],
+["features.messages.impl.timeline_TimelineView_Day_6_en","features.messages.impl.timeline_TimelineView_Night_6_en",20252,],
["features.messages.impl.timeline_TimelineView_Day_7_en","features.messages.impl.timeline_TimelineView_Night_7_en",0,],
-["features.messages.impl.timeline_TimelineView_Day_8_en","features.messages.impl.timeline_TimelineView_Night_8_en",20238,],
+["features.messages.impl.timeline_TimelineView_Day_8_en","features.messages.impl.timeline_TimelineView_Night_8_en",20252,],
["features.messages.impl.timeline_TimelineView_Day_9_en","features.messages.impl.timeline_TimelineView_Night_9_en",0,],
["libraries.designsystem.theme.components_TopAppBar_App_Bars_en","",0,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_0_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_0_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_1_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_1_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_2_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_2_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_3_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_3_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_4_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_4_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_5_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_5_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_6_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_6_en",20238,],
-["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_7_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_7_en",20238,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_0_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_0_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_1_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_1_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_2_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_2_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_3_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_3_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_4_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_4_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_5_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_5_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_6_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_6_en",20252,],
+["libraries.troubleshoot.impl_TroubleshootNotificationsView_Day_7_en","libraries.troubleshoot.impl_TroubleshootNotificationsView_Night_7_en",20252,],
["features.messages.impl.typing_TypingNotificationView_Day_0_en","features.messages.impl.typing_TypingNotificationView_Night_0_en",0,],
-["features.messages.impl.typing_TypingNotificationView_Day_1_en","features.messages.impl.typing_TypingNotificationView_Night_1_en",20238,],
-["features.messages.impl.typing_TypingNotificationView_Day_2_en","features.messages.impl.typing_TypingNotificationView_Night_2_en",20238,],
-["features.messages.impl.typing_TypingNotificationView_Day_3_en","features.messages.impl.typing_TypingNotificationView_Night_3_en",20238,],
-["features.messages.impl.typing_TypingNotificationView_Day_4_en","features.messages.impl.typing_TypingNotificationView_Night_4_en",20238,],
-["features.messages.impl.typing_TypingNotificationView_Day_5_en","features.messages.impl.typing_TypingNotificationView_Night_5_en",20238,],
-["features.messages.impl.typing_TypingNotificationView_Day_6_en","features.messages.impl.typing_TypingNotificationView_Night_6_en",20238,],
+["features.messages.impl.typing_TypingNotificationView_Day_1_en","features.messages.impl.typing_TypingNotificationView_Night_1_en",20252,],
+["features.messages.impl.typing_TypingNotificationView_Day_2_en","features.messages.impl.typing_TypingNotificationView_Night_2_en",20252,],
+["features.messages.impl.typing_TypingNotificationView_Day_3_en","features.messages.impl.typing_TypingNotificationView_Night_3_en",20252,],
+["features.messages.impl.typing_TypingNotificationView_Day_4_en","features.messages.impl.typing_TypingNotificationView_Night_4_en",20252,],
+["features.messages.impl.typing_TypingNotificationView_Day_5_en","features.messages.impl.typing_TypingNotificationView_Night_5_en",20252,],
+["features.messages.impl.typing_TypingNotificationView_Day_6_en","features.messages.impl.typing_TypingNotificationView_Night_6_en",20252,],
["features.messages.impl.typing_TypingNotificationView_Day_7_en","features.messages.impl.typing_TypingNotificationView_Night_7_en",0,],
["features.messages.impl.typing_TypingNotificationView_Day_8_en","features.messages.impl.typing_TypingNotificationView_Night_8_en",0,],
["libraries.designsystem.atomic.atoms_UnreadIndicatorAtom_Day_0_en","libraries.designsystem.atomic.atoms_UnreadIndicatorAtom_Night_0_en",0,],
-["libraries.matrix.ui.components_UnresolvedUserRow_en","",20238,],
+["libraries.matrix.ui.components_UnresolvedUserRow_en","",20252,],
["libraries.matrix.ui.components_UnsavedAvatar_Day_0_en","libraries.matrix.ui.components_UnsavedAvatar_Night_0_en",0,],
["libraries.designsystem.components.avatar_UserAvatarColors_Day_0_en","libraries.designsystem.components.avatar_UserAvatarColors_Night_0_en",0,],
-["features.roomdetails.impl.notificationsettings_UserDefinedRoomNotificationSettingsView_Day_0_en","features.roomdetails.impl.notificationsettings_UserDefinedRoomNotificationSettingsView_Night_0_en",20238,],
-["features.createroom.impl.components_UserListView_Day_0_en","features.createroom.impl.components_UserListView_Night_0_en",20238,],
-["features.createroom.impl.components_UserListView_Day_1_en","features.createroom.impl.components_UserListView_Night_1_en",20238,],
-["features.createroom.impl.components_UserListView_Day_2_en","features.createroom.impl.components_UserListView_Night_2_en",20238,],
+["features.roomdetails.impl.notificationsettings_UserDefinedRoomNotificationSettingsView_Day_0_en","features.roomdetails.impl.notificationsettings_UserDefinedRoomNotificationSettingsView_Night_0_en",20252,],
+["features.createroom.impl.components_UserListView_Day_0_en","features.createroom.impl.components_UserListView_Night_0_en",20252,],
+["features.createroom.impl.components_UserListView_Day_1_en","features.createroom.impl.components_UserListView_Night_1_en",20252,],
+["features.createroom.impl.components_UserListView_Day_2_en","features.createroom.impl.components_UserListView_Night_2_en",20252,],
["features.createroom.impl.components_UserListView_Day_3_en","features.createroom.impl.components_UserListView_Night_3_en",0,],
["features.createroom.impl.components_UserListView_Day_4_en","features.createroom.impl.components_UserListView_Night_4_en",0,],
["features.createroom.impl.components_UserListView_Day_5_en","features.createroom.impl.components_UserListView_Night_5_en",0,],
["features.createroom.impl.components_UserListView_Day_6_en","features.createroom.impl.components_UserListView_Night_6_en",0,],
-["features.createroom.impl.components_UserListView_Day_7_en","features.createroom.impl.components_UserListView_Night_7_en",20238,],
+["features.createroom.impl.components_UserListView_Day_7_en","features.createroom.impl.components_UserListView_Night_7_en",20252,],
["features.createroom.impl.components_UserListView_Day_8_en","features.createroom.impl.components_UserListView_Night_8_en",0,],
-["features.createroom.impl.components_UserListView_Day_9_en","features.createroom.impl.components_UserListView_Night_9_en",20238,],
+["features.createroom.impl.components_UserListView_Day_9_en","features.createroom.impl.components_UserListView_Night_9_en",20252,],
["features.preferences.impl.user_UserPreferences_Day_0_en","features.preferences.impl.user_UserPreferences_Night_0_en",0,],
["features.preferences.impl.user_UserPreferences_Day_1_en","features.preferences.impl.user_UserPreferences_Night_1_en",0,],
["features.preferences.impl.user_UserPreferences_Day_2_en","features.preferences.impl.user_UserPreferences_Night_2_en",0,],
-["features.userprofile.shared_UserProfileHeaderSectionWithVerificationViolation_Day_0_en","features.userprofile.shared_UserProfileHeaderSectionWithVerificationViolation_Night_0_en",20238,],
-["features.userprofile.shared_UserProfileHeaderSection_Day_0_en","features.userprofile.shared_UserProfileHeaderSection_Night_0_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_0_en","features.userprofile.shared_UserProfileView_Night_0_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_1_en","features.userprofile.shared_UserProfileView_Night_1_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_2_en","features.userprofile.shared_UserProfileView_Night_2_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_3_en","features.userprofile.shared_UserProfileView_Night_3_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_4_en","features.userprofile.shared_UserProfileView_Night_4_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_5_en","features.userprofile.shared_UserProfileView_Night_5_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_6_en","features.userprofile.shared_UserProfileView_Night_6_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_7_en","features.userprofile.shared_UserProfileView_Night_7_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_8_en","features.userprofile.shared_UserProfileView_Night_8_en",20238,],
-["features.userprofile.shared_UserProfileView_Day_9_en","features.userprofile.shared_UserProfileView_Night_9_en",20238,],
+["features.userprofile.shared_UserProfileHeaderSectionWithVerificationViolation_Day_0_en","features.userprofile.shared_UserProfileHeaderSectionWithVerificationViolation_Night_0_en",20252,],
+["features.userprofile.shared_UserProfileHeaderSection_Day_0_en","features.userprofile.shared_UserProfileHeaderSection_Night_0_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_0_en","features.userprofile.shared_UserProfileView_Night_0_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_1_en","features.userprofile.shared_UserProfileView_Night_1_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_2_en","features.userprofile.shared_UserProfileView_Night_2_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_3_en","features.userprofile.shared_UserProfileView_Night_3_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_4_en","features.userprofile.shared_UserProfileView_Night_4_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_5_en","features.userprofile.shared_UserProfileView_Night_5_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_6_en","features.userprofile.shared_UserProfileView_Night_6_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_7_en","features.userprofile.shared_UserProfileView_Night_7_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_8_en","features.userprofile.shared_UserProfileView_Night_8_en",20252,],
+["features.userprofile.shared_UserProfileView_Day_9_en","features.userprofile.shared_UserProfileView_Night_9_en",20252,],
["features.verifysession.impl.ui_VerificationUserProfileContent_Day_0_en","features.verifysession.impl.ui_VerificationUserProfileContent_Night_0_en",0,],
["libraries.designsystem.ruler_VerticalRuler_Day_0_en","libraries.designsystem.ruler_VerticalRuler_Night_0_en",0,],
["libraries.mediaviewer.impl.gallery.ui_VideoItemView_Day_0_en","libraries.mediaviewer.impl.gallery.ui_VideoItemView_Night_0_en",0,],
@@ -1480,7 +1468,7 @@ export const screenshots = [
["features.viewfolder.impl.file_ViewFileView_Day_0_en","features.viewfolder.impl.file_ViewFileView_Night_0_en",0,],
["features.viewfolder.impl.file_ViewFileView_Day_1_en","features.viewfolder.impl.file_ViewFileView_Night_1_en",0,],
["features.viewfolder.impl.file_ViewFileView_Day_2_en","features.viewfolder.impl.file_ViewFileView_Night_2_en",0,],
-["features.viewfolder.impl.file_ViewFileView_Day_3_en","features.viewfolder.impl.file_ViewFileView_Night_3_en",20238,],
+["features.viewfolder.impl.file_ViewFileView_Day_3_en","features.viewfolder.impl.file_ViewFileView_Night_3_en",20252,],
["features.viewfolder.impl.file_ViewFileView_Day_4_en","features.viewfolder.impl.file_ViewFileView_Night_4_en",0,],
["features.viewfolder.impl.file_ViewFileView_Day_5_en","features.viewfolder.impl.file_ViewFileView_Night_5_en",0,],
["features.viewfolder.impl.folder_ViewFolderView_Day_0_en","features.viewfolder.impl.folder_ViewFolderView_Night_0_en",0,],
@@ -1499,6 +1487,6 @@ export const screenshots = [
["libraries.textcomposer.components_VoiceMessageRecording_Day_0_en","libraries.textcomposer.components_VoiceMessageRecording_Night_0_en",0,],
["libraries.textcomposer.components_VoiceMessage_Day_0_en","libraries.textcomposer.components_VoiceMessage_Night_0_en",0,],
["libraries.designsystem.components.media_WaveformPlaybackView_Day_0_en","libraries.designsystem.components.media_WaveformPlaybackView_Night_0_en",0,],
-["features.ftue.impl.welcome_WelcomeView_Day_0_en","features.ftue.impl.welcome_WelcomeView_Night_0_en",20238,],
+["features.ftue.impl.welcome_WelcomeView_Day_0_en","features.ftue.impl.welcome_WelcomeView_Night_0_en",20252,],
["libraries.designsystem.ruler_WithRulers_Day_0_en","libraries.designsystem.ruler_WithRulers_Night_0_en",0,],
];
diff --git a/services/toolbox/test/build.gradle.kts b/services/toolbox/test/build.gradle.kts
index 9f3f9bfee3..8d2f2b8a2d 100644
--- a/services/toolbox/test/build.gradle.kts
+++ b/services/toolbox/test/build.gradle.kts
@@ -14,4 +14,5 @@ android {
dependencies {
api(projects.services.toolbox.api)
+ implementation(projects.tests.testutils)
}
diff --git a/services/toolbox/test/src/main/kotlin/io/element/android/services/toolbox/test/intent/FakeExternalIntentLauncher.kt b/services/toolbox/test/src/main/kotlin/io/element/android/services/toolbox/test/intent/FakeExternalIntentLauncher.kt
index 721a6ebe1b..a8e9589b6d 100644
--- a/services/toolbox/test/src/main/kotlin/io/element/android/services/toolbox/test/intent/FakeExternalIntentLauncher.kt
+++ b/services/toolbox/test/src/main/kotlin/io/element/android/services/toolbox/test/intent/FakeExternalIntentLauncher.kt
@@ -9,9 +9,10 @@ package io.element.android.services.toolbox.test.intent
import android.content.Intent
import io.element.android.services.toolbox.api.intent.ExternalIntentLauncher
+import io.element.android.tests.testutils.lambda.lambdaError
class FakeExternalIntentLauncher(
- var launchLambda: (Intent) -> Unit = {},
+ var launchLambda: (Intent) -> Unit = { lambdaError() },
) : ExternalIntentLauncher {
override fun launch(intent: Intent) {
launchLambda(intent)
diff --git a/tests/testutils/src/main/kotlin/io/element/android/tests/testutils/SemanticsNodeInteractionsProviderExtensions.kt b/tests/testutils/src/main/kotlin/io/element/android/tests/testutils/SemanticsNodeInteractionsProviderExtensions.kt
index 440af51676..55371a960d 100644
--- a/tests/testutils/src/main/kotlin/io/element/android/tests/testutils/SemanticsNodeInteractionsProviderExtensions.kt
+++ b/tests/testutils/src/main/kotlin/io/element/android/tests/testutils/SemanticsNodeInteractionsProviderExtensions.kt
@@ -16,6 +16,7 @@ import androidx.compose.ui.test.hasTestTag
import androidx.compose.ui.test.hasText
import androidx.compose.ui.test.junit4.AndroidComposeTestRule
import androidx.compose.ui.test.onFirst
+import androidx.compose.ui.test.onNodeWithText
import androidx.compose.ui.test.performClick
import io.element.android.libraries.ui.strings.CommonStrings
import org.junit.rules.TestRule
@@ -54,3 +55,8 @@ fun AndroidComposeTestRule.pressBackKey() {
fun SemanticsNodeInteractionsProvider.pressTag(tag: String) {
onNode(hasTestTag(tag)).performClick()
}
+
+fun AndroidComposeTestRule.assertNoNodeWithText(@StringRes res: Int) {
+ val text = activity.getString(res)
+ onNodeWithText(text).assertDoesNotExist()
+}
diff --git a/tests/uitests/src/test/snapshots/images/features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_en.png b/tests/uitests/src/test/snapshots/images/features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_en.png
new file mode 100644
index 0000000000..d7e0c73390
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.call.impl.ui_InvalidAudioDeviceDialog_Day_0_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:3c2a698cd7518bc96296bcd4f9b0b51b7a09094a178bca84b853efc03b58c228
+size 25365
diff --git a/tests/uitests/src/test/snapshots/images/features.call.impl.ui_InvalidAudioDeviceDialog_Night_0_en.png b/tests/uitests/src/test/snapshots/images/features.call.impl.ui_InvalidAudioDeviceDialog_Night_0_en.png
new file mode 100644
index 0000000000..d5d6f55e1d
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.call.impl.ui_InvalidAudioDeviceDialog_Night_0_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:3302dd631da6a38d569425e4a827051c00d20ab5755c7787739bf7ff37441dfd
+size 23622
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Day_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Day_0_en.png
index 052885e97e..8b6135c4fa 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Day_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Day_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:19f6f6dcdf49e9ffd2fbb0ea81c3fe0374faf79cecccc812ea1e1d8c05578671
-size 22344
+oid sha256:8823f1cca4a240779ade39486854332689d114efe2d2213a9ab0720113c7f04b
+size 22353
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Night_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Night_0_en.png
index 1e43118d49..226dc55779 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Night_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.messagecomposer.suggestions_SuggestionsPickerView_Night_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:12266ee1fc3477aec0f47e731294ccd2f93ecf4a3a1fada6cf4cb8ba6f7430ac
-size 22661
+oid sha256:49916050cd93d9b4aa4a90aa3ecd19bec6095e8b7cb472a3543867c0ce6f9ffa
+size 22783
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Day_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Day_0_en.png
index 16e9f5cc43..829cf58db8 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Day_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Day_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:138be910fa88b2e59882b909f5d83824503d88676d23d327c1f4948121cbebe0
-size 14297
+oid sha256:f4494a2cf13d267a1051ea3fbe4476d2354b8c7827d1b93aabacf5bbe063dc3a
+size 49269
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Night_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Night_0_en.png
index 5808ed69cf..8e03a6e18d 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Night_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components.virtual_TimelineItemRoomBeginningView_Night_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:4b9ce5853af7f03ac91da6bb318bd4f033936279d211e87efff4ef6ec8794f51
-size 13988
+oid sha256:affff20aa09000132ffa8535a81d888263e9d530144c8b96e15d25c1873254c9
+size 54426
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_0_en.png
index f498c22ffe..a76b26e9aa 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:74bf9b7af113c4299c1d9807ac017117b3967e2c6edb0c3f84dfb2e8aa5efc70
-size 5543
+oid sha256:b491cce2773778b379853898e495301778fc97bc31e045360b39a2b09f29f844
+size 5789
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_10_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_10_en.png
deleted file mode 100644
index f60f6ad5b1..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_10_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:643d87a9c1f2befdb5407a88a7590fa8598807db995d10c8b9c6460910a61b2e
-size 5594
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_11_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_11_en.png
deleted file mode 100644
index 0b38c37c2a..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_11_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:27e390a8045e54f5042bf038bba1b24df23e160abd662519d16483323d638ac6
-size 5411
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_12_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_12_en.png
deleted file mode 100644
index 1563e58f86..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_12_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:9fc37060281ce74491304a8b64e10e1664a29c1fb0d590ec80ac2e8336610198
-size 5780
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_13_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_13_en.png
deleted file mode 100644
index 183b92a6cb..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_13_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:f179e72eede44c7a1add39698519b07649bb978dd63170405c57fed261bfa871
-size 5618
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_14_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_14_en.png
deleted file mode 100644
index 41780cbc77..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_14_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:d068727866699683382b9b2344d685246568dd4a1fa27a91bf73c3b7a4ef76af
-size 5773
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_15_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_15_en.png
deleted file mode 100644
index 89f4be732c..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_15_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:d823b36a5eeb8e888a5351633d47f8fcc70713021d224d37f302711c189398ea
-size 5605
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_1_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_1_en.png
index 5bc122015d..65909d6d48 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_1_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_1_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:7e65e7d7fa6a9b781e67c28d160278988241e73107f721bbfb3298dcb317d167
-size 5377
+oid sha256:675122178c926902a7c6b92ca15b7652a3099de144b9f990c7ef8a495e41b148
+size 5833
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_2_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_2_en.png
index 0ad5b2ae4f..67df9853a1 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_2_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_2_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:a6ffa4545e93d9ff24a32c94b4da23029b7316537c7328f4347f2a3de257c9df
-size 5504
+oid sha256:6b5981fda0fd6d7016f77c4fe9955690f2d6dab5825f320f1795d3fd460ffa63
+size 6076
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_3_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_3_en.png
index 748bf14d95..5b61d53e6d 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_3_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_3_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:69eb45afa5b3b408c4ad0a713f87df56e6574e23538ed33694f352502b8401c8
-size 5333
+oid sha256:a9b027e16bf586857cad161205b7ca0445932d00c1f6b630dc50126394233153
+size 6192
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_4_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_4_en.png
index 1685d89c08..d5ef562f0e 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_4_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_4_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:a3ea0f61fd842467be5ca9804265c29243b329ed7852a55dc7447dc3140e6658
-size 5807
+oid sha256:3fe1e1da27262a08ed7c59d7c0951e72836b26ec554688f0426ac9a38f436d0f
+size 5846
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_5_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_5_en.png
index cbee49d65e..ef512ba6ed 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_5_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_5_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:8e37bc6f4a19e25c238f3fb6c6e919a41a1da3fde930b951b7a08b15b7ab97e1
-size 5666
+oid sha256:8022a0fc45eca8d244a4aa2ddaa25e50c1ff03ad380f39c4c4693b8cfc978148
+size 5902
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_6_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_6_en.png
index 97a25a3169..e20b582e84 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_6_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_6_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:b6b7b54481a82deeedbdb66ce90191a4894fe25244cc3c70fba571fac74544e5
-size 5899
+oid sha256:2e1a2505f900b21e0396bee6733b5ce9170fddd9c15038f121abbbe30ae95281
+size 6076
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_7_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_7_en.png
index ca29f20049..f20043707f 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_7_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_7_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:cfd4525483b1be593b9ad6fb098ff7597c7300e6c5b50e2b8316941c4cdba405
-size 5704
+oid sha256:cb5c7bdb55eaa8b5cd532b3b1b60158a18c4f13f559b1b6040807696343b8775
+size 6096
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_8_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_8_en.png
deleted file mode 100644
index 43a7044112..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_8_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:7450b6d88936c9ea016d6bc39dd9bcd6efb61e28a3282d2f7808a178e8ecd355
-size 5545
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_9_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_9_en.png
deleted file mode 100644
index b3d1b807ef..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Day_9_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:d29074ffc73aa10e27b4cb89b65ea736d50952e060bcf312a04b417e7f253e9a
-size 5387
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_0_en.png
index c8aee9eda7..c58b83d0ef 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:96f0584206f23483d1ad6831dbfaece6f7531edcc76bcdba11d7cd1aa57fca4e
-size 5659
+oid sha256:c98e2c35da18aaa8f5fce58515e86f171cc4df8787d34ae3b1a9567d49c4137e
+size 5924
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_10_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_10_en.png
deleted file mode 100644
index b88bbac098..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_10_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:00f73509f6efad9f6f2ce54f3a9706b9ccb2720e9119a0c9ba7abf8eea3856f8
-size 5603
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_11_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_11_en.png
deleted file mode 100644
index efee6943a9..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_11_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:d1d1fc4bac417bcd906c813e3d0442b2d38593c9e9fdaf7d93aa6dc20ecb3c44
-size 5417
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_12_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_12_en.png
deleted file mode 100644
index a695072c6f..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_12_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:e7045956cb362717e97cb10573cccf7774c872664c9b2178e6e73195eaa9c76a
-size 5980
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_13_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_13_en.png
deleted file mode 100644
index f80ceab33b..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_13_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:8e2728835c30759efc96ba5a7d93af9b692fe059ec2f09b879f4c045ab6b6a5e
-size 5804
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_14_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_14_en.png
deleted file mode 100644
index dfb8a91ae2..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_14_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:2edea761c0bbd7f9d0d68f39eff5d69cf5dc9599a71c27ba2c5730d862c99692
-size 5801
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_15_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_15_en.png
deleted file mode 100644
index c8963479ec..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_15_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:a35938676790d0d69ea6688f3e5d1c0440684dd69ea2e97162e60fab8c250c26
-size 5636
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_1_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_1_en.png
index 28315f21c1..b75dd051f0 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_1_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_1_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:22d7f35612dd607d238774b3dd23ff07f8a22b882b15386d6ebed94eb6db642d
-size 5483
+oid sha256:d8ec24f4135061fbf08aebd29b4b7d8bf3f988bf3b0d28bf602410afcc4a80f4
+size 5815
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_2_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_2_en.png
index 82ce25b7e4..373431a91f 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_2_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_2_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:d9dd8b04317b9c35c13ec156c94c275074e6779a6ed6505a44fbb73d384fd6e3
-size 5512
+oid sha256:d86a47bcce5e883f2b94b98258fa7c944532d96f0db518d3bba4365cfde530ed
+size 6222
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_3_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_3_en.png
index c2e484ad40..ffbd6b1195 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_3_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_3_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:1cdb682c8952c3c0b687e391f412ac5a39c2dd6b8152c12ed161efa045fd97a5
-size 5344
+oid sha256:afff10df66307d03f037911b93d58396ab401e020cb74952a4ef76d8564a6cde
+size 6167
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_4_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_4_en.png
index 2e766a434d..80a74dbf26 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_4_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_4_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:3ea127648d6a70bffa2cba9a9b576c3625a06e82fcb2eae3adc8426d621309f1
-size 5892
+oid sha256:9e0d88f051140b6a31b3007b6ab92f9ba742f7c2de60dc3924a05834533e0e96
+size 5976
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_5_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_5_en.png
index 531b18baaf..499fde9e32 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_5_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_5_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:5c3da8139ef0f63b421b5637cd6f89ea5a048bd7804018740d528dac4d2179db
-size 5754
+oid sha256:44113dd74f49efb18cb98b363c8ff01323cdd8aada466560a8360205732e56d5
+size 5906
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_6_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_6_en.png
index 702f44844b..5c5992d39f 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_6_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_6_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:43a5225c0a3a6709fd220144469bb2f7961f4257816ed70c770093f1c2b5dc18
-size 5854
+oid sha256:f47934caa1ed08f3c3a9f70830367b7180f5a2e658d4b6c99f39e339f51dcddd
+size 6235
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_7_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_7_en.png
index 344b5be2f8..c77cfeda16 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_7_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_7_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:29975b9dd1530aa42a10302c45045929ab81c87e970c70c432a4aacb1daf0bcf
-size 5686
+oid sha256:a13158fb8eec57147ce15ca8ed29ca485986b99fe4f2801ab166bf6b90cc586d
+size 6110
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_8_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_8_en.png
deleted file mode 100644
index b2efbc710f..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_8_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:cfdbc0d7f4d7ed694f91f3e8fb9cd02701e2d2db98373bba6361911983d6d225
-size 5674
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_9_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_9_en.png
deleted file mode 100644
index a30a2e62c8..0000000000
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageEventBubble_Night_9_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:956670b8fb12cc76126c8fd9bb79c877ebfa81ade6783a91b8f2147a434e23a0
-size 5502
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Day_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Day_0_en.png
index b078dca532..aaeb39225f 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Day_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Day_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:4c389d128a7f89f8351b31c6043e9b6870af2c71e5e6e7eefbf3c632e6209f8b
-size 36218
+oid sha256:dc2234e1f00b0edbe3389464b1ccf375a034bb4f6daca6c80345c85dc2d4a267
+size 44822
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Night_0_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Night_0_en.png
index 28871cc02f..9c06f766d9 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Night_0_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl.timeline.components_MessageShieldView_Night_0_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:260b0e20954785563d6abc1a66fbc8823efecf2c8125802fe13b30aa1ab21786
-size 35104
+oid sha256:caa64bc210b30027a5f0eb1ea8c20b3d170b37ee3e1ac8f535233b3209feefc7
+size 43436
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_14_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_14_en.png
new file mode 100644
index 0000000000..38e26d3deb
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_14_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:45ead771fc133b1c992d090f35c93f0de4166b52966b818d8a401e75e5b63caf
+size 62982
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_5_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_5_en.png
index dbd685291f..5b6906e54a 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_5_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Day_5_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:62475d0e6b37cff42980135438faeccebe74bc110f517c12616351be8469c448
-size 55208
+oid sha256:4493799d889522a540435c10f0bf3642a438c38d6b219491afff4a72a169ce1c
+size 58416
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_14_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_14_en.png
new file mode 100644
index 0000000000..2b750a8c5c
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_14_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:5864ca4671dee1caef50d0444ffdeb0c7d2a5d9ed28ebc64937efbc469f6031a
+size 65288
diff --git a/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_5_en.png b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_5_en.png
index 012203b274..e58339319e 100644
--- a/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_5_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.messages.impl_MessagesView_Night_5_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:f4209f327f3a7cb3fbb0de25230604857e9d0e39b7ca0b2bec948656f08b2e08
-size 54804
+oid sha256:b44213fdccb6b194466d3daa7474b77378f96ab9b35559c0ba392dde49ecf175
+size 58055
diff --git a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_17_en.png b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_17_en.png
index 4e7871b133..d3792f6a0a 100644
--- a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_17_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_17_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:60571dc08867db9ad2f6528e95cc65df0eb57b9840bf8e96e6e1fbd802ad3a26
-size 38778
+oid sha256:f3cc4924fbbb2fea5937bf481b1322da14e1d2c8ea2cf4351fd6d0d222357738
+size 41304
diff --git a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_18_en.png b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_18_en.png
index fcb6f77177..4e7871b133 100644
--- a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_18_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_18_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:69d9aaf46305802861df8be0341abd73068376893bfd7aef43d7b8f3251350dd
-size 38735
+oid sha256:60571dc08867db9ad2f6528e95cc65df0eb57b9840bf8e96e6e1fbd802ad3a26
+size 38778
diff --git a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_19_en.png b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_19_en.png
new file mode 100644
index 0000000000..fcb6f77177
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetailsDark_19_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:69d9aaf46305802861df8be0341abd73068376893bfd7aef43d7b8f3251350dd
+size 38735
diff --git a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_17_en.png b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_17_en.png
index e60ef55c42..c9734faef5 100644
--- a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_17_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_17_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:cabfc7c5bf6f9b612e933cad211b8261b236cd981488cfa081e0226940626339
-size 39499
+oid sha256:63c75fdca8960f015caaa11bbb970c6e7621e87afbe7761d23db875664c55cd1
+size 42360
diff --git a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_18_en.png b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_18_en.png
index 2e3298b2ff..e60ef55c42 100644
--- a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_18_en.png
+++ b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_18_en.png
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:cf96db08ac0382185c34863b38603fe55eb3aab691fa3c42b6d73e4167ce8f82
-size 39383
+oid sha256:cabfc7c5bf6f9b612e933cad211b8261b236cd981488cfa081e0226940626339
+size 39499
diff --git a/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_19_en.png b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_19_en.png
new file mode 100644
index 0000000000..2e3298b2ff
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomdetails.impl_RoomDetails_19_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:cf96db08ac0382185c34863b38603fe55eb3aab691fa3c42b6d73e4167ce8f82
+size 39383
diff --git a/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_BatteryOptimizationBanner_Day_0_en.png b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_BatteryOptimizationBanner_Day_0_en.png
new file mode 100644
index 0000000000..6b81678de0
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_BatteryOptimizationBanner_Day_0_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:ef31a93af4f24ebada1e1436812c01d949e75d09f1259fabbe0d7a2a7eae3400
+size 26278
diff --git a/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_BatteryOptimizationBanner_Night_0_en.png b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_BatteryOptimizationBanner_Night_0_en.png
new file mode 100644
index 0000000000..6440604848
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_BatteryOptimizationBanner_Night_0_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:9bf4b769592e06e707a727bae111a6ebf27ced4c272c4aaace3368049873182b
+size 25324
diff --git a/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_RoomSummaryRow_Day_34_en.png b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_RoomSummaryRow_Day_34_en.png
new file mode 100644
index 0000000000..dd6fcb47f4
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_RoomSummaryRow_Day_34_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:26ec46ce726cb5a36accb280cc019a1a93d065bc6f6c74027d42efb4f7709f6a
+size 14566
diff --git a/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_RoomSummaryRow_Night_34_en.png b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_RoomSummaryRow_Night_34_en.png
new file mode 100644
index 0000000000..b66b1007fa
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomlist.impl.components_RoomSummaryRow_Night_34_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:dc7cf18c82801dd7aea6383a0f17fdbba11e92f9e4cead38ac609d7a2238837f
+size 14203
diff --git a/tests/uitests/src/test/snapshots/images/features.roomlist.impl_RoomListView_Day_11_en.png b/tests/uitests/src/test/snapshots/images/features.roomlist.impl_RoomListView_Day_11_en.png
new file mode 100644
index 0000000000..b7e1278591
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomlist.impl_RoomListView_Day_11_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:6041a7693307a30183606e7f8f2b605ba4c9bfb8c7ad5d8122837749813d6e2c
+size 99928
diff --git a/tests/uitests/src/test/snapshots/images/features.roomlist.impl_RoomListView_Night_11_en.png b/tests/uitests/src/test/snapshots/images/features.roomlist.impl_RoomListView_Night_11_en.png
new file mode 100644
index 0000000000..6cafa75e88
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/features.roomlist.impl_RoomListView_Night_11_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:7563629f9df4012d7cc35b2805e1ac381ccdb171935b35cad0d1ea60186e3e7d
+size 105496
diff --git a/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_AvatarCluster_Avatars_en.png b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_AvatarCluster_Avatars_en.png
new file mode 100644
index 0000000000..72b14d9cc3
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_AvatarCluster_Avatars_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:c6afcae51ee69dcdb9dbf60c8f72e55b9b07e4feb72dfba0a40ffeebed6ab681
+size 25730
diff --git a/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_CompositeAvatar_Avatars_en.png b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_CompositeAvatar_Avatars_en.png
deleted file mode 100644
index d14745b783..0000000000
--- a/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_CompositeAvatar_Avatars_en.png
+++ /dev/null
@@ -1,3 +0,0 @@
-version https://git-lfs.github.com/spec/v1
-oid sha256:374b810a6ef7011ec1270b7d4faddc8feacef10d167a5b2fc2c920d87f7d8e2c
-size 27831
diff --git a/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_TextAvatar_Avatars_en.png b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_TextAvatar_Avatars_en.png
new file mode 100644
index 0000000000..c0cc7d6d18
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_TextAvatar_Avatars_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:0645d454bcaac9e38fe9b6400347ee0fc92a71ef531f72b9ec527f644e050862
+size 5488
diff --git a/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_TombstonedRoomAvatar_Avatars_en.png b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_TombstonedRoomAvatar_Avatars_en.png
new file mode 100644
index 0000000000..c812b2a714
--- /dev/null
+++ b/tests/uitests/src/test/snapshots/images/libraries.designsystem.components.avatar_TombstonedRoomAvatar_Avatars_en.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:50abd66f2c58d8cc18a96c73120a779882cd121049e473646518ff6841e25e30
+size 5106
diff --git a/tools/localazy/checkForbiddenTerms.py b/tools/localazy/checkForbiddenTerms.py
index 5d04743529..2ebe582ba3 100755
--- a/tools/localazy/checkForbiddenTerms.py
+++ b/tools/localazy/checkForbiddenTerms.py
@@ -23,6 +23,7 @@ forbiddenTerms = {
"screen_onboarding_welcome_title",
# Contains "Element Call"
"screen_incoming_call_subtitle_android",
+ "call_invalid_audio_device_bluetooth_devices_disabled",
# Contains "Element X"
"screen_room_timeline_legacy_call",
]
diff --git a/tools/localazy/config.json b/tools/localazy/config.json
index b299c39ef7..dbe8c4221a 100644
--- a/tools/localazy/config.json
+++ b/tools/localazy/config.json
@@ -165,13 +165,14 @@
"name" : ":features:roomlist:impl",
"includeRegex" : [
"screen_roomlist_.*",
+ "screen\\.roomlist\\..*",
"session_verification_banner_.*",
"confirm_recovery_key_banner_.*",
"banner\\.set_up_recovery\\..*",
+ "banner\\.battery_optimization\\..*",
"full_screen_intent_banner_.*",
"screen_migration_.*",
- "screen_invites_.*",
- "screen\\.join_room\\.knock_sent_title"
+ "screen_invites_.*"
]
},
{
@@ -210,6 +211,7 @@
"screen_room_message.*",
"screen_room_retry.*",
"screen_room_timeline.*",
+ "screen\\.room_timeline.*",
"screen_room_typing.*"
]
},
@@ -242,6 +244,12 @@
"screen_polls_history_.*"
]
},
+ {
+ "name" : ":features:poll:api",
+ "includeRegex" : [
+ "a11y\\.polls\\..*"
+ ]
+ },
{
"name" : ":features:securebackup:impl",
"includeRegex" : [