allWithout11Window

This commit is contained in:
Your Name 2025-04-28 03:08:03 +03:00
parent 0fabe5b283
commit 1a4496c06b
23 changed files with 2553 additions and 160 deletions

View File

@ -22,10 +22,15 @@ kotlin {
sourceSets {
val desktopMain by getting
val commonMain by getting {
resources.srcDir("src/commonMain/composeResources")
}
androidMain.dependencies {
implementation(compose.preview)
implementation(libs.androidx.activity.compose)
implementation(libs.androidx.lifecycle.viewmodel)
implementation("io.ktor:ktor-client-okhttp:2.3.2")
}
commonMain.dependencies {
val voyagerVersion = "1.1.0-beta02"
@ -40,10 +45,20 @@ kotlin {
implementation("cafe.adriel.voyager:voyager-screenmodel:$voyagerVersion")
implementation(compose.preview)
implementation(libs.androidx.lifecycle.viewmodel)
implementation("media.kamel:kamel-image:0.7.0")
implementation("io.ktor:ktor-client-core:2.3.2")
implementation("io.ktor:ktor-client-cio:2.3.2")
implementation("io.ktor:ktor-client-okhttp:2.3.2")
repositories {
google()
mavenCentral()
}
}
desktopMain.dependencies {
implementation(compose.desktop.currentOs)
implementation(libs.kotlinx.coroutines.swing)
implementation("io.ktor:ktor-client-okhttp:2.3.2")
}
}
}

View File

@ -0,0 +1,80 @@
//package org.example.project.ViewModel
//
//import android.app.DatePickerDialog
//import android.widget.DatePicker
//import androidx.compose.material.OutlinedTextField
//import androidx.compose.material.Text
//import androidx.compose.material.icons.Icons
//import androidx.compose.material.icons.filled.DateRange
//import androidx.compose.runtime.*
//import androidx.compose.ui.platform.LocalContext
//import androidx.compose.ui.Modifier
//import androidx.compose.foundation.clickable
//import androidx.compose.material.Icon
//import java.util.*
//
//@Composable
//actual fun DatePickerField(
// onDateSelected: (String) -> Unit,
// trigger: Boolean,
// onDismissRequest: () -> Unit
//) {
//// val context = LocalContext.current
//// val calendar = Calendar.getInstance()
////
//// val datePickerDialog = remember {
//// DatePickerDialog(
//// context,
//// { _: DatePicker, year: Int, month: Int, dayOfMonth: Int ->
//// val formatted = "%02d.%02d.%04d".format(dayOfMonth, month + 1, year)
//// onDateSelected(formatted)
//// },
//// calendar.get(Calendar.YEAR),
//// calendar.get(Calendar.MONTH),
//// calendar.get(Calendar.DAY_OF_MONTH)
//// )
//// }
////
//// OutlinedTextField(
//// value = selectedDate,
//// onValueChange = {},
//// label = { Text("Выберите дату") },
//// trailingIcon = { Icon(Icons.Default.DateRange, contentDescription = null) },
//// readOnly = true,
//// modifier = modifier.clickable { datePickerDialog.show() }
//// )
//}
package org.example.project.ViewModel
import android.app.DatePickerDialog
import android.widget.DatePicker
import androidx.compose.runtime.*
import androidx.compose.ui.platform.LocalContext
import java.util.*
@Composable
actual fun DatePickerField(
onDateSelected: (String) -> Unit,
trigger: Boolean,
onDismissRequest: () -> Unit
) {
val context = LocalContext.current
if (trigger) {
LaunchedEffect(Unit) {
val calendar = Calendar.getInstance()
DatePickerDialog(
context,
{ _: DatePicker, year: Int, month: Int, dayOfMonth: Int ->
val formatted = "%02d.%02d.%04d".format(dayOfMonth, month + 1, year)
onDateSelected(formatted)
onDismissRequest()
},
calendar.get(Calendar.YEAR),
calendar.get(Calendar.MONTH),
calendar.get(Calendar.DAY_OF_MONTH)
).show()
}
}
}

View File

@ -0,0 +1,61 @@
//package org.example.project.ViewModel
//
//import androidx.compose.runtime.Composable
//
//@Composable
//actual fun GetPath(onPathSelected: (String) -> Unit){
//
//}
package org.example.project.ViewModel
import android.app.Activity
import android.content.Intent
import android.net.Uri
import android.provider.OpenableColumns
import androidx.activity.compose.rememberLauncherForActivityResult
import androidx.activity.result.contract.ActivityResultContracts
import androidx.compose.runtime.*
import androidx.compose.ui.platform.LocalContext
import java.io.File
import java.io.FileOutputStream
@Composable
actual fun GetPath(onPathSelected: (String) -> Unit) {
val context = LocalContext.current
var launched by remember { mutableStateOf(false) }
val launcher = rememberLauncherForActivityResult(
contract = ActivityResultContracts.GetContent(),
onResult = { uri: Uri? ->
if (uri != null) {
val inputStream = context.contentResolver.openInputStream(uri)
val fileName = getFileName(context.contentResolver, uri) ?: "temp_image.jpg"
val file = File(context.cacheDir, fileName)
val outputStream = FileOutputStream(file)
inputStream?.copyTo(outputStream)
inputStream?.close()
outputStream.close()
onPathSelected(file.absolutePath)
}
}
)
LaunchedEffect(Unit) {
if (!launched) {
launched = true
launcher.launch("image/*")
}
}
}
fun getFileName(contentResolver: android.content.ContentResolver, uri: Uri): String? {
val returnCursor = contentResolver.query(uri, null, null, null, null)
returnCursor?.use {
val nameIndex = it.getColumnIndex(OpenableColumns.DISPLAY_NAME)
if (it.moveToFirst()) {
return it.getString(nameIndex)
}
}
return null
}

View File

@ -0,0 +1,71 @@
package org.example.project.ViewModel
import android.graphics.BitmapFactory
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.ImageBitmap
import androidx.compose.ui.graphics.asImageBitmap
import androidx.compose.ui.graphics.painter.BitmapPainter
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.res.imageResource
import org.example.project.R
import java.io.File
@Composable
actual fun ImageFromPath(path: String, modifier: Modifier) {
val imageBitmap: ImageBitmap? = when {
path.isEmpty() -> {
ImageBitmap.imageResource(id = R.drawable.basic_photo)
}
else -> {
val file = File(path)
if (file.exists()) {
val bitmap = BitmapFactory.decodeFile(file.absolutePath)
bitmap?.asImageBitmap()
} else null
}
}
if (imageBitmap != null) {
Image(
painter = BitmapPainter(imageBitmap),
contentDescription = null,
modifier = modifier,
contentScale = ContentScale.Crop
)
} else {
Box(modifier = modifier.fillMaxSize())
}
}
//@Composable
//actual fun ImageFromPath(path: String, modifier: Modifier) {
// // Попытка загрузить изображение из локального пути
// if (path == ""){
// path =
// }
//
// val file = File(path)
// val imageBitmap: ImageBitmap? = if (file.exists()) {
// val bitmap = BitmapFactory.decodeFile(file.absolutePath)
// bitmap?.asImageBitmap()
// } else {
// null
// }
//
// if (imageBitmap != null) {
// Image(
// painter = BitmapPainter(imageBitmap),
// contentDescription = null,
// modifier = modifier,
// contentScale = ContentScale.Crop
// )
// } else {
// Box(modifier = modifier.fillMaxSize())
// }
//}

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View File

@ -0,0 +1,23 @@
package org.example.project.ViewModel
import androidx.compose.foundation.clickable
import androidx.compose.material.OutlinedTextField
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.material.Text
import androidx.compose.ui.Modifier
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.material.Icon
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.DateRange
import java.util.Calendar
@Composable
expect fun DatePickerField(
onDateSelected: (String) -> Unit,
trigger: Boolean,
onDismissRequest: () -> Unit
)

View File

@ -0,0 +1,106 @@
package org.example.project.ViewModel
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.Box
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.DropdownMenu
import androidx.compose.material.DropdownMenuItem
import androidx.compose.material.Icon
import androidx.compose.material.Text
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.ArrowDropDown
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.graphics.Color
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.TextUnit
import androidx.compose.ui.unit.dp
@Composable
fun FieldWithDropdown(
label: String,
options: List<String>,
selectedOption: String,
onOptionSelected: (String) -> Unit,
fontSize: TextUnit,
labelWidth: Float
) {
var expanded by remember { mutableStateOf(false) }
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.weight(labelWidth)) {
Text(
text = label,
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
)
}
Box(
modifier = Modifier
.weight(1f)
.fillMaxWidth()
.background(Color.White, shape = RoundedCornerShape(4.dp))
.border(
width = 1.dp,
color = Color(0xFFCCCCCC),
shape = RoundedCornerShape(4.dp)
)
.clickable { expanded = true }
.padding(12.dp)
) {
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween,
modifier = Modifier.fillMaxWidth()
) {
Text(
text = selectedOption.ifEmpty { "..." },
fontSize = fontSize,
color = if (selectedOption.isEmpty()) Color.LightGray else Color.Black
)
Icon(
imageVector = Icons.Default.ArrowDropDown,
contentDescription = "Dropdown Arrow",
tint = Color.Gray
)
}
DropdownMenu(
expanded = expanded,
onDismissRequest = { expanded = false },
modifier = Modifier
.background(Color.White)
.fillMaxWidth()
) {
options.forEach { option ->
DropdownMenuItem(
onClick = {
onOptionSelected(option)
expanded = false
}
) {
Text(option, fontSize = fontSize, color = Color.Black)
}
}
}
}
}
}

