diff --git a/.idea/codeStyles/Project.xml b/.idea/codeStyles/Project.xml deleted file mode 100644 index 7643783..0000000 --- a/.idea/codeStyles/Project.xml +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - - - - \ No newline at end of file diff --git a/.idea/codeStyles/codeStyleConfig.xml b/.idea/codeStyles/codeStyleConfig.xml deleted file mode 100644 index 79ee123..0000000 --- a/.idea/codeStyles/codeStyleConfig.xml +++ /dev/null @@ -1,5 +0,0 @@ - - - - \ No newline at end of file diff --git a/.idea/inspectionProfiles/Project_Default.xml b/.idea/inspectionProfiles/Project_Default.xml new file mode 100644 index 0000000..44ca2d9 --- /dev/null +++ b/.idea/inspectionProfiles/Project_Default.xml @@ -0,0 +1,41 @@ + + + + \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000..94a25f7 --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/app/build.gradle.kts b/app/build.gradle.kts index b2ff921..80591b8 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -15,15 +15,15 @@ android { versionName = "1.0" testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner" - vectorDrawables { - useSupportLibrary = true - } } buildTypes { release { isMinifyEnabled = false - proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro") + proguardFiles( + getDefaultProguardFile("proguard-android-optimize.txt"), + "proguard-rules.pro" + ) } } compileOptions { @@ -49,13 +49,17 @@ android { dependencies { implementation("androidx.core:core-ktx:1.9.0") - implementation("androidx.lifecycle:lifecycle-runtime-ktx:2.6.1") - implementation("androidx.activity:activity-compose:1.7.0") + implementation("androidx.lifecycle:lifecycle-runtime-ktx:2.6.2") + implementation("androidx.activity:activity-compose:1.7.2") implementation(platform("androidx.compose:compose-bom:2023.03.00")) + implementation("androidx.navigation:navigation-compose:2.6.0") implementation("androidx.compose.ui:ui") implementation("androidx.compose.ui:ui-graphics") implementation("androidx.compose.ui:ui-tooling-preview") implementation("androidx.compose.material3:material3") + implementation("com.jakewharton.threetenabp:threetenabp:1.2.1") + implementation("androidx.datastore:datastore-preferences:1.0.0") + testImplementation("junit:junit:4.13.2") androidTestImplementation("androidx.test.ext:junit:1.1.5") androidTestImplementation("androidx.test.espresso:espresso-core:3.5.1") diff --git a/app/src/images/photo.jpg b/app/src/images/photo.jpg new file mode 100644 index 0000000..9fb88cf Binary files /dev/null and b/app/src/images/photo.jpg differ diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index e013846..2900ac3 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -10,13 +10,13 @@ android:label="@string/app_name" android:roundIcon="@mipmap/ic_launcher_round" android:supportsRtl="true" - android:theme="@style/Theme.MyApplication" + android:theme="@style/Theme.Pmudemo" tools:targetApi="31"> + android:theme="@style/Theme.Pmudemo"> diff --git a/app/src/main/java/com/example/myapplication/MainActivity.kt b/app/src/main/java/com/example/myapplication/MainActivity.kt deleted file mode 100644 index 34bce68..0000000 --- a/app/src/main/java/com/example/myapplication/MainActivity.kt +++ /dev/null @@ -1,43 +0,0 @@ -package com.example.myapplication - -import android.os.Bundle -import androidx.activity.ComponentActivity -import androidx.activity.compose.setContent -import androidx.compose.foundation.layout.fillMaxSize -import androidx.compose.material3.MaterialTheme -import androidx.compose.material3.Surface -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.myapplication.ui.theme.MyApplicationTheme - -class MainActivity : ComponentActivity() { - override fun onCreate(savedInstanceState: Bundle?) { - super.onCreate(savedInstanceState) - setContent { - MyApplicationTheme { - // A surface container using the 'background' color from the theme - Surface(modifier = Modifier.fillMaxSize(), color = MaterialTheme.colorScheme.background) { - Greeting("Android") - } - } - } - } -} - -@Composable -fun Greeting(name: String, modifier: Modifier = Modifier) { - Text( - text = "Hello $name!", - modifier = modifier - ) -} - -@Preview(showBackground = true) -@Composable -fun GreetingPreview() { - MyApplicationTheme { - Greeting("Android") - } -} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/MainComposeActivity.kt b/app/src/main/java/com/example/myapplication/MainComposeActivity.kt new file mode 100644 index 0000000..a68d190 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/MainComposeActivity.kt @@ -0,0 +1,60 @@ +package com.example.myapplication + +import android.content.res.Configuration +import android.os.Bundle +import androidx.activity.ComponentActivity +import androidx.activity.compose.setContent +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.rememberCoroutineScope +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import com.example.myapplication.composeui.navigation.MainNavbar +import com.example.myapplication.datastore.DataStoreManager +import com.example.myapplication.ui.theme.PmudemoTheme + +class MainComposeActivity : ComponentActivity() { + private val dataStoreManager = DataStoreManager(this) + private val isDarkTheme = mutableStateOf(true) + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + setContent { + PmudemoTheme(darkTheme = isDarkTheme.value) { + LaunchedEffect(key1 = true) { + dataStoreManager.getSettings().collect { setting -> + isDarkTheme.value = setting.isDarkTheme + } + } + Surface( + modifier = Modifier.fillMaxSize(), + color = MaterialTheme.colorScheme.background + ) { + MainNavbar( + isDarkTheme = isDarkTheme, + dataStoreManager = dataStoreManager + ) + } + } + } + + } +} +/* +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun MainNavbarPreview() { + val dataStoreManager = DataStoreManager(MainComposeActivity) + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + MainNavbar(remember { mutableStateOf(true) }) + } + } +}*/ diff --git a/app/src/main/java/com/example/myapplication/cinema/composeui/CinemaList.kt b/app/src/main/java/com/example/myapplication/cinema/composeui/CinemaList.kt new file mode 100644 index 0000000..bf14b2b --- /dev/null +++ b/app/src/main/java/com/example/myapplication/cinema/composeui/CinemaList.kt @@ -0,0 +1,88 @@ +package com.example.myapplication.cinema.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.Image +import androidx.compose.foundation.background +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material3.Button +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.core.content.ContextCompat +import androidx.navigation.NavController +import com.example.myapplication.R +import com.example.myapplication.cinema.model.getCinemas +import com.example.myapplication.composeui.navigation.Screen +import com.example.myapplication.ui.theme.Gray +import com.example.myapplication.ui.theme.PmudemoTheme + +@Composable +fun CinemaList(navController: NavController?) { + LazyColumn( + modifier = Modifier + .fillMaxSize() + .padding(all = 10.dp) + ) { + items(getCinemas().indices.toList()) { index -> + val cinema = getCinemas()[index] + val cinemaId = Screen.CinemaView.route.replace("{id}", index.toString()) + Box( + modifier = Modifier + .fillMaxWidth() + .padding(all = 10.dp) + .clickable { navController?.navigate(cinemaId) } + .background( + color = MaterialTheme.colorScheme.secondary, + shape = RoundedCornerShape(16.dp) + ) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(8.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.spacedBy(8.dp) + ) { + Image( + painter = painterResource(id = cinema.image), + contentDescription = null, + modifier = Modifier.size(90.dp) + ) + + Text("${cinema.name}, ${cinema.year}", color = MaterialTheme.colorScheme.onSecondary) + } + } + } + } +} + +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun CinemaListPreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + CinemaList(navController = null) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/cinema/composeui/CinemaView.kt b/app/src/main/java/com/example/myapplication/cinema/composeui/CinemaView.kt new file mode 100644 index 0000000..4ca55f2 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/cinema/composeui/CinemaView.kt @@ -0,0 +1,169 @@ +package com.example.myapplication.cinema.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.Image +import androidx.compose.foundation.background +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.ShoppingCart +import androidx.compose.material3.Icon +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.draw.clip +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.text.TextStyle +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import com.example.myapplication.cinema.model.getCinemas +import com.example.myapplication.session.model.getSessions +import com.example.myapplication.ui.theme.PmudemoTheme +import org.threeten.bp.format.DateTimeFormatter + +@Composable +fun CinemaView(id: Int) { + val cinema = getCinemas()[id] + + LazyColumn( + modifier = Modifier + .fillMaxSize() + .padding(16.dp) + ) { + item { + Box( + modifier = Modifier + .fillMaxSize() + .background( + color = MaterialTheme.colorScheme.secondary, + shape = RoundedCornerShape(16.dp) + ) + ) { + Column( + modifier = Modifier + .fillMaxWidth() + .padding(16.dp) + .background(color = MaterialTheme.colorScheme.secondary), + verticalArrangement = Arrangement.spacedBy(8.dp) + ) { + Text( + text = "${cinema.name}, ${cinema.year}", + style = TextStyle( + fontWeight = FontWeight.Bold, + fontSize = 18.sp, + color = MaterialTheme.colorScheme.onSecondary + ), + modifier = Modifier + .fillMaxWidth() + .padding(bottom = 8.dp) + ) + + Image( + painter = painterResource(id = cinema.image), + contentDescription = null, + modifier = Modifier + .fillMaxWidth() + .height(200.dp) + ) + + Text(text = cinema.description, color = MaterialTheme.colorScheme.onSecondary) + } + } + } + item { + Text( + text = "Сеансы", + style = TextStyle( + fontWeight = FontWeight.Bold, + fontSize = 18.sp, + color = MaterialTheme.colorScheme.onBackground + ), + modifier = Modifier + .fillMaxWidth() + .padding(top = 8.dp, bottom = 8.dp), + ) + } + + + items(getSessions(cinema)) { session -> + val dateFormatter = DateTimeFormatter.ofPattern("dd.MM.yyyy HH:mm") + val formattedDate = dateFormatter.format(session.dateTime) + Text( + text = formattedDate, + color = MaterialTheme.colorScheme.onBackground, + ) + Box( + modifier = Modifier + .fillMaxWidth() + .padding(10.dp) + .clip(RoundedCornerShape(16.dp)) + .background(MaterialTheme.colorScheme.secondary) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(8.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Image( + painter = painterResource(id = session.cinema.image), + contentDescription = null, + modifier = Modifier.size(90.dp) + ) + + Column( + modifier = Modifier.weight(1f), + verticalArrangement = Arrangement.spacedBy(4.dp) + ) { + Text( + text = "${session.currentCount}/${session.maxCount}", + color = MaterialTheme.colorScheme.onSecondary + ) + } + } + + Icon( + imageVector = Icons.Filled.ShoppingCart, + contentDescription = null, + modifier = Modifier + .padding(10.dp) + .size(24.dp) + .clickable {} + .align(Alignment.CenterEnd), + tint = MaterialTheme.colorScheme.onSecondary + ) + } + } + } +} + + +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun CinemaViewPreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + CinemaView(id = 0) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/cinema/model/Cinema.kt b/app/src/main/java/com/example/myapplication/cinema/model/Cinema.kt new file mode 100644 index 0000000..e9dbeb7 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/cinema/model/Cinema.kt @@ -0,0 +1,20 @@ +package com.example.myapplication.cinema.model + +import com.example.myapplication.R +import com.example.myapplication.session.model.Session +import com.example.myapplication.session.model.getSessions +import java.io.Serializable + +data class Cinema( + val name: String, + val description: String, + val image: Int, + val year: Long +) : Serializable + +fun getCinemas(): List { + return listOf( + Cinema("First1", "new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema new cinema ", R.drawable.photo, 2023), + Cinema("First2", "new cinema 123", R.drawable.photo, 2024) + ) +} diff --git a/app/src/main/java/com/example/myapplication/composeui/Cart.kt b/app/src/main/java/com/example/myapplication/composeui/Cart.kt new file mode 100644 index 0000000..7205777 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/composeui/Cart.kt @@ -0,0 +1,168 @@ +package com.example.myapplication.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.Image +import androidx.compose.foundation.background +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.layout.width +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.itemsIndexed +import androidx.compose.foundation.shape.CircleShape +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.Add +import androidx.compose.material.icons.filled.Delete +import androidx.compose.material3.Button +import androidx.compose.material3.Icon +import androidx.compose.material3.IconButton +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +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.draw.clip +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.vector.ImageVector +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.vectorResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.example.myapplication.R +import com.example.myapplication.session.model.getSessions +import com.example.myapplication.ui.theme.DarkGray +import com.example.myapplication.ui.theme.Gray +import com.example.myapplication.ui.theme.PmudemoTheme +import org.threeten.bp.format.DateTimeFormatter + +@Composable +fun Cart() { + val sessions = getSessions() + + LazyColumn( + modifier = Modifier + .padding(all = 10.dp) + ) { + itemsIndexed(sessions) { index, session -> + var currentCount by remember { mutableStateOf(session.currentCount) } + + val dateFormatter = DateTimeFormatter.ofPattern("dd.MM.yyyy HH:mm") + val formattedDate = dateFormatter.format(session.dateTime) + + Text( + text = formattedDate, + color = MaterialTheme.colorScheme.onBackground, + ) + Box( + modifier = Modifier + .fillMaxWidth() + .padding(10.dp) + .clip(RoundedCornerShape(16.dp)) + .background(MaterialTheme.colorScheme.secondary) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(8.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Image( + painter = painterResource(id = session.cinema.image), + contentDescription = null, + modifier = Modifier.size(90.dp) + ) + + Column( + modifier = Modifier.weight(1f), + verticalArrangement = Arrangement.spacedBy(4.dp) + ) { + Text(text = "${session.cinema.name}, ${session.cinema.year}\n" + + "$currentCount/${session.maxCount}", color = MaterialTheme.colorScheme.onSecondary) + } + + Box( + modifier = Modifier + .background(color = MaterialTheme.colorScheme.background, shape = RoundedCornerShape(10.dp)) // Задаем фон для кнопок + ) { + Row( + verticalAlignment = Alignment.CenterVertically + ) { + IconButton( + onClick = { + if (currentCount > 0) { + currentCount-- + } + } + ) { + Icon( + imageVector = ImageVector.vectorResource(id = R.drawable.minus), + contentDescription = "Уменьшить", + tint = MaterialTheme.colorScheme.onBackground, + modifier = Modifier.size(10.dp) + ) + } + + Text( + text = "$currentCount", + color = MaterialTheme.colorScheme.onBackground + ) + + IconButton( + onClick = { + if (currentCount < session.maxCount) { + currentCount++ + } + } + ) { + Icon( + imageVector = Icons.Default.Add, + contentDescription = "Увеличить", + tint = MaterialTheme.colorScheme.onBackground, + modifier = Modifier.size(10.dp) + ) + } + } + } + } + } + } + } + Column() { + Spacer(modifier = Modifier.weight(1f)) + + Button( + onClick = { }, + modifier = Modifier + .padding(16.dp) + .fillMaxWidth() + ) { Text("Купить") } + } +} + + +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun CartPreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + Cart() + } + } +} diff --git a/app/src/main/java/com/example/myapplication/composeui/navigation/MainNavbar.kt b/app/src/main/java/com/example/myapplication/composeui/navigation/MainNavbar.kt new file mode 100644 index 0000000..a3d075e --- /dev/null +++ b/app/src/main/java/com/example/myapplication/composeui/navigation/MainNavbar.kt @@ -0,0 +1,230 @@ +package com.example.myapplication.composeui.navigation + +import android.content.res.Configuration +import androidx.compose.foundation.background +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.layout.width +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.foundation.text.BasicTextField +import androidx.compose.foundation.text.KeyboardActions +import androidx.compose.foundation.text.KeyboardOptions +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.ArrowBack +import androidx.compose.material.icons.filled.Person +import androidx.compose.material.icons.filled.Search +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.Icon +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.NavigationBar +import androidx.compose.material3.NavigationBarItem +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.runtime.MutableState +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.graphics.Color +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.navigation.NavDestination +import androidx.navigation.NavDestination.Companion.hierarchy +import androidx.navigation.NavGraph.Companion.findStartDestination +import androidx.navigation.NavHostController +import androidx.navigation.NavType +import androidx.navigation.compose.NavHost +import androidx.navigation.compose.composable +import androidx.navigation.compose.currentBackStackEntryAsState +import androidx.navigation.compose.rememberNavController +import androidx.navigation.navArgument +import com.example.myapplication.cinema.composeui.CinemaList +import com.example.myapplication.cinema.composeui.CinemaView +import com.example.myapplication.composeui.Cart +import com.example.myapplication.datastore.DataStoreManager +import com.example.myapplication.order.composeui.OrderList +import com.example.myapplication.order.composeui.OrderView +import com.example.myapplication.session.composeui.SessionList +import com.example.myapplication.ui.theme.DarkGray +import com.example.myapplication.ui.theme.PmudemoTheme +import com.example.myapplication.user.composeui.UserProfile + +@Composable +fun Topbar( + navController: NavHostController, + currentScreen: Screen? +) { + var searchQuery by remember { mutableStateOf("") } + Box( + modifier = Modifier + .fillMaxWidth() + .background(color = MaterialTheme.colorScheme.primary) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(10.dp), + verticalAlignment = Alignment.CenterVertically + ) { + if ( + navController.previousBackStackEntry != null + && (currentScreen == null || !currentScreen.showInBottomBar) + ) { + Icon( + imageVector = Icons.Filled.ArrowBack, + contentDescription = null, + modifier = Modifier + .size(30.dp) + .clickable { navController.navigateUp() }, + tint = MaterialTheme.colorScheme.secondary + ) + } else + Icon( + imageVector = Icons.Default.Person, + contentDescription = null, + modifier = Modifier + .size(30.dp) + .clickable { navController.navigate(Screen.UserProfile.route) }, + tint = MaterialTheme.colorScheme.secondary + ) + + Spacer(modifier = Modifier.width(16.dp)) + + BasicTextField( + value = searchQuery, + onValueChange = { newValue -> searchQuery = newValue }, + modifier = Modifier + .weight(1f) + .height(36.dp) + .background(color = MaterialTheme.colorScheme.onPrimary, RoundedCornerShape(18.dp)) + .padding(start = 13.dp, top = 8.dp), + keyboardOptions = KeyboardOptions.Default.copy( + imeAction = androidx.compose.ui.text.input.ImeAction.Search + ), + keyboardActions = KeyboardActions( + onSearch = { } + ) + ) + + Spacer(modifier = Modifier.width(16.dp)) + + Icon( + imageVector = Icons.Default.Search, + contentDescription = null, + modifier = Modifier + .size(30.dp) + .clickable { }, + tint = MaterialTheme.colorScheme.secondary + ) + } + } +} + +@Composable +fun Navbar( + navController: NavHostController, + currentDestination: NavDestination?, + modifier: Modifier = Modifier +) { + NavigationBar(modifier = modifier, containerColor = MaterialTheme.colorScheme.primary) { + Screen.bottomBarItems.forEach { screen -> + NavigationBarItem( + icon = { Icon(screen.icon, contentDescription = null, tint = MaterialTheme.colorScheme.secondary) }, + label = { Text(stringResource(screen.resourceId)) }, + selected = currentDestination?.hierarchy?.any { it.route == screen.route } == true, + onClick = { + navController.navigate(screen.route) { + popUpTo(navController.graph.findStartDestination().id) { + saveState = true + } + launchSingleTop = true + restoreState = true + } + } + ) + } + } +} + +@Composable +fun Navhost( + navController: NavHostController, + innerPadding: PaddingValues, + isDarkTheme: MutableState, + dataStore: DataStoreManager, + modifier: Modifier = Modifier, +) { + NavHost( + navController, + startDestination = Screen.CinemaList.route, + modifier.padding(innerPadding) + ) { + composable(Screen.CinemaList.route) { CinemaList(navController) } + composable(Screen.OrderList.route) { OrderList(navController) } + composable(Screen.Cart.route) { Cart() } + composable(Screen.UserProfile.route) { UserProfile(navController, isDarkTheme, dataStore) } + composable(Screen.SessionList.route) { SessionList() } + composable( + Screen.CinemaView.route, + arguments = listOf(navArgument("id") { type = NavType.IntType }) + ) { backStackEntry -> + backStackEntry.arguments?.let { CinemaView(it.getInt("id")) } + } + composable( + Screen.OrderView.route, + arguments = listOf(navArgument("id") { type = NavType.IntType }) + ) { backStackEntry -> + backStackEntry.arguments?.let { OrderView(it.getInt("id")) } + } + } +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun MainNavbar( + isDarkTheme: MutableState, + dataStoreManager: DataStoreManager +) { + val navController = rememberNavController() + val navBackStackEntry by navController.currentBackStackEntryAsState() + val currentDestination = navBackStackEntry?.destination + val currentScreen = currentDestination?.route?.let { Screen.getItem(it) } + + Scaffold( + topBar = { + Topbar(navController, currentScreen) + }, + bottomBar = { + if (currentScreen == null || currentScreen.showInBottomBar) { + Navbar(navController, currentDestination) + } + } + ) { innerPadding -> + Navhost(navController, innerPadding, isDarkTheme, dataStoreManager) + } +} +/* +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun MainNavbarPreview() { + PmudemoTheme() { + Surface( + color = MaterialTheme.colorScheme.background + ) { + MainNavbar(remember { mutableStateOf(true) }, DataStoreManager) + } + } +}*/ diff --git a/app/src/main/java/com/example/myapplication/composeui/navigation/Screen.kt b/app/src/main/java/com/example/myapplication/composeui/navigation/Screen.kt new file mode 100644 index 0000000..ade816d --- /dev/null +++ b/app/src/main/java/com/example/myapplication/composeui/navigation/Screen.kt @@ -0,0 +1,57 @@ +package com.example.myapplication.composeui.navigation + +import androidx.annotation.StringRes +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.Favorite +import androidx.compose.material.icons.filled.Home +import androidx.compose.material.icons.filled.Info +import androidx.compose.material.icons.filled.List +import androidx.compose.material.icons.filled.ShoppingCart +import androidx.compose.material3.Icon +import androidx.compose.runtime.Composable +import androidx.compose.ui.graphics.vector.ImageVector +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.vectorResource +import com.example.myapplication.R + +enum class Screen( + val route: String, + @StringRes val resourceId: Int, + val icon: ImageVector = Icons.Filled.Favorite, + val showInBottomBar: Boolean = true +) { + CinemaList( + "Cinema-list", R.string.Cinema_main_title, Icons.Filled.Home + ), + SessionList( + "Session-list", R.string.Sessions_title, showInBottomBar = false + ), + Cart( + "cart", R.string.Cart_title, Icons.Filled.ShoppingCart + ), + OrderList( + "Order-list", R.string.Order_title, Icons.Filled.List + ), + CinemaView( + "Cinema-view/{id}", R.string.Cinema_view_title, showInBottomBar = false + ), + OrderView( + "Order-view/{id}", R.string.Order_view_title, showInBottomBar = false + ), + UserProfile( + "User-profile", R.string.Profile_title, showInBottomBar = false + ); + + companion object { + val bottomBarItems = listOf( + CinemaList, + Cart, + OrderList + ) + + fun getItem(route: String): Screen? { + val findRoute = route.split("/").first() + return values().find { value -> value.route.startsWith(findRoute) } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/datastore/DataStoreManager.kt b/app/src/main/java/com/example/myapplication/datastore/DataStoreManager.kt new file mode 100644 index 0000000..09b6c76 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/datastore/DataStoreManager.kt @@ -0,0 +1,24 @@ +package com.example.myapplication.datastore + +import android.content.Context +import androidx.datastore.core.DataStore +import androidx.datastore.preferences.core.Preferences +import androidx.datastore.preferences.core.booleanPreferencesKey +import androidx.datastore.preferences.core.edit +import androidx.datastore.preferences.preferencesDataStore +import kotlinx.coroutines.flow.map + +private val Context.dataStore: DataStore by preferencesDataStore("data_store") + +class DataStoreManager(private val context : Context) { + suspend fun saveSettings(settingData: SettingData) { + context.dataStore.edit { pref -> + pref[booleanPreferencesKey("isDarkTheme")] = settingData.isDarkTheme + } + } + fun getSettings() = context.dataStore.data.map { pref -> + return@map SettingData( + pref[booleanPreferencesKey("isDarkTheme")] ?: true + ) + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/datastore/SettingData.kt b/app/src/main/java/com/example/myapplication/datastore/SettingData.kt new file mode 100644 index 0000000..f74f0cb --- /dev/null +++ b/app/src/main/java/com/example/myapplication/datastore/SettingData.kt @@ -0,0 +1,5 @@ +package com.example.myapplication.datastore + +data class SettingData( + val isDarkTheme: Boolean +) \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/order/composeui/OrderList.kt b/app/src/main/java/com/example/myapplication/order/composeui/OrderList.kt new file mode 100644 index 0000000..5379056 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/order/composeui/OrderList.kt @@ -0,0 +1,76 @@ +package com.example.myapplication.order.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.Image +import androidx.compose.foundation.background +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.navigation.NavController +import com.example.myapplication.composeui.navigation.Screen +import com.example.myapplication.order.model.getOrders +import com.example.myapplication.ui.theme.Gray +import com.example.myapplication.ui.theme.PmudemoTheme + +@Composable +fun OrderList(navController: NavController?) { + LazyColumn( + modifier = Modifier + .fillMaxSize() + .padding(all = 10.dp) + ) { + items(getOrders().indices.toList()) { index -> + val orderId = Screen.OrderView.route.replace("{id}", index.toString()) + Box( + modifier = Modifier + .fillMaxWidth() + .padding(all = 10.dp) + .clickable { navController?.navigate(orderId) } + .background( + color = MaterialTheme.colorScheme.secondary, + shape = RoundedCornerShape(16.dp) + ) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(8.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.spacedBy(8.dp) + ) { + Text("Заказ №${index}", color = MaterialTheme.colorScheme.onSecondary) + } + } + } + } +} + +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun OrderListPreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + OrderList(navController = null) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/order/composeui/OrderView.kt b/app/src/main/java/com/example/myapplication/order/composeui/OrderView.kt new file mode 100644 index 0000000..3d88571 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/order/composeui/OrderView.kt @@ -0,0 +1,96 @@ +package com.example.myapplication.order.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.Image +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.draw.clip +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.example.myapplication.order.model.getOrders +import com.example.myapplication.ui.theme.PmudemoTheme +import org.threeten.bp.format.DateTimeFormatter + +@Composable +fun OrderView(id: Int) { + val order = getOrders()[id] + LazyColumn( + modifier = Modifier + .padding(10.dp) + ) { + items(order.sessions) { pair -> + val session = pair.first + val count = pair.second + val dateFormatter = DateTimeFormatter.ofPattern("dd.MM.yyyy HH:mm") + val formattedDate = dateFormatter.format(session.dateTime) + + Text( + text = formattedDate, + color = MaterialTheme.colorScheme.onBackground, + ) + Box( + modifier = Modifier + .fillMaxWidth() + .padding(10.dp) + .clip(RoundedCornerShape(16.dp)) + .background(MaterialTheme.colorScheme.secondary) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(8.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Image( + painter = painterResource(id = session.cinema.image), + contentDescription = null, + modifier = Modifier.size(90.dp) + ) + + Column( + modifier = Modifier + .weight(1f) + .padding(start = 8.dp), + verticalArrangement = Arrangement.spacedBy(4.dp) + ) { + Text( + text = "${session.cinema.name}, ${session.cinema.year}\n" + + "Количество: $count", + color = MaterialTheme.colorScheme.onSecondary + ) + } + } + } + } + } +} + +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun OrderViewPreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + OrderView(id = 0) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/order/model/Order.kt b/app/src/main/java/com/example/myapplication/order/model/Order.kt new file mode 100644 index 0000000..b53cf04 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/order/model/Order.kt @@ -0,0 +1,20 @@ +package com.example.myapplication.order.model + +import com.example.myapplication.cinema.model.Cinema +import com.example.myapplication.cinema.model.getCinemas +import com.example.myapplication.session.model.Session +import com.example.myapplication.session.model.getSessions +import org.threeten.bp.LocalDateTime +import java.io.Serializable + +data class Order( + val sessions: List> +) : Serializable + +fun getOrders(): List { + return listOf( + Order(listOf(Pair(getSessions()[0], 5), Pair(getSessions()[1], 2))), + Order(listOf(Pair(getSessions()[0], 1), Pair(getSessions()[1], 4))), + Order(listOf(Pair(getSessions()[0], 1), Pair(getSessions()[1], 7))) + ) +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/session/composeui/SessionList.kt b/app/src/main/java/com/example/myapplication/session/composeui/SessionList.kt new file mode 100644 index 0000000..c246fe7 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/session/composeui/SessionList.kt @@ -0,0 +1,108 @@ +package com.example.myapplication.session.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.Image +import androidx.compose.foundation.background +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.ShoppingCart +import androidx.compose.material3.Icon +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.draw.clip +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.navigation.NavController +import com.example.myapplication.session.model.getSessions +import com.example.myapplication.ui.theme.Gray +import com.example.myapplication.ui.theme.PmudemoTheme +import org.threeten.bp.format.DateTimeFormatter + +@Composable +fun SessionList() { + LazyColumn( + modifier = Modifier.padding(all = 10.dp) + ) { + items(getSessions()) { session -> + val dateFormatter = DateTimeFormatter.ofPattern("dd.MM.yyyy HH:mm") + val formattedDate = dateFormatter.format(session.dateTime) + + Text( + text = formattedDate, + color = MaterialTheme.colorScheme.onBackground, + ) + Box( + modifier = Modifier + .fillMaxWidth() + .padding(10.dp) + .clip(RoundedCornerShape(16.dp)) + .background(MaterialTheme.colorScheme.secondary) + ) { + Row( + modifier = Modifier + .fillMaxWidth() + .padding(8.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Image( + painter = painterResource(id = session.cinema.image), + contentDescription = null, + modifier = Modifier.size(90.dp) + ) + + Column( + modifier = Modifier.weight(1f), + verticalArrangement = Arrangement.spacedBy(4.dp) + ) { + Text( + text = "${session.cinema.name}, ${session.cinema.year}\n" + + "${session.currentCount}/${session.maxCount}", + color = MaterialTheme.colorScheme.onSecondary + ) + } + } + + Icon( + imageVector = Icons.Filled.ShoppingCart, + contentDescription = null, + modifier = Modifier + .padding(10.dp) + .size(24.dp) + .clickable {} + .align(Alignment.CenterEnd), + tint = MaterialTheme.colorScheme.onSecondary + ) + } + } + } +} + +@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun SessionListPreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + SessionList() + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/session/model/Session.kt b/app/src/main/java/com/example/myapplication/session/model/Session.kt new file mode 100644 index 0000000..22cc323 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/session/model/Session.kt @@ -0,0 +1,26 @@ +package com.example.myapplication.session.model + +import com.example.myapplication.cinema.model.Cinema +import com.example.myapplication.cinema.model.getCinemas +import java.io.Serializable +import org.threeten.bp.LocalDateTime; +import kotlin.streams.toList + +data class Session( + val dateTime: LocalDateTime, + val cinema: Cinema, + val currentCount: Int, + val maxCount: Int + ) + +fun getSessions(cinema: Cinema): List { + return getSessions().stream().filter{ value -> value.cinema == cinema }.toList(); +} + +fun getSessions(): List { + return listOf( + Session(LocalDateTime.of(2023, 10, 10, 18, 30), getCinemas()[0], 50, 120), + Session(LocalDateTime.of(2027, 10, 10, 18, 30), getCinemas()[0], 20, 120), + Session(LocalDateTime.of(2025, 10, 10, 18, 30), getCinemas()[1], 10, 120), + ) +} diff --git a/app/src/main/java/com/example/myapplication/ui.theme/Color.kt b/app/src/main/java/com/example/myapplication/ui.theme/Color.kt new file mode 100644 index 0000000..38003a8 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/ui.theme/Color.kt @@ -0,0 +1,11 @@ +package com.example.myapplication.ui.theme + +import androidx.compose.ui.graphics.Color + +val LightGray = Color(0xFFB2CCD6) +val LightBlueGray = Color(0xFF70A3B2) +val LightBgGray = Color(0xFFCED6DC) + +val Gray = Color(0xFFD6D6D6) +val DarkGray = Color(0xFF191A1F) +val BgGray = Color(0xFF2A2D32) \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/ui/theme/Theme.kt b/app/src/main/java/com/example/myapplication/ui.theme/Theme.kt similarity index 71% rename from app/src/main/java/com/example/myapplication/ui/theme/Theme.kt rename to app/src/main/java/com/example/myapplication/ui.theme/Theme.kt index 111ec67..8c4e3dc 100644 --- a/app/src/main/java/com/example/myapplication/ui/theme/Theme.kt +++ b/app/src/main/java/com/example/myapplication/ui.theme/Theme.kt @@ -10,23 +10,33 @@ import androidx.compose.material3.dynamicLightColorScheme import androidx.compose.material3.lightColorScheme import androidx.compose.runtime.Composable import androidx.compose.runtime.SideEffect +import androidx.compose.ui.graphics.Color import androidx.compose.ui.graphics.toArgb import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalView import androidx.core.view.WindowCompat private val DarkColorScheme = darkColorScheme( - primary = Purple80, - secondary = PurpleGrey80, - tertiary = Pink80 + primary = DarkGray, + onPrimary = Color.White, + + secondary = Gray, + onSecondary = Color.Black, + + background = BgGray, + onBackground = Color.White, ) private val LightColorScheme = lightColorScheme( - primary = Purple40, - secondary = PurpleGrey40, - tertiary = Pink40 + primary = LightBlueGray, + onPrimary = Color.White, - /* Other default colors to override + secondary = LightGray, + onSecondary = Color.Black, + + onBackground = Color.Black, + + /* Other default colors to override background = Color(0xFFFFFBFE), surface = Color(0xFFFFFBFE), onPrimary = Color.White, @@ -38,11 +48,11 @@ private val LightColorScheme = lightColorScheme( ) @Composable -fun MyApplicationTheme( - darkTheme: Boolean = isSystemInDarkTheme(), - // Dynamic color is available on Android 12+ - dynamicColor: Boolean = true, - content: @Composable () -> Unit +fun PmudemoTheme( + darkTheme: Boolean = isSystemInDarkTheme(), + // Dynamic color is available on Android 12+ + dynamicColor: Boolean = false, + content: @Composable () -> Unit ) { val colorScheme = when { dynamicColor && Build.VERSION.SDK_INT >= Build.VERSION_CODES.S -> { @@ -63,8 +73,8 @@ fun MyApplicationTheme( } MaterialTheme( - colorScheme = colorScheme, - typography = Typography, - content = content + colorScheme = colorScheme, + typography = Typography, + content = content ) } \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/ui/theme/Type.kt b/app/src/main/java/com/example/myapplication/ui.theme/Type.kt similarity index 71% rename from app/src/main/java/com/example/myapplication/ui/theme/Type.kt rename to app/src/main/java/com/example/myapplication/ui.theme/Type.kt index 5335f88..64846a0 100644 --- a/app/src/main/java/com/example/myapplication/ui/theme/Type.kt +++ b/app/src/main/java/com/example/myapplication/ui.theme/Type.kt @@ -8,14 +8,14 @@ import androidx.compose.ui.unit.sp // Set of Material typography styles to start with val Typography = Typography( - bodyLarge = TextStyle( - fontFamily = FontFamily.Default, - fontWeight = FontWeight.Normal, - fontSize = 16.sp, - lineHeight = 24.sp, - letterSpacing = 0.5.sp - ) - /* Other default text styles to override + bodyLarge = TextStyle( + fontFamily = FontFamily.Default, + fontWeight = FontWeight.Normal, + fontSize = 16.sp, + lineHeight = 24.sp, + letterSpacing = 0.5.sp + ) + /* Other default text styles to override titleLarge = TextStyle( fontFamily = FontFamily.Default, fontWeight = FontWeight.Normal, diff --git a/app/src/main/java/com/example/myapplication/ui/theme/Color.kt b/app/src/main/java/com/example/myapplication/ui/theme/Color.kt deleted file mode 100644 index 1ce3e5d..0000000 --- a/app/src/main/java/com/example/myapplication/ui/theme/Color.kt +++ /dev/null @@ -1,11 +0,0 @@ -package com.example.myapplication.ui.theme - -import androidx.compose.ui.graphics.Color - -val Purple80 = Color(0xFFD0BCFF) -val PurpleGrey80 = Color(0xFFCCC2DC) -val Pink80 = Color(0xFFEFB8C8) - -val Purple40 = Color(0xFF6650a4) -val PurpleGrey40 = Color(0xFF625b71) -val Pink40 = Color(0xFF7D5260) \ No newline at end of file diff --git a/app/src/main/java/com/example/myapplication/user/composeui/UserProfile.kt b/app/src/main/java/com/example/myapplication/user/composeui/UserProfile.kt new file mode 100644 index 0000000..692eaef --- /dev/null +++ b/app/src/main/java/com/example/myapplication/user/composeui/UserProfile.kt @@ -0,0 +1,176 @@ +package com.example.myapplication.user.composeui + +import android.content.res.Configuration +import androidx.compose.foundation.background +import androidx.compose.foundation.border +import androidx.compose.foundation.clickable +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.foundation.text.BasicTextField +import androidx.compose.foundation.text.KeyboardActions +import androidx.compose.foundation.text.KeyboardOptions +import androidx.compose.material3.Button +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Switch +import androidx.compose.material3.SwitchDefaults +import androidx.compose.material3.Text +import androidx.compose.material3.TextField +import androidx.compose.runtime.Composable +import androidx.compose.runtime.MutableState +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.rememberCoroutineScope +import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.text.input.PasswordVisualTransformation +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.navigation.NavController +import com.example.myapplication.composeui.navigation.Screen +import com.example.myapplication.datastore.DataStoreManager +import com.example.myapplication.datastore.SettingData +import com.example.myapplication.session.composeui.SessionList +import com.example.myapplication.ui.theme.Gray +import com.example.myapplication.ui.theme.PmudemoTheme +import kotlinx.coroutines.launch + +@Composable +fun UserProfile(navController: NavController?, isDarkTheme: MutableState, dataStoreManager: DataStoreManager) { + var username by remember { mutableStateOf("") } + var password by remember { mutableStateOf("") } + var isRegistration by remember { mutableStateOf(false) } + + LazyColumn() { + item { + Column( + modifier = Modifier + .fillMaxSize() + .padding(16.dp), + verticalArrangement = Arrangement.spacedBy(16.dp) + ) { + Text( + text = "Логин", + modifier = Modifier.align(Alignment.CenterHorizontally) + ) + BasicTextField( + value = username, + onValueChange = { newValue -> username = newValue }, + modifier = Modifier + .fillMaxWidth() + .size(36.dp) + .background(MaterialTheme.colorScheme.secondary, RoundedCornerShape(18.dp)) + .padding(start = 13.dp, top = 8.dp) + ) + + Text( + text = "Пароль", + modifier = Modifier.align(Alignment.CenterHorizontally) + ) + BasicTextField( + value = password, + onValueChange = { newValue -> password = newValue }, + modifier = Modifier + .fillMaxWidth() + .size(36.dp) + .background(MaterialTheme.colorScheme.secondary, RoundedCornerShape(18.dp)) + .padding(start = 13.dp, top = 8.dp), + visualTransformation = PasswordVisualTransformation() + ) + + if (isRegistration) { + Button( + onClick = { }, + modifier = Modifier + .fillMaxWidth() + .padding(8.dp) + ) { + Text("Регистрация") + } + Text( + text = "Уже есть аккаунт? Войти", + modifier = Modifier + .clickable { + isRegistration = false + } + .align(Alignment.CenterHorizontally), + color = MaterialTheme.colorScheme.onBackground + ) + } else { + Button( + onClick = { }, + modifier = Modifier + .fillMaxWidth() + .padding(8.dp) + ) { + Text("Вход") + } + Text( + text = "Нет аккаунта? Зарегистрироваться", + modifier = Modifier + .clickable { + isRegistration = true + } + .align(Alignment.CenterHorizontally), + color = MaterialTheme.colorScheme.onBackground + ) + } + val switchColors = SwitchDefaults.colors( + checkedThumbColor = MaterialTheme.colorScheme.primary, // Change the color when the switch is checked + checkedTrackColor = MaterialTheme.colorScheme.secondary, // Change the color of the track when the switch is checked + uncheckedThumbColor = MaterialTheme.colorScheme.primary, // Change the color when the switch is unchecked + uncheckedTrackColor = MaterialTheme.colorScheme.onPrimary // Change the color of the track when the switch is unchecked + ) + Row( + modifier = Modifier + .fillMaxWidth() + .padding(16.dp), + horizontalArrangement = Arrangement.End + ) { + Text( + "Темная тема", modifier = Modifier + .align(Alignment.CenterVertically) + .padding(5.dp) + ) + + val coroutine = rememberCoroutineScope() + + Switch( + checked = isDarkTheme.value, + onCheckedChange = { + isDarkTheme.value = !isDarkTheme.value + coroutine.launch { + dataStoreManager.saveSettings(SettingData(isDarkTheme = isDarkTheme.value)) + } + }, + colors = switchColors + ) + } + } + } + } +} + +/*@Preview(name = "Light Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_NO) +@Preview(name = "Dark Mode", showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +fun UserProfilePreview() { + PmudemoTheme { + Surface( + color = MaterialTheme.colorScheme.background + ) { + UserProfile(navController = null, isDarkTheme = remember { mutableStateOf(true) }) + } + } +}*/ diff --git a/app/src/main/java/com/example/myapplication/user/model/User.kt b/app/src/main/java/com/example/myapplication/user/model/User.kt new file mode 100644 index 0000000..b5bedb2 --- /dev/null +++ b/app/src/main/java/com/example/myapplication/user/model/User.kt @@ -0,0 +1,15 @@ +package com.example.myapplication.user.model + +import java.io.Serializable + +data class User( + val login: String, + val password: String +) : Serializable + +fun getUsers(): List { + return listOf( + User("login123", "password123"), + User("login321", "password321"), + ) +} \ No newline at end of file diff --git a/app/src/main/res/drawable/minus.xml b/app/src/main/res/drawable/minus.xml new file mode 100644 index 0000000..0ff475a --- /dev/null +++ b/app/src/main/res/drawable/minus.xml @@ -0,0 +1,8 @@ + + + \ No newline at end of file diff --git a/app/src/main/res/drawable/photo.jpg b/app/src/main/res/drawable/photo.jpg new file mode 100644 index 0000000..9fb88cf Binary files /dev/null and b/app/src/main/res/drawable/photo.jpg differ diff --git a/app/src/main/res/drawable/ticket.xml b/app/src/main/res/drawable/ticket.xml new file mode 100644 index 0000000..9e5fe53 --- /dev/null +++ b/app/src/main/res/drawable/ticket.xml @@ -0,0 +1,25 @@ + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 3de1a39..2c381a8 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1,3 +1,14 @@ - My Application + pmu-demo + Фильмы + Фильм + Заказ + Название + Год + Описание + Изображение + Корзина + Мои заказы + Профиль + Сеансы \ No newline at end of file diff --git a/app/src/main/res/values/themes.xml b/app/src/main/res/values/themes.xml index e48770a..bf6a6ee 100644 --- a/app/src/main/res/values/themes.xml +++ b/app/src/main/res/values/themes.xml @@ -1,5 +1,5 @@ -