mirror of
https://github.com/atsunatsu/Look4Sat.git
synced 2026-10-02 03:15:37 +00:00
Added current moon/sun positions to the RadarScreen
This commit is contained in:
1 parent
18f8ab517d
commit
b166e896c2
5 files changed
+72
-10
No files matched your search
+1
-1
@@ -114,7 +114,7 @@ object CelestialComputer {
|
|||||||
distance = 1.0 + ((obsSet[2] - ASTRONOMICAL_UNIT) / ASTRONOMICAL_UNIT),
|
distance = 1.0 + ((obsSet[2] - ASTRONOMICAL_UNIT) / ASTRONOMICAL_UNIT),
|
||||||
rangeRate = 1000.0 * obsSet[3],
|
rangeRate = 1000.0 * obsSet[3],
|
||||||
latitude = latLon[0].toDegrees(),
|
latitude = latLon[0].toDegrees(),
|
||||||
longitude = 360.0 - latLon[1].toDegrees(),
|
longitude = latLon[1].toDegrees().let { if (it > 180.0) it - 360.0 else it },
|
||||||
rightAscension = raDec[0].toDegrees(),
|
rightAscension = raDec[0].toDegrees(),
|
||||||
declination = raDec[1].toDegrees()
|
declination = raDec[1].toDegrees()
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -180,7 +180,9 @@ private fun RadarCard(uiState: RadarState, modifier: Modifier = Modifier) {
|
|||||||
azimElev = uiState.orientationValues,
|
azimElev = uiState.orientationValues,
|
||||||
shouldShowSweep = uiState.shouldShowSweep,
|
shouldShowSweep = uiState.shouldShowSweep,
|
||||||
shouldUseCompass = uiState.shouldUseCompass,
|
shouldUseCompass = uiState.shouldUseCompass,
|
||||||
modifier = Modifier.align(Alignment.Center)
|
modifier = Modifier.align(Alignment.Center),
|
||||||
|
sunPosition = uiState.sunPosition,
|
||||||
|
moonPosition = uiState.moonPosition,
|
||||||
)
|
)
|
||||||
PositionOverlay(position)
|
PositionOverlay(position)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,6 +18,7 @@
|
|||||||
package com.rtbishop.look4sat.feature.radar
|
package com.rtbishop.look4sat.feature.radar
|
||||||
|
|
||||||
import com.rtbishop.look4sat.core.domain.model.SatRadio
|
import com.rtbishop.look4sat.core.domain.model.SatRadio
|
||||||
|
import com.rtbishop.look4sat.core.domain.predict.CelestialComputer
|
||||||
import com.rtbishop.look4sat.core.domain.predict.OrbitalPass
|
import com.rtbishop.look4sat.core.domain.predict.OrbitalPass
|
||||||
import com.rtbishop.look4sat.core.domain.predict.OrbitalPos
|
import com.rtbishop.look4sat.core.domain.predict.OrbitalPos
|
||||||
|
|
||||||
@@ -32,6 +33,8 @@ data class RadarState(
|
|||||||
val satTrack: List<OrbitalPos> = emptyList(),
|
val satTrack: List<OrbitalPos> = emptyList(),
|
||||||
val shouldShowSweep: Boolean = false,
|
val shouldShowSweep: Boolean = false,
|
||||||
val shouldUseCompass: Boolean = false,
|
val shouldUseCompass: Boolean = false,
|
||||||
|
val sunPosition: CelestialComputer.SunPosition? = null,
|
||||||
|
val moonPosition: CelestialComputer.MoonPosition? = null,
|
||||||
val transmitters: List<SatRadio> = emptyList(),
|
val transmitters: List<SatRadio> = emptyList(),
|
||||||
val selectedTransmitterUuid: String? = null,
|
val selectedTransmitterUuid: String? = null,
|
||||||
val selectedFrequency: Long? = null
|
val selectedFrequency: Long? = null
|
||||||
|
|||||||
@@ -32,6 +32,7 @@ import androidx.compose.runtime.remember
|
|||||||
import androidx.compose.runtime.setValue
|
import androidx.compose.runtime.setValue
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.geometry.Offset
|
import androidx.compose.ui.geometry.Offset
|
||||||
|
import androidx.compose.ui.geometry.Size
|
||||||
import androidx.compose.ui.graphics.Color
|
import androidx.compose.ui.graphics.Color
|
||||||
import androidx.compose.ui.graphics.Path
|
import androidx.compose.ui.graphics.Path
|
||||||
import androidx.compose.ui.graphics.PathEffect
|
import androidx.compose.ui.graphics.PathEffect
|
||||||
@@ -44,14 +45,19 @@ import androidx.compose.ui.graphics.drawscope.Fill
|
|||||||
import androidx.compose.ui.graphics.drawscope.Stroke
|
import androidx.compose.ui.graphics.drawscope.Stroke
|
||||||
import androidx.compose.ui.graphics.drawscope.rotate
|
import androidx.compose.ui.graphics.drawscope.rotate
|
||||||
import androidx.compose.ui.graphics.drawscope.translate
|
import androidx.compose.ui.graphics.drawscope.translate
|
||||||
|
import androidx.compose.ui.graphics.drawscope.withTransform
|
||||||
|
import androidx.compose.ui.graphics.painter.Painter
|
||||||
|
import androidx.compose.ui.res.painterResource
|
||||||
import androidx.compose.ui.text.TextMeasurer
|
import androidx.compose.ui.text.TextMeasurer
|
||||||
import androidx.compose.ui.text.TextStyle
|
import androidx.compose.ui.text.TextStyle
|
||||||
import androidx.compose.ui.text.drawText
|
import androidx.compose.ui.text.drawText
|
||||||
import androidx.compose.ui.text.rememberTextMeasurer
|
import androidx.compose.ui.text.rememberTextMeasurer
|
||||||
import androidx.compose.ui.unit.sp
|
import androidx.compose.ui.unit.sp
|
||||||
|
import com.rtbishop.look4sat.core.domain.predict.CelestialComputer
|
||||||
import com.rtbishop.look4sat.core.domain.predict.OrbitalPos
|
import com.rtbishop.look4sat.core.domain.predict.OrbitalPos
|
||||||
import com.rtbishop.look4sat.core.domain.predict.PI_2
|
import com.rtbishop.look4sat.core.domain.predict.PI_2
|
||||||
import com.rtbishop.look4sat.core.domain.utility.toRadians
|
import com.rtbishop.look4sat.core.domain.utility.toRadians
|
||||||
|
import com.rtbishop.look4sat.core.presentation.R
|
||||||
import kotlin.math.cos
|
import kotlin.math.cos
|
||||||
import kotlin.math.sin
|
import kotlin.math.sin
|
||||||
|
|
||||||
@@ -66,11 +72,14 @@ fun RadarViewCompose(
|
|||||||
azimElev: Pair<Float, Float>,
|
azimElev: Pair<Float, Float>,
|
||||||
shouldShowSweep: Boolean,
|
shouldShowSweep: Boolean,
|
||||||
shouldUseCompass: Boolean,
|
shouldUseCompass: Boolean,
|
||||||
modifier: Modifier = Modifier
|
modifier: Modifier = Modifier,
|
||||||
|
sunPosition: CelestialComputer.SunPosition? = null,
|
||||||
|
moonPosition: CelestialComputer.MoonPosition? = null,
|
||||||
) {
|
) {
|
||||||
val radarColor = MaterialTheme.colorScheme.secondary
|
|
||||||
val trackColor = MaterialTheme.colorScheme.primary
|
|
||||||
val aimColor = MaterialTheme.colorScheme.error
|
val aimColor = MaterialTheme.colorScheme.error
|
||||||
|
val primaryColor = MaterialTheme.colorScheme.primary
|
||||||
|
val radarColor = MaterialTheme.colorScheme.secondary
|
||||||
|
val sunColor = MaterialTheme.colorScheme.primary
|
||||||
val animTransition = rememberInfiniteTransition(label = "animScale")
|
val animTransition = rememberInfiniteTransition(label = "animScale")
|
||||||
val animScale by animTransition.animateFloat(
|
val animScale by animTransition.animateFloat(
|
||||||
initialValue = 16f,
|
initialValue = 16f,
|
||||||
@@ -79,6 +88,8 @@ fun RadarViewCompose(
|
|||||||
label = "animScale"
|
label = "animScale"
|
||||||
)
|
)
|
||||||
val measurer = rememberTextMeasurer()
|
val measurer = rememberTextMeasurer()
|
||||||
|
val sunPainter = painterResource(R.drawable.ic_sun)
|
||||||
|
val moonPainter = painterResource(R.drawable.ic_moon)
|
||||||
var sweepDegrees by remember { mutableFloatStateOf(0f) }
|
var sweepDegrees by remember { mutableFloatStateOf(0f) }
|
||||||
var cachedRadius by remember { mutableFloatStateOf(0f) }
|
var cachedRadius by remember { mutableFloatStateOf(0f) }
|
||||||
var trackPath by remember { mutableStateOf(Path()) }
|
var trackPath by remember { mutableStateOf(Path()) }
|
||||||
@@ -92,13 +103,26 @@ fun RadarViewCompose(
|
|||||||
cachedRadius = radius
|
cachedRadius = radius
|
||||||
}
|
}
|
||||||
rotate(if (shouldUseCompass) -azimElev.first else 0f) {
|
rotate(if (shouldUseCompass) -azimElev.first else 0f) {
|
||||||
if (shouldShowSweep) drawSweep(center, sweepDegrees, radius, trackColor)
|
if (shouldShowSweep) drawSweep(center, sweepDegrees, radius, primaryColor)
|
||||||
drawRadar(radius, radarColor)
|
drawRadar(radius, radarColor)
|
||||||
drawElevationLabels(radius, trackColor, measurer)
|
drawElevationLabels(radius, primaryColor, measurer)
|
||||||
translate(center.x, center.y) {
|
translate(center.x, center.y) {
|
||||||
drawTrack(trackPath, trackEffect, aimColor, trackColor)
|
drawTrack(trackPath, trackEffect, aimColor, primaryColor)
|
||||||
if (item.elevation > 0) {
|
if (item.elevation > 0) {
|
||||||
drawPosition(item, radius, animScale, trackColor)
|
drawPosition(item, radius, animScale, primaryColor)
|
||||||
|
}
|
||||||
|
sunPosition?.let { sun ->
|
||||||
|
if (sun.elevation > 0) drawBodyIcon(sun.azimuth, sun.elevation, radius, sunColor, sunPainter, 52f)
|
||||||
|
}
|
||||||
|
moonPosition?.let { moon ->
|
||||||
|
if (moon.elevation > 0) drawBodyIcon(
|
||||||
|
moon.azimuth,
|
||||||
|
moon.elevation,
|
||||||
|
radius,
|
||||||
|
radarColor,
|
||||||
|
moonPainter,
|
||||||
|
52f
|
||||||
|
)
|
||||||
}
|
}
|
||||||
if (shouldUseCompass) drawAim(azimElev.first, azimElev.second, radius, aimColor)
|
if (shouldUseCompass) drawAim(azimElev.first, azimElev.second, radius, aimColor)
|
||||||
}
|
}
|
||||||
@@ -180,6 +204,27 @@ private fun createTrackEffect(trackPath: Path): PathEffect {
|
|||||||
return PathEffect.stampedPathEffect(shape, trackLength / 2f, trackLength / 4f, StampedPathEffectStyle.Rotate)
|
return PathEffect.stampedPathEffect(shape, trackLength / 2f, trackLength / 4f, StampedPathEffectStyle.Rotate)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun DrawScope.drawBodyIcon(
|
||||||
|
azimDeg: Double,
|
||||||
|
elevDeg: Double,
|
||||||
|
radius: Float,
|
||||||
|
color: Color,
|
||||||
|
painter: Painter,
|
||||||
|
iconSize: Float
|
||||||
|
) {
|
||||||
|
val azimRad = azimDeg.toRadians()
|
||||||
|
val elevRad = elevDeg.toRadians()
|
||||||
|
val pos = sph2Cart(azimRad, elevRad, radius.toDouble())
|
||||||
|
val half = iconSize / 2f
|
||||||
|
withTransform({
|
||||||
|
translate(pos.x - half, pos.y - half)
|
||||||
|
}) {
|
||||||
|
with(painter) {
|
||||||
|
draw(Size(iconSize, iconSize), colorFilter = androidx.compose.ui.graphics.ColorFilter.tint(color))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private fun sph2Cart(azim: Double, elev: Double, r: Double): Offset {
|
private fun sph2Cart(azim: Double, elev: Double, r: Double): Offset {
|
||||||
val radius = r * (PI_2 - elev) / PI_2
|
val radius = r * (PI_2 - elev) / PI_2
|
||||||
return Offset(
|
return Offset(
|
||||||
|
|||||||
@@ -23,6 +23,7 @@ import androidx.lifecycle.viewModelScope
|
|||||||
import androidx.lifecycle.viewmodel.initializer
|
import androidx.lifecycle.viewmodel.initializer
|
||||||
import androidx.lifecycle.viewmodel.viewModelFactory
|
import androidx.lifecycle.viewmodel.viewModelFactory
|
||||||
import com.rtbishop.look4sat.core.domain.model.SatRadio
|
import com.rtbishop.look4sat.core.domain.model.SatRadio
|
||||||
|
import com.rtbishop.look4sat.core.domain.predict.CelestialComputer
|
||||||
import com.rtbishop.look4sat.core.domain.predict.OrbitalObject
|
import com.rtbishop.look4sat.core.domain.predict.OrbitalObject
|
||||||
import com.rtbishop.look4sat.core.domain.predict.OrbitalPos
|
import com.rtbishop.look4sat.core.domain.predict.OrbitalPos
|
||||||
import com.rtbishop.look4sat.core.domain.repository.IContainerProvider
|
import com.rtbishop.look4sat.core.domain.repository.IContainerProvider
|
||||||
@@ -101,9 +102,20 @@ class RadarViewModel(
|
|||||||
while (isActive) {
|
while (isActive) {
|
||||||
val timeNow = System.currentTimeMillis()
|
val timeNow = System.currentTimeMillis()
|
||||||
val pos = satelliteRepo.getPosition(satPass.orbitalObject, stationPos, timeNow)
|
val pos = satelliteRepo.getPosition(satPass.orbitalObject, stationPos, timeNow)
|
||||||
|
val sunPos = CelestialComputer.getSunPosition(stationPos, timeNow)
|
||||||
|
val moonPos = CelestialComputer.getMoonPosition(stationPos, timeNow)
|
||||||
val (time, isAos) = computeTimer(satPass.isDeepSpace, satPass.aosTime, satPass.losTime, timeNow)
|
val (time, isAos) = computeTimer(satPass.isDeepSpace, satPass.aosTime, satPass.losTime, timeNow)
|
||||||
val isLos = !satPass.isDeepSpace && timeNow > satPass.losTime
|
val isLos = !satPass.isDeepSpace && timeNow > satPass.losTime
|
||||||
_uiState.update { it.copy(currentTime = time, isTimeAos = isAos, isLos = isLos, orbitalPos = pos) }
|
_uiState.update {
|
||||||
|
it.copy(
|
||||||
|
currentTime = time,
|
||||||
|
isTimeAos = isAos,
|
||||||
|
isLos = isLos,
|
||||||
|
orbitalPos = pos,
|
||||||
|
sunPosition = sunPos,
|
||||||
|
moonPosition = moonPos
|
||||||
|
)
|
||||||
|
}
|
||||||
processRadios(transmitters, satPass.orbitalObject, timeNow)
|
processRadios(transmitters, satPass.orbitalObject, timeNow)
|
||||||
sendPassData(pos)
|
sendPassData(pos)
|
||||||
delay(1000)
|
delay(1000)
|
||||||
|
|||||||
Reference in new issue
Block a user