View File

@ -0,0 +1,73 @@
package org.example.project.ViewModel
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.material.OutlinedTextField
import androidx.compose.material.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.text.style.TextAlign
import androidx.compose.ui.unit.TextUnit
import androidx.compose.ui.unit.dp
@Composable
fun FieldWithLabel(
label: String,
value: String,
onValueChange: (String) -> Unit,
placeholder: String,
fontSize: TextUnit,
labelWidth: Float,
enabled: Boolean = true,
) {
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.weight(labelWidth)) {
Text(
text = label,
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
modifier = Modifier
)
}
OutlinedTextField(
value = value,
onValueChange = onValueChange,
placeholder = {
if (placeholder.isNotEmpty()) {
Text(
text = placeholder,
fontSize = fontSize,
color = Color.LightGray
)
}
},
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSize,
color = Color.Black
),
enabled = enabled,
colors = androidx.compose.material.TextFieldDefaults.outlinedTextFieldColors(
backgroundColor = Color.White,
cursorColor = Color.Black,
textColor = Color.Black,
placeholderColor = Color.LightGray,
focusedBorderColor = Color(0xFFCCCCCC),
unfocusedBorderColor = Color(0xFFCCCCCC),
disabledBorderColor = Color(0xFFCCCCCC)
),
modifier = Modifier.weight(1f).wrapContentWidth().fillMaxWidth()
)
}
}

View File

@ -0,0 +1,86 @@
package org.example.project.ViewModel
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.foundation.text.KeyboardOptions
import androidx.compose.material.OutlinedTextField
import androidx.compose.material.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.text.input.KeyboardType
import androidx.compose.ui.text.input.ImeAction
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.TextUnit
import androidx.compose.ui.unit.dp
@Composable
fun FieldWithLabelInt(
label: String,
value: Int,
onValueChange: (Int) -> Unit,
placeholder: String,
fontSize: TextUnit,
labelWidth: Float,
enabled: Boolean = true,
) {
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.weight(labelWidth)) {
Text(
text = label,
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
)
}
OutlinedTextField(
value = value.toString(),
onValueChange = { newValue ->
val intValue = newValue.toIntOrNull()
if (intValue != null) {
onValueChange(intValue)
}
},
placeholder = {
if (placeholder.isNotEmpty()) {
Text(
text = placeholder,
fontSize = fontSize,
color = Color.LightGray
)
}
},
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSize,
color = Color.Black
),
enabled = enabled,
colors = androidx.compose.material.TextFieldDefaults.outlinedTextFieldColors(
backgroundColor = Color.White,
cursorColor = Color.Black,
textColor = Color.Black,
placeholderColor = Color.LightGray,
focusedBorderColor = Color(0xFFCCCCCC),
unfocusedBorderColor = Color(0xFFCCCCCC),
disabledBorderColor = Color(0xFFCCCCCC)
),
keyboardOptions = KeyboardOptions(
keyboardType = KeyboardType.Number,
imeAction = ImeAction.Done
),
modifier = Modifier
.weight(1f)
.wrapContentWidth()
.fillMaxWidth()
)
}
}

View File

@ -0,0 +1,7 @@
package org.example.project.ViewModel
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
@Composable
expect fun GetPath(onPathSelected: (String) -> Unit)

View File

@ -0,0 +1,18 @@
package org.example.project.ViewModel
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.remember
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.painter.Painter
import androidx.compose.ui.layout.ContentScale
import io.kamel.image.asyncPainterResource
import io.kamel.core.Resource
import io.kamel.core.getOrNull
@Composable
expect fun ImageFromPath(path: String = "", modifier: Modifier = Modifier)

View File

