feat: render every preview under the five conditions a screen has to survive

Phase 8, item three. The tree had 51 previews and every one of them rendered one
thing: a light theme, at whatever width the preview pane happened to be, at 100%
text. That is the only condition under which this app has never had a defect.

`@ConformancePreviews` replaces the bare `@Preview` at all 53 sites -- the two
outside `ui/` included -- and renders each under five: light, dark, 200% text,
compact 400dp, expanded 1000dp. `@Preview` is `@Repeatable`, so this is one
annotation rather than five copied onto every preview and drifting apart. Each of
the four new conditions is where a defect in this app has actually been: a colour
that only fails in dark, a fixed-height container that clips at 200%, a layout
that stretches because nothing held it, a row that reflows badly at phone width.

It also gives phase 6 the check it could not make. "Every screen renders correctly
at 400dp, 700dp, 1000dp, 1400dp and 1800dp" was verified structurally -- the
measure applied at every root and asserted at those widths -- but never looked at
per screen. Two of those widths are now one click away on every screen in the app.

**High contrast is deliberately not in the annotation**, and the argument is worth
stating because the omission looks like a gap. Contrast is a property of the
*scheme*, not of a screen: the app declares six, `ColorSchemeContrastTest`
measures every pair in all six, and a screen right in the default scheme is right
in the high-contrast one by construction. Per-screen high-contrast previews would
be 51 more renders of something already proved -- and there is no `@Preview`
parameter for it in any case, since it needs `TorchTheme(contrast = …)` in the
body.

`ThemeGallery` covers them instead, once, over components rather than screens: all
six schemes side by side, with body copy on surface, a card holding a list item --
the arrangement that rendered a headline at 1.00:1 before phase 3 -- and the three
button emphases. `dynamicColor = false` on purpose, or an android 12+ preview
paints all six columns from the wallpaper and the gallery shows nothing. It is the
only place the medium and high contrast schemes can be seen at all: in the app
they are reachable only through a platform setting, and on android only with
dynamic colour off.

99 lines changed across 50 files, all of them one annotation and its import.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Kgothatso NgakoandClaude Opus 5 committed 2026-09-08 08:24:49 +02:00
1 parent 9946f98ca8
commit 5f0afdf34d
52 files changed
+258 -103

No files matched your search

