mirror of
https://github.com/atsunatsu/Look4Sat.git
synced 2026-10-02 03:15:37 +00:00
Added SatPass CardView, RecyclerView with SatPasses, moved the code to SkyFragment.
This commit is contained in:
1 parent
7510453f39
commit
b7291db0f9
10 files changed
+275
-20
No files matched your search
@@ -140,7 +140,7 @@ class MainActivity : AppCompatActivity() {
|
||||
|
||||
override fun onTick(millisUntilFinished: Long) {
|
||||
timeToAos.text = String.format(
|
||||
resources.getString(R.string.next_aos_pattern),
|
||||
resources.getString(R.string.toolbar_aos_in),
|
||||
TimeUnit.MILLISECONDS.toHours(millisUntilFinished) % 60,
|
||||
TimeUnit.MILLISECONDS.toMinutes(millisUntilFinished) % 60,
|
||||
TimeUnit.MILLISECONDS.toSeconds(millisUntilFinished) % 60
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
package com.rtbishop.lookingsat.ui
|
||||
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.widget.TextView
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import com.github.amsacode.predict4java.SatPassTime
|
||||
import com.rtbishop.lookingsat.R
|
||||
import java.text.SimpleDateFormat
|
||||
import java.util.*
|
||||
|
||||
class SatPassAdapter(private val satPassList: MutableList<SatPassTime>) :
|
||||
RecyclerView.Adapter<SatPassAdapter.ViewHolder>() {
|
||||
|
||||
override fun getItemCount(): Int {
|
||||
return satPassList.size
|
||||
}
|
||||
|
||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
|
||||
val itemView =
|
||||
LayoutInflater.from(parent.context).inflate(R.layout.sat_pass_card, parent, false)
|
||||
return ViewHolder(itemView)
|
||||
}
|
||||
|
||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
||||
val satPass = satPassList[position]
|
||||
|
||||
val satName = holder.itemView.findViewById<TextView>(R.id.card_sat_name)
|
||||
val passVector = holder.itemView.findViewById<TextView>(R.id.card_pass_vector)
|
||||
val maxEl = holder.itemView.findViewById<TextView>(R.id.card_max_el)
|
||||
val passStart = holder.itemView.findViewById<TextView>(R.id.card_pass_start)
|
||||
val passEnd = holder.itemView.findViewById<TextView>(R.id.card_pass_end)
|
||||
|
||||
satName.text = String.format("%s", "Meteor M2-2")
|
||||
passVector.text = String.format("V: %02d° -> %02d°", satPass.aosAzimuth, satPass.losAzimuth)
|
||||
maxEl.text = String.format("%.1f°", satPass.maxEl)
|
||||
passStart.text = SimpleDateFormat("HH:mm:ss", Locale.getDefault()).format(satPass.startTime)
|
||||
passEnd.text = SimpleDateFormat("HH:mm:ss", Locale.getDefault()).format(satPass.endTime)
|
||||
}
|
||||
|
||||
inner class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView),
|
||||
View.OnClickListener {
|
||||
override fun onClick(v: View?) {}
|
||||
}
|
||||
}
|
||||
@@ -4,11 +4,22 @@ import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.widget.ImageButton
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.lifecycle.ViewModelProvider
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import com.rtbishop.lookingsat.R
|
||||
import com.rtbishop.lookingsat.vm.MainViewModel
|
||||
|
||||
class SkyFragment : Fragment() {
|
||||
|
||||
private lateinit var viewModel: MainViewModel
|
||||
private lateinit var recView: RecyclerView
|
||||
private lateinit var recAdapter: RecyclerView.Adapter<*>
|
||||
private lateinit var recLayoutManager: RecyclerView.LayoutManager
|
||||
private lateinit var btnRefresh: ImageButton
|
||||
|
||||
override fun onCreateView(
|
||||
inflater: LayoutInflater,
|
||||
container: ViewGroup?,
|
||||
@@ -16,4 +27,22 @@ class SkyFragment : Fragment() {
|
||||
): View? {
|
||||
return inflater.inflate(R.layout.fragment_sky, container, false)
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
viewModel = ViewModelProvider(activity as MainActivity).get(MainViewModel::class.java)
|
||||
btnRefresh = (activity as MainActivity).findViewById(R.id.toolbar_btn_refresh)
|
||||
|
||||
btnRefresh.setOnClickListener {
|
||||
val satPassList = viewModel.updateRecycler()
|
||||
|
||||
recLayoutManager = LinearLayoutManager(activity)
|
||||
recAdapter = SatPassAdapter(satPassList)
|
||||
recView = view.findViewById(R.id.recycler_sky)
|
||||
|
||||
recView.setHasFixedSize(true)
|
||||
recView.layoutManager = recLayoutManager
|
||||
recView.adapter = recAdapter
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -11,18 +11,24 @@ import androidx.lifecycle.MutableLiveData
|
||||
import androidx.lifecycle.viewModelScope
|
||||
import androidx.preference.PreferenceManager
|
||||
import com.github.amsacode.predict4java.GroundStationPosition
|
||||
import com.github.amsacode.predict4java.PassPredictor
|
||||
import com.github.amsacode.predict4java.SatPassTime
|
||||
import com.github.amsacode.predict4java.TLE
|
||||
import com.google.android.gms.location.LocationServices
|
||||
import com.rtbishop.lookingsat.Injector
|
||||
import com.rtbishop.lookingsat.repo.Repository
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.launch
|
||||
import java.io.FileNotFoundException
|
||||
import java.io.IOException
|
||||
import java.util.*
|
||||
|
||||
class MainViewModel(application: Application) : AndroidViewModel(application) {
|
||||
|
||||
private val keyLat = "LATITUDE"
|
||||
private val keyLon = "LONGITUDE"
|
||||
private val keyHeight = "HEIGHT"
|
||||
private val tleFile = "tles.txt"
|
||||
|
||||
private val repository: Repository = Injector.provideRepository(application)
|
||||
private val preferences = PreferenceManager.getDefaultSharedPreferences(application)
|
||||
@@ -38,6 +44,19 @@ class MainViewModel(application: Application) : AndroidViewModel(application) {
|
||||
)
|
||||
val gsp: LiveData<GroundStationPosition> = _gsp
|
||||
|
||||
fun updateRecycler(): MutableList<SatPassTime> {
|
||||
var satPassList = mutableListOf<SatPassTime>()
|
||||
try {
|
||||
val tles = TLE.importSat(getApplication<Application>().openFileInput(tleFile))
|
||||
|
||||
val passPredictor = PassPredictor(tles[0], _gsp.value)
|
||||
satPassList = passPredictor.getPasses(Date(), 6, false)
|
||||
} catch (exception: FileNotFoundException) {
|
||||
_debugMessage.postValue("TLE file wasn't found")
|
||||
}
|
||||
return satPassList
|
||||
}
|
||||
|
||||
fun updateLocation() {
|
||||
fusedLocationClient.lastLocation.addOnSuccessListener { location: Location? ->
|
||||
val lat = location?.latitude ?: 0.0
|
||||
@@ -56,10 +75,9 @@ class MainViewModel(application: Application) : AndroidViewModel(application) {
|
||||
}
|
||||
|
||||
fun updateTwoLineElementFile() {
|
||||
val fileName = "tles.txt"
|
||||
viewModelScope.launch(Dispatchers.IO) {
|
||||
try {
|
||||
getApplication<Application>().openFileOutput(fileName, Context.MODE_PRIVATE).use {
|
||||
getApplication<Application>().openFileOutput(tleFile, Context.MODE_PRIVATE).use {
|
||||
it.write(repository.fetchTleStream().readBytes())
|
||||
}
|
||||
_debugMessage.postValue("TLE file was updated")
|
||||
|
||||
@@ -0,0 +1,45 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="180dp"
|
||||
android:height="52dp"
|
||||
android:viewportWidth="180"
|
||||
android:viewportHeight="52">
|
||||
<path
|
||||
android:fillAlpha="1"
|
||||
android:fillColor="#00000000"
|
||||
android:fillType="evenOdd"
|
||||
android:pathData="M90.228,25.867m-18.678,0a18.678,18.678 0,1 1,37.356 0a18.678,18.678 0,1 1,-37.356 0"
|
||||
android:strokeWidth="1.2"
|
||||
android:strokeColor="#C0C0C0" />
|
||||
<path
|
||||
android:fillColor="#00000000"
|
||||
android:pathData="m179.999,0.23c-25.023,0.051 -50.046,0.102 -63.817,1.503 -13.771,1.402 -16.29,4.154 -18.809,6.906"
|
||||
android:strokeWidth="0.8"
|
||||
android:strokeAlpha="1"
|
||||
android:strokeColor="#C0C0C0"
|
||||
android:strokeLineCap="butt"
|
||||
android:strokeLineJoin="miter" />
|
||||
<path
|
||||
android:fillColor="#00000000"
|
||||
android:pathData="m179.999,51.77c-25.023,-0.051 -50.046,-0.102 -63.817,-1.503 -13.771,-1.402 -16.29,-4.154 -18.809,-6.906"
|
||||
android:strokeWidth="0.8"
|
||||
android:strokeAlpha="1"
|
||||
android:strokeColor="#C0C0C0"
|
||||
android:strokeLineCap="butt"
|
||||
android:strokeLineJoin="miter" />
|
||||
<path
|
||||
android:fillColor="#00000000"
|
||||
android:pathData="m0.001,51.77c25.023,-0.051 50.046,-0.102 63.817,-1.503 13.771,-1.402 16.29,-4.154 18.809,-6.906"
|
||||
android:strokeWidth="0.8"
|
||||
android:strokeAlpha="1"
|
||||
android:strokeColor="#C0C0C0"
|
||||
android:strokeLineCap="butt"
|
||||
android:strokeLineJoin="miter" />
|
||||
<path
|
||||
android:fillColor="#00000000"
|
||||
android:pathData="m0.001,0.23c25.023,0.051 50.046,0.102 63.817,1.503 13.771,1.402 16.29,4.154 18.809,6.906"
|
||||
android:strokeWidth="0.8"
|
||||
android:strokeAlpha="1"
|
||||
android:strokeColor="#C0C0C0"
|
||||
android:strokeLineCap="butt"
|
||||
android:strokeLineJoin="miter" />
|
||||
</vector>
|
||||
@@ -35,7 +35,7 @@
|
||||
<TextView
|
||||
android:id="@+id/drawer_lat"
|
||||
style="@style/DrawerHeader.Item"
|
||||
android:text="@string/latitude"
|
||||
android:text="@string/drawer_latitude"
|
||||
app:layout_constraintBottom_toTopOf="@+id/drawer_lon_value"
|
||||
app:layout_constraintStart_toStartOf="@+id/drawer_lon" />
|
||||
|
||||
@@ -43,14 +43,14 @@
|
||||
android:id="@+id/drawer_lat_value"
|
||||
style="@style/DrawerHeader.Value"
|
||||
android:layout_marginStart="8dp"
|
||||
android:text="@string/latitude_def"
|
||||
android:text="@string/drawer_latitude_value"
|
||||
app:layout_constraintBaseline_toBaselineOf="@+id/drawer_lat"
|
||||
app:layout_constraintStart_toEndOf="@+id/drawer_lat" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/drawer_lon"
|
||||
style="@style/DrawerHeader.Item"
|
||||
android:text="@string/longitude"
|
||||
android:text="@string/drawer_longitude"
|
||||
app:layout_constraintBottom_toTopOf="@+id/drawer_height_value"
|
||||
app:layout_constraintStart_toStartOf="@+id/drawer_height" />
|
||||
|
||||
@@ -58,7 +58,7 @@
|
||||
android:id="@+id/drawer_lon_value"
|
||||
style="@style/DrawerHeader.Value"
|
||||
android:layout_marginStart="8dp"
|
||||
android:text="@string/longitude_def"
|
||||
android:text="@string/drawer_longitude_value"
|
||||
app:layout_constraintBaseline_toBaselineOf="@+id/drawer_lon"
|
||||
app:layout_constraintStart_toEndOf="@+id/drawer_lon" />
|
||||
|
||||
@@ -67,7 +67,7 @@
|
||||
style="@style/DrawerHeader.Item"
|
||||
android:layout_marginStart="4dp"
|
||||
android:layout_marginBottom="4dp"
|
||||
android:text="@string/height"
|
||||
android:text="@string/drawer_height"
|
||||
app:layout_constraintBottom_toTopOf="@+id/drawer_btn_loc"
|
||||
app:layout_constraintStart_toStartOf="@+id/drawer_btn_loc" />
|
||||
|
||||
@@ -75,7 +75,7 @@
|
||||
android:id="@+id/drawer_height_value"
|
||||
style="@style/DrawerHeader.Value"
|
||||
android:layout_marginStart="8dp"
|
||||
android:text="@string/height_def"
|
||||
android:text="@string/drawer_height_value"
|
||||
app:layout_constraintBaseline_toBaselineOf="@+id/drawer_height"
|
||||
app:layout_constraintStart_toEndOf="@+id/drawer_height" />
|
||||
|
||||
|
||||
@@ -6,6 +6,15 @@
|
||||
android:layout_height="match_parent"
|
||||
tools:context=".ui.SkyFragment">
|
||||
|
||||
<androidx.recyclerview.widget.RecyclerView
|
||||
android:id="@+id/recycler_sky"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="0dp"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<com.google.android.material.floatingactionbutton.FloatingActionButton
|
||||
android:id="@+id/sky_fab"
|
||||
android:layout_width="wrap_content"
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<com.google.android.material.card.MaterialCardView xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/card_view"
|
||||
style="@style/CardSatPass"
|
||||
android:layout_height="104dp"
|
||||
android:layout_marginStart="4dp"
|
||||
android:layout_marginTop="4dp"
|
||||
android:layout_marginEnd="4dp"
|
||||
app:cardElevation="8dp">
|
||||
|
||||
<androidx.constraintlayout.widget.ConstraintLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/imageView"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="0dp"
|
||||
android:contentDescription="@string/placeholder"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent"
|
||||
app:srcCompat="@drawable/ic_drawing" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_sat_name"
|
||||
style="@style/CardSatPass.SideText"
|
||||
android:layout_marginStart="8dp"
|
||||
android:text="@string/card_sat_name"
|
||||
app:layout_constraintBottom_toTopOf="@+id/card_max_el"
|
||||
app:layout_constraintStart_toStartOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_pass_vector"
|
||||
style="@style/CardSatPass.SideText"
|
||||
android:layout_marginStart="8dp"
|
||||
android:text="@string/card_pass_vector"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/card_max_el" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_max_el"
|
||||
style="@style/CardSatPass.MaxEl"
|
||||
android:text="@string/card_max_el"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_pass_start"
|
||||
style="@style/CardSatPass.SideText"
|
||||
android:layout_marginEnd="8dp"
|
||||
android:text="@string/card_pass_aos_time"
|
||||
app:layout_constraintBottom_toTopOf="@+id/card_max_el"
|
||||
app:layout_constraintEnd_toEndOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_pass_end"
|
||||
style="@style/CardSatPass.SideText"
|
||||
android:text="@string/card_pass_los_time"
|
||||
app:layout_constraintStart_toStartOf="@+id/card_pass_start"
|
||||
app:layout_constraintTop_toBottomOf="@+id/card_max_el" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_pass_aos"
|
||||
style="@style/CardSatPass.SideText"
|
||||
android:layout_marginEnd="4dp"
|
||||
android:text="@string/card_pass_aos"
|
||||
app:layout_constraintBaseline_toBaselineOf="@+id/card_pass_start"
|
||||
app:layout_constraintEnd_toStartOf="@+id/card_pass_start" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/card_pass_los"
|
||||
style="@style/CardSatPass.SideText"
|
||||
android:text="@string/card_pass_los"
|
||||
app:layout_constraintBaseline_toBaselineOf="@+id/card_pass_end"
|
||||
app:layout_constraintEnd_toEndOf="@+id/card_pass_aos" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
</com.google.android.material.card.MaterialCardView>
|
||||
@@ -3,7 +3,13 @@
|
||||
<string name="app_name">LookingSat</string>
|
||||
<string name="title">L∞king</string>
|
||||
<string name="subtitle">S@t</string>
|
||||
<string name="drawer_header_link">https://github.com/rt-bishop/LookingSat</string>
|
||||
|
||||
<string name="drawer_latitude">Latitude: </string>
|
||||
<string name="drawer_latitude_value">51.5074</string>
|
||||
<string name="drawer_longitude">Longitude: </string>
|
||||
<string name="drawer_longitude_value">0.1278</string>
|
||||
<string name="drawer_height">Height AMSL: </string>
|
||||
<string name="drawer_height_value">48.0m</string>
|
||||
|
||||
<string name="menu_sky">Sky at a Glance</string>
|
||||
<string name="menu_radar">Radar View</string>
|
||||
@@ -12,17 +18,17 @@
|
||||
<string name="menu_credits">Credits</string>
|
||||
<string name="menu_about">About the App</string>
|
||||
|
||||
<string name="latitude">Latitude: </string>
|
||||
<string name="latitude_def">51.5074</string>
|
||||
<string name="longitude">Longitude: </string>
|
||||
<string name="longitude_def">0.1278</string>
|
||||
<string name="height">Height AMSL: </string>
|
||||
<string name="height_def">48.0m</string>
|
||||
<string name="toolbar_aos_in">AOS in %02d:%02d:%02d</string>
|
||||
<string name="toolbar_refresh">Refresh</string>
|
||||
|
||||
<string name="menu_refresh">Refresh</string>
|
||||
<string name="card_sat_name">Meteor M2–2</string>
|
||||
<string name="card_pass_vector">V: 180° -> 360°</string>
|
||||
<string name="card_max_el">75.5°</string>
|
||||
<string name="card_pass_aos">AOS -</string>
|
||||
<string name="card_pass_los">LOS -</string>
|
||||
<string name="card_pass_aos_time">13:14:15</string>
|
||||
<string name="card_pass_los_time">16:17:18</string>
|
||||
|
||||
<string name="next_aos_pattern">AOS in %02d:%02d:%02d</string>
|
||||
<string name="drawer_locator">Drawer Locator</string>
|
||||
<string name="map_content">Nasa Map</string>
|
||||
<string name="placeholder">Placeholder</string>
|
||||
<string name="about">About</string>
|
||||
|
||||
@@ -49,7 +49,7 @@
|
||||
<item name="android:layout_width">wrap_content</item>
|
||||
<item name="android:layout_height">wrap_content</item>
|
||||
<item name="android:gravity">center</item>
|
||||
<item name="android:text">@string/next_aos_pattern</item>
|
||||
<item name="android:text">@string/toolbar_aos_in</item>
|
||||
<item name="android:textSize">30sp</item>
|
||||
<item name="android:textStyle">bold</item>
|
||||
<item name="android:textColor">@color/themeAccent</item>
|
||||
@@ -62,4 +62,23 @@
|
||||
<item name="android:backgroundTint">@color/toolbarButton</item>
|
||||
</style>
|
||||
|
||||
<style name="CardSatPass">
|
||||
<item name="android:layout_width">match_parent</item>
|
||||
<item name="android:layout_height">104dp</item>
|
||||
</style>
|
||||
|
||||
<style name="CardSatPass.SideText">
|
||||
<item name="android:layout_width">wrap_content</item>
|
||||
<item name="android:layout_height">wrap_content</item>
|
||||
<item name="android:textSize">20sp</item>
|
||||
</style>
|
||||
|
||||
<style name="CardSatPass.MaxEl">
|
||||
<item name="android:layout_width">wrap_content</item>
|
||||
<item name="android:layout_height">wrap_content</item>
|
||||
<item name="android:textSize">24sp</item>
|
||||
<item name="android:textColor">@color/themeAccent</item>
|
||||
<item name="android:textStyle">bold</item>
|
||||
</style>
|
||||
|
||||
</resources>
|
||||
Reference in new issue
Block a user