@ -0,0 +1,217 @@
package org.example.project.ui.Screens
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxWithConstraints
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.aspectRatio
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.Button
import androidx.compose.material.ButtonDefaults
import androidx.compose.material.MaterialTheme
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.TimerViewModel
class ConfirmRunnerScreen(private val timerViewModel: TimerViewModel) :
Screen {
@Composable
override fun Content() {
val navigator = LocalNavigator.currentOrThrow
Scaffold(
topBar = { ConfirmRunnerTopBar() },
bottomBar = { ConfirmRunnerBottomBar(timerViewModel = timerViewModel) }
) { paddingValues ->
Box(
modifier = Modifier.padding(paddingValues)
) {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
.padding(horizontal = 100.dp)
) {
val fontSizeFirst = (maxWidth.value / 30).sp
val fontSizeSecond = (maxWidth.value / 40).sp
Column(
modifier = Modifier
.fillMaxWidth().padding(bottom = 16.dp),
horizontalAlignment = Alignment.CenterHorizontally,
) {
Spacer(modifier = Modifier.weight(0.2f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Спасибо за вашу регистрацию в качестве бегуна!",
color = Color.Gray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.2f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Спасибо за вашу регистрацию в качестве бегуна в Marathon Skills 2016!\n С вами свяжутся по поводу оплаты.",
color = Color.Black,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.2f))
Button(
onClick = { navigator.push(InfoRunnerScreen(timerViewModel)) },
modifier = Modifier
.fillMaxWidth()
.height(48.dp),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Ок", fontSize = fontSizeSecond)
}
Spacer(modifier = Modifier.weight(1f))
}
}
}
}
}
@Composable
private fun ConfirmRunnerTopBar() {
val navigator = LocalNavigator.currentOrThrow
Box {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
) {
val fontSizeButton = (maxWidth.value / 50).sp
val fontSizeText = (maxWidth.value / 25).sp
Row(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(16.dp),
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween
) {
Button(
onClick = { },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Назад",
color = Color.Black,
fontSize = fontSizeButton
)
}
Spacer(modifier = Modifier.width(24.dp))
Text(
text = "MARATHON SKILLS 2016",
style = MaterialTheme.typography.h6,
modifier = Modifier.weight(1f),
textAlign = TextAlign.Left,
fontWeight = FontWeight.Bold,
fontSize = fontSizeText,
color = Color.White
)
Spacer(modifier = Modifier.width(64.dp))
Button(
onClick = { navigator.push(MainScreen()) },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Logout",
color = Color.Black,
fontSize = fontSizeButton
)
}
}
}
}
}
@Composable
private fun ConfirmRunnerBottomBar(timerViewModel: TimerViewModel) {
val remainingTime = timerViewModel.remainingTime.collectAsState().value
Box {
BoxWithConstraints(
modifier = Modifier
.align(Alignment.Center)
) {
val fontSize = (maxWidth.value / 50).sp
Column(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(8.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Text(
text = remainingTime,
color = Color.White,
fontSize = fontSize
)
}
}
}
}
}

View File

@ -0,0 +1,235 @@
package org.example.project.ui.Screens
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxWithConstraints
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.aspectRatio
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.Button
import androidx.compose.material.ButtonDefaults
import androidx.compose.material.MaterialTheme
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.TimerViewModel
class ConfirmSponsorScreen(private val timerViewModel: TimerViewModel, private val sumSpons: String, private val runner: String, private val blagot: String) :
Screen {
@Composable
override fun Content() {
val navigator = LocalNavigator.currentOrThrow
Scaffold(
topBar = { ConfirmSponsorTopBar() },
bottomBar = { ConfirmSponsorBottomBar(timerViewModel = timerViewModel) }
) { paddingValues ->
Box(
modifier = Modifier.padding(paddingValues)
) {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
.padding(horizontal = 100.dp)
) {
val fontSize = (maxWidth.value / 60).sp
val fontSizeFirst = (maxWidth.value / 30).sp
val fontSizeSecond = (maxWidth.value / 40).sp
val fontSizeThird = (maxWidth.value / 50).sp
val fontSizeFourth = (maxWidth.value / 10).sp
val fontSizeFiveth = (maxWidth.value / 20).sp
Column(
modifier = Modifier
.fillMaxWidth().padding(bottom = 16.dp),
horizontalAlignment = Alignment.CenterHorizontally,
) {
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Спасибо за вашу спонсорскую поддержку!",
color = Color.Gray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Спасибо за поддержку бегуна в Marathon Skills 2016! Ваше пожертвование пойдёт в его благотворительную организацию",
color = Color.Black,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = runner,
color = Color.Black,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = blagot,
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFiveth,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = sumSpons,
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFourth,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Button(
onClick = { navigator.push(MainScreen()) },
modifier = Modifier
.fillMaxWidth()
.height(48.dp),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Назад", fontSize = fontSizeSecond)
}
}
}
}
}
}
@Composable
private fun ConfirmSponsorTopBar() {
val navigator = LocalNavigator.currentOrThrow
Box {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
) {
val fontSizeButton = (maxWidth.value / 50).sp
val fontSizeText = (maxWidth.value / 25).sp
Row(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(16.dp),
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween
) {
Button(
onClick = { },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Назад",
color = Color.Black,
fontSize = fontSizeButton
)
}
Spacer(modifier = Modifier.width(24.dp))
Text(
text = "MARATHON SKILLS 2016",
style = MaterialTheme.typography.h6,
modifier = Modifier.weight(1f),
textAlign = TextAlign.Left,
fontWeight = FontWeight.Bold,
fontSize = fontSizeText,
color = Color.White
)
}
}
}
}
@Composable
private fun ConfirmSponsorBottomBar(timerViewModel: TimerViewModel) {
val remainingTime = timerViewModel.remainingTime.collectAsState().value
Box {
BoxWithConstraints(
modifier = Modifier
.align(Alignment.Center)
) {
val fontSize = (maxWidth.value / 50).sp
Column(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(8.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Text(
text = remainingTime,
color = Color.White,
fontSize = fontSize
)
}
}
}
}
}

View File

