From 68b9aa93e518749cb616f388b808562e9d44259a Mon Sep 17 00:00:00 2001 From: paulwasthere <132862961+ZBZFirst@users.noreply.github.com> Date: Thu, 5 Mar 2026 13:49:31 -0800 Subject: [PATCH] Fix palette_hint string escaping issue --- .../java/com/example/templei/MainActivity.kt | 36 +----- .../templei/feature/camera/CameraFeature.kt | 6 + .../templei/feature/export/ExportFeature.kt | 6 + .../com/example/templei/ui/app/TempleIApp.kt | 15 +++ .../templei/ui/components/PulseButton.kt | 68 +++++++++++ .../templei/ui/components/UiPaletteBar.kt | 53 +++++++++ .../example/templei/ui/navigation/NavGraph.kt | 6 + .../example/templei/ui/navigation/Routes.kt | 5 + .../templei/ui/screens/home/HomeScreen.kt | 108 ++++++++++++++++++ .../com/example/templei/ui/state/HomeEvent.kt | 5 + .../example/templei/ui/state/HomeUiState.kt | 6 + app/src/main/res/layout/activity_main.xml | 62 ++++++++++ app/src/main/res/values/strings.xml | 7 +- gradlew | 0 14 files changed, 347 insertions(+), 36 deletions(-) create mode 100644 app/src/main/java/com/example/templei/feature/camera/CameraFeature.kt create mode 100644 app/src/main/java/com/example/templei/feature/export/ExportFeature.kt create mode 100644 app/src/main/java/com/example/templei/ui/app/TempleIApp.kt create mode 100644 app/src/main/java/com/example/templei/ui/components/PulseButton.kt create mode 100644 app/src/main/java/com/example/templei/ui/components/UiPaletteBar.kt create mode 100644 app/src/main/java/com/example/templei/ui/navigation/NavGraph.kt create mode 100644 app/src/main/java/com/example/templei/ui/navigation/Routes.kt create mode 100644 app/src/main/java/com/example/templei/ui/screens/home/HomeScreen.kt create mode 100644 app/src/main/java/com/example/templei/ui/state/HomeEvent.kt create mode 100644 app/src/main/java/com/example/templei/ui/state/HomeUiState.kt create mode 100644 app/src/main/res/layout/activity_main.xml mode change 100644 => 100755 gradlew diff --git a/app/src/main/java/com/example/templei/MainActivity.kt b/app/src/main/java/com/example/templei/MainActivity.kt index 3b13f66..9a20283 100644 --- a/app/src/main/java/com/example/templei/MainActivity.kt +++ b/app/src/main/java/com/example/templei/MainActivity.kt @@ -2,46 +2,12 @@ package com.example.templei import android.os.Bundle import androidx.activity.ComponentActivity -import androidx.activity.compose.setContent import androidx.activity.enableEdgeToEdge -import androidx.compose.foundation.layout.fillMaxSize -import androidx.compose.foundation.layout.padding -import androidx.compose.material3.Scaffold -import androidx.compose.material3.Text -import androidx.compose.runtime.Composable -import androidx.compose.ui.Modifier -import androidx.compose.ui.tooling.preview.Preview -import com.example.templei.ui.theme.TempleITheme class MainActivity : ComponentActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) enableEdgeToEdge() - setContent { - TempleITheme { - Scaffold(modifier = Modifier.fillMaxSize()) { innerPadding -> - Greeting( - name = "Android", - modifier = Modifier.padding(innerPadding) - ) - } - } - } + setContentView(R.layout.activity_main) } } - -@Composable -fun Greeting(name: String, modifier: Modifier = Modifier) { - Text( - text = "Hello $name!", - modifier = modifier - ) -} - -@Preview(showBackground = true) -@Composable -fun GreetingPreview() { - TempleITheme { - Greeting("Android") - } -} \ No newline at end of file diff --git a/app/src/main/java/com/example/templei/feature/camera/CameraFeature.kt b/app/src/main/java/com/example/templei/feature/camera/CameraFeature.kt new file mode 100644 index 0000000..8888467 --- /dev/null +++ b/app/src/main/java/com/example/templei/feature/camera/CameraFeature.kt @@ -0,0 +1,6 @@ +package com.example.templei.feature.camera + +/** + * Placeholder for future camera capture pipeline. + */ +object CameraFeature diff --git a/app/src/main/java/com/example/templei/feature/export/ExportFeature.kt b/app/src/main/java/com/example/templei/feature/export/ExportFeature.kt new file mode 100644 index 0000000..ae6c126 --- /dev/null +++ b/app/src/main/java/com/example/templei/feature/export/ExportFeature.kt @@ -0,0 +1,6 @@ +package com.example.templei.feature.export + +/** + * Placeholder for future export pipeline. + */ +object ExportFeature diff --git a/app/src/main/java/com/example/templei/ui/app/TempleIApp.kt b/app/src/main/java/com/example/templei/ui/app/TempleIApp.kt new file mode 100644 index 0000000..0bc7104 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/app/TempleIApp.kt @@ -0,0 +1,15 @@ +package com.example.templei.ui.app + +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.Scaffold +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import com.example.templei.ui.screens.home.HomeScreen + +@Composable +fun TempleIApp() { + Scaffold(modifier = Modifier.fillMaxSize()) { innerPadding -> + HomeScreen(modifier = Modifier.padding(innerPadding)) + } +} diff --git a/app/src/main/java/com/example/templei/ui/components/PulseButton.kt b/app/src/main/java/com/example/templei/ui/components/PulseButton.kt new file mode 100644 index 0000000..f99b033 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/components/PulseButton.kt @@ -0,0 +1,68 @@ +package com.example.templei.ui.components + +import androidx.compose.animation.animateColorAsState +import androidx.compose.animation.core.RepeatMode +import androidx.compose.animation.core.animateFloat +import androidx.compose.animation.core.infiniteRepeatable +import androidx.compose.animation.core.rememberInfiniteTransition +import androidx.compose.animation.core.tween +import androidx.compose.foundation.layout.defaultMinSize +import androidx.compose.material3.Button +import androidx.compose.material3.ButtonDefaults +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.graphicsLayer +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.example.templei.ui.theme.TempleITheme + +@Composable +fun PulseButton( + isFlashing: Boolean, + onClick: () -> Unit, + modifier: Modifier = Modifier +) { + val transition = rememberInfiniteTransition(label = "pulseTransition") + val pulseScale = transition.animateFloat( + initialValue = 1f, + targetValue = if (isFlashing) 1.08f else 1f, + animationSpec = infiniteRepeatable( + animation = tween(550), + repeatMode = RepeatMode.Reverse + ), + label = "pulseScale" + ) + + val containerColor = animateColorAsState( + targetValue = if (isFlashing) { + MaterialTheme.colorScheme.primary + } else { + MaterialTheme.colorScheme.secondaryContainer + }, + label = "pulseColor" + ) + + Button( + onClick = onClick, + modifier = modifier + .defaultMinSize(minWidth = 180.dp) + .graphicsLayer { + val animatedScale = if (isFlashing) pulseScale.value else 1f + scaleX = animatedScale + scaleY = animatedScale + }, + colors = ButtonDefaults.buttonColors(containerColor = containerColor.value) + ) { + Text(if (isFlashing) "Stop Flash" else "Start Flash") + } +} + +@Preview(showBackground = true) +@Composable +private fun PulseButtonPreview() { + TempleITheme { + PulseButton(isFlashing = true, onClick = {}) + } +} diff --git a/app/src/main/java/com/example/templei/ui/components/UiPaletteBar.kt b/app/src/main/java/com/example/templei/ui/components/UiPaletteBar.kt new file mode 100644 index 0000000..6ce75d5 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/components/UiPaletteBar.kt @@ -0,0 +1,53 @@ +package com.example.templei.ui.components + +import androidx.compose.foundation.horizontalScroll +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.rememberScrollState +import androidx.compose.material3.AssistChip +import androidx.compose.material3.AssistChipDefaults +import androidx.compose.material3.MaterialTheme +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.example.templei.ui.theme.TempleITheme + +@Composable +fun UiPaletteBar( + items: List, + onItemClick: (String) -> Unit, + modifier: Modifier = Modifier +) { + Row( + modifier = modifier + .fillMaxWidth() + .horizontalScroll(rememberScrollState()), + horizontalArrangement = Arrangement.spacedBy(8.dp) + ) { + items.forEach { item -> + AssistChip( + onClick = { onItemClick(item) }, + label = { Text(text = item) }, + colors = AssistChipDefaults.assistChipColors( + labelColor = MaterialTheme.colorScheme.onSurface + ) + ) + } + } +} + +@Preview(showBackground = true) +@Composable +private fun UiPaletteBarPreview() { + TempleITheme { + UiPaletteBar( + items = listOf("Button", "Text", "Card", "Image"), + onItemClick = {}, + modifier = Modifier.padding(16.dp) + ) + } +} diff --git a/app/src/main/java/com/example/templei/ui/navigation/NavGraph.kt b/app/src/main/java/com/example/templei/ui/navigation/NavGraph.kt new file mode 100644 index 0000000..112f248 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/navigation/NavGraph.kt @@ -0,0 +1,6 @@ +package com.example.templei.ui.navigation + +/** + * Placeholder for app navigation wiring once a second destination is introduced. + */ +object NavGraph diff --git a/app/src/main/java/com/example/templei/ui/navigation/Routes.kt b/app/src/main/java/com/example/templei/ui/navigation/Routes.kt new file mode 100644 index 0000000..5e4b2b8 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/navigation/Routes.kt @@ -0,0 +1,5 @@ +package com.example.templei.ui.navigation + +object Routes { + const val HOME = "home" +} diff --git a/app/src/main/java/com/example/templei/ui/screens/home/HomeScreen.kt b/app/src/main/java/com/example/templei/ui/screens/home/HomeScreen.kt new file mode 100644 index 0000000..f259c42 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/screens/home/HomeScreen.kt @@ -0,0 +1,108 @@ +package com.example.templei.ui.screens.home + +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +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.example.templei.ui.components.PulseButton +import com.example.templei.ui.components.UiPaletteBar +import com.example.templei.ui.state.HomeEvent +import com.example.templei.ui.state.HomeUiState +import com.example.templei.ui.theme.TempleITheme + +private val PaletteItems = listOf("Button", "Text", "Card", "Image", "Row", "Column") + +@Composable +fun HomeScreen(modifier: Modifier = Modifier) { + var uiState by remember { mutableStateOf(HomeUiState()) } + var selectedPaletteItem by remember { mutableStateOf("Button") } + + HomeScreen( + uiState = uiState, + selectedPaletteItem = selectedPaletteItem, + onPaletteItemSelected = { selectedPaletteItem = it }, + onEvent = { event -> + when (event) { + HomeEvent.PulsePressed -> { + val isFlashing = !uiState.isFlashing + uiState = uiState.copy( + isFlashing = isFlashing, + statusText = if (isFlashing) "Flashing" else "Ready" + ) + } + } + }, + modifier = modifier + ) +} + +@Composable +fun HomeScreen( + uiState: HomeUiState, + selectedPaletteItem: String, + onPaletteItemSelected: (String) -> Unit, + onEvent: (HomeEvent) -> Unit, + modifier: Modifier = Modifier +) { + Column( + modifier = modifier + .fillMaxSize() + .padding(24.dp), + verticalArrangement = Arrangement.Center, + horizontalAlignment = Alignment.CenterHorizontally + ) { + Text( + text = "UI Palette", + style = MaterialTheme.typography.titleMedium, + modifier = Modifier.align(Alignment.Start) + ) + UiPaletteBar( + items = PaletteItems, + onItemClick = onPaletteItemSelected, + modifier = Modifier.padding(top = 8.dp, bottom = 16.dp) + ) + Text( + text = "Selected: $selectedPaletteItem", + style = MaterialTheme.typography.bodyMedium, + modifier = Modifier.align(Alignment.Start) + ) + Text( + text = "TempleI", + style = MaterialTheme.typography.headlineMedium, + modifier = Modifier.padding(top = 24.dp) + ) + Text( + text = uiState.statusText, + style = MaterialTheme.typography.bodyLarge, + modifier = Modifier.padding(top = 8.dp, bottom = 24.dp) + ) + PulseButton( + isFlashing = uiState.isFlashing, + onClick = { onEvent(HomeEvent.PulsePressed) } + ) + } +} + +@Preview(showBackground = true) +@Composable +private fun HomeScreenPreview() { + TempleITheme { + HomeScreen( + uiState = HomeUiState(isFlashing = true, statusText = "Flashing"), + selectedPaletteItem = "Button", + onPaletteItemSelected = {}, + onEvent = {} + ) + } +} diff --git a/app/src/main/java/com/example/templei/ui/state/HomeEvent.kt b/app/src/main/java/com/example/templei/ui/state/HomeEvent.kt new file mode 100644 index 0000000..bb139eb --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/state/HomeEvent.kt @@ -0,0 +1,5 @@ +package com.example.templei.ui.state + +sealed interface HomeEvent { + data object PulsePressed : HomeEvent +} diff --git a/app/src/main/java/com/example/templei/ui/state/HomeUiState.kt b/app/src/main/java/com/example/templei/ui/state/HomeUiState.kt new file mode 100644 index 0000000..dd43236 --- /dev/null +++ b/app/src/main/java/com/example/templei/ui/state/HomeUiState.kt @@ -0,0 +1,6 @@ +package com.example.templei.ui.state + +data class HomeUiState( + val isFlashing: Boolean = false, + val statusText: String = "Ready" +) diff --git a/app/src/main/res/layout/activity_main.xml b/app/src/main/res/layout/activity_main.xml new file mode 100644 index 0000000..ee2cb1c --- /dev/null +++ b/app/src/main/res/layout/activity_main.xml @@ -0,0 +1,62 @@ + + + + + + + + + +