diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/Previews.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/Previews.kt deleted file mode 100644 index 846e459..0000000 --- a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/Previews.kt +++ /dev/null @@ -1,31 +0,0 @@ -package com.rafaelfelipeac.replyradar - -import androidx.compose.runtime.Composable -import androidx.compose.ui.tooling.preview.Preview -import com.rafaelfelipeac.replyradar.features.reply.domain.model.Reply -import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListScreen -import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListState -import kotlinx.coroutines.flow.flowOf - -private val replies = (1L..10L).map { - Reply( - id = it, - name = "Reply $it", - subject = "Subject $it", - isResolved = true - ) -} - -@Preview -@Composable -private fun ReplyListScreenPreview() { - ReplyListScreen( - state = ReplyListState( - replies = replies - ), - onIntent = {}, - onSettingsClick = {}, - onActivityLogClick = {}, - effect = flowOf() - ) -} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ActivityLogListItemPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ActivityLogListItemPreview.kt new file mode 100644 index 0000000..76feaf4 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ActivityLogListItemPreview.kt @@ -0,0 +1,338 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.activitylog.presentation.ActivityLogListItem +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserAction +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType.Feedback +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType.Language +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType.Message +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType.Rate +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType.Theme +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Archive +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Create +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Delete +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Edit +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Open +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.OpenedNotification +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Reopen +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Resolve +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Scheduled +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType.Unarchive +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import kotlinx.datetime.Clock + +@Preview(showBackground = true) +@Composable +fun PreviewCreateMessage() = PreviewAction( + id = 1, + type = Create, + target = Message, + name = Replies.OnTheRadar.reply1.name +) + +@Preview(showBackground = true) +@Composable +fun PreviewEditMessage() = PreviewAction( + id = 2, + type = Edit, + target = Message, + name = Replies.OnTheRadar.reply2.name, + timeOffsetMillis = 1_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewResolveMessage() = PreviewAction( + id = 3, + type = Resolve, + target = Message, + name = Replies.Resolved.reply3.name, + timeOffsetMillis = 2_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewReopenMessage() = PreviewAction( + id = 4, + type = Reopen, + target = Message, + name = Replies.Resolved.reply4.name, + timeOffsetMillis = 3_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewArchiveMessage() = PreviewAction( + id = 5, + type = Archive, + target = Message, + name = Replies.Archived.reply1.name, + timeOffsetMillis = 4_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewUnarchiveMessage() = PreviewAction( + id = 6, + type = Unarchive, + target = Message, + name = Replies.Archived.reply2.name, + timeOffsetMillis = 5_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewDeleteMessage() = PreviewAction( + id = 7, + type = Delete, + target = Message, + name = Replies.OnTheRadar.reply3.name, + timeOffsetMillis = 6_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewScheduledMessage() = PreviewAction( + id = 8, + type = Scheduled, + target = Message, + name = Replies.OnTheRadar.reply4.name, + timeOffsetMillis = 7_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewOpenedNotificationMessage() = PreviewAction( + id = 9, + type = OpenedNotification, + target = Message, + name = Replies.OnTheRadar.reply5.name, + timeOffsetMillis = 8_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewOpenMessage() = PreviewAction( + id = 10, + type = Open, + target = Message, + name = Replies.OnTheRadar.reply1.name, + timeOffsetMillis = 9_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateTheme() = PreviewAction( + id = 11, + type = Create, + target = Theme, + name = null, + timeOffsetMillis = 10_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateLanguage() = PreviewAction( + id = 12, + type = Create, + target = Language, + name = null, + timeOffsetMillis = 11_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateFeedback() = PreviewAction( + id = 13, + type = Create, + target = Feedback, + name = null, + timeOffsetMillis = 12_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateRate() = PreviewAction( + id = 14, + type = Create, + target = Rate, + name = null, + timeOffsetMillis = 13_000_000L +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateMessageDark() = PreviewAction( + id = 1, + type = Create, + target = Message, + name = Replies.OnTheRadar.reply1.name, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewEditMessageDark() = PreviewAction( + id = 2, + type = Edit, + target = Message, + name = Replies.OnTheRadar.reply2.name, + timeOffsetMillis = 1_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewResolveMessageDark() = PreviewAction( + id = 3, + type = Resolve, + target = Message, + name = Replies.Resolved.reply3.name, + timeOffsetMillis = 2_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewReopenMessageDark() = PreviewAction( + id = 4, + type = Reopen, + target = Message, + name = Replies.Resolved.reply4.name, + timeOffsetMillis = 3_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewArchiveMessageDark() = PreviewAction( + id = 5, + type = Archive, + target = Message, + name = Replies.Archived.reply1.name, + timeOffsetMillis = 4_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewUnarchiveMessageDark() = PreviewAction( + id = 6, + type = Unarchive, + target = Message, + name = Replies.Archived.reply2.name, + timeOffsetMillis = 5_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewDeleteMessageDark() = PreviewAction( + id = 7, + type = Delete, + target = Message, + name = Replies.OnTheRadar.reply3.name, + timeOffsetMillis = 6_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewScheduledMessageDark() = PreviewAction( + id = 8, + type = Scheduled, + target = Message, + name = Replies.OnTheRadar.reply4.name, + timeOffsetMillis = 7_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewOpenedNotificationMessageDark() = PreviewAction( + id = 9, + type = OpenedNotification, + target = Message, + name = Replies.OnTheRadar.reply5.name, + timeOffsetMillis = 8_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewOpenMessageDark() = PreviewAction( + id = 10, + type = Open, + target = Message, + name = Replies.OnTheRadar.reply1.name, + timeOffsetMillis = 9_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateThemeDark() = PreviewAction( + id = 11, + type = Create, + target = Theme, + name = null, + timeOffsetMillis = 10_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateLanguageDark() = PreviewAction( + id = 12, + type = Create, + target = Language, + name = null, + timeOffsetMillis = 11_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateFeedbackDark() = PreviewAction( + id = 13, + type = Create, + target = Feedback, + name = null, + timeOffsetMillis = 12_000_000L, + darkTheme = true +) + +@Preview(showBackground = true) +@Composable +fun PreviewCreateRateDark() = PreviewAction( + id = 14, + type = Create, + target = Rate, + name = null, + timeOffsetMillis = 13_000_000L, + darkTheme = true +) + +@Composable +private fun PreviewAction( + id: Long, + type: UserActionType, + target: UserActionTargetType, + name: String? = null, + timeOffsetMillis: Long = 0L, + darkTheme: Boolean = false +) = ReplyRadarPreviewWrapper(darkTheme = darkTheme) { + ActivityLogListItem( + userAction = UserAction( + id = id, + actionType = type, + targetType = target, + targetName = name, + createdAt = Clock.System.now().toEpochMilliseconds() - timeOffsetMillis + ) + ) +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/FloatingActionButtonPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/FloatingActionButtonPreview.kt new file mode 100644 index 0000000..cef6033 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/FloatingActionButtonPreview.kt @@ -0,0 +1,46 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.FloatingActionButton +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun FloatingActionButtonPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(4.dp) + ) { + FloatingActionButton( + onIntent = {}, + colorScheme = MaterialTheme.colorScheme + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun FloatingActionButtonDarkPreview() { + ReplyRadarPreviewWrapper(darkTheme = true) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(4.dp) + ) { + FloatingActionButton( + onIntent = {}, + colorScheme = MaterialTheme.colorScheme + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/PlatformDatePickerPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/PlatformDatePickerPreview.kt new file mode 100644 index 0000000..3cab439 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/PlatformDatePickerPreview.kt @@ -0,0 +1,39 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.datetime.PlatformDatePicker +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +@Preview(showBackground = true) +@Composable +fun PlatformDatePickerPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + PlatformDatePicker( + selectedDate = null, + selectedTime = null, + onDateSelected = {}, + confirmButtonText = PreviewStringsFake.replyListReminderDatePickerConfirmButton, + dismissButtonText = PreviewStringsFake.replyListReminderDatePickerDismissButton, + onTimeInvalidated = {}, + onDismiss = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun PlatformDatePickerDarkPreview() { + ReplyRadarPreviewWrapper(darkTheme = true) { + PlatformDatePicker( + selectedDate = null, + selectedTime = null, + onDateSelected = {}, + confirmButtonText = PreviewStringsFake.replyListReminderDatePickerConfirmButton, + dismissButtonText = PreviewStringsFake.replyListReminderDatePickerDismissButton, + onTimeInvalidated = {}, + onDismiss = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/PlatformTimePickerPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/PlatformTimePickerPreview.kt new file mode 100644 index 0000000..808f0e4 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/PlatformTimePickerPreview.kt @@ -0,0 +1,39 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.datetime.PlatformTimePicker +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +@Preview(showBackground = true) +@Composable +fun PlatformTimePickerPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + PlatformTimePicker( + selectedTime = null, + selectedDate = null, + onTimeSelected = {}, + onDismiss = {}, + confirmButtonText = PreviewStringsFake.replyListReminderTimePickerConfirmButton, + dismissButtonText = PreviewStringsFake.replyListReminderTimePickerDismissButton, + pickerTimeTitle = PreviewStringsFake.replyListReminderTimePickerTitle + ) + } +} + +@Preview(showBackground = true) +@Composable +fun PlatformTimePickerDarkPreview() { + ReplyRadarPreviewWrapper(darkTheme = true) { + PlatformTimePicker( + selectedTime = null, + selectedDate = null, + onTimeSelected = {}, + onDismiss = {}, + confirmButtonText = PreviewStringsFake.replyListReminderTimePickerConfirmButton, + dismissButtonText = PreviewStringsFake.replyListReminderTimePickerDismissButton, + pickerTimeTitle = PreviewStringsFake.replyListReminderTimePickerTitle + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesArchivedScreenPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesArchivedScreenPreview.kt new file mode 100644 index 0000000..2afd79d --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesArchivedScreenPreview.kt @@ -0,0 +1,39 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.util.AppConstants.ARCHIVED_INDEX +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListState +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.RepliesScreen +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun RepliesArchivedScreenPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + RepliesScreen( + pageIndex = ARCHIVED_INDEX, + state = ReplyListState( + isLoading = false, + archivedReplies = Replies.Archived.replies + ), + onIntent = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun RepliesArchivedScreenDarkPreview() { + ReplyRadarPreviewWrapper(darkTheme = true) { + RepliesScreen( + pageIndex = ARCHIVED_INDEX, + state = ReplyListState( + isLoading = false, + archivedReplies = Replies.Archived.replies + ), + onIntent = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesOnTheRadarScreenPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesOnTheRadarScreenPreview.kt new file mode 100644 index 0000000..470007f --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesOnTheRadarScreenPreview.kt @@ -0,0 +1,43 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.util.AppConstants.ON_THE_RADAR_INDEX +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListState +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.RepliesScreen +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun RepliesScreenPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + RepliesScreen( + pageIndex = ON_THE_RADAR_INDEX, + state = ReplyListState( + isLoading = false, + replies = Replies.OnTheRadar.replies + ), + onIntent = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun RepliesScreenDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + RepliesScreen( + pageIndex = ON_THE_RADAR_INDEX, + state = ReplyListState( + isLoading = false, + replies = Replies.OnTheRadar.replies + ), + onIntent = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesResolvedScreenPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesResolvedScreenPreview.kt new file mode 100644 index 0000000..62bbf25 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/RepliesResolvedScreenPreview.kt @@ -0,0 +1,43 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.util.AppConstants.RESOLVED_INDEX +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListState +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.RepliesScreen +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun RepliesResolvedScreenPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + RepliesScreen( + pageIndex = RESOLVED_INDEX, + state = ReplyListState( + isLoading = false, + resolvedReplies = Replies.Resolved.replies + ), + onIntent = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun RepliesResolvedScreenDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + RepliesScreen( + pageIndex = RESOLVED_INDEX, + state = ReplyListState( + isLoading = false, + resolvedReplies = Replies.Resolved.replies + ), + onIntent = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyBottomSheetActionsPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyBottomSheetActionsPreview.kt new file mode 100644 index 0000000..605f99b --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyBottomSheetActionsPreview.kt @@ -0,0 +1,107 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetActions +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetMode +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetState +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetActionsPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyBottomSheetActions( + state = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.CREATE + ), + onArchive = {}, + onResolve = {}, + onDelete = {}, + onSave = {}, + onInvalidReminderValue = {}, + selectedDate = null, + selectedTime = null, + reply = null, + name = "", + subject = "" + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetActionsPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyBottomSheetActions( + state = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.EDIT, + reply = Replies.OnTheRadar.reply1 + ), + onArchive = {}, + onResolve = {}, + onDelete = {}, + onSave = {}, + onInvalidReminderValue = {}, + selectedDate = null, + selectedTime = null, + reply = null, + name = Replies.OnTheRadar.reply1.name, + subject = Replies.OnTheRadar.reply1.subject + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetActionsDarkPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyBottomSheetActions( + state = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.CREATE + ), + onArchive = {}, + onResolve = {}, + onDelete = {}, + onSave = {}, + onInvalidReminderValue = {}, + selectedDate = null, + selectedTime = null, + reply = null, + name = "", + subject = "" + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetActionsDarkPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyBottomSheetActions( + state = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.EDIT, + reply = Replies.OnTheRadar.reply1 + ), + onArchive = {}, + onResolve = {}, + onDelete = {}, + onSave = {}, + onInvalidReminderValue = {}, + selectedDate = null, + selectedTime = null, + reply = null, + name = Replies.OnTheRadar.reply1.name, + subject = Replies.OnTheRadar.reply1.subject + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyBottomSheetContentPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyBottomSheetContentPreview.kt new file mode 100644 index 0000000..814806c --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyBottomSheetContentPreview.kt @@ -0,0 +1,87 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetContent +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetMode +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetState +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetContentPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyBottomSheetContent( + replyBottomSheetState = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.CREATE + ), + onSave = {}, + onResolve = {}, + onArchive = {}, + onDelete = {}, + onInvalidReminderValue = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetContentPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyBottomSheetContent( + replyBottomSheetState = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.EDIT, + reply = Replies.OnTheRadar.reply1 + ), + onSave = {}, + onResolve = {}, + onArchive = {}, + onDelete = {}, + onInvalidReminderValue = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetContentDarkPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyBottomSheetContent( + replyBottomSheetState = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.CREATE + ), + onSave = {}, + onResolve = {}, + onArchive = {}, + onDelete = {}, + onInvalidReminderValue = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyBottomSheetContentDarkPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyBottomSheetContent( + replyBottomSheetState = ReplyBottomSheetState( + replyBottomSheetMode = ReplyBottomSheetMode.EDIT, + reply = Replies.OnTheRadar.reply1 + ), + onSave = {}, + onResolve = {}, + onArchive = {}, + onDelete = {}, + onInvalidReminderValue = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyButtonPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyButtonPreview.kt new file mode 100644 index 0000000..977397d --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyButtonPreview.kt @@ -0,0 +1,52 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyButton +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyButtonPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyButton( + modifier = Modifier, + text = "Button", + onClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyButtonDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyButton( + modifier = Modifier, + text = "Button", + onClick = {} + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyConfirmationDialogPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyConfirmationDialogPreview.kt new file mode 100644 index 0000000..5e01c0a --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyConfirmationDialogPreview.kt @@ -0,0 +1,51 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyConfirmationDialog +import com.rafaelfelipeac.replyradar.core.util.format +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +@Preview +@Composable +fun ReplyConfirmationDialogPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyConfirmationDialog( + title = PreviewStringsFake.replyListDeleteDialogTitle, + description = + format( + PreviewStringsFake.replyListDeleteDialogDescription, + Replies.OnTheRadar.reply1.name + ), + confirm = PreviewStringsFake.replyListDeleteDialogConfirm, + dismiss = PreviewStringsFake.replyListDeleteDialogDismiss, + onDismiss = {}, + onConfirm = {} + ) + } +} + +@Preview +@Composable +fun ReplyConfirmationDialogDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyConfirmationDialog( + title = PreviewStringsFake.replyListDeleteDialogTitle, + description = + format( + PreviewStringsFake.replyListDeleteDialogDescription, + Replies.OnTheRadar.reply1.name + ), + confirm = PreviewStringsFake.replyListDeleteDialogConfirm, + dismiss = PreviewStringsFake.replyListDeleteDialogDismiss, + onDismiss = {}, + onConfirm = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyListItemPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyListItemPreview.kt new file mode 100644 index 0000000..7d6343e --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyListItemPreview.kt @@ -0,0 +1,63 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.ReplyListItem +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyListItemPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListItem( + reply = Replies.OnTheRadar.reply1, + onClick = {}, + onToggle = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListItemPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListItem( + reply = Replies.OnTheRadar.reply2, + onClick = {}, + onToggle = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListItemDarkPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListItem( + reply = Replies.OnTheRadar.reply1, + onClick = {}, + onToggle = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListItemDarkPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListItem( + reply = Replies.OnTheRadar.reply2, + onClick = {}, + onToggle = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyListPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyListPreview.kt new file mode 100644 index 0000000..464ddfa --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyListPreview.kt @@ -0,0 +1,47 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.ReplyList +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyListPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.background) + ) { + ReplyList( + replies = Replies.OnTheRadar.replies, + onReplyClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.background) + ) { + ReplyList( + replies = Replies.OnTheRadar.replies, + onReplyClick = {} + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyNotificationPermissionDialogPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyNotificationPermissionDialogPreview.kt new file mode 100644 index 0000000..a9bb825 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyNotificationPermissionDialogPreview.kt @@ -0,0 +1,32 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.NotificationPermissionDialog +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview +@Composable +fun ReplyNotificationPermissionDialogPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + NotificationPermissionDialog( + onDismiss = {}, + onGoToSettings = {} + ) + } +} + +@Preview +@Composable +fun ReplyNotificationPermissionDialogDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + NotificationPermissionDialog( + onDismiss = {}, + onGoToSettings = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyOutlinedButtonPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyOutlinedButtonPreview.kt new file mode 100644 index 0000000..44d39e4 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyOutlinedButtonPreview.kt @@ -0,0 +1,175 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyOutlinedButton +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake +import replyradar.composeapp.generated.resources.Res +import replyradar.composeapp.generated.resources.ic_archive +import replyradar.composeapp.generated.resources.ic_check +import replyradar.composeapp.generated.resources.ic_delete +import replyradar.composeapp.generated.resources.ic_reopen +import replyradar.composeapp.generated.resources.ic_unarchive + +@Preview(showBackground = true) +@Composable +fun ReplyOutlinedButtonActiveStatePreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Row( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetResolve, + icon = Res.drawable.ic_check, + onClick = {} + ) + + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetArchive, + icon = Res.drawable.ic_archive, + onClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyOutlinedButtonResolvedStatePreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Row( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetReopen, + icon = Res.drawable.ic_reopen, + onClick = {} + ) + + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetArchive, + icon = Res.drawable.ic_archive, + onClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyOutlinedButtonArchivedStatePreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Row( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetUnarchive, + icon = Res.drawable.ic_unarchive, + onClick = {} + ) + + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetDelete, + icon = Res.drawable.ic_delete, + onClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyOutlinedButtonActiveStateDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Row( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetResolve, + icon = Res.drawable.ic_check, + onClick = {} + ) + + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetArchive, + icon = Res.drawable.ic_archive, + onClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyOutlinedButtonResolvedStateDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Row( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetReopen, + icon = Res.drawable.ic_reopen, + onClick = {} + ) + + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetArchive, + icon = Res.drawable.ic_archive, + onClick = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyOutlinedButtonArchivedStateDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Row( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetUnarchive, + icon = Res.drawable.ic_unarchive, + onClick = {} + ) + + ReplyOutlinedButton( + text = PreviewStringsFake.replyListBottomSheetDelete, + icon = Res.drawable.ic_delete, + onClick = {} + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyProgressPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyProgressPreview.kt new file mode 100644 index 0000000..c6dc2b3 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyProgressPreview.kt @@ -0,0 +1,47 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +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.rafaelfelipeac.replyradar.core.common.ui.components.ReplyProgress +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyProgressPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.background) + .padding(16.dp), + contentAlignment = Alignment.Center + ) { + ReplyProgress() + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyProgressDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.background) + .padding(16.dp), + contentAlignment = Alignment.Center + ) { + ReplyProgress() + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRadarErrorPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRadarErrorPreview.kt new file mode 100644 index 0000000..fcf2cc0 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRadarErrorPreview.kt @@ -0,0 +1,80 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyRadarError +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyRadarErrorPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.surface), + contentAlignment = Alignment.Center + ) { + ReplyRadarError() + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyRadarErrorPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.surface), + contentAlignment = Alignment.Center + ) { + ReplyRadarError("Custom error message.") + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyRadarErrorDarkPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.surface), + contentAlignment = Alignment.Center + ) { + ReplyRadarError() + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyRadarErrorDarkPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.surface), + contentAlignment = Alignment.Center + ) { + ReplyRadarError("Custom error message.") + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRadarPlaceholderPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRadarPlaceholderPreview.kt new file mode 100644 index 0000000..5a370f3 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRadarPlaceholderPreview.kt @@ -0,0 +1,51 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyRadarPlaceholder +import com.rafaelfelipeac.replyradar.core.strings.LocalReplyRadarStrings +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyRadarPlaceholderPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.background), + contentAlignment = Alignment.Center + ) { + ReplyRadarPlaceholder( + message = LocalReplyRadarStrings.current.replyListPlaceholderOnTheRadar + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyRadarPlaceholderDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.background), + contentAlignment = Alignment.Center + ) { + ReplyRadarPlaceholder( + message = LocalReplyRadarStrings.current.replyListPlaceholderOnTheRadar + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyReminderPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyReminderPreview.kt new file mode 100644 index 0000000..8b96af5 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyReminderPreview.kt @@ -0,0 +1,47 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyReminder +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import kotlinx.datetime.Clock +import kotlinx.datetime.TimeZone +import kotlinx.datetime.toLocalDateTime + +@Preview(showBackground = true) +@Composable +fun ReplyReminderPreview() { + val now = Clock.System.now().toLocalDateTime(TimeZone.currentSystemDefault()) + + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + // ReminderText wasn't showing in Preview because the icon row was collapsing the layout. + ReplyReminder( + selectedTime = now.time, + selectedDate = now.date, + onSelectedTimeChange = {}, + onSelectedDateChange = {}, + closeKeyboard = { } + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyReminderDarkPreview() { + val now = Clock.System.now().toLocalDateTime(TimeZone.currentSystemDefault()) + + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + // ReminderText wasn't showing in Preview because the icon row was collapsing the layout. + ReplyReminder( + selectedTime = now.time, + selectedDate = now.date, + onSelectedTimeChange = {}, + onSelectedDateChange = {}, + closeKeyboard = { } + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRoundedCornerPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRoundedCornerPreview.kt new file mode 100644 index 0000000..1c3339c --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyRoundedCornerPreview.kt @@ -0,0 +1,46 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.size +import androidx.compose.material3.MaterialTheme.colorScheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyRoundedCorner +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview +@Composable +fun ReplyRoundedCornerPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .size(100.dp) + .background( + color = colorScheme.primary, + shape = ReplyRoundedCorner() + ) + ) + } +} + +@Preview +@Composable +fun ReplyRoundedCornerDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .size(100.dp) + .background( + color = colorScheme.primary, + shape = ReplyRoundedCorner() + ) + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplySnackbarPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplySnackbarPreview.kt new file mode 100644 index 0000000..0d16886 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplySnackbarPreview.kt @@ -0,0 +1,62 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme.colorScheme +import androidx.compose.material3.Snackbar +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.rafaelfelipeac.replyradar.core.theme.snackbarBackgroundColor +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +// ReplySnackbar can't be used directly in Preview because SnackbarHostState requires an active SnackbarData, +// which is only created at runtime via showSnackbar() inside a coroutine. +// Since @Preview doesn't execute effects like LaunchedEffect, no snackbar is shown. +// This manually simulates the visual result of ReplySnackbar. + +@Preview(showBackground = true) +@Composable +fun ReplySnackbarPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .background(colorScheme.onSurface) + .padding(4.dp) + ) { + Snackbar( + containerColor = colorScheme.snackbarBackgroundColor, + contentColor = colorScheme.onSurface + ) { + Text(PreviewStringsFake.replyListSnackbarResolved) + } + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplySnackbarDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .background(colorScheme.onSurface) + .padding(4.dp) + ) { + Snackbar( + containerColor = colorScheme.snackbarBackgroundColor, + contentColor = colorScheme.onSurface + ) { + Text(PreviewStringsFake.replyListSnackbarResolved) + } + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTabPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTabPreview.kt new file mode 100644 index 0000000..c7f6e5b --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTabPreview.kt @@ -0,0 +1,216 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.TabRow +import androidx.compose.material3.TabRowDefaults +import androidx.compose.material3.TabRowDefaults.tabIndicatorOffset +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyTab +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +@Preview(showBackground = true) +@Composable +fun ReplyTabOnTheRadarPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + TabRow( + selectedTabIndex = 0, + containerColor = MaterialTheme.colorScheme.background, + indicator = { tabPositions -> + TabRowDefaults.SecondaryIndicator( + modifier = Modifier.tabIndicatorOffset(tabPositions[0]), + color = MaterialTheme.colorScheme.secondary + ) + } + ) { + ReplyTab( + selected = true, + onClick = {}, + text = PreviewStringsFake.replyListTabOnTheRadar + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabResolved + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabArchived + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTabDarkOnTheRadarPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + TabRow( + selectedTabIndex = 0, + containerColor = MaterialTheme.colorScheme.background, + indicator = { tabPositions -> + TabRowDefaults.SecondaryIndicator( + modifier = Modifier.tabIndicatorOffset(tabPositions[0]), + color = MaterialTheme.colorScheme.secondary + ) + } + ) { + ReplyTab( + selected = true, + onClick = {}, + text = PreviewStringsFake.replyListTabOnTheRadar + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabResolved + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabArchived + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTabResolvedPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + TabRow( + selectedTabIndex = 1, + containerColor = MaterialTheme.colorScheme.background, + indicator = { tabPositions -> + TabRowDefaults.SecondaryIndicator( + modifier = Modifier.tabIndicatorOffset(tabPositions[1]), + color = MaterialTheme.colorScheme.secondary + ) + } + ) { + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabOnTheRadar + ) + ReplyTab( + selected = true, + onClick = {}, + text = PreviewStringsFake.replyListTabResolved + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabArchived + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTabDarkResolvedPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + TabRow( + selectedTabIndex = 1, + containerColor = MaterialTheme.colorScheme.background, + indicator = { tabPositions -> + TabRowDefaults.SecondaryIndicator( + modifier = Modifier.tabIndicatorOffset(tabPositions[1]), + color = MaterialTheme.colorScheme.secondary + ) + } + ) { + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabOnTheRadar + ) + ReplyTab( + selected = true, + onClick = {}, + text = PreviewStringsFake.replyListTabResolved + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabArchived + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTabArchivedPreview() { + ReplyRadarPreviewWrapper(darkTheme = false) { + TabRow( + selectedTabIndex = 2, + containerColor = MaterialTheme.colorScheme.background, + indicator = { tabPositions -> + TabRowDefaults.SecondaryIndicator( + modifier = Modifier.tabIndicatorOffset(tabPositions[2]), + color = MaterialTheme.colorScheme.secondary + ) + } + ) { + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabOnTheRadar + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabResolved + ) + ReplyTab( + selected = true, + onClick = {}, + text = PreviewStringsFake.replyListTabArchived + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTabDarkArchivedPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + TabRow( + selectedTabIndex = 2, + containerColor = MaterialTheme.colorScheme.background, + indicator = { tabPositions -> + TabRowDefaults.SecondaryIndicator( + modifier = Modifier.tabIndicatorOffset(tabPositions[2]), + color = MaterialTheme.colorScheme.secondary + ) + } + ) { + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabOnTheRadar + ) + ReplyTab( + selected = false, + onClick = {}, + text = PreviewStringsFake.replyListTabResolved + ) + ReplyTab( + selected = true, + onClick = {}, + text = PreviewStringsFake.replyListTabArchived + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTextFieldPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTextFieldPreview.kt new file mode 100644 index 0000000..1f75a0e --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTextFieldPreview.kt @@ -0,0 +1,64 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyTextField +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +@Preview(showBackground = true) +@Composable +fun ReplyTextFieldPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyTextField( + value = Replies.OnTheRadar.reply1.name, + placeholder = PreviewStringsFake.replyListBottomSheetName, + onValueChange = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTextFieldPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyTextField( + value = "", + placeholder = PreviewStringsFake.replyListBottomSheetName, + onValueChange = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTextFieldDarkPreview1() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyTextField( + value = "", + placeholder = PreviewStringsFake.replyListBottomSheetName, + onValueChange = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTextFieldDarkPreview2() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyTextField( + value = Replies.OnTheRadar.reply1.name, + placeholder = PreviewStringsFake.replyListBottomSheetName, + onValueChange = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTimestampInfoPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTimestampInfoPreview.kt new file mode 100644 index 0000000..cc8e8fd --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTimestampInfoPreview.kt @@ -0,0 +1,50 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Column +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.ReplyTimestampInfo +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet.ReplyBottomSheetState +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyTimestampInfoPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Column( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + ) { + ReplyTimestampInfo( + state = ReplyBottomSheetState( + reply = Replies.OnTheRadar.reply1 + ) + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyTimestampInfoDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Column( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + ) { + ReplyTimestampInfo( + state = ReplyBottomSheetState( + reply = Replies.OnTheRadar.reply1 + ) + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTogglePreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTogglePreview.kt new file mode 100644 index 0000000..c62dfc0 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/ReplyTogglePreview.kt @@ -0,0 +1,50 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.rafaelfelipeac.replyradar.core.common.ui.components.ReplyToggle +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun ReplyTogglePreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyToggle( + isResolved = false, + onToggle = {} + ) + } + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyToggleDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + Box( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(8.dp) + ) { + ReplyToggle( + isResolved = false, + onToggle = {} + ) + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/TopBarPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/TopBarPreview.kt new file mode 100644 index 0000000..5f72271 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/components/TopBarPreview.kt @@ -0,0 +1,32 @@ +package com.rafaelfelipeac.replyradar.previews.components + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.TopBar +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper + +@Preview(showBackground = true) +@Composable +fun TopBarPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + TopBar( + onActivityLogClick = {}, + onSettingsClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun TopBarDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + TopBar( + onActivityLogClick = {}, + onSettingsClick = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/ActivityLogScreenPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/ActivityLogScreenPreview.kt new file mode 100644 index 0000000..0d4ccae --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/ActivityLogScreenPreview.kt @@ -0,0 +1,72 @@ +package com.rafaelfelipeac.replyradar.previews.screens + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.activitylog.presentation.ActivityLogScreen +import com.rafaelfelipeac.replyradar.features.activitylog.presentation.ActivityLogState +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.previewActivityLogItems + +@Preview(showBackground = true) +@Composable +fun ActivityLogScreenEmptyPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ActivityLogScreen( + state = ActivityLogState( + isLoading = false, + activityLogItems = emptyList() + ), + onBackClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ActivityLogScreenPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ActivityLogScreen( + state = ActivityLogState( + isLoading = false, + activityLogItems = previewActivityLogItems + ), + onBackClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ActivityLogScreenEmptyDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ActivityLogScreen( + state = ActivityLogState( + isLoading = false, + activityLogItems = emptyList() + ), + onBackClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ActivityLogScreenDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ActivityLogScreen( + state = ActivityLogState( + isLoading = false, + activityLogItems = previewActivityLogItems + ), + onBackClick = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/ReplyListScreenPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/ReplyListScreenPreview.kt new file mode 100644 index 0000000..d35ddaf --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/ReplyListScreenPreview.kt @@ -0,0 +1,254 @@ +package com.rafaelfelipeac.replyradar.previews.screens + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListScreen +import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListState +import com.rafaelfelipeac.replyradar.previews.shared.Replies +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import kotlinx.coroutines.flow.emptyFlow + +// Note: We're not using @PreviewParameter here due to limitations in Compose Preview when used in Kotlin Multiplatform (KMP). +// Although @PreviewParameter is ideal for generating multiple previews from a provider, it causes runtime errors (NPE) +// in KMP projects because the IDE tries to invoke the function without a parameter. +// As a workaround, we use separate @Preview-annotated functions with hardcoded configurations instead. + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenOnTheRadarEmptyPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 0, + isLoading = false, + replies = emptyList() + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenOnTheRadarPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 0, + isLoading = false, + replies = Replies.OnTheRadar.replies + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenResolvedEmptyPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 1, + isLoading = false, + resolvedReplies = emptyList() + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenResolvedPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 1, + isLoading = false, + resolvedReplies = Replies.Resolved.replies + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenArchivedEmptyPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 2, + isLoading = false, + archivedReplies = emptyList() + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenArchivedPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 2, + isLoading = false, + archivedReplies = Replies.Archived.replies + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenOnTheRadarEmptyDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 0, + isLoading = false, + replies = emptyList() + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenOnTheRadarDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 0, + isLoading = false, + replies = Replies.OnTheRadar.replies + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenResolvedEmptyDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 1, + isLoading = false, + resolvedReplies = emptyList() + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenResolvedDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 1, + isLoading = false, + resolvedReplies = Replies.Resolved.replies + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenArchivedEmptyDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 2, + isLoading = false, + archivedReplies = emptyList() + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} + +@Preview(showBackground = true) +@Composable +fun ReplyListScreenArchivedDarkPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + ReplyListScreen( + state = ReplyListState( + selectedTabIndex = 2, + isLoading = false, + archivedReplies = Replies.Archived.replies + ), + effect = emptyFlow(), + onIntent = {}, + onSettingsClick = {}, + onActivityLogClick = {} + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/SettingsScreenPreview.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/SettingsScreenPreview.kt new file mode 100644 index 0000000..5f0cabf --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/screens/SettingsScreenPreview.kt @@ -0,0 +1,51 @@ +package com.rafaelfelipeac.replyradar.previews.screens + +import androidx.compose.runtime.Composable +import androidx.compose.ui.tooling.preview.Preview +import com.rafaelfelipeac.replyradar.core.language.AppLanguage.ENGLISH +import com.rafaelfelipeac.replyradar.core.theme.model.AppTheme.DARK +import com.rafaelfelipeac.replyradar.core.theme.model.AppTheme.LIGHT +import com.rafaelfelipeac.replyradar.features.settings.presentation.SettingsScreen +import com.rafaelfelipeac.replyradar.features.settings.presentation.SettingsState +import com.rafaelfelipeac.replyradar.previews.shared.ReplyRadarPreviewWrapper +import com.rafaelfelipeac.replyradar.previews.shared.appVersion + +@Preview(showBackground = true) +@Composable +fun SettingsScreenEnglishPreview() { + ReplyRadarPreviewWrapper( + darkTheme = false + ) { + SettingsScreen( + state = SettingsState( + theme = LIGHT, + language = ENGLISH, + isLoading = false + ), + onBackClick = {}, + onActivityLogClick = {}, + onIntent = {}, + appVersion = appVersion + ) + } +} + +@Preview(showBackground = true) +@Composable +fun SettingsScreenDarkEnglishPreview() { + ReplyRadarPreviewWrapper( + darkTheme = true + ) { + SettingsScreen( + state = SettingsState( + theme = DARK, + language = ENGLISH, + isLoading = false + ), + onBackClick = {}, + onActivityLogClick = {}, + onIntent = {}, + appVersion = appVersion + ) + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/ReplyRadarPreviewWrapper.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/ReplyRadarPreviewWrapper.kt new file mode 100644 index 0000000..e981746 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/ReplyRadarPreviewWrapper.kt @@ -0,0 +1,21 @@ +package com.rafaelfelipeac.replyradar.previews.shared + +import androidx.compose.runtime.Composable +import androidx.compose.runtime.CompositionLocalProvider +import com.rafaelfelipeac.replyradar.core.notification.LocalNotificationPermissionManager +import com.rafaelfelipeac.replyradar.core.strings.LocalReplyRadarStrings +import com.rafaelfelipeac.replyradar.core.theme.ReplyRadarTheme +import com.rafaelfelipeac.replyradar.previews.shared.fakes.FakeNotificationPermissionManager +import com.rafaelfelipeac.replyradar.previews.shared.fakes.PreviewStringsFake + +@Composable +fun ReplyRadarPreviewWrapper(darkTheme: Boolean = false, content: @Composable () -> Unit) { + CompositionLocalProvider( + LocalReplyRadarStrings provides PreviewStringsFake, + LocalNotificationPermissionManager provides FakeNotificationPermissionManager() + ) { + ReplyRadarTheme(darkTheme = darkTheme) { + content() + } + } +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/Shared.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/Shared.kt new file mode 100644 index 0000000..daef753 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/Shared.kt @@ -0,0 +1,206 @@ +package com.rafaelfelipeac.replyradar.previews.shared + +import com.rafaelfelipeac.replyradar.features.reply.domain.model.Reply +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserAction +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionTargetType +import com.rafaelfelipeac.replyradar.features.useractions.domain.model.UserActionType + +const val appVersion = "1.0.0 - Preview" + +sealed class Replies { + + data object OnTheRadar : Replies() { + val reply1 = Reply( + id = 1, + name = "Lucas Almeida", + subject = "Wanna grab coffee sometime?", + createdAt = 1741120800000L + ) + val reply2 = Reply( + id = 2, + name = "Sofia Ribeiro", + subject = "Update on Monday's project" + ) + val reply3 = Reply( + id = 3, + name = "Thiago Martins", + subject = "Did you get a chance to check the contract?" + ) + val reply4 = Reply( + id = 4, + name = "Marina Costa", + subject = "You're invited to my birthday 🎉" + ) + val reply5 = Reply( + id = 5, + name = "Diego Fernandes", + subject = "Meeting moved to Friday, okay?" + ) + + val replies = listOf(reply1, reply2, reply3, reply4, reply5) + } + + data object Resolved : Replies() { + val reply1 = Reply( + id = 1, + name = "Lucas Almeida", + subject = "Wanna grab coffee sometime?", + isResolved = true, + createdAt = 1741120800000L, + resolvedAt = 1741120800000L + ) + val reply2 = Reply( + id = 2, + name = "Sofia Ribeiro", + subject = "Update on Monday's project", + isResolved = true + ) + val reply3 = Reply( + id = 3, + name = "Thiago Martins", + subject = "Did you get a chance to check the contract?", + isResolved = true + ) + val reply4 = Reply( + id = 4, + name = "Marina Costa", + subject = "You're invited to my birthday 🎉", + isResolved = true + ) + val reply5 = Reply( + id = 5, + name = "Diego Fernandes", + subject = "Meeting moved to Friday, okay?", + isResolved = true + ) + + val replies = listOf(reply1, reply2, reply3, reply4, reply5) + } + + data object Archived : Replies() { + val reply1 = Reply( + id = 1, + name = "Lucas Almeida", + subject = "Wanna grab coffee sometime?", + isArchived = true, + isResolved = true, + createdAt = 1741120800000L, + resolvedAt = 1741120800000L, + archivedAt = 1741120800000L + ) + val reply2 = Reply( + id = 2, + name = "Sofia Ribeiro", + subject = "Update on Monday's project", + isArchived = true + ) + val reply3 = Reply( + id = 3, + name = "Thiago Martins", + subject = "Did you get a chance to check the contract?", + isArchived = true, + isResolved = true + ) + val reply4 = Reply( + id = 4, + name = "Marina Costa", + subject = "You're invited to my birthday 🎉", + isArchived = true + ) + val reply5 = Reply( + id = 5, + name = "Diego Fernandes", + subject = "Meeting moved to Friday, okay?", + isArchived = true + ) + + val replies = listOf(reply1, reply2, reply3, reply4, reply5) + } +} + +val previewActivityLogItems = listOf( + UserAction( + id = 1L, + actionType = UserActionType.Create, + targetType = UserActionTargetType.Message, + targetName = "Lucas Almeida", + createdAt = System.currentTimeMillis() + ), + UserAction( + id = 2L, + actionType = UserActionType.Edit, + targetType = UserActionTargetType.Message, + targetName = "Carla Mendes", + createdAt = System.currentTimeMillis() - 1_000_000L + ), + UserAction( + id = 3L, + actionType = UserActionType.Resolve, + targetType = UserActionTargetType.Message, + targetName = "João Victor", + createdAt = System.currentTimeMillis() - 2_000_000L + ), + UserAction( + id = 4L, + actionType = UserActionType.Archive, + targetType = UserActionTargetType.Message, + targetName = "Ana Paula", + createdAt = System.currentTimeMillis() - 3_000_000L + ), + UserAction( + id = 5L, + actionType = UserActionType.OpenedNotification, + targetType = UserActionTargetType.Message, + targetName = "Marcelo Costa", + createdAt = System.currentTimeMillis() - 4_000_000L + ), + UserAction( + id = 6L, + actionType = UserActionType.Open, + targetType = UserActionTargetType.Message, + targetName = "Beatriz Rocha", + createdAt = System.currentTimeMillis() - 5_000_000L + ), + UserAction( + id = 7L, + actionType = UserActionType.Delete, + targetType = UserActionTargetType.Message, + targetName = "Henrique Silva", + createdAt = System.currentTimeMillis() - 6_000_000L + ), + UserAction( + id = 8L, + actionType = UserActionType.Scheduled, + targetType = UserActionTargetType.Message, + targetName = "Fernanda Luz", + createdAt = System.currentTimeMillis() - 7_000_000L + ), + UserAction( + id = 9L, + actionType = UserActionType.Create, + targetType = UserActionTargetType.Feedback, + targetName = null, + createdAt = System.currentTimeMillis() - 8_000_000L + ), + UserAction( + id = 10L, + actionType = UserActionType.Create, + targetType = UserActionTargetType.Language, + targetName = null, + createdAt = System.currentTimeMillis() - 9_000_000L + ), + UserAction( + id = 11L, + actionType = UserActionType.Create, + targetType = UserActionTargetType.Theme, + targetName = null, + createdAt = System.currentTimeMillis() - 10_000_000L + ), + UserAction( + id = 12L, + actionType = UserActionType.Create, + targetType = UserActionTargetType.Rate, + targetName = null, + createdAt = System.currentTimeMillis() - 11_000_000L + ) +) diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/fakes/FakeNotificationPermissionManager.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/fakes/FakeNotificationPermissionManager.kt new file mode 100644 index 0000000..9ab2efd --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/fakes/FakeNotificationPermissionManager.kt @@ -0,0 +1,9 @@ +package com.rafaelfelipeac.replyradar.previews.shared.fakes + +import com.rafaelfelipeac.replyradar.core.notification.NotificationPermissionManager + +@Suppress("EmptyFunctionBlock") +class FakeNotificationPermissionManager : NotificationPermissionManager { + override suspend fun ensureNotificationPermission(): Boolean = true + override suspend fun goToAppSettings() {} +} diff --git a/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/fakes/PreviewStringsFake.kt b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/fakes/PreviewStringsFake.kt new file mode 100644 index 0000000..cc5f8a1 --- /dev/null +++ b/composeApp/src/androidMain/kotlin/com/rafaelfelipeac/replyradar/previews/shared/fakes/PreviewStringsFake.kt @@ -0,0 +1,128 @@ +package com.rafaelfelipeac.replyradar.previews.shared.fakes + +import com.rafaelfelipeac.replyradar.core.strings.Strings + +// ktlint-disable max-line-length +@Suppress("MaxLineLength") +object PreviewStringsFake : Strings { + override val appName = "Reply Radar" + + override val genericErrorMessage = "An unexpected error occurred." + + override val replyListActivityLog = "Activity Log" + override val replyListTabOnTheRadar = "On the Radar" + override val replyListTabResolved = "Resolved" + override val replyListTabArchived = "Archived" + override val replyListPlaceholderOnTheRadar = + "Nothing on the radar for now!\nHow about adding something?" + override val replyListGetRepliesError = "Failed to load your replies. Please try again." + override val replyListPlaceholderResolved = + "No resolved replies yet.\nTime to get something done?" + override val replyListPlaceholderArchived = + "Archive’s looking empty!\nTime to clear your radar?" + override val replyListBottomSheetName = "Name" + override val replyListBottomSheetSubject = "Subject" + override val replyListBottomSheetAdd = "Add" + override val replyListBottomSheetSave = "Save" + override val replyListBottomSheetResolve = "Resolve" + override val replyListBottomSheetReopen = "Reopen" + override val replyListBottomSheetArchive = "Archive" + override val replyListBottomSheetUnarchive = "Unarchive" + override val replyListBottomSheetDelete = "Delete" + override val replyListItemResolve = "Resolve" + override val replyListItemCreatedAt = "Created at: %1" + override val replyListItemUpdatedAt = "Updated at: %1" + override val replyListItemResolvedAt = "Resolved at: %1" + override val replyListItemArchivedAt = "Archived at: %1" + override val replyListFabContentDescription = "Add a new reply to your radar." + override val replyListDeleteDialogTitle = "Are you sure?" + override val replyListDeleteDialogDescription = "This action will permanently delete \"%1\" and cannot be undone." + override val replyListDeleteDialogConfirm = "Delete" + override val replyListDeleteDialogDismiss = "Cancel" + override val replyListSnackbarArchived = "Item successfully archived." + override val replyListSnackbarRemoved = "Item permanently deleted." + override val replyListSnackbarReopened = "Item reopened and back on the radar." + override val replyListSnackbarResolved = "Item marked as resolved." + override val replyListSnackbarUnarchived = "Item successfully unarchived." + override val replyListReminder = "Reminder" + override val replyListReminderSet = "Reminder set for:" + override val replyListReminderSetSeparator = "%1 at %2" + override val replyListReminderToday = "today" + override val replyListReminderTomorrow = "tomorrow" + override val replyListReminderTimeIconContentDescription = "Time" + override val replyListReminderDateIconContentDescription = "Date" + override val replyListReminderCloseIconContentDescription = "Close" + override val replyListReminderInvalidDateTime = "The selected date and time has already passed." + override val replyListReminderTimePickerTitle = "Select time" + override val replyListReminderTimePickerConfirmButton = "OK" + override val replyListReminderTimePickerDismissButton = "Cancel" + override val replyListReminderDatePickerConfirmButton = "OK" + override val replyListReminderDatePickerDismissButton = "Cancel" + + override val settingsTitle = "Settings" + override val settingsBackButton = "Back" + override val settingsTheme = "Theme" + override val settingsThemeLight = "Light" + override val settingsThemeDark = "Dark" + override val settingsThemeSystem = "Use system default" + override val settingsLanguage = "Language" + override val settingsLanguageEnglish = "English" + override val settingsLanguagePortuguese = "Portuguese" + override val settingsLanguageGerman = "German" + override val settingsLanguageFrench = "French" + override val settingsLanguageSpanish = "Spanish" + override val settingsLanguageSystem = "Use system default" + override val settingsFeedbackTitle = "Feedback" + override val settingsFeedbackDescription = + "Send us an email with questions, suggestions or to report a bug. Your feedback helps make Reply Radar better!" + override val settingsFeedbackEmailSubject = "Reply Radar - Feedback & Suggestions" + override val settingsFeedbackEmailBody = """ +Hello! + +Feel free to share your questions, suggestions or report a bug. + +All feedback is very welcome :) + +--- + +App version: 1.0.0-dev + """.trimIndent() + override val settingsRateTitle = "Rate the app" + override val settingsRateDescription = + "Enjoying Reply Radar? Leave a review on the Play Store and help others discover the app!" + override val settingsAppVersion = "Reply Radar - Version:" + + override val activityLogTitle = "Activity Log" + override val activityLogBackButton = "Back" + override val activityLogItemContentDescription = "Activity log item" + override val activityLogPlaceholder = + "No activity just yet!\nYour radar’s waiting for some action." + override val activityLogGetActivityLogsError = + "Failed to load your activity log. Please try again." + override val activityLogMessageFormat = "You %1 %2" + override val activityLogMessageItem = "the item \"%1\"." + override val activityLogMessageItemRemoved = "an item that no longer exists." + override val activityLogUserActionArchiveVerb = "archived" + override val activityLogUserActionCreateVerb = "created" + override val activityLogUserActionDeleteVerb = "deleted" + override val activityLogUserActionEditVerb = "edited" + override val activityLogUserActionReopenVerb = "reopened" + override val activityLogUserActionResolveVerb = "resolved" + override val activityLogUserActionUnarchiveVerb = "unarchived" + override val activityLogUserActionOpenVerb = "opened" + override val activityLogUserActionScheduledVerb = "scheduled a reminder for" + override val activityLogUserActionOpenedNotificationVerb = "opened a notification for" + override val activityLogUserActionTheme = "You switched the app theme." + override val activityLogUserActionLanguage = "You changed the app language." + override val activityLogUserActionFeedback = "You gave feedback about the app." + override val activityLogUserActionRate = "You rated the app." + + override val notificationPermissionDialogTitle = "Notification Permission" + override val notificationPermissionDialogDescription = "To remind you to reply to your messages, we need permission to send notifications. \n\nYou can enable it in the app settings." + override val notificationPermissionDialogConfirmButton = "Open Settings" + override val notificationPermissionDialogDismissButton = "Got it" + override val notificationTitle = "Hey, how about replying to %1?" + override val notificationContent = "%1 is waiting for your reply about \"%2\"." + override val notificationContentWithoutSubject = "%1 is waiting for your reply." +} +// ktlint-enable max-line-length diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarError.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarError.kt index a973dc8..7499270 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarError.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarError.kt @@ -1,16 +1,22 @@ package com.rafaelfelipeac.replyradar.core.common.ui.components +import androidx.compose.foundation.background +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.MaterialTheme.typography import androidx.compose.material3.Text import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier import androidx.compose.ui.text.style.TextAlign import com.rafaelfelipeac.replyradar.core.strings.LocalReplyRadarStrings @Composable -fun ReplyRadarError(errorMessage: String?) { +fun ReplyRadarError(errorMessage: String? = null) { Text( + modifier = Modifier + .background(MaterialTheme.colorScheme.surface), text = errorMessage ?: LocalReplyRadarStrings.current.genericErrorMessage, textAlign = TextAlign.Center, - style = typography.headlineSmall + style = typography.headlineSmall, + color = MaterialTheme.colorScheme.onSurface ) } diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarPlaceholder.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarPlaceholder.kt index 824f7c8..54aa753 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarPlaceholder.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyRadarPlaceholder.kt @@ -1,6 +1,7 @@ package com.rafaelfelipeac.replyradar.core.common.ui.components import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.MaterialTheme.typography import androidx.compose.material3.Text import androidx.compose.runtime.Composable @@ -14,6 +15,7 @@ fun ReplyRadarPlaceholder(message: String) { modifier = Modifier .padding(horizontal = paddingMedium), text = message, + color = MaterialTheme.colorScheme.onSurface, textAlign = TextAlign.Center, style = typography.headlineSmall ) diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyReminder.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyReminder.kt index 3046273..f9535ac 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyReminder.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyReminder.kt @@ -1,5 +1,6 @@ package com.rafaelfelipeac.replyradar.core.common.ui.components +import androidx.compose.foundation.background import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.fillMaxWidth @@ -114,7 +115,8 @@ fun ReplyReminder( Row( modifier = Modifier .fillMaxWidth() - .padding(top = paddingSmall), + .padding(top = paddingSmall) + .background(colorScheme.surface), horizontalArrangement = Arrangement.Start ) { IconButton( @@ -167,7 +169,8 @@ private fun ReminderText(reminderText: String?, onDeleteClick: () -> Unit) { if (reminderText != null) { Row( modifier = Modifier - .fillMaxWidth(), + .fillMaxWidth() + .background(colorScheme.surface), horizontalArrangement = Arrangement.Start, verticalAlignment = Alignment.CenterVertically ) { @@ -175,7 +178,8 @@ private fun ReminderText(reminderText: String?, onDeleteClick: () -> Unit) { modifier = Modifier .padding(start = paddingSmall, top = paddingSmall), text = reminderText, - style = typography.bodySmall + style = typography.bodySmall, + color = colorScheme.onSurface ) IconButton( diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyTab.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyTab.kt index ef878ec..5f274b2 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyTab.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/common/ui/components/ReplyTab.kt @@ -10,7 +10,7 @@ import com.rafaelfelipeac.replyradar.core.common.ui.tabVerticalPadding import com.rafaelfelipeac.replyradar.core.theme.unselectedTabColor @Composable -fun ReplyTab(modifier: Modifier, selected: Boolean, onClick: () -> Unit, text: String) { +fun ReplyTab(modifier: Modifier = Modifier, selected: Boolean, onClick: () -> Unit, text: String) { Tab( modifier = modifier, selected = selected, diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/navigation/AppNavHost.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/navigation/AppNavHost.kt index 82ea131..a395557 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/navigation/AppNavHost.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/core/navigation/AppNavHost.kt @@ -13,11 +13,11 @@ import com.rafaelfelipeac.replyradar.core.navigation.Route.ActivityLog import com.rafaelfelipeac.replyradar.core.navigation.Route.ReplyGraph import com.rafaelfelipeac.replyradar.core.navigation.Route.ReplyList import com.rafaelfelipeac.replyradar.core.navigation.Route.Settings -import com.rafaelfelipeac.replyradar.features.activitylog.presentation.ActivityLogScreen +import com.rafaelfelipeac.replyradar.features.activitylog.presentation.ActivityLogScreenRoot import com.rafaelfelipeac.replyradar.features.activitylog.presentation.ActivityLogViewModel import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListScreenRoot import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListViewModel -import com.rafaelfelipeac.replyradar.features.settings.presentation.SettingsScreen +import com.rafaelfelipeac.replyradar.features.settings.presentation.SettingsScreenRoot import com.rafaelfelipeac.replyradar.features.settings.presentation.SettingsViewModel import org.koin.compose.viewmodel.koinViewModel @@ -52,7 +52,7 @@ fun AppNavHost(navController: NavHostController, pendingReplyId: Long?) { ) { val viewModel = koinViewModel() - SettingsScreen( + SettingsScreenRoot( viewModel = viewModel, onBackClick = { navController.popBackStack() }, onActivityLogClick = { navController.navigate(ActivityLog) } @@ -67,7 +67,7 @@ fun AppNavHost(navController: NavHostController, pendingReplyId: Long?) { ) { val viewModel = koinViewModel() - ActivityLogScreen( + ActivityLogScreenRoot( viewModel = viewModel, onBackClick = { navController.popBackStack() } ) diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/activitylog/presentation/ActivityLogScreen.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/activitylog/presentation/ActivityLogScreen.kt index cedaa37..61583f0 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/activitylog/presentation/ActivityLogScreen.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/activitylog/presentation/ActivityLogScreen.kt @@ -83,11 +83,22 @@ import replyradar.composeapp.generated.resources.ic_theme import replyradar.composeapp.generated.resources.ic_time import replyradar.composeapp.generated.resources.ic_unarchive -@OptIn(ExperimentalMaterial3Api::class) @Composable -fun ActivityLogScreen(viewModel: ActivityLogViewModel = koinViewModel(), onBackClick: () -> Unit) { +fun ActivityLogScreenRoot( + viewModel: ActivityLogViewModel = koinViewModel(), + onBackClick: () -> Unit +) { val state by viewModel.state.collectAsStateWithLifecycle() + ActivityLogScreen( + state = state, + onBackClick = onBackClick + ) +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun ActivityLogScreen(state: ActivityLogState, onBackClick: () -> Unit) { Scaffold( topBar = { TopAppBar( diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/ReplyListScreen.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/ReplyListScreen.kt index 2f9910a..6cc6837 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/ReplyListScreen.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/ReplyListScreen.kt @@ -115,7 +115,8 @@ fun ReplyListScreen( val strings = LocalReplyRadarStrings.current val notificationPermissionManager = LocalNotificationPermissionManager.current - val pagerState = rememberPagerState { PAGER_PAGE_COUNT } + val pagerState = + rememberPagerState(initialPage = state.selectedTabIndex, pageCount = { PAGER_PAGE_COUNT }) val snackbarHostState = remember { SnackbarHostState() } val sheetState = rememberModalBottomSheetState( skipPartiallyExpanded = true diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/FloatingActionButton.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/FloatingActionButton.kt index 18f7e80..efdfb9a 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/FloatingActionButton.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/FloatingActionButton.kt @@ -11,7 +11,7 @@ import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.Reply import com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.ReplyListScreenIntent.ReplyListIntent.OnAddReplyClick @Composable -fun FloatingActionButton(onIntent: (ReplyListScreenIntent) -> Unit, colorScheme: ColorScheme) { +fun FloatingActionButton(onIntent: (ReplyListScreenIntent) -> Unit = {}, colorScheme: ColorScheme) { FloatingActionButton( onClick = { onIntent(OnAddReplyClick) }, containerColor = colorScheme.secondary diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyList.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyList.kt index cd0a9e8..61a33eb 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyList.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyList.kt @@ -1,5 +1,6 @@ package com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components +import androidx.compose.foundation.background import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth @@ -33,6 +34,7 @@ fun ReplyList( Column( modifier = Modifier .fillMaxWidth() + .background(colorScheme.surface) ) { ReplyListItem( modifier = Modifier diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyTimestampInfo.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyTimestampInfo.kt index 8134f26..3015410 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyTimestampInfo.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/ReplyTimestampInfo.kt @@ -2,6 +2,7 @@ package com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.comp import androidx.compose.foundation.layout.ColumnScope import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.MaterialTheme.typography import androidx.compose.material3.Text import androidx.compose.runtime.Composable @@ -23,7 +24,8 @@ fun ColumnScope.ReplyTimestampInfo(state: ReplyBottomSheetState) { .padding(start = paddingSmall, top = paddingSmall) .align(Start), text = getTimestampInfo(reply), - style = typography.bodySmall + style = typography.bodySmall, + color = MaterialTheme.colorScheme.onSurface ) } } diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/TopBar.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/TopBar.kt index a5924c0..c5cc3ae 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/TopBar.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/TopBar.kt @@ -1,5 +1,6 @@ package com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components +import androidx.compose.foundation.background import androidx.compose.foundation.clickable import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.fillMaxWidth @@ -28,6 +29,7 @@ fun TopBar(onActivityLogClick: () -> Unit, onSettingsClick: () -> Unit) { Box( modifier = Modifier .fillMaxWidth() + .background(colorScheme.surface) ) { Text( modifier = Modifier diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/replybottomsheet/ReplyBottomSheetActions.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/replybottomsheet/ReplyBottomSheetActions.kt index 532eb37..039b732 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/replybottomsheet/ReplyBottomSheetActions.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/reply/presentation/replylist/components/replybottomsheet/ReplyBottomSheetActions.kt @@ -1,5 +1,6 @@ package com.rafaelfelipeac.replyradar.features.reply.presentation.replylist.components.replybottomsheet +import androidx.compose.foundation.background import androidx.compose.foundation.layout.Arrangement.End import androidx.compose.foundation.layout.Arrangement.spacedBy import androidx.compose.foundation.layout.Row @@ -7,6 +8,7 @@ import androidx.compose.foundation.layout.RowScope import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.wrapContentWidth +import androidx.compose.material3.MaterialTheme.colorScheme import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue import androidx.compose.runtime.mutableStateOf @@ -54,6 +56,7 @@ fun ReplyBottomSheetActions( Row( modifier = Modifier .fillMaxWidth() + .background(colorScheme.surface) .padding(top = paddingSmall, bottom = paddingMedium, end = paddingSmall), horizontalArrangement = if (isEditMode(state)) spacedBy(paddingSmall) else End, verticalAlignment = Alignment.CenterVertically diff --git a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/settings/presentation/SettingsScreen.kt b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/settings/presentation/SettingsScreen.kt index c8a319a..7bec6ef 100644 --- a/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/settings/presentation/SettingsScreen.kt +++ b/composeApp/src/commonMain/kotlin/com/rafaelfelipeac/replyradar/features/settings/presentation/SettingsScreen.kt @@ -64,15 +64,33 @@ import replyradar.composeapp.generated.resources.Res.drawable import replyradar.composeapp.generated.resources.ic_email import replyradar.composeapp.generated.resources.ic_rate -@OptIn(ExperimentalMaterial3Api::class) @Composable -fun SettingsScreen( +fun SettingsScreenRoot( viewModel: SettingsViewModel = koinViewModel(), + appVersion: String = getAppVersion(), onBackClick: () -> Unit, onActivityLogClick: () -> Unit ) { val state by viewModel.state.collectAsStateWithLifecycle() + SettingsScreen( + state = state, + appVersion = appVersion, + onBackClick = onBackClick, + onActivityLogClick = onActivityLogClick, + onIntent = { viewModel.onIntent(it) } + ) +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun SettingsScreen( + state: SettingsState, + appVersion: String, + onBackClick: () -> Unit, + onActivityLogClick: () -> Unit, + onIntent: (SettingsIntent) -> Unit +) { Scaffold( topBar = { TopAppBar( @@ -109,26 +127,27 @@ fun SettingsScreen( .padding(vertical = paddingMedium) ) - Theme(state = state, onIntent = { viewModel.onIntent(it) }) + Theme(state = state, onIntent = onIntent) HorizontalDivider( modifier = Modifier .padding(vertical = paddingMedium) ) - Language(state = state, onIntent = { viewModel.onIntent(it) }) + Language(state = state, onIntent = onIntent) HorizontalDivider( modifier = Modifier .padding(vertical = paddingMedium) ) - App(onIntent = { viewModel.onIntent(it) }) + App(onIntent = onIntent) } AppVersionFooter( modifier = Modifier - .align(Alignment.BottomCenter) + .align(Alignment.BottomCenter), + appVersion = appVersion ) } } @@ -361,7 +380,7 @@ fun SettingsItem(text: String, description: String, icon: DrawableResource, onCl } @Composable -fun AppVersionFooter(modifier: Modifier = Modifier) { +fun AppVersionFooter(modifier: Modifier = Modifier, appVersion: String) { Box( modifier = modifier .fillMaxWidth() @@ -373,7 +392,7 @@ fun AppVersionFooter(modifier: Modifier = Modifier) { ) Text( - text = "${LocalReplyRadarStrings.current.settingsAppVersion} ${getAppVersion()}", + text = "${LocalReplyRadarStrings.current.settingsAppVersion} $appVersion", style = typography.bodySmall, modifier = Modifier .align(Alignment.Center)