@ -0,0 +1,464 @@
package org.example.project.ui.Screens
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.BoxWithConstraints
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.aspectRatio
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.layout.wrapContentWidth
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.Button
import androidx.compose.material.ButtonDefaults
import androidx.compose.material.Icon
import androidx.compose.material.MaterialTheme
import androidx.compose.material.OutlinedTextField
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.DateRange
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.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.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.FieldWithDropdown
import org.example.project.ViewModel.FieldWithLabel
import org.example.project.ViewModel.TimerViewModel
class ForSponsorScreen(private val timerViewModel: TimerViewModel) : Screen {
@Composable
override fun Content() {
val navigator = LocalNavigator.currentOrThrow
Scaffold(
topBar = { ForSponsorTopBar() },
bottomBar = { ForSposnorBottomBar(timerViewModel = timerViewModel) }
) { paddingValues ->
Box(
modifier = Modifier.padding(paddingValues)
) {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
.padding(horizontal = 100.dp)
) {
val fontSize = (maxWidth.value / 60).sp
val fontSizeFirst = (maxWidth.value / 30).sp
val fontSizeSecond = (maxWidth.value / 40).sp
val fontSizeThird = (maxWidth.value / 50).sp
val fontSizeFourth = (maxWidth.value / 10).sp
val labelWidth = 0.5f
var fio by remember { mutableStateOf("") }
val runners = listOf(
"bob",
"bobby",
"baby"
)
var runner by remember { mutableStateOf("") }
var cardName by remember { mutableStateOf("") }
var cardNum by remember { mutableStateOf("") }
var srokM by remember { mutableStateOf("") }
var srokY by remember { mutableStateOf("") }
var cvc by remember { mutableStateOf("") }
var sumChangStr by remember { mutableStateOf("10")}
var sumChang by remember { mutableStateOf(sumChangStr.toInt()) }
var sumSpons by remember { mutableStateOf(0)}
Column(
modifier = Modifier
.fillMaxWidth().padding(bottom = 16.dp),
horizontalAlignment = Alignment.CenterHorizontally,
) {
Text(
text = "Спонсор бегуна",
color = Color.DarkGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.fillMaxWidth()
)
Spacer(Modifier.weight(0.1f))
Text(
text = "Пожалуйста выберите бегуна, которого вы хотели бы спонсировать и сумму, которую вы хотели бы спонсировать. Спасибо за вашу поддержку бегунов и их благотворительных учреждений.",
color = Color.DarkGray,
textAlign = TextAlign.Center,
fontSize = fontSizeSecond,
modifier = Modifier.fillMaxWidth(),
)
Spacer(Modifier.weight(0.2f))
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.spacedBy(16.dp)
) {
Column(modifier = Modifier.weight(1f),) {
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Информация о спонсоре",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Ваше имя:",
value = fio,
onValueChange = { fio = it },
placeholder = "Ваше имя",
fontSize = fontSizeSecond,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithDropdown(
label = "Бегун:",
options = runners,
selectedOption = runner,
onOptionSelected = { runner = it },
fontSize = fontSizeSecond,
labelWidth = labelWidth
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Карта:",
value = cardName,
onValueChange = { cardName = it },
placeholder = "Владелец карты",
fontSize = fontSizeSecond,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Номер карты#:",
value = cardNum,
onValueChange = { cardNum = it },
placeholder = "...",
fontSize = fontSizeSecond,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
Row(
verticalAlignment = Alignment.CenterVertically,
modifier = Modifier.fillMaxWidth()
) {
Text(
text = "Срок действия:",
fontSize = fontSizeSecond,
color = Color.Black,
modifier = Modifier.weight(labelWidth)
)
OutlinedTextField(
value = srokM,
onValueChange = { srokM = it },
placeholder = { Text("MM", fontSize = fontSizeSecond) },
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSizeSecond,
color = Color.Black
),
modifier = Modifier
.weight((1f - labelWidth) / 2)
.padding(end = 4.dp),
singleLine = true
)
OutlinedTextField(
value = srokY,
onValueChange = { srokY = it },
placeholder = { Text("YY", fontSize = fontSizeSecond) },
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSizeSecond,
color = Color.Black
),
modifier = Modifier
.weight((1f - labelWidth) / 2)
.padding(start = 4.dp),
singleLine = true
)
}
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "CVC:",
value = cvc,
onValueChange = { cvc = it },
placeholder = "...",
fontSize = fontSizeSecond,
labelWidth = labelWidth,
)
}
Column(modifier = Modifier.weight(1f),) {
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Благотворительность",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "blagot...",
color = Color.Black,
textAlign = TextAlign.Center,
fontSize = fontSizeSecond,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.5f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Сумма пожертвования",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "$" + sumSpons.toString(),
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFourth,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Row(
verticalAlignment = Alignment.CenterVertically,
modifier = Modifier.fillMaxWidth()
) {
Button(
modifier = Modifier
.weight(0.2f)
.aspectRatio(1f),
onClick = {
sumSpons -= sumChang
},
shape = RoundedCornerShape(8.dp),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
) {
Text("-", fontSize = fontSizeSecond)
}
OutlinedTextField(
value = sumChangStr,
onValueChange = {
sumChangStr = it
sumChang = it.toIntOrNull() ?: 0
},
placeholder = { Text("...", fontSize = fontSizeSecond) },
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSizeSecond,
color = Color.Black,
textAlign = TextAlign.Center
),
modifier = Modifier
.weight(0.6f)
.padding(horizontal = 4.dp),
singleLine = true
)
Button(
modifier = Modifier
.weight(0.2f)
.aspectRatio(1f),
onClick = {
sumSpons += sumChang
},
shape = RoundedCornerShape(8.dp),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
) {
Text("+", fontSize = fontSizeSecond)
}
}
Spacer(modifier = Modifier.weight(0.5f))
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceEvenly,
modifier = Modifier
.fillMaxWidth()
.padding(horizontal = 16.dp, vertical = 8.dp)
) {
Button(
onClick = { navigator.push(ConfirmSponsorScreen(timerViewModel, sumSpons.toString(), runner, "blagodat..."))},
modifier = Modifier.weight(1f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Заплатить", fontSize = fontSizeThird)
}
Spacer(modifier = Modifier.weight(0.1f))
Button(
onClick = { navigator.push(MainScreen()) },
modifier = Modifier.weight(1f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Отмена", fontSize = fontSizeThird)
}
}
}
}
}
}
}
}
}
@Composable
private fun ForSponsorTopBar() {
val navigator = LocalNavigator.currentOrThrow
Box {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
) {
val fontSizeButton = (maxWidth.value / 50).sp
val fontSizeText = (maxWidth.value / 25).sp
Row(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(16.dp),
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween
) {
Button(
onClick = { },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Назад",
color = Color.Black,
fontSize = fontSizeButton
)
}
Spacer(modifier = Modifier.width(24.dp))
Text(
text = "MARATHON SKILLS 2016",
style = MaterialTheme.typography.h6,
modifier = Modifier.weight(1f),
textAlign = TextAlign.Left,
fontWeight = FontWeight.Bold,
fontSize = fontSizeText,
color = Color.White
)
}
}
}
}
@Composable
private fun ForSposnorBottomBar(timerViewModel: TimerViewModel) {
val remainingTime = timerViewModel.remainingTime.collectAsState().value
Box {
BoxWithConstraints(
modifier = Modifier
.align(Alignment.Center)
) {
val fontSize = (maxWidth.value / 50).sp
Column(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(8.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Text(
text = remainingTime,
color = Color.White,
fontSize = fontSize
)
}
}
}
}
}

View File

