Make WeatherDetailsCard vertically scrollable and add safeContentPadding

This commit is contained in:
Nebojsa Vuksic 2025-08-05 12:41:19 +02:00
parent 11dfe41249
commit f25ee25399

View File

@ -18,10 +18,7 @@ import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp import androidx.compose.ui.unit.sp
import org.jetbrains.jewel.foundation.theme.JewelTheme import org.jetbrains.jewel.foundation.theme.JewelTheme
import org.jetbrains.jewel.ui.component.ActionButton import org.jetbrains.jewel.ui.component.*
import org.jetbrains.jewel.ui.component.HorizontallyScrollableContainer
import org.jetbrains.jewel.ui.component.Icon
import org.jetbrains.jewel.ui.component.Text
import org.jetbrains.jewel.ui.icons.AllIconsKeys import org.jetbrains.jewel.ui.icons.AllIconsKeys
import org.jetbrains.plugins.template.ComposeTemplateBundle import org.jetbrains.plugins.template.ComposeTemplateBundle
import org.jetbrains.plugins.template.weatherApp.WeatherAppColors import org.jetbrains.plugins.template.weatherApp.WeatherAppColors
@ -54,127 +51,170 @@ fun WeatherDetailsCard(
val cardColor = getCardColorByTemperature(currentWeatherForecast.temperature, isNightTime) val cardColor = getCardColorByTemperature(currentWeatherForecast.temperature, isNightTime)
val textColor = Color.White val textColor = Color.White
Box( VerticallyScrollableContainer(modifier = modifier.safeContentPadding()) {
modifier = modifier Box(
.clip(RoundedCornerShape(16.dp))
.background(cardColor)
.padding(16.dp)
) {
// Card content
Column(
modifier = Modifier modifier = Modifier
.fillMaxWidth() .clip(RoundedCornerShape(16.dp))
.background(cardColor)
.padding(16.dp)
) { ) {
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.SpaceBetween
) {
// Current Time
Text(
text = ComposeTemplateBundle.message("weather.app.time.text", timeToDisplay),
color = textColor,
fontSize = JewelTheme.defaultTextStyle.fontSize,
fontWeight = FontWeight.Bold
)
ActionButton( // Card content
modifier = Modifier Column(
.clip(RoundedCornerShape(8.dp)) modifier = Modifier
.background(Color.Transparent) .fillMaxWidth()
.padding(8.dp), ) {
tooltip = { Text("Refresh weather data") }, Row(
onClick = { onReloadWeatherData(weatherForecastData.location) }, modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.SpaceBetween
) { ) {
// Current Time
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text(
text = ComposeTemplateBundle.message(
"weather.app.time.text",
formatDateTime(currentWeatherForecast.date)
),
color = textColor,
fontSize = JewelTheme.defaultTextStyle.fontSize,
fontWeight = FontWeight.Bold
)
/**
* Jewel org.jetbrains.jewel.ui.component.ActionButton
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Button.kt
*/
ActionButton(
modifier = Modifier
.clip(RoundedCornerShape(8.dp))
.background(Color.Transparent)
.padding(8.dp),
tooltip = {
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text("Refresh weather data")
},
onClick = { onReloadWeatherData(weatherForecastData.location) },
) {
/**
* Jewel org.jetbrains.jewel.ui.component.Icon
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Icon.kt
*/
Icon(
key = AllIconsKeys.Actions.Refresh,
contentDescription = "Refresh",
tint = Color.White
)
}
}
Spacer(modifier = Modifier.height(16.dp))
// Temperature and weather type column (vertically aligned)
Column(
modifier = Modifier.fillMaxWidth(),
horizontalAlignment = Alignment.CenterHorizontally
) {
/**
* Jewel org.jetbrains.jewel.ui.component.Icon
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Icon.kt
*/
Icon( Icon(
key = AllIconsKeys.Actions.Refresh, key = when {
contentDescription = "Refresh", isNightTime -> currentWeatherForecast.weatherType.nightIconKey
tint = Color.White else -> currentWeatherForecast.weatherType.dayIconKey
},
contentDescription = currentWeatherForecast.weatherType.label,
hint = EmbeddedToInlineCssSvgTransformerHint
)
Spacer(modifier = Modifier.height(8.dp))
// Temperature (emphasized)
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text(
text = ComposeTemplateBundle.message(
"weather.app.temperature.text",
currentWeatherForecast.temperature.toInt()
),
color = textColor,
fontSize = 32.sp,
fontWeight = FontWeight.ExtraBold
)
Spacer(modifier = Modifier.height(8.dp))
// City name
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text(
text = weatherForecastData.location.label,
color = textColor,
fontSize = 18.sp,
fontWeight = FontWeight.Bold
) )
} }
}
Spacer(modifier = Modifier.height(16.dp)) Spacer(modifier = Modifier.height(16.dp))
// Temperature and weather type column (vertically aligned) // Wind and humidity info
Column( Row(
modifier = Modifier.fillMaxWidth(), modifier = Modifier.fillMaxWidth(),
horizontalAlignment = Alignment.CenterHorizontally horizontalArrangement = Arrangement.SpaceBetween
) { ) {
// Wind info
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text(
text = ComposeTemplateBundle.message(
"weather.app.wind.direction.text",
currentWeatherForecast.windSpeed.toInt(),
currentWeatherForecast.windDirection.label
),
color = textColor,
fontSize = 18.sp,
)
Icon( // Humidity info
key = when { /**
isNightTime -> currentWeatherForecast.weatherType.nightIconKey * Jewel org.jetbrains.jewel.ui.component.Text
else -> currentWeatherForecast.weatherType.dayIconKey * @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
}, */
contentDescription = currentWeatherForecast.weatherType.label, Text(
hint = EmbeddedToInlineCssSvgTransformerHint text = ComposeTemplateBundle.message(
) "weather.app.humidity.text",
currentWeatherForecast.humidity
),
color = textColor,
fontSize = 18.sp,
)
}
Spacer(modifier = Modifier.height(8.dp)) Spacer(modifier = Modifier.height(24.dp))
// Temperature (emphasized) // 7-day forecast section
Text( SevenDaysForecastWidget(
text = ComposeTemplateBundle.message( weatherForecastData,
"weather.app.temperature.text", Modifier
currentWeatherForecast.temperature.toInt() .fillMaxWidth()
), .wrapContentHeight()
color = textColor, .align(Alignment.CenterHorizontally),
fontSize = 32.sp, textColor
fontWeight = FontWeight.ExtraBold
)
Spacer(modifier = Modifier.height(8.dp))
// City name
Text(
text = weatherForecastData.location.label,
color = textColor,
fontSize = 18.sp,
fontWeight = FontWeight.Bold
) )
} }
Spacer(modifier = Modifier.height(16.dp))
// Wind and humidity info
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.SpaceBetween
) {
// Wind info
Text(
text = ComposeTemplateBundle.message(
"weather.app.wind.direction.text",
currentWeatherForecast.windSpeed.toInt(),
currentWeatherForecast.windDirection.label
),
color = textColor,
fontSize = 18.sp,
)
// Humidity info
Text(
text = ComposeTemplateBundle.message(
"weather.app.humidity.text",
currentWeatherForecast.humidity
),
color = textColor,
fontSize = 18.sp,
)
}
Spacer(modifier = Modifier.height(24.dp))
// 7-day forecast section
SevenDaysForecastWidget(
weatherForecastData,
Modifier
.fillMaxWidth()
.wrapContentHeight()
.align(Alignment.CenterHorizontally),
textColor
)
} }
} }
} }
@ -187,6 +227,10 @@ private fun SevenDaysForecastWidget(
) { ) {
if (weatherForecastData.dailyForecasts.isNotEmpty()) { if (weatherForecastData.dailyForecasts.isNotEmpty()) {
Column(modifier) { Column(modifier) {
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text( Text(
text = ComposeTemplateBundle.message("weather.app.7days.forecast.title.text"), text = ComposeTemplateBundle.message("weather.app.7days.forecast.title.text"),
color = textColor, color = textColor,
@ -198,8 +242,12 @@ private fun SevenDaysForecastWidget(
Spacer(modifier = Modifier.height(8.dp)) Spacer(modifier = Modifier.height(8.dp))
val scrollState = rememberLazyListState() val scrollState = rememberLazyListState()
/**
* Jewel org.jetbrains.jewel.ui.component.HorizontallyScrollableContainer
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/ScrollableContainer.kt
*/
HorizontallyScrollableContainer( HorizontallyScrollableContainer(
modifier = Modifier.fillMaxWidth(), modifier = Modifier.fillMaxWidth().safeContentPadding(),
scrollState = scrollState, scrollState = scrollState,
) { ) {
LazyRow( LazyRow(
@ -244,6 +292,10 @@ private fun DayForecastItem(
.padding(8.dp) .padding(8.dp)
) { ) {
// Day name // Day name
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text( Text(
text = dayName, text = dayName,
color = textColor, color = textColor,
@ -252,6 +304,10 @@ private fun DayForecastItem(
textAlign = TextAlign.Center textAlign = TextAlign.Center
) )
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text( Text(
text = date, text = date,
color = textColor, color = textColor,
@ -263,6 +319,10 @@ private fun DayForecastItem(
Spacer(modifier = Modifier.height(8.dp)) Spacer(modifier = Modifier.height(8.dp))
// Weather icon // Weather icon
/**
* Jewel org.jetbrains.jewel.ui.component.Icon
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Icon.kt
*/
Icon( Icon(
key = if (isNightTime(forecast.date)) forecast.weatherType.nightIconKey else forecast.weatherType.dayIconKey, key = if (isNightTime(forecast.date)) forecast.weatherType.nightIconKey else forecast.weatherType.dayIconKey,
contentDescription = forecast.weatherType.label, contentDescription = forecast.weatherType.label,
@ -273,6 +333,10 @@ private fun DayForecastItem(
Spacer(modifier = Modifier.height(8.dp)) Spacer(modifier = Modifier.height(8.dp))
// Temperature // Temperature
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text( Text(
text = ComposeTemplateBundle.message( text = ComposeTemplateBundle.message(
"weather.app.temperature.text", "weather.app.temperature.text",
@ -286,6 +350,10 @@ private fun DayForecastItem(
Spacer(modifier = Modifier.height(8.dp)) Spacer(modifier = Modifier.height(8.dp))
// Humidity // Humidity
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text( Text(
text = ComposeTemplateBundle.message( text = ComposeTemplateBundle.message(
"weather.app.humidity.text", "weather.app.humidity.text",
@ -298,6 +366,10 @@ private fun DayForecastItem(
Spacer(modifier = Modifier.height(8.dp)) Spacer(modifier = Modifier.height(8.dp))
// Wind direction // Wind direction
/**
* Jewel org.jetbrains.jewel.ui.component.Text
* @see https://github.com/JetBrains/intellij-community/blob/master/platform/jewel/ui/src/main/kotlin/org/jetbrains/jewel/ui/component/Text.kt
*/
Text( Text(
text = ComposeTemplateBundle.message( text = ComposeTemplateBundle.message(
"weather.app.wind.direction.text", "weather.app.wind.direction.text",