fix(map): chart fill padding and dropdown selected border
- AirMQChart: add bottom padding so fill extends below line and thick line stays in bounds - DeviceSensorDropdown: show border on selected item when dropdown is opened Made-with: Cursor
This commit is contained in:
@@ -179,15 +179,17 @@ fun AirMQChart(
|
|||||||
val innerLeft = with(density) { ChartPaddingLeftDp.toPx() }
|
val innerLeft = with(density) { ChartPaddingLeftDp.toPx() }
|
||||||
val innerRight = w - with(density) { ChartPaddingRightDp.toPx() }
|
val innerRight = w - with(density) { ChartPaddingRightDp.toPx() }
|
||||||
val innerTop = with(density) { ChartPaddingTopDp.toPx() }
|
val innerTop = with(density) { ChartPaddingTopDp.toPx() }
|
||||||
|
val bottomPaddingPx = with(density) { 12.dp.toPx() }
|
||||||
val bottomMarginPx = with(density) { 16.dp.toPx() }
|
val bottomMarginPx = with(density) { 16.dp.toPx() }
|
||||||
val fakePieceTop = h - bottomMarginPx - 1f
|
// fillBottom = where the fill extends to (space below line is filled with same color)
|
||||||
val innerBottomLegacy = h - with(density) { ChartPaddingBottomDp.toPx() }
|
// chartBottom = where the line's lowest point plots (keeps thick line inside bounds, padding above fillBottom)
|
||||||
val fillBottom = if (config.roundCorners) fakePieceTop else innerBottomLegacy + bottomMarginPx
|
val fillBottom = if (config.roundCorners) h - bottomMarginPx - 1f else h
|
||||||
|
val chartBottom = fillBottom - bottomPaddingPx
|
||||||
val chartWidth = innerRight - innerLeft
|
val chartWidth = innerRight - innerLeft
|
||||||
val chartHeight = fillBottom - innerTop
|
val chartHeight = chartBottom - innerTop
|
||||||
|
|
||||||
fun toX(ts: Long) = innerLeft + ((ts - xMin) / rangeX.toFloat()) * chartWidth
|
fun toX(ts: Long) = innerLeft + ((ts - xMin) / rangeX.toFloat()) * chartWidth
|
||||||
fun toY(v: Float) = fillBottom - ((v - yMin) / rangeY) * chartHeight
|
fun toY(v: Float) = chartBottom - ((v - yMin) / rangeY) * chartHeight
|
||||||
|
|
||||||
drawChartBackground(
|
drawChartBackground(
|
||||||
left = innerLeft,
|
left = innerLeft,
|
||||||
@@ -244,7 +246,7 @@ fun AirMQChart(
|
|||||||
innerLeft = innerLeft,
|
innerLeft = innerLeft,
|
||||||
innerRight = innerRight,
|
innerRight = innerRight,
|
||||||
innerTop = innerTop,
|
innerTop = innerTop,
|
||||||
fillBottom = fillBottom,
|
chartBottom = chartBottom,
|
||||||
config = config,
|
config = config,
|
||||||
unit = unit,
|
unit = unit,
|
||||||
textMeasurer = textMeasurer
|
textMeasurer = textMeasurer
|
||||||
@@ -264,7 +266,7 @@ fun AirMQChart(
|
|||||||
innerLeft = innerLeft,
|
innerLeft = innerLeft,
|
||||||
innerRight = innerRight,
|
innerRight = innerRight,
|
||||||
innerTop = innerTop,
|
innerTop = innerTop,
|
||||||
fillBottom = fillBottom,
|
chartBottom = chartBottom,
|
||||||
textMeasurer = textMeasurer
|
textMeasurer = textMeasurer
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@@ -520,7 +522,7 @@ private fun DrawScope.drawLabels(
|
|||||||
innerLeft: Float,
|
innerLeft: Float,
|
||||||
innerRight: Float,
|
innerRight: Float,
|
||||||
innerTop: Float,
|
innerTop: Float,
|
||||||
fillBottom: Float,
|
chartBottom: Float,
|
||||||
config: ChartConfig,
|
config: ChartConfig,
|
||||||
unit: String,
|
unit: String,
|
||||||
textMeasurer: androidx.compose.ui.text.TextMeasurer
|
textMeasurer: androidx.compose.ui.text.TextMeasurer
|
||||||
@@ -533,15 +535,15 @@ private fun DrawScope.drawLabels(
|
|||||||
val pad = with(density) { 8.dp.toPx() }
|
val pad = with(density) { 8.dp.toPx() }
|
||||||
val textLayout = textMeasurer.measure("0", TextStyle(fontSize = LabelTextSizeSp.sp))
|
val textLayout = textMeasurer.measure("0", TextStyle(fontSize = LabelTextSizeSp.sp))
|
||||||
val baselineOffset = textLayout.size.height * 0.75f
|
val baselineOffset = textLayout.size.height * 0.75f
|
||||||
val chartHeight = fillBottom - innerTop
|
val chartHeight = chartBottom - innerTop
|
||||||
val midY = (maxY + minY) / 2f
|
val midY = (maxY + minY) / 2f
|
||||||
val midText = formatRounded(midY, rangeY)
|
val midText = formatRounded(midY, rangeY)
|
||||||
val midYpos = innerTop + chartHeight / 2f + baselineOffset
|
val midYpos = innerTop + chartHeight / 2f + baselineOffset
|
||||||
val bottomBaseline = fillBottom + baselineOffset
|
val bottomBaseline = chartBottom + baselineOffset
|
||||||
drawTextLabelRightAligned(maxText, innerLeft - pad, innerTop + baselineOffset, labelColor, textMeasurer)
|
drawTextLabelRightAligned(maxText, innerLeft - pad, innerTop + baselineOffset, labelColor, textMeasurer)
|
||||||
drawTextLabelRightAligned(midText, innerLeft - pad, midYpos, labelColor, textMeasurer)
|
drawTextLabelRightAligned(midText, innerLeft - pad, midYpos, labelColor, textMeasurer)
|
||||||
drawTextLabelRightAligned(minText, innerLeft - pad, bottomBaseline, labelColor, textMeasurer)
|
drawTextLabelRightAligned(minText, innerLeft - pad, bottomBaseline, labelColor, textMeasurer)
|
||||||
val lastYpos = fillBottom - ((lastY - minY) / rangeY) * chartHeight
|
val lastYpos = chartBottom - ((lastY - minY) / rangeY) * chartHeight
|
||||||
val lastTextLayout = textMeasurer.measure(lastText, TextStyle(fontSize = LabelTextSizeSp.sp))
|
val lastTextLayout = textMeasurer.measure(lastText, TextStyle(fontSize = LabelTextSizeSp.sp))
|
||||||
val lastBaseline = lastYpos - lastTextLayout.size.height / 3f
|
val lastBaseline = lastYpos - lastTextLayout.size.height / 3f
|
||||||
drawTextLabel(lastText, innerRight + pad, lastBaseline, labelColor, textMeasurer)
|
drawTextLabel(lastText, innerRight + pad, lastBaseline, labelColor, textMeasurer)
|
||||||
@@ -592,11 +594,11 @@ private fun DrawScope.drawMarker(
|
|||||||
innerLeft: Float,
|
innerLeft: Float,
|
||||||
innerRight: Float,
|
innerRight: Float,
|
||||||
innerTop: Float,
|
innerTop: Float,
|
||||||
fillBottom: Float,
|
chartBottom: Float,
|
||||||
textMeasurer: androidx.compose.ui.text.TextMeasurer
|
textMeasurer: androidx.compose.ui.text.TextMeasurer
|
||||||
) {
|
) {
|
||||||
drawLine(config.lineColor, Offset(innerLeft, y), Offset(innerRight, y), strokeWidth = 1f)
|
drawLine(config.lineColor, Offset(innerLeft, y), Offset(innerRight, y), strokeWidth = 1f)
|
||||||
drawLine(config.lineColor, Offset(x, innerTop - 16), Offset(x, fillBottom + 16), strokeWidth = 1f)
|
drawLine(config.lineColor, Offset(x, innerTop - 16), Offset(x, chartBottom + 16), strokeWidth = 1f)
|
||||||
drawCircle(config.lineColor, radius = MarkerRadiusPx, center = Offset(x, y))
|
drawCircle(config.lineColor, radius = MarkerRadiusPx, center = Offset(x, y))
|
||||||
|
|
||||||
val valueStr = "${formatRounded(point.value, rangeY)} $unit".trim()
|
val valueStr = "${formatRounded(point.value, rangeY)} $unit".trim()
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package org.db3.airmq.features.map
|
package org.db3.airmq.features.map
|
||||||
|
|
||||||
import androidx.compose.foundation.background
|
import androidx.compose.foundation.background
|
||||||
|
import androidx.compose.foundation.border
|
||||||
import androidx.compose.foundation.clickable
|
import androidx.compose.foundation.clickable
|
||||||
import androidx.compose.foundation.layout.Arrangement
|
import androidx.compose.foundation.layout.Arrangement
|
||||||
import androidx.compose.foundation.layout.Box
|
import androidx.compose.foundation.layout.Box
|
||||||
@@ -27,6 +28,7 @@ import androidx.compose.material3.OutlinedTextField
|
|||||||
import androidx.compose.material3.Surface
|
import androidx.compose.material3.Surface
|
||||||
import androidx.compose.material3.Text
|
import androidx.compose.material3.Text
|
||||||
import androidx.compose.animation.AnimatedVisibility
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
|
import androidx.compose.animation.core.tween
|
||||||
import androidx.compose.animation.expandVertically
|
import androidx.compose.animation.expandVertically
|
||||||
import androidx.compose.animation.shrinkVertically
|
import androidx.compose.animation.shrinkVertically
|
||||||
import androidx.compose.runtime.getValue
|
import androidx.compose.runtime.getValue
|
||||||
@@ -576,8 +578,8 @@ private fun DeviceSensorDropdown(
|
|||||||
) {
|
) {
|
||||||
AnimatedVisibility(
|
AnimatedVisibility(
|
||||||
visible = isExpanded,
|
visible = isExpanded,
|
||||||
enter = expandVertically(),
|
enter = expandVertically(animationSpec = tween(durationMillis = 150)),
|
||||||
exit = shrinkVertically()
|
exit = shrinkVertically(animationSpec = tween(durationMillis = 150))
|
||||||
) {
|
) {
|
||||||
Surface(
|
Surface(
|
||||||
modifier = Modifier.fillMaxWidth(),
|
modifier = Modifier.fillMaxWidth(),
|
||||||
@@ -593,6 +595,7 @@ private fun DeviceSensorDropdown(
|
|||||||
DeviceSensorDropdownOption(
|
DeviceSensorDropdownOption(
|
||||||
sensorType = sensorType,
|
sensorType = sensorType,
|
||||||
selected = selectedSensor == sensorType,
|
selected = selectedSensor == sensorType,
|
||||||
|
showSelectedBorder = isExpanded && selectedSensor == sensorType,
|
||||||
onClick = {
|
onClick = {
|
||||||
onSelected(sensorType)
|
onSelected(sensorType)
|
||||||
isExpanded = false
|
isExpanded = false
|
||||||
@@ -664,12 +667,17 @@ private fun sensorLabelRes(sensorType: DeviceSensorType): Int = when (sensorType
|
|||||||
private fun DeviceSensorDropdownOption(
|
private fun DeviceSensorDropdownOption(
|
||||||
sensorType: DeviceSensorType,
|
sensorType: DeviceSensorType,
|
||||||
selected: Boolean,
|
selected: Boolean,
|
||||||
|
showSelectedBorder: Boolean,
|
||||||
onClick: () -> Unit
|
onClick: () -> Unit
|
||||||
) {
|
) {
|
||||||
val textColor = if (selected) Color(0xFF1C1C1C) else Color(0xFF616161)
|
val textColor = if (selected) Color(0xFF1C1C1C) else Color(0xFF616161)
|
||||||
|
val borderModifier = if (showSelectedBorder) {
|
||||||
|
Modifier.border(1.dp, Color(0x61000000), RoundedCornerShape(8.dp))
|
||||||
|
} else Modifier
|
||||||
Row(
|
Row(
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.fillMaxWidth()
|
.fillMaxWidth()
|
||||||
|
.then(borderModifier)
|
||||||
.clickable(onClick = onClick)
|
.clickable(onClick = onClick)
|
||||||
.padding(horizontal = 16.dp, vertical = 10.dp),
|
.padding(horizontal = 16.dp, vertical = 10.dp),
|
||||||
verticalAlignment = Alignment.CenterVertically
|
verticalAlignment = Alignment.CenterVertically
|
||||||
|
|||||||
Reference in New Issue
Block a user