@ -0,0 +1,234 @@
package org.example.project.ui.Screens
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxWithConstraints
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.height
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.Button
import androidx.compose.material.ButtonDefaults
import androidx.compose.material.MaterialTheme
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.font.FontStyle
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.TextUnit
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.TimerViewModel
class InfoRunnerScreen(private val timerViewModel: TimerViewModel) : Screen {
@Composable
override fun Content() {
val navigator = LocalNavigator.currentOrThrow
Scaffold(
topBar = { InfoRunnerTopBar() },
bottomBar = { InfoRunnerBottomBar(timerViewModel = timerViewModel) }
) { paddingValues ->
Box(
modifier = Modifier
.padding(paddingValues)
) {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
.padding(horizontal = 100.dp)
) {
val fontSize = (maxWidth.value / 25).sp
val fontSizeButton = (maxWidth.value / 40).sp
Column(
modifier = Modifier
.padding(16.dp)
.fillMaxSize(),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.SpaceBetween
) {
Text(
text = "Подробная информация",
color = Color.DarkGray,
textAlign = TextAlign.Center,
fontSize = fontSize,
)
Row(
modifier = Modifier
.fillMaxWidth()
.weight(1f),
horizontalArrangement = Arrangement.SpaceEvenly,
verticalAlignment = Alignment.CenterVertically
) {
Column(
modifier = Modifier
.weight(1f)
.padding(end = 8.dp),
verticalArrangement = Arrangement.spacedBy(16.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
InfoButton("Регистрация на марафон", fontSizeButton)
InfoButton("Редактирование профиля", fontSizeButton)
InfoButton("Контакты", fontSizeButton)
}
Column(
modifier = Modifier
.weight(1f)
.padding(start = 8.dp),
verticalArrangement = Arrangement.spacedBy(16.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
InfoButton("Мои результаты", fontSizeButton)
InfoButton("Мои спонсоры", fontSizeButton)
}
}
}
}
}
}
}
@Composable
private fun InfoButton(text: String, fontSize: TextUnit) {
Button(
onClick = { },
modifier = Modifier
.fillMaxWidth()
.height(80.dp),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text(text = text, fontStyle = FontStyle.Italic, fontSize = fontSize, textAlign = TextAlign.Center)
}
}
@Composable
private fun InfoRunnerTopBar() {
val navigator = LocalNavigator.currentOrThrow
Box {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
) {
val fontSizeButton = (maxWidth.value / 50).sp
val fontSizeText = (maxWidth.value / 25).sp
Row(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(16.dp),
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween
) {
Button(
onClick = { navigator.push(MainScreen()) },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Назад",
color = Color.Black,
fontSize = fontSizeButton
)
}
Spacer(modifier = Modifier.width(24.dp))
Text(
text = "MARATHON SKILLS 2016",
style = MaterialTheme.typography.h6,
modifier = Modifier.weight(1f),
textAlign = TextAlign.Left,
fontWeight = FontWeight.Bold,
fontSize = fontSizeText,
color = Color.White
)
Spacer(modifier = Modifier.width(64.dp))
Button(
onClick = { navigator.push(MainScreen()) },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Logout",
color = Color.Black,
fontSize = fontSizeButton
)
}
}
}
}
}
@Composable
private fun InfoRunnerBottomBar(timerViewModel: TimerViewModel) {
val remainingTime = timerViewModel.remainingTime.collectAsState().value
Box {
BoxWithConstraints(
modifier = Modifier
.align(Alignment.Center)
) {
val fontSize = (maxWidth.value / 50).sp
Column(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(8.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Text(
text = remainingTime,
color = Color.White,
fontSize = fontSize
)
}
}
}
}
}

View File