@@ -13,7 +13,6 @@ import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.room3.Entity
import androidx.room3.ForeignKey
@@ -27,6 +26,7 @@ import press.mantra.compose.ui.composable.widgets.profile.ProfileColor
import press.mantra.compose.ui.theme.TorchTheme
import kotlin.time.Clock
import kotlin.time.Instant
import press.mantra.compose.ui.theme.ConformancePreviews
@Entity(
foreignKeys = [
@@ -170,7 +170,7 @@ data class Profile(
}
}
@Preview
@ConformancePreviews
@Composable
fun ProfileRenderAsListItemPreview() {
val profile = Profile(
@@ -11,7 +11,6 @@ import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.room3.Embedded
import androidx.room3.Relation
@@ -23,6 +22,7 @@ import press.mantra.compose.database.model.QuotedRelation
import press.mantra.compose.ui.composable.widgets.content.RichContent
import press.mantra.compose.ui.composable.widgets.profile.ProfileAvatar
import press.mantra.compose.ui.theme.TorchTheme
import press.mantra.compose.ui.theme.ConformancePreviews
data class LocalQuotedNostrEvent(
@Embedded val quotedRelation: press.mantra.compose.database.model.QuotedRelation,
@@ -110,7 +110,7 @@ data class LocalQuotedNostrEvent(
}
}
@Preview
@ConformancePreviews
@Composable
private fun LocalQuotedNostrEventPreview() {
TorchTheme {
@@ -34,7 +34,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.NostrEvent
@@ -71,6 +70,7 @@ import androidx.compose.material3.FilledTonalButton
import androidx.compose.material3.ButtonDefaults
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -389,7 +389,7 @@ fun ActiveProfileScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnannouncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -49,7 +49,6 @@ import androidx.compose.ui.graphics.Color
import androidx.compose.ui.semantics.disabled
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.ChatRoom
@@ -87,6 +86,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class, ExperimentalLayoutApi::class)
@Composable
@@ -402,7 +402,7 @@ fun AddArtifactScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun AddArtifactScreenPreview() {
TorchTheme {
@@ -34,7 +34,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.disabled
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -68,6 +67,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -310,7 +310,7 @@ fun AddChapterScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun AddChapterScreenPreview() {
TorchTheme {
@@ -39,7 +39,6 @@ import androidx.compose.ui.graphics.Color
import androidx.compose.ui.semantics.disabled
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -71,6 +70,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -337,7 +337,7 @@ fun AddDialectScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun AddDialectScreenPreview() {
TorchTheme {
@@ -23,7 +23,6 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.ChatRoom
@@ -50,6 +49,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -214,7 +214,7 @@ fun AddMemberToChatRoomConfirmationScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ChatRoomDetailScreenPreview() {
TorchTheme {
@@ -37,7 +37,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.disabled
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -69,6 +68,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class, ExperimentalLayoutApi::class)
@Composable
@@ -314,7 +314,7 @@ fun AddTranslationArtifactVersionScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun AddTranslationArtifactVersionScreenPreview() {
TorchTheme {
@@ -32,7 +32,6 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -68,6 +67,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -330,7 +330,7 @@ fun ArtifactDetailScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ArtifactDetailScreenPreview() {
TorchTheme {
@@ -28,7 +28,6 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -52,6 +51,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -196,7 +196,7 @@ fun ChapterDetailScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ChapterDetailScreenPreview() {
TorchTheme {
@@ -22,7 +22,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.input.KeyboardType
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.ui.composable.navigation.routes.Route
@@ -41,6 +40,7 @@ import mantra.composeapp.generated.resources.what_will_be_discussed_in_this_chat
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun ChatRoomCreationScreen(
@@ -172,7 +172,7 @@ fun ChatRoomCreationScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun LoadingScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -43,7 +43,6 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.ChatRoom
@@ -96,6 +95,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -740,7 +740,7 @@ private fun ReindexMarmotGroupEventsButton(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ChatRoomMessagingScreenPreview() {
TorchTheme {
@@ -38,7 +38,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.ChatRoom
@@ -71,6 +70,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -459,7 +459,7 @@ fun ChatRoomMessagingScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ChatRoomMessagingScreenPreview() {
TorchTheme {
@@ -29,7 +29,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.input.KeyboardType
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.repository.MarmotRepository
@@ -62,6 +61,7 @@ import mantra.composeapp.generated.resources.you_will_be_in_full_control_of_this
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -393,7 +393,7 @@ fun CreateProfileScreen(
}
}
@Preview
@ConformancePreviews
@Composable
fun CreateAccountScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -46,7 +46,6 @@ import androidx.compose.ui.text.buildAnnotatedString
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.text.withStyle
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.platform.LocalClipboardManager
import androidx.compose.ui.text.AnnotatedString
import androidx.compose.ui.text.font.FontFamily
@@ -103,6 +102,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
/**
* The shared-key ceremony: a ChillDKG ritual run across the group's NIP-17
@@ -682,7 +682,7 @@ private fun QuorumStepper(
}
}
@Preview
@ConformancePreviews
@Composable
private fun DkgRitualScreenPreview() {
TorchTheme {
@@ -39,7 +39,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.Event
@@ -72,6 +71,7 @@ import mantra.composeapp.generated.resources.events_signed_together
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
/**
* One signing session, and the member's decision about it.
@@ -407,7 +407,7 @@ private fun statusOf(session: FrostSigningSession): String = when (session.stage
FrostSigningStage.FAILED -> "Abandoned. Nothing was signed, and it is safe to ask again."
}
@Preview
@ConformancePreviews
@Composable
private fun FrostSigningScreenPreview() {
TorchTheme {
@@ -37,7 +37,6 @@ import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.testTag
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.NostrEvent
@@ -75,6 +74,7 @@ import press.mantra.compose.ui.theme.listPaneWidthFor
import press.mantra.compose.ui.theme.readableContent
import mantra.composeapp.generated.resources.pick_a_conversation_to_read_it_here
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class, ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -344,7 +344,7 @@ fun HomeScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun HomeScreenPreview() {
TorchTheme {
@@ -11,7 +11,6 @@ import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -20,6 +19,7 @@ import mantra.composeapp.generated.resources.functionality_coming_soon_2
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun ImplementationPendingScreen(
@@ -44,7 +44,7 @@ fun ImplementationPendingScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ImplementationPendingScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -32,7 +32,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.MarmotKeyPackageBundle
@@ -60,6 +59,7 @@ import mantra.composeapp.generated.resources.key_package_published
import mantra.composeapp.generated.resources.key_package_rotated
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -243,7 +243,7 @@ fun KeyPackageManagementScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnannouncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -17,7 +17,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -32,6 +31,7 @@ import mantra.composeapp.generated.resources.sign_in_to_torch_via_nsec_or_remote
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun LandingScreen(
@@ -112,7 +112,7 @@ fun LandingScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun LandingScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -7,10 +7,10 @@ import androidx.compose.material3.Scaffold
import androidx.compose.material3.Surface
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun LoadingScreen(
@@ -28,7 +28,7 @@ fun LoadingScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun LoadingScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -13,7 +13,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.NostrEvent
@@ -43,6 +42,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -146,7 +146,7 @@ fun NostrEventDetailScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun NostrEventDetailScreenPreview() {
TorchTheme {
@@ -37,7 +37,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -66,6 +65,7 @@ import mantra.composeapp.generated.resources.of_them_could_not_be_read
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
/**
* Everything the group has asked its shared key to sign.
@@ -404,7 +404,7 @@ private fun statusOf(proposal: ProposalListUIState.Proposal): String {
}
}
@Preview
@ConformancePreviews
@Composable
private fun ProposalListScreenPreview() {
val session = FrostSigningSession(
@@ -24,7 +24,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.ChatRoom
@@ -50,6 +49,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -223,7 +223,7 @@ fun SearchMemberToAddToChatRoomScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun ChatRoomDetailScreenPreview() {
TorchTheme {
@@ -46,7 +46,6 @@ import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.semantics.traversalIndex
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.ui.composable.widgets.feed.ListView
@@ -66,6 +65,7 @@ import press.mantra.compose.ui.composable.widgets.ErrorState
import press.mantra.compose.ui.composable.widgets.EmptyState
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class, ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -281,7 +281,7 @@ fun SearchResultScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun SearchResultScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -49,7 +49,6 @@ import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.semantics.traversalIndex
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.repository.NostrRepository
@@ -72,6 +71,7 @@ import mantra.composeapp.generated.resources.search_hashtags
import mantra.composeapp.generated.resources.trending_notes_functionality_coming_soon_in
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class, ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -423,7 +423,7 @@ fun SearchScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun SearchScreenPreview() {
TorchTheme {
@@ -30,7 +30,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.Profile
@@ -57,6 +56,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
/**
* Second step of group creation: pick who is in the group.
@@ -280,7 +280,7 @@ fun SelectChatRoomMembersScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun SelectChatRoomMembersScreenPreview() {
TorchTheme {
@@ -38,7 +38,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.Profile
@@ -74,6 +73,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
/**
* Last step of group creation: convenient (one admin) or robust (everyone
@@ -462,7 +462,7 @@ private fun QuorumPicker(
}
}
@Preview
@ConformancePreviews
@Composable
private fun SelectChatRoomTypeScreenPreview() {
TorchTheme {
@@ -29,7 +29,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalClipboardManager
import androidx.compose.ui.text.buildAnnotatedString
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.NostrEvent
@@ -56,6 +55,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalMaterial3Api::class)
@Composable
@@ -227,7 +227,7 @@ fun ShareProfileScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnannouncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -26,7 +26,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.text.input.ImeAction
import androidx.compose.ui.text.input.KeyboardType
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip19Bech32.entities.NPub
@@ -47,6 +46,7 @@ import mantra.composeapp.generated.resources.this_will_give_you_write_access_to_
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -273,7 +273,7 @@ fun SignInToProfileScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun SignInToProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -20,7 +20,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -34,6 +33,7 @@ import mantra.composeapp.generated.resources.who_will_you_be_passing_the_aux_to
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun SocialPreconditionScreen(
@@ -124,7 +124,7 @@ fun SocialPreconditionScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun SocialPreconditionScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -36,7 +36,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.disabled
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -66,6 +65,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -267,7 +267,7 @@ fun TranslateChunkScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun TranslateChunkScreenPreview() {
TorchTheme {
@@ -30,7 +30,6 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -61,6 +60,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -284,7 +284,7 @@ fun TranslationArtifactVersionDetailScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun TranslationArtifactVersionDetailScreenPreview() {
TorchTheme {
@@ -34,7 +34,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -56,6 +55,7 @@ import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.composable.widgets.ScreenStateTransition
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@@ -242,7 +242,7 @@ private fun TableRow(
}
}
@Preview
@ConformancePreviews
@Composable
private fun TranslationChapterScreenPreview() {
TorchTheme {
@@ -15,7 +15,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -25,6 +24,7 @@ import mantra.composeapp.generated.resources.torch_will_be_broadcast_what_you_pu
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -76,7 +76,7 @@ fun UnannouncedProfileScreen() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnannouncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -15,7 +15,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -25,6 +24,7 @@ import mantra.composeapp.generated.resources.everything_is_cryptographical_sound
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -76,7 +76,7 @@ fun UnindexedProfileScreen() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnannouncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -15,7 +15,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -25,6 +24,7 @@ import mantra.composeapp.generated.resources.everything_is_cryptographical_sound
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -76,7 +76,7 @@ fun UnqueuedProfileScreen() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnannouncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -16,7 +16,6 @@ import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.ui.theme.spacing
@@ -27,6 +26,7 @@ import mantra.composeapp.generated.resources.we_are_searching_the_internet_to_fi
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -88,7 +88,7 @@ fun UnqueuedProfileSynchronizationScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnqueuedProfileSynchronizationScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -15,7 +15,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -25,6 +24,7 @@ import mantra.composeapp.generated.resources.your_profile_is_almost_ready_just_g
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -70,7 +70,7 @@ fun UnsignedProfileScreen() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnsignedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -15,7 +15,6 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
@@ -25,6 +24,7 @@ import mantra.composeapp.generated.resources.we_are_searching_the_internet_to_fi
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -72,7 +72,7 @@ fun UnsyncedProfileScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun UnsyncedProfileScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -37,7 +37,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.text.SpanStyle
import androidx.compose.ui.text.input.KeyboardType
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.extensions.toFormattedTimeAndDateString
@@ -59,6 +58,7 @@ import mantra.composeapp.generated.resources.replying_to
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class, ExperimentalFoundationApi::class)
@Composable
@@ -465,7 +465,7 @@ fun WriteNewNoteScreen(
}
}
@Preview
@ConformancePreviews
@Composable
private fun WriteNewNoteScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -12,9 +12,9 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.ui.theme.spacing
import press.mantra.compose.ui.theme.ConformancePreviews
/**
* The app's one loading state, used at 41 call sites.
@@ -66,7 +66,7 @@ fun LoadingDataIndicator(
}
@Preview
@ConformancePreviews
@Composable
private fun TransferHistoryScreenPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -17,13 +17,13 @@ import androidx.compose.material3.minimumInteractiveComponentSize
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import com.vitorpamplona.quartz.nip01Core.core.HexKey
import press.mantra.compose.ui.theme.spacing
import mantra.composeapp.generated.resources.Res
import org.jetbrains.compose.resources.stringResource
import mantra.composeapp.generated.resources.loading_note
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun QuotedNote(
@@ -117,7 +117,7 @@ fun QuotedNote(
}
}
@Preview
@ConformancePreviews
@Composable
private fun QuotedNotePreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -26,7 +26,6 @@ import androidx.compose.ui.text.buildAnnotatedString
import androidx.compose.ui.text.style.TextDecoration
import androidx.compose.ui.text.withLink
import androidx.compose.ui.text.withStyle
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import co.touchlab.kermit.Logger
import coil3.compose.AsyncImage
@@ -36,6 +35,7 @@ import mantra.composeapp.generated.resources.Res
import org.jetbrains.compose.resources.stringResource
import mantra.composeapp.generated.resources.nostr
import mantra.composeapp.generated.resources.nostr_2
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun RichContent(
@@ -398,7 +398,7 @@ fun RichContent(
}
}
@Preview
@ConformancePreviews
@Composable
private fun RichContentPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -40,7 +40,6 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.input.nestedscroll.nestedScroll
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.database.model.NostrEvent
@@ -70,6 +69,7 @@ import mantra.composeapp.generated.resources.unfollow
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class, ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -322,7 +322,7 @@ fun MetadataEventDetail(
}
}
@Preview
@ConformancePreviews
@Composable
private fun MetadataEventEventDetailPreview() {
@@ -42,7 +42,6 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.input.nestedscroll.nestedScroll
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import press.mantra.compose.extensions.toFormattedTimeAndDateString
@@ -59,6 +58,7 @@ import press.mantra.compose.ui.composable.widgets.ErrorState
import androidx.compose.material3.SnackbarHost
import press.mantra.compose.ui.composable.widgets.LocalSnackbarHostState
import press.mantra.compose.ui.theme.readableContent
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3Api::class, ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -389,7 +389,7 @@ fun TextNoteEventDetail(
}
}
@Preview
@ConformancePreviews
@Composable
private fun TextNoteEventDetailPreview() {
@@ -30,7 +30,6 @@ import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.compose.ui.window.Dialog
import press.mantra.compose.extensions.bech32ToHexOrNull
@@ -51,6 +50,7 @@ import org.jetbrains.compose.resources.stringResource
import mantra.composeapp.generated.resources.input_npub_or_nip05
import mantra.composeapp.generated.resources.start_chat
import mantra.composeapp.generated.resources.start_chat_via_npub_or_nip05
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun StartDirectMessageToNpubOrNip05Dialog(
@@ -187,7 +187,7 @@ fun StartDirectMessageToNpubOrNip05Dialog(
}
}
@Preview
@ConformancePreviews
@Composable
private fun StartDirectMessageToNpubOrNip05DialogPreview() {
TorchTheme {
@@ -17,7 +17,6 @@ import androidx.compose.material3.minimumInteractiveComponentSize
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.extensions.toFormattedTimeAndDateString
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -30,6 +29,7 @@ import org.jetbrains.compose.resources.stringResource
import mantra.composeapp.generated.resources.loading_author_information_2
import mantra.composeapp.generated.resources.malformed_note
import mantra.composeapp.generated.resources.reposted
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun press.mantra.compose.database.model.intermdiate.LocalNostrEvent.ListView(
@@ -126,7 +126,7 @@ fun press.mantra.compose.database.model.intermdiate.LocalNostrEvent.ListView(
}
@Preview
@ConformancePreviews
@Composable
private fun EventListViewRepostedPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -177,7 +177,7 @@ private fun EventListViewRepostedPreview() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun EventListViewInReplyPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -21,7 +21,6 @@ import androidx.compose.runtime.mutableStateOf
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import press.mantra.compose.extensions.toFormattedTimeAndDateString
import com.vitorpamplona.quartz.nip01Core.core.HexKey
@@ -30,6 +29,7 @@ import mantra.composeapp.generated.resources.Res
import org.jetbrains.compose.resources.stringResource
import mantra.composeapp.generated.resources.loading_author_information
import mantra.composeapp.generated.resources.loading_information
import press.mantra.compose.ui.theme.ConformancePreviews
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@Composable
@@ -184,7 +184,7 @@ internal fun TextNoteFeedItem(
}
@Preview
@ConformancePreviews
@Composable
private fun TextNoteFeedItemPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -215,7 +215,7 @@ private fun TextNoteFeedItemPreview() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun TextNoteFeedItemInReplyToPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -269,7 +269,7 @@ private fun TextNoteFeedItemInReplyToPreview() {
}
}
@Preview
@ConformancePreviews
@Composable
private fun TextNoteFeedItemQuoteNostrEventPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -17,11 +17,11 @@ import androidx.compose.ui.graphics.ColorFilter
import androidx.compose.ui.graphics.Shape
import androidx.compose.ui.graphics.vector.rememberVectorPainter
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
import coil3.compose.AsyncImage
import press.mantra.compose.ui.theme.spacing
import press.mantra.compose.ui.theme.ConformancePreviews
@Composable
fun ProfileAvatar(
@@ -90,7 +90,7 @@ fun ProfileAvatar(
// TODO: Show cards...
}
@Preview
@ConformancePreviews
@Composable
fun ProfileAvatarPreview() {
press.mantra.compose.ui.theme.TorchTheme {
@@ -0,0 +1,43 @@
package press.mantra.compose.ui.theme
import androidx.compose.ui.tooling.preview.Preview
/**
* The five conditions every screen has to survive, as one annotation.
*
* A screen renders under a light theme on a phone because that is the only way anybody
* ever looks at it. The other four are where this app's defects have actually been: a
* colour that only fails in dark, a fixed-height container that clips at 200% text, a
* layout that stretches to 1000dp because nothing ever held it, a row that reflows badly
* at 400dp. Each of those is invisible in a diff and obvious in a render.
*
* Replaces a bare `@Preview` at the 51 preview sites in the tree. `@Preview` is
* `@Repeatable`, so this is five renders from one annotation rather than five annotations
* copied onto every preview and drifting apart.
*
* **High contrast is deliberately not here**, and that is an argument rather than an
* omission. Contrast is a property of the *scheme*, not of a screen: the app declares six
* schemes and `ColorSchemeContrastTest` measures every pair in all six, so a screen that
* is right in the default scheme is right in the high-contrast one by construction. A
* per-screen high-contrast preview would be 51 more renders checking something already
* proved, and there is no `@Preview` parameter for it anyway -- it needs
* `TorchTheme(contrast = …)` in the body. [ThemeGallery] covers the schemes once, over
* the components rather than over the screens.
*
* @see ThemeGallery
*/
@Preview(name = "Light", group = "conformance")
@Preview(name = "Dark", group = "conformance", uiMode = UiModeNightYes)
@Preview(name = "200% text", group = "conformance", fontScale = 2f)
@Preview(name = "Compact 400dp", group = "conformance", widthDp = 400, heightDp = 800)
@Preview(name = "Expanded 1000dp", group = "conformance", widthDp = 1000, heightDp = 800)
annotation class ConformancePreviews
/**
* `Configuration.UI_MODE_NIGHT_YES or UI_MODE_TYPE_NORMAL`.
*
* Written as a literal because `android.content.res.Configuration` is not reachable from
* common code, and as a named constant rather than an inline `0x21` because a bare hex
* number in a preview annotation says nothing about which of the two flags it carries.
*/
private const val UiModeNightYes = 0x21
@@ -0,0 +1,112 @@
package press.mantra.compose.ui.theme
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.Star
import androidx.compose.material3.Button
import androidx.compose.material3.Card
import androidx.compose.material3.FilledTonalButton
import androidx.compose.material3.HorizontalDivider
import androidx.compose.material3.Icon
import androidx.compose.material3.ListItem
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Surface
import androidx.compose.material3.Text
import androidx.compose.material3.TextButton
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import press.mantra.compose.ui.composable.widgets.Decorative
/**
* All six schemes, side by side, over the components that carry text.
*
* The one place the medium and high contrast schemes can be looked at. They are reachable
* in the app only through a platform setting -- and on android 12 and up, only with
* dynamic colour switched off -- so without this they are values in `Color.kt` that
* nobody has seen.
*
* Over components rather than over screens, and that is the point of it. Contrast is a
* property of the scheme: `ColorSchemeContrastTest` measures every pair in all six, so
* what a render adds is not proof but judgement -- whether `secondaryContainer` still
* reads as a container in high contrast, whether the outline is doing its job. Six renders
* of this answer that for the whole app; six renders of each of 51 screens would answer it
* 51 times.
*/
@Preview(name = "Six schemes", group = "schemes", widthDp = 1200, heightDp = 900)
@Composable
private fun ThemeGalleryPreview() {
// One render holding all six, not six renders. The contrast step is a `TorchTheme`
// parameter and no preview annotation can set it, so the combinations have to be laid
// out in the body -- and laying them out side by side is what makes them comparable,
// which is the only reason to look at them at all.
Column {
listOf(false, true).forEach { dark ->
Row(modifier = Modifier.fillMaxWidth()) {
ThemeContrast.entries.forEach { contrast ->
Column(modifier = Modifier.weight(1f)) {
ThemeGallery(darkTheme = dark, contrast = contrast)
}
}
}
}
}
}
/**
* One scheme's worth of components. Public so a screen's own preview can borrow it.
*
* `dynamicColor = false` on purpose: with it left on, an android 12+ preview renders the
* wallpaper palette and every column here comes out identical. That is correct app
* behaviour and useless as a gallery of the six schemes.
*/
@Composable
fun ThemeGallery(darkTheme: Boolean, contrast: ThemeContrast) {
TorchTheme(darkTheme = darkTheme, contrast = contrast, dynamicColor = false) {
Surface {
Column(
modifier = Modifier.padding(MaterialTheme.spacing.compactPadding),
verticalArrangement = Arrangement.spacedBy(MaterialTheme.spacing.relatedGap),
) {
Text(
text = "${if (darkTheme) "Dark" else "Light"} · ${contrast.name}",
style = MaterialTheme.typography.labelSmall,
)
// Body copy on the plain surface: the pairing every screen uses most, and
// the one that has to hold 4.5:1.
Text("Body on surface", style = MaterialTheme.typography.bodyMedium)
Text(
text = "Secondary text",
style = MaterialTheme.typography.bodySmall,
color = MaterialTheme.colorScheme.onSurfaceVariant,
)
HorizontalDivider()
// A card with a container role and a list item inside it -- the exact
// arrangement that rendered a headline at 1.00:1 before phase 3, because
// ListItem does not read LocalContentColor.
Card {
ListItem(
headlineContent = { Text("Awaiting your signature") },
supportingContent = { Text("Two events") },
leadingContent = { Icon(Icons.Default.Star, contentDescription = Decorative) },
)
}
// The three button emphases, which is where the extended brand colours and
// the error role are seen.
Button(onClick = {}) { Text("Primary") }
FilledTonalButton(onClick = {}) { Text("Tonal") }
TextButton(onClick = {}) {
Text("Sign out", color = MaterialTheme.colorScheme.error)
}
}
}
}
}