Author: Adam <git@apiote.xyz>
reformat
%!v(PANIC=String method: strings: negative Repeat count)
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index d2478c7b8a3b0a9eff5234a919762e5ff954ce86..3dda5bd2202ae415c42e7a46cbf35e869f85359d 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -36,8 +36,7 @@ android:exported="false" /> <activity android:name=".search.ResultsActivity" android:exported="false" - android:label="@string/title_activity_results" - android:theme="@style/Theme.Bimba.Style" /> + android:label="@string/title_activity_results" /> <activity android:name=".dashboard.MainActivity" android:exported="false" diff --git a/app/src/main/java/ml/adamsprogs/bimba/api/Api.kt b/app/src/main/java/ml/adamsprogs/bimba/api/Api.kt index db337e6501eacb2db359c1a0d07169c80cdf2ce2..6786b6a8fe2f3ee6a38d00b7b623fdddda9aee8d 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/api/Api.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/api/Api.kt @@ -27,7 +27,7 @@ suspend fun locateItems(server: Server, plusCode: String): InputStream? { return request(server, "items", mapOf("near" to plusCode)) } -suspend fun getDepartures(server: Server, stop: String, line: String?): InputStream? { +suspend fun getDepartures(server: Server, stop: String, line: String? = null): InputStream? { val params = mutableMapOf("code" to stop) if (line != null) { params["line"] = line diff --git a/app/src/main/java/ml/adamsprogs/bimba/api/Responses.kt b/app/src/main/java/ml/adamsprogs/bimba/api/Responses.kt index c909c287b157221e2c2104426ca740a7aca8657f..527f9975d70cd1b6a4dc629b3dd6ee8718eda5d0 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/api/Responses.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/api/Responses.kt @@ -5,15 +5,6 @@ import java.io.InputStream interface DeparturesResponse { companion object { - fun printable(it: String) = it.map { - when (Character.getType(it).toByte()) { - Character.CONTROL, Character.FORMAT, Character.PRIVATE_USE, - Character.SURROGATE, Character.UNASSIGNED, Character.OTHER_SYMBOL - -> "\\u%04x".format(it.code) - else -> it.toString() - } - }.joinToString("") - fun unmarshall(stream: InputStream): DeparturesResponse { val reader = Reader(stream) when (reader.readUInt()) { @@ -142,6 +133,6 @@ } } } -data class Error(val message: String) : ItemsResponse, DeparturesResponse { +data class Error(val message: String) : ItemsResponse, DeparturesResponse, FeedsResponse { } \ No newline at end of file diff --git a/app/src/main/java/ml/adamsprogs/bimba/api/Structs.kt b/app/src/main/java/ml/adamsprogs/bimba/api/Structs.kt index 72b68952db24dc2ba3c1b54e4cbf5d616991a5a4..0fb37650fd4fddbaf31805944da035af90c8c68f 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/api/Structs.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/api/Structs.kt @@ -297,6 +297,7 @@ dpToPixel(1.6f), dpToPixel(1.6f), dpToPixelI(10.4f) ), Paint().apply { color = colour.toInt() }) + val iconID = when (type) { LineType.BUS -> R.drawable.ic_bus_black_24dp LineType.TRAM -> R.drawable.ic_tram_black_24dp diff --git a/app/src/main/java/ml/adamsprogs/bimba/dashboard/MainActivity.kt b/app/src/main/java/ml/adamsprogs/bimba/dashboard/MainActivity.kt index 5034bc457a778d3284aa02db0798a7257a070b92..b7050351283bcb2b9de8b36629e81e9bb8fa4f2e 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/dashboard/MainActivity.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/dashboard/MainActivity.kt @@ -30,13 +30,11 @@ import ml.adamsprogs.bimba.departures.DeparturesActivity class MainActivity : AppCompatActivity() { - private lateinit var binding: ActivityMainBinding private lateinit var locationPermissionRequest: ActivityResultLauncher<Array<String>> override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) - binding = ActivityMainBinding.inflate(layoutInflater) setContentView(binding.root) @@ -122,7 +120,6 @@ is Stop -> { val intent = Intent(this, DeparturesActivity::class.java).apply { putExtra("code", item.code) putExtra("name", item.name) - // todo line, date, etc } startActivity(intent) } diff --git a/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeFragment.kt b/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeFragment.kt index 2f3a65df25748b68bc7294bc1af3b82cfac9d41a..049677ff850b90b70b9f64f5af0b5d9dac9dc8be 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeFragment.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeFragment.kt @@ -15,9 +15,7 @@ import ml.adamsprogs.bimba.api.Item import ml.adamsprogs.bimba.databinding.FragmentHomeBinding class HomeFragment : Fragment() { - private var _binding: FragmentHomeBinding? = null - private val binding get() = _binding!! private var lastSuggestions = listOf<Item>() @@ -27,15 +25,10 @@ inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle? ): View { + _binding = FragmentHomeBinding.inflate(inflater, container, false) + val homeViewModel = ViewModelProvider(this)[HomeViewModel::class.java] - - _binding = FragmentHomeBinding.inflate(inflater, container, false) - val root: View = binding.root - - val shp = requireContext().getSharedPreferences("shp", AppCompatActivity.MODE_PRIVATE) - - binding.searchBar.lastSuggestions = listOf<Item>() homeViewModel.items.observe(viewLifecycleOwner) { binding.searchBar.updateLastSuggestions(it) } @@ -81,7 +74,7 @@ binding.searchBar.lastSuggestions = lastSuggestions } }*/ - return root + return binding.root } override fun onDestroyView() { diff --git a/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeViewModel.kt b/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeViewModel.kt index 287426107c8a599cba17349d16ab17c50bb03fdc..4327e3af558a8306a823fbdd0cc554ccc881865b 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeViewModel.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/dashboard/ui/home/HomeViewModel.kt @@ -16,7 +16,6 @@ import ml.adamsprogs.bimba.api.* import java.io.InputStream class HomeViewModel : ViewModel() { - private val mutableItems = MutableLiveData<List<Item>>() val items: LiveData<List<Item>> = mutableItems @@ -36,7 +35,7 @@ is ItemsSuccess -> { return@withContext response.items } else -> { - TODO("Error response") + TODO("Error response") } } } diff --git a/app/src/main/java/ml/adamsprogs/bimba/departures/Departures.kt b/app/src/main/java/ml/adamsprogs/bimba/departures/Departures.kt index 596b5f1baf1f850d332b2fb4ed6e16f617959895..30abca2865d228a9cda756829cfce9a5efb1da31 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/departures/Departures.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/departures/Departures.kt @@ -1,5 +1,6 @@ package ml.adamsprogs.bimba.departures +import android.annotation.SuppressLint import android.content.Context import android.util.Log import android.view.LayoutInflater @@ -21,6 +22,7 @@ val headsign: TextView = itemView.findViewById(R.id.departure_headsign) companion object { + @SuppressLint("SetTextI18n") fun bind( departure: Departure, holder: BimbaDepartureViewHolder?, @@ -31,7 +33,8 @@ holder?.root?.setOnClickListener { onClickListener(departure) } holder?.lineIcon?.setImageBitmap(departure.line.icon(context!!)) - holder?.headsign?.text = "${departure.line.name} » ${departure.headsign}" + holder?.headsign?.text = + "${departure.line.name} » ${departure.headsign}" // check if >> is a11y val now = Calendar.getInstance() val departureTime = Calendar.getInstance().apply { set(Calendar.HOUR_OF_DAY, departure.time.Hour.toInt()) @@ -41,14 +44,11 @@ // todo zone roll(Calendar.DAY_OF_MONTH, departure.time.DayOffset.toInt()) } var duration = departureTime.timeInMillis - now.timeInMillis - val days = duration / (24 * 60 * 60 * 1000) - duration %= (24 * 60 * 60 * 1000) val hours = duration / (60 * 60 * 1000) duration %= (60 * 60 * 1000) val minutes = duration / (60 * 1000) duration %= (60 * 1000) - val seconds = duration / 1000 - holder?.departureTime?.text = when (departure.status.toInt()) { + holder?.departureTime?.text = when (departure.status.toInt()) { // todo(i18n) plurals 0 -> { "in " + if (hours > 0) { diff --git a/app/src/main/java/ml/adamsprogs/bimba/departures/DeparturesActivity.kt b/app/src/main/java/ml/adamsprogs/bimba/departures/DeparturesActivity.kt index ca814dc1cebfd445554539279afac988f8e8458d..5896a7bc1f2a91b21377e2cd31053206292ef947 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/departures/DeparturesActivity.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/departures/DeparturesActivity.kt @@ -1,6 +1,7 @@ package ml.adamsprogs.bimba.departures import android.content.Context +import android.content.SharedPreferences import androidx.appcompat.app.AppCompatActivity import android.os.Bundle import android.util.Log @@ -18,9 +19,10 @@ import java.io.InputStream class DeparturesActivity : AppCompatActivity() { private var _binding: ActivityDeparturesBinding? = null - private val binding get() = _binding!! + private lateinit var preferences: SharedPreferences + private lateinit var adapter: BimbaDeparturesAdapter override fun onCreate(savedInstanceState: Bundle?) { @@ -39,8 +41,7 @@ } binding.departuresRecycler.adapter = adapter WindowCompat.setDecorFitsSystemWindows(window, false) - val shp = getSharedPreferences("shp", MODE_PRIVATE) - val host = shp.getString("host", "bimba.apiote.xyz")!! + preferences = getSharedPreferences("shp", MODE_PRIVATE) // todo check every 30s @@ -48,8 +49,8 @@ MainScope().launch { intent?.extras?.getString("code")?.let { val departuresStream = getDepartures( Server( - host, shp.getString("token", "")!!, - shp.getString("${host}_feeds", "")!! + host, preferences.getString("token", "")!!, + preferences.getString("${host}_feeds", "")!! ), it, null ) if (departuresStream == null) { diff --git a/app/src/main/java/ml/adamsprogs/bimba/search/Results.kt b/app/src/main/java/ml/adamsprogs/bimba/search/Results.kt index 576997efda9bb9db7bc74b89daa12ba069d3541d..bcc2e5cbc4286454282862dcacfd1655da85d70c 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/search/Results.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/search/Results.kt @@ -1,20 +1,18 @@ package ml.adamsprogs.bimba.search +import android.annotation.SuppressLint import android.content.Context -import android.graphics.PorterDuff import android.util.Log import android.view.LayoutInflater import android.view.View import android.view.ViewGroup import android.widget.ImageView import android.widget.TextView -import androidx.appcompat.content.res.AppCompatResources import androidx.recyclerview.widget.RecyclerView import com.mancj.materialsearchbar.adapter.SuggestionsAdapter import ml.adamsprogs.bimba.R import ml.adamsprogs.bimba.api.Item import ml.adamsprogs.bimba.api.Line -import ml.adamsprogs.bimba.api.LineType import ml.adamsprogs.bimba.api.Stop class BimbaViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) { @@ -31,38 +29,40 @@ context: Context?, onClickListener: (Item) -> Unit ) { when (item) { - is Stop -> { - holder?.icon?.setImageResource(R.drawable.ic_stop_black_24dp) // todo stop icon // todo dark theme colour - holder?.title?.text = "${item.name} [${item.code}]" - holder?.description?.text = - item.changeOptions.groupBy { it.line }.map{ Pair(it.key, it.value.joinToString { co-> co.headsign })}.joinToString { "${it.first} » ${it.second}" } - } - is Line -> { - val icon = item.icon(context!!) - holder?.icon?.apply { - setImageBitmap(icon) - colorFilter = null - Log.v("Colour", "${item.name}: ${item.colour}, ${item.colour.toInt().toString(16)}") - Log.v("Colour", "${item.name}: ${item.textColour()}, ${item.textColour().toString(16)}") - } - holder?.title?.text = item.name - holder?.description?.text = - "${item.headsignsThere.joinToString { it }} «» ${item.headsignsBack.joinToString { it }}" - } - else -> TODO("Shouldn't happen") + is Stop -> bindStop(item, holder) + is Line -> bindLine(item, holder, context) + else -> throw NotImplementedError("Shouldn't happen") } holder?.root?.setOnClickListener { onClickListener(item) } - /*holder!!.root.setOnClickListener { - onSuggestionClickListener.onSuggestionClickListener(suggestion) - } - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { - holder.text.text = Html.fromHtml(suggestion.getBody(context), Html.FROM_HTML_MODE_LEGACY) - } else { - @Suppress("DEPRECATION") - holder.text.text = Html.fromHtml(suggestion.getBody(context)) + } + + @SuppressLint("SetTextI18n") + fun bindStop(stop: Stop, holder: BimbaViewHolder?) { + holder?.icon?.setImageResource(R.drawable.ic_stop_black_24dp) // todo(ui,dark) stop icon // todo dark theme colour + holder?.title?.text = "${stop.name} [${stop.code}]" + holder?.description?.text = + stop.changeOptions.groupBy { it.line } + .map { Pair(it.key, it.value.joinToString { co -> co.headsign }) } + .joinToString { "${it.first} » ${it.second}" } + } + + @SuppressLint("SetTextI18n") + fun bindLine(line: Line, holder: BimbaViewHolder?, context: Context?) { + val icon = line.icon(context!!) + holder?.icon?.apply { + setImageBitmap(icon) + colorFilter = null + Log.v("Colour", "${line.name}: ${line.colour}, ${line.colour.toInt().toString(16)}") + Log.v("Colour", "${line.name}: ${line.textColour()}, ${line.textColour().toString(16)}") } + holder?.title?.text = line.name + holder?.description?.text = + "${line.headsignsThere.joinToString { it }} «» ${line.headsignsBack.joinToString { it }}" + } + } +} interface Adapter { fun createViewHolder( diff --git a/app/src/main/java/ml/adamsprogs/bimba/search/ResultsActivity.kt b/app/src/main/java/ml/adamsprogs/bimba/search/ResultsActivity.kt index 9ef7fa066249335b95328fc21c70eaeb5c86abc7..6ce9b705b3da1c076159a5bce9bb6962343f23b2 100644 --- a/app/src/main/java/ml/adamsprogs/bimba/search/ResultsActivity.kt +++ b/app/src/main/java/ml/adamsprogs/bimba/search/ResultsActivity.kt @@ -27,19 +27,17 @@ MODE_LOCATION, MODE_SEARCH } private var _binding: ActivityResultsBinding? = null - private val binding get() = _binding!! private lateinit var adapter: BimbaResultsAdapter - - private lateinit var shp: SharedPreferences + private lateinit var preferences: SharedPreferences override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) _binding = ActivityResultsBinding.inflate(layoutInflater) setContentView(binding.root) - shp = getSharedPreferences("shp", MODE_PRIVATE) + preferences = getSharedPreferences("shp", MODE_PRIVATE) binding.resultsRecycler.layoutManager = LinearLayoutManager(this) adapter = BimbaResultsAdapter(layoutInflater, this, listOf()) { @@ -48,12 +46,11 @@ is Stop -> { val intent = Intent(this, DeparturesActivity::class.java).apply { putExtra("code", it.code) putExtra("name", it.name) - // todo line, date, etc } startActivity(intent) } is Line -> { - TODO("start line graph actvity") + TODO("start line graph activity") } } } @@ -71,11 +68,11 @@ } Mode.MODE_SEARCH -> { val query = intent.extras?.getString("query")!! supportActionBar?.title = "Results for ‘$query’" - val host = shp.getString("host", "bimba.apiote.xyz")!! + val host = preferences.getString("host", "bimba.apiote.xyz")!! getItemsByQuery( Server( - host, shp.getString("token", "")!!, - shp.getString("${host}_feeds", "")!! + host, preferences.getString("token", "")!!, + preferences.getString("${host}_feeds", "")!! ), query ) } @@ -96,11 +93,11 @@ Log.v("Location", "found $location") val code = OpenLocationCode.encode(location.latitude, location.longitude) val locationManager = getSystemService(Context.LOCATION_SERVICE) as LocationManager locationManager.removeUpdates(this) - val host = shp.getString("host", "bimba.apiote.xyz")!! + val host = preferences.getString("host", "bimba.apiote.xyz")!! getItemsByLocation( Server( - host, shp.getString("token", "")!!, - shp.getString("${host}_feeds", "")!! + host, preferences.getString("token", "")!!, + preferences.getString("${host}_feeds", "")!! ), code ) } diff --git a/app/src/main/res/layout/activity_departures.xml b/app/src/main/res/layout/activity_departures.xml index 81649a0c4b35fff32622ac71c348438035fd5da1..783da782471292a2ce18f33c274c2ed6dbb6c215 100644 --- a/app/src/main/res/layout/activity_departures.xml +++ b/app/src/main/res/layout/activity_departures.xml @@ -3,6 +3,7 @@xmlns:app="http://schemas.android.com/apk/res-auto" android:layout_width="match_parent" android:layout_height="match_parent"> + <androidx.constraintlayout.widget.ConstraintLayout android:id="@+id/departures_progress" android:layout_width="match_parent" @@ -26,18 +27,18 @@ <!-- todo toolbar font family --> <com.google.android.material.appbar.CollapsingToolbarLayout android:id="@+id/collapsing_layout" - app:layout_scrollFlags="scroll|exitUntilCollapsed|snap" style="?attr/collapsingToolbarLayoutMediumStyle" android:layout_width="match_parent" - app:maxLines="2" - android:layout_height="?attr/collapsingToolbarLayoutMediumSize"> + android:layout_height="?attr/collapsingToolbarLayoutMediumSize" + app:layout_scrollFlags="scroll|exitUntilCollapsed|snap" + app:maxLines="2"> <com.google.android.material.appbar.MaterialToolbar android:id="@+id/departures_app_bar" android:layout_width="match_parent" - app:layout_collapseMode="pin" android:layout_height="?attr/actionBarSize" - android:elevation="0dp" /> + android:elevation="0dp" + app:layout_collapseMode="pin" /> </com.google.android.material.appbar.CollapsingToolbarLayout> diff --git a/app/src/main/res/layout/departure.xml b/app/src/main/res/layout/departure.xml index 906911d4c1f911da7ed8d86df5989c7956ce993d..cf20ee4ca1b84bf6c447bed2d9117b49abb78f96 100644 --- a/app/src/main/res/layout/departure.xml +++ b/app/src/main/res/layout/departure.xml @@ -10,7 +10,6 @@ android:id="@+id/line_icon" android:layout_width="24dp" android:layout_height="24dp" - android:layout_marginStart="8dp" app:layout_constraintBottom_toTopOf="@+id/departure_headsign" app:layout_constraintStart_toStartOf="parent"