@ -38,6 +38,7 @@ import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.FieldWithLabel
import org.example.project.ViewModel.TimerViewModel
class LoginScreen(private val timerViewModel: TimerViewModel) : Screen {
@ -63,7 +64,7 @@ class LoginScreen(private val timerViewModel: TimerViewModel) : Screen {
val fontSize = (maxWidth.value / 25).sp
val fontSizeFirst = (maxWidth.value / 20).sp
val fontSizeSecond = (maxWidth.value / 35).sp
val labelWidth = 120.dp
val labelWidth = 0.25f
var email by remember { mutableStateOf("") }
var password by remember { mutableStateOf("") }
@ -94,69 +95,25 @@ class LoginScreen(private val timerViewModel: TimerViewModel) : Screen {
Spacer(Modifier.weight(0.25f))
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.width(labelWidth)) {
Text(
text = "Email:",
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
modifier = Modifier.padding(start = 40.dp),
)
}
TextField(
FieldWithLabel(
label = "Email:",
value = email,
onValueChange = { email = it },
placeholder = {
Text(
text = "Enter your email address",
placeholder = "Enter your email address",
fontSize = fontSize,
color = Color.LightGray
labelWidth = labelWidth,
)
},
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSize
),
modifier = Modifier
.weight(1f)
)
}
Spacer(Modifier.weight(0.25f))
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.width(labelWidth)) {
Text(
text = "Password:",
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
)
}
TextField(
FieldWithLabel(
label = "Password:",
value = password,
onValueChange = { password = it },
placeholder = {
Text(
text = "Enter your password",
placeholder = "Enter your password",
fontSize = fontSize,
color = Color.LightGray
labelWidth = labelWidth,
)
},
modifier = Modifier
.weight(1f)
)
}
Spacer(Modifier.weight(0.25f))
@ -165,7 +122,7 @@ class LoginScreen(private val timerViewModel: TimerViewModel) : Screen {
horizontalArrangement = Arrangement.Center
) {
Button(
onClick = { },
onClick = { navigator.push(InfoRunnerScreen(timerViewModel))},
modifier = Modifier
.fillMaxWidth()
.weight(1f),
@ -184,7 +141,7 @@ class LoginScreen(private val timerViewModel: TimerViewModel) : Screen {
Spacer(Modifier.weight(0.25f))
Button(
onClick = { },
onClick = { navigator.push(MainScreen()) },
modifier = Modifier
.fillMaxWidth()
.weight(1f),

View File

@ -65,7 +65,7 @@ class MainScreen : Screen {
Spacer(modifier = Modifier.height(16.dp))
Button(
onClick = { },
onClick = { navigator.push(ForSponsorScreen(timerViewModel))},
modifier = Modifier
.fillMaxWidth()
.weight(1f),

View File

@ -0,0 +1,415 @@
package org.example.project.ui.Screens
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxWithConstraints
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.Button
import androidx.compose.material.ButtonDefaults
import androidx.compose.material.Checkbox
import androidx.compose.material.MaterialTheme
import androidx.compose.material.RadioButton
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.FieldWithDropdown
import org.example.project.ViewModel.FieldWithLabel
import org.example.project.ViewModel.FieldWithLabelInt
import org.example.project.ViewModel.TimerViewModel
class RegMaraphonScreen(private val timerViewModel: TimerViewModel) : Screen {
@Composable
override fun Content() {
val navigator = LocalNavigator.currentOrThrow
Scaffold(
topBar = { RegMaraphonTopBar() },
bottomBar = { RegMaraphonBottomBar(timerViewModel = timerViewModel) }
) { paddingValues ->
Box(
modifier = Modifier.padding(paddingValues)
) {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
.padding(horizontal = 100.dp)
) {
val fontSize = (maxWidth.value / 60).sp
val fontSizeFirst = (maxWidth.value / 30).sp
val fontSizeSecond = (maxWidth.value / 40).sp
val fontSizeThird = (maxWidth.value / 50).sp
val fontSizeFourth = (maxWidth.value / 10).sp
var finalSum by remember { mutableStateOf(0) }
var previousAddonPrice by remember { mutableStateOf(0) }
var checked1 by remember { mutableStateOf(false) }
var checked2 by remember { mutableStateOf(false) }
var checked3 by remember { mutableStateOf(false) }
val options = listOf(
"Вариант А($0): Номер бегуна + RFID браслет",
"Вариант B($20): вариант A + бейсболка + бутылка воды",
"Вариант C($45): Вариант B + футболка + сувенирный буклет"
)
var blagi = listOf(
"Что-то",
"Ещё что-то"
)
var selectedOption by remember { mutableStateOf(options[0]) }
var vznos by remember { mutableStateOf("")}
var sumVznos by remember { mutableStateOf(0)}
Column(
modifier = Modifier
.fillMaxWidth().padding(bottom = 16.dp),
horizontalAlignment = Alignment.CenterHorizontally,
) {
Text(
text = "Регистрация на марафон",
color = Color.DarkGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.fillMaxWidth()
)
Spacer(Modifier.weight(0.1f))
Text(
text = "Пожалуйста, заполните всю информацию, чтобы зарегестрироваться на Skills Marathon 2016 проводимом в Москве. Russia. С вами свяжутся после регистрации для уточнения оплаты и другой информации.",
color = Color.DarkGray,
textAlign = TextAlign.Center,
fontSize = fontSizeSecond,
modifier = Modifier.fillMaxWidth(),
)
Spacer(Modifier.weight(0.2f))
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.spacedBy(16.dp)
) {
Column(modifier = Modifier.weight(1f), ) {
Spacer(modifier = Modifier.weight(0.1f))
Text(
text = "Вид марафона",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier
)
Row(verticalAlignment = Alignment.CenterVertically) {
Checkbox(
checked = checked1,
onCheckedChange = { isChecked ->
checked1 = isChecked
if (isChecked) {
finalSum += 145
} else {
finalSum -= 145
}
}
)
Spacer(modifier = Modifier.width(8.dp))
Text(text = "42km Полный марафон($145)", fontSize = fontSizeSecond)
}
Row(verticalAlignment = Alignment.CenterVertically) {
Checkbox(
checked = checked2,
onCheckedChange = { isChecked ->
checked2 = isChecked
if (isChecked) {
finalSum += 75
} else {
finalSum -= 75
}
}
)
Spacer(modifier = Modifier.width(8.dp))
Text(text = "21km Поулмарафон($75)", fontSize = fontSizeSecond)
}
Row(verticalAlignment = Alignment.CenterVertically) {
Checkbox(
checked = checked3,
onCheckedChange = { isChecked ->
checked3 = isChecked
if (isChecked) {
finalSum += 20
} else {
finalSum -= 20
}
}
)
Spacer(modifier = Modifier.width(8.dp))
Text(text = "5km Малая дистанция($20)", fontSize = fontSizeSecond)
}
Text(
text = "Детали спонсорства",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier
)
FieldWithDropdown(
label = "Взнос:",
options = blagi,
selectedOption = vznos,
onOptionSelected = { vznos = it },
fontSize = fontSizeSecond,
labelWidth = 0.5f
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabelInt(
label = "Сумма взноса:",
value = sumVznos,
onValueChange = { sumVznos = it },
placeholder = "$$$",
fontSize = fontSizeSecond,
labelWidth = 0.5f,
)
Spacer(modifier = Modifier.weight(0.1f))
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceEvenly,
modifier = Modifier
.fillMaxWidth()
.padding(horizontal = 16.dp, vertical = 8.dp)
) {
Button(
onClick = { navigator.push(ConfirmRunnerScreen(timerViewModel))},
modifier = Modifier.weight(1f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Регистрация", fontSize = fontSizeThird)
}
Spacer(modifier = Modifier.weight(0.1f))
Button(
onClick = { navigator.push(MainScreen()) },
modifier = Modifier.weight(1f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Отмена", fontSize = fontSizeThird)
}
}
}
Column(modifier = Modifier.weight(1f)) {
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Варианты комплектов",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
options.forEach { text ->
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center
) {
RadioButton(
selected = (text == selectedOption),
onClick = {
val newAddonPrice = when (text) {
options[0] -> 0
options[1] -> 20
options[2] -> 45
else -> 0
}
finalSum = finalSum - previousAddonPrice + newAddonPrice
previousAddonPrice = newAddonPrice
selectedOption = text
}
)
Spacer(modifier = Modifier.weight(0.01f))
Text(text = text, fontSize = fontSizeSecond)
}
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "Регистрационный взнос",
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFirst,
modifier = Modifier.align(Alignment.Center)
)
}
Spacer(modifier = Modifier.weight(0.1f))
Box(modifier = Modifier.fillMaxWidth()) {
Text(
text = "$" + finalSum.toString(),
color = Color.LightGray,
textAlign = TextAlign.Center,
fontSize = fontSizeFourth,
modifier = Modifier.align(Alignment.Center)
)
}
}
}
}
}
}
}
}
@Composable
private fun RegMaraphonTopBar() {
val navigator = LocalNavigator.currentOrThrow
Box {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
) {
val fontSizeButton = (maxWidth.value / 50).sp
val fontSizeText = (maxWidth.value / 25).sp
Row(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(16.dp),
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceBetween
) {
Button(
onClick = { },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Назад",
color = Color.Black,
fontSize = fontSizeButton
)
}
Spacer(modifier = Modifier.width(24.dp))
Text(
text = "MARATHON SKILLS 2016",
style = MaterialTheme.typography.h6,
modifier = Modifier.weight(1f),
textAlign = TextAlign.Left,
fontWeight = FontWeight.Bold,
fontSize = fontSizeText,
color = Color.White
)
Spacer(modifier = Modifier.width(64.dp))
Button(
onClick = { navigator.push(MainScreen()) },
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
elevation = null,
shape = RoundedCornerShape(15.dp),
modifier = Modifier
.wrapContentWidth()
) {
Text(
text = "Logout",
color = Color.Black,
fontSize = fontSizeButton
)
}
}
}
}
}
@Composable
private fun RegMaraphonBottomBar(timerViewModel: TimerViewModel) {
val remainingTime = timerViewModel.remainingTime.collectAsState().value
Box {
BoxWithConstraints(
modifier = Modifier
.align(Alignment.Center)
) {
val fontSize = (maxWidth.value / 50).sp
Column(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(8.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Text(
text = remainingTime,
color = Color.White,
fontSize = fontSize
)
}
}
}
}
}

View File

@ -1,23 +1,40 @@
package org.example.project.ui.Screens
import androidx.compose.foundation.background
import androidx.compose.foundation.Image
import androidx.compose.ui.res.painterResource
import androidx.compose.foundation.border
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxWithConstraints
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.height
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.size
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.layout.wrapContentWidth
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.Button
import androidx.compose.material.ButtonDefaults
import androidx.compose.material.DropdownMenu
import androidx.compose.material.DropdownMenuItem
import androidx.compose.material.Icon
import androidx.compose.material.IconButton
import androidx.compose.material.MaterialTheme
import androidx.compose.material.OutlinedTextField
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.material.TextField
import androidx.compose.material.contentColorFor
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.ArrowDropDown
import androidx.compose.material.icons.filled.DateRange
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
@ -26,6 +43,7 @@ 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.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
@ -36,6 +54,11 @@ import androidx.compose.ui.unit.sp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import org.example.project.ViewModel.DatePickerField
import org.example.project.ViewModel.FieldWithDropdown
import org.example.project.ViewModel.FieldWithLabel
import org.example.project.ViewModel.GetPath
import org.example.project.ViewModel.ImageFromPath
import org.example.project.ViewModel.TimerViewModel
class RegRunnerScreen(private val timerViewModel: TimerViewModel) : Screen {
@ -46,31 +69,53 @@ class RegRunnerScreen(private val timerViewModel: TimerViewModel) : Screen {
Scaffold(
topBar = { RegRunnerTopBar() },
bottomBar = { RegRunnerBottomBar(timerViewModel = timerViewModel) }
bottomBar = { BottomSection(timerViewModel = timerViewModel) }
) { paddingValues ->
Box(
modifier = Modifier.padding(paddingValues)
modifier = Modifier.padding(paddingValues).fillMaxSize()
) {
BoxWithConstraints(
modifier = Modifier
.fillMaxWidth()
.align(Alignment.Center)
.padding(horizontal = 100.dp)
.padding(horizontal = 10.dp)
) {
val fontSize = (maxWidth.value / 25).sp
val fontSizeFirst = (maxWidth.value / 20).sp
val fontSizeSecond = (maxWidth.value / 35).sp
val labelWidth = 120.dp
val fontSize = (maxWidth.value / 60).sp
val fontSizeFirst = (maxWidth.value / 30).sp
val fontSizeSecond = (maxWidth.value / 40).sp
val labelWidth = 0.5f
var email by remember { mutableStateOf("") }
var password by remember { mutableStateOf("") }
var secondPassword by remember { mutableStateOf("") }
var name by remember { mutableStateOf("") }
var surname by remember { mutableStateOf("") }
var gender by remember { mutableStateOf("") }
var country by remember { mutableStateOf("") }
var photoPath by remember { mutableStateOf("") }
var openPicker by remember { mutableStateOf(false) }
if (openPicker) {
GetPath { selected ->
photoPath = selected
openPicker = false
}
}
var showDatePicker by remember { mutableStateOf(false) }
var dateBirthday by remember { mutableStateOf("") }
if (showDatePicker) {
DatePickerField(
onDateSelected = {
dateBirthday = it
},
trigger = true,
onDismissRequest = { showDatePicker = false }
)
}
Column(
modifier = Modifier
.fillMaxWidth(),
.fillMaxWidth().padding(bottom = 16.dp),
horizontalAlignment = Alignment.CenterHorizontally,
) {
Spacer(Modifier.weight(0.25f))
Text(
text = "Регистрация бегуна",
color = Color.DarkGray,
@ -79,7 +124,7 @@ class RegRunnerScreen(private val timerViewModel: TimerViewModel) : Screen {
modifier = Modifier.fillMaxWidth()
)
Spacer(Modifier.weight(0.25f))
Spacer(Modifier.weight(0.1f))
Text(
text = "Пожалуйста, заполните всю информацию, чтобы зарегестрироваться в качестве участника",
@ -93,101 +138,233 @@ class RegRunnerScreen(private val timerViewModel: TimerViewModel) : Screen {
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.spacedBy(32.dp)
horizontalArrangement = Arrangement.spacedBy(16.dp)
) {
Column(modifier = Modifier.weight(1f)) {
Column(modifier = Modifier.weight(0.8f)) {
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Email:",
value = email,
onValueChange = { email = it },
placeholder = "Enter your email address",
placeholder = "Email",
fontSize = fontSize,
labelWidth = labelWidth
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Password:",
label = "Пароль:",
value = password,
onValueChange = { password = it },
placeholder = "Enter your password",
placeholder = "Пароль",
fontSize = fontSize,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Повторите пароль:",
value = secondPassword,
onValueChange = { secondPassword = it },
placeholder = "Повторите пароль",
fontSize = fontSize,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Имя:",
value = name,
onValueChange = { name = it },
placeholder = "Имя",
fontSize = fontSize,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithLabel(
label = "Фамилия:",
value = surname,
onValueChange = { surname = it },
placeholder = "Фамилия",
fontSize = fontSize,
labelWidth = labelWidth,
)
Spacer(modifier = Modifier.weight(0.1f))
FieldWithDropdown(
label = "Пол:",
options = listOf("Мужской", "Остальное"),
selectedOption = gender,
onOptionSelected = { gender = it },
fontSize = fontSize,
labelWidth = labelWidth
)
}
Column(modifier = Modifier.weight(1f)) {
FieldWithLabel(
label = "Email:",
value = email,
onValueChange = { email = it },
placeholder = "Enter your email address",
fontSize = fontSize,
labelWidth = labelWidth
ImageFromPath(
path = photoPath,
modifier = Modifier
.weight(0.4f)
.clip(RoundedCornerShape(8.dp))
.border(1.dp, Color.Gray, RoundedCornerShape(8.dp)).align(Alignment.End)
)
Spacer(modifier = Modifier.weight(0.1f))
Spacer(modifier = Modifier.weight(0.05f))
FieldWithLabel(
label = "Password:",
value = password,
onValueChange = { password = it },
placeholder = "Enter your password",
fontSize = fontSize,
labelWidth = labelWidth
)
}
}
}
}
}
}
}
@Composable
fun FieldWithLabel(
label: String,
value: String,
onValueChange: (String) -> Unit,
placeholder: String,
fontSize: TextUnit,
labelWidth: Dp,
enabled: Boolean = true
) {
Row(
verticalAlignment = Alignment.CenterVertically,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.width(labelWidth)) {
Column(modifier = Modifier.weight(0.3f)) {
Text(
text = label,
text = "Фото файл:",
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
modifier = Modifier.padding(start = 40.dp),
modifier = Modifier
)
}
TextField(
value = value,
onValueChange = onValueChange,
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
OutlinedTextField(
value = photoPath,
onValueChange = {photoPath = it},
placeholder = {
if (placeholder.isNotEmpty()) {
Text(
text = placeholder,
text = "Photo_logo.jpg",
fontSize = fontSize,
color = Color.LightGray
)
}
},
textStyle = androidx.compose.ui.text.TextStyle(fontSize = fontSize),
modifier = Modifier.weight(1f),
enabled = enabled
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSize,
color = Color.Black
),
enabled = true,
colors = androidx.compose.material.TextFieldDefaults.outlinedTextFieldColors(
backgroundColor = Color.White,
cursorColor = Color.Black,
textColor = Color.Black,
placeholderColor = Color.LightGray,
focusedBorderColor = Color(0xFFCCCCCC),
unfocusedBorderColor = Color(0xFFCCCCCC),
disabledBorderColor = Color(0xFFCCCCCC)
),
modifier = Modifier.weight(0.6f).wrapContentWidth().fillMaxWidth()
)
Spacer(modifier = Modifier.weight(0.05f))
Button(
onClick = { openPicker = true},
modifier = Modifier
.fillMaxWidth()
.weight(0.5f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text(
"Просмотр",
fontSize = fontSize
)
}
}
Spacer(modifier = Modifier.weight(0.05f))
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.Center,
modifier = Modifier.fillMaxWidth()
) {
Box(modifier = Modifier.weight(labelWidth)) {
Text(
text = "Дата рождения",
color = Color.DarkGray,
textAlign = TextAlign.Start,
fontSize = fontSize,
modifier = Modifier
)
}
OutlinedTextField(
value = dateBirthday,
onValueChange = {dateBirthday = it},
placeholder = {
Text(
text = "...",
fontSize = fontSize,
color = Color.LightGray
)
},
textStyle = androidx.compose.ui.text.TextStyle(
fontSize = fontSize,
color = Color.Black
),
enabled = true,
colors = androidx.compose.material.TextFieldDefaults.outlinedTextFieldColors(
backgroundColor = Color.White,
cursorColor = Color.Black,
textColor = Color.Black,
placeholderColor = Color.LightGray,
focusedBorderColor = Color(0xFFCCCCCC),
unfocusedBorderColor = Color(0xFFCCCCCC),
disabledBorderColor = Color(0xFFCCCCCC)
),
modifier = Modifier.weight(0.9f).wrapContentWidth()
)
Spacer(modifier = Modifier.weight(0.05f))
Box(
modifier = Modifier
.weight(0.5f)
.fillMaxWidth()
.clip(RoundedCornerShape(15.dp))
.background(Color.LightGray)
.clickable { showDatePicker = true }
.padding(vertical = 8.dp),
contentAlignment = Alignment.Center
) {
Icon(
imageVector = Icons.Default.DateRange,
contentDescription = "Выбрать дату",
tint = Color.Black,
modifier = Modifier.size(24.dp)
)
}
}
Spacer(modifier = Modifier.weight(0.05f))
FieldWithDropdown(
label = "Страна:",
options = listOf("Russia", "Other"),
selectedOption = country,
onOptionSelected = { country = it },
fontSize = fontSize,
labelWidth = labelWidth
)
}
}
}
}
}
}
}
}
@Composable
private fun RegRunnerTopBar() {
val navigator = LocalNavigator.currentOrThrow
@ -250,27 +427,67 @@ class RegRunnerScreen(private val timerViewModel: TimerViewModel) : Screen {
@Composable
private fun RegRunnerBottomBar(timerViewModel: TimerViewModel) {
val remainingTime = timerViewModel.remainingTime.collectAsState().value
Box {
BoxWithConstraints(
modifier = Modifier
.align(Alignment.Center)
) {
val fontSize = (maxWidth.value / 50).sp
Column(
Box(
modifier = Modifier
.fillMaxWidth()
.background(Color.DarkGray)
.padding(8.dp),
horizontalAlignment = Alignment.CenterHorizontally
contentAlignment = Alignment.Center
) {
Text(
text = remainingTime,
color = Color.White,
fontSize = fontSize
fontSize = 16.sp
)
}
}
@Composable
private fun BottomSection(
timerViewModel: TimerViewModel
) {
val navigator = LocalNavigator.currentOrThrow
Column(
modifier = Modifier
.fillMaxWidth()
.background(Color.White)
) {
Row(
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceEvenly,
modifier = Modifier
.fillMaxWidth()
.padding(horizontal = 16.dp, vertical = 8.dp)
) {
Button(
onClick = { navigator.push(RegMaraphonScreen(timerViewModel)) },
modifier = Modifier.weight(1f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Регистрация")
}
Spacer(modifier = Modifier.width(16.dp))
Button(
onClick = { navigator.push(MainScreen()) },
modifier = Modifier.weight(1f),
colors = ButtonDefaults.buttonColors(
backgroundColor = Color.LightGray,
contentColor = Color.Black
),
shape = RoundedCornerShape(15.dp)
) {
Text("Отмена")
}
}
RegRunnerBottomBar(timerViewModel = timerViewModel)
}
}
}

View File

@ -0,0 +1,38 @@
package org.example.project.ViewModel
import androidx.compose.runtime.*
import java.text.SimpleDateFormat
import javax.swing.*
import java.util.*
@Composable
actual fun DatePickerField(
onDateSelected: (String) -> Unit,
trigger: Boolean,
onDismissRequest: () -> Unit
) {
if (trigger) {
LaunchedEffect(Unit) {
val dialog = JDialog()
dialog.title = "Выбор даты"
val model = SpinnerDateModel()
val spinner = JSpinner(model)
val panel = JPanel()
val button = JButton("OK")
panel.add(spinner)
panel.add(button)
dialog.contentPane = panel
dialog.setSize(200, 100)
button.addActionListener {
val date = model.date
val formatted = SimpleDateFormat("dd.MM.yyyy").format(date)
onDateSelected(formatted)
dialog.dispose()
onDismissRequest()
}
dialog.isVisible = true
}
}
}

View File

@ -0,0 +1,29 @@
package org.example.project.ViewModel
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import java.io.File
import javax.swing.JFileChooser
@Composable
actual fun GetPath(onPathSelected: (String) -> Unit) {
LaunchedEffect(Unit) {
val selectedPath = withContext(Dispatchers.IO) {
val chooser = JFileChooser()
chooser.dialogTitle = "Выберите изображение"
chooser.fileSelectionMode = JFileChooser.FILES_ONLY
val result = chooser.showOpenDialog(null)
if (result == JFileChooser.APPROVE_OPTION) {
val file: File = chooser.selectedFile
file.absolutePath
} else {
""
}
}
onPathSelected(selectedPath)
}
}

View File

@ -0,0 +1,47 @@
package org.example.project.ViewModel
import androidx.compose.runtime.Composable
import androidx.compose.ui.graphics.ImageBitmap
import androidx.compose.ui.graphics.painter.BitmapPainter
import androidx.compose.ui.graphics.toComposeImageBitmap
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.ui.Modifier
import androidx.compose.ui.layout.ContentScale
import org.jetbrains.skia.Image
import java.io.File
import java.nio.file.Files
@Composable
actual fun ImageFromPath(path: String, modifier: Modifier) {
val imageBitmap: ImageBitmap? = try {
if (path.isBlank()) {
// Загружаем из ресурсов
val resourceStream = Thread.currentThread().contextClassLoader.getResourceAsStream("drawable/basicPhoto.png")
val bytes = resourceStream.readAllBytes()
Image.makeFromEncoded(bytes).toComposeImageBitmap()
} else {
// Загружаем с абсолютного пути
val file = File(path)
if (file.exists()) {
val bytes = Files.readAllBytes(file.toPath())
Image.makeFromEncoded(bytes).toComposeImageBitmap()
} else null
}
} catch (e: Exception) {
println("Ошибка загрузки изображения: ${e.message}")
null
}
if (imageBitmap != null) {
Image(
painter = BitmapPainter(imageBitmap),
contentDescription = null,
modifier = modifier,
contentScale = ContentScale.Crop
)
} else {
Box(modifier = modifier.fillMaxSize())
}
}