From f5355cf5b6281c8475a06061ac5fc80f7b9cdedf Mon Sep 17 00:00:00 2001 From: Iván Ávalos Date: Sun, 16 Jan 2022 16:39:00 -0600 Subject: Moved stuff to shared package --- .../android/details/reports/UnitReportsFragment.kt | 2 +- .../TrackerMap/android/devices/DevicesAdapter.kt | 8 +- .../TrackerMap/android/devices/DevicesFragment.kt | 11 +- .../TrackerMap/android/devices/UnitRenderData.kt | 218 -------------------- .../TrackerMap/android/map/MapFragment.kt | 1 + .../android/map/MarkerTransformations.kt | 142 ------------- .../TrackerMap/android/map/UnitMapFragment.kt | 14 +- .../android/shared/MarkerTransformations.kt | 143 +++++++++++++ .../TrackerMap/android/shared/UnitRenderData.kt | 221 +++++++++++++++++++++ 9 files changed, 382 insertions(+), 378 deletions(-) delete mode 100644 androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/UnitRenderData.kt delete mode 100644 androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MarkerTransformations.kt create mode 100644 androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/MarkerTransformations.kt create mode 100644 androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/UnitRenderData.kt (limited to 'androidApp') diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/details/reports/UnitReportsFragment.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/details/reports/UnitReportsFragment.kt index 20d2a48..3b3570b 100644 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/details/reports/UnitReportsFragment.kt +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/details/reports/UnitReportsFragment.kt @@ -22,7 +22,7 @@ import mx.trackermap.TrackerMap.android.R import mx.trackermap.TrackerMap.android.databinding.UnitDetailsReportsBinding import mx.trackermap.TrackerMap.android.details.UnitDetailsAdapter import mx.trackermap.TrackerMap.android.map.MapFragment -import mx.trackermap.TrackerMap.android.map.MarkerTransformations +import mx.trackermap.TrackerMap.android.shared.MarkerTransformations import mx.trackermap.TrackerMap.client.models.EventInformation import mx.trackermap.TrackerMap.client.models.Position import mx.trackermap.TrackerMap.client.models.Stop diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesAdapter.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesAdapter.kt index 344907c..b1854a9 100644 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesAdapter.kt +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesAdapter.kt @@ -1,19 +1,15 @@ package mx.trackermap.TrackerMap.android.devices -import android.util.TypedValue import android.view.LayoutInflater import android.view.ViewGroup -import android.widget.FrameLayout import androidx.core.view.updateLayoutParams import androidx.recyclerview.widget.RecyclerView import mx.trackermap.TrackerMap.android.R import mx.trackermap.TrackerMap.android.databinding.UnitItemBinding +import mx.trackermap.TrackerMap.android.shared.ActionCallback +import mx.trackermap.TrackerMap.android.shared.UnitRenderData import mx.trackermap.TrackerMap.client.models.UnitInformation -enum class Action { - CLICK, DETAILS, REPORTS, COMMANDS -} - class DevicesAdapter( private val units: List, private val actionCallback: ActionCallback? diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesFragment.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesFragment.kt index 96d4696..b1a3663 100644 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesFragment.kt +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/DevicesFragment.kt @@ -6,12 +6,11 @@ import android.util.Log import android.view.LayoutInflater import android.view.View import android.view.ViewGroup -import android.view.ViewTreeObserver -import android.widget.Toast import androidx.recyclerview.widget.LinearLayoutManager import kotlinx.coroutines.DelicateCoroutinesApi import mx.trackermap.TrackerMap.android.databinding.DevicesFragmentBinding import mx.trackermap.TrackerMap.android.details.DetailsActivity +import mx.trackermap.TrackerMap.android.shared.UnitRenderData import mx.trackermap.TrackerMap.android.units.UnitFragment import mx.trackermap.TrackerMap.android.units.UnitsViewModel import mx.trackermap.TrackerMap.client.models.UnitInformation @@ -82,9 +81,11 @@ class DevicesFragment(private val unitsViewModel: UnitsViewModel) : UnitFragment unitsViewModel.units.removeObservers(viewLifecycleOwner) } - private fun itemAction(unit: UnitInformation, action: Action) { + private fun itemAction(unit: UnitInformation, action: UnitRenderData.Action) { when (action) { - Action.DETAILS, Action.REPORTS, Action.COMMANDS -> { + UnitRenderData.Action.DETAILS, + UnitRenderData.Action.REPORTS, + UnitRenderData.Action.COMMANDS -> { Log.d("DevicesFragment", "Action: $action - Unit: $unit") val activity = requireActivity() val intent = Intent(activity.applicationContext, DetailsActivity::class.java) @@ -93,7 +94,7 @@ class DevicesFragment(private val unitsViewModel: UnitsViewModel) : UnitFragment intent.putExtra(DetailsActivity.ACTION_EXTRA, action) startActivity(intent) } - Action.CLICK -> { + UnitRenderData.Action.CLICK -> { unitsViewModel.selectUnit(unit) } } diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/UnitRenderData.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/UnitRenderData.kt deleted file mode 100644 index c7999de..0000000 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/devices/UnitRenderData.kt +++ /dev/null @@ -1,218 +0,0 @@ -package mx.trackermap.TrackerMap.android.devices - -import android.content.Context -import android.graphics.Color -import android.util.TypedValue -import android.view.Gravity -import android.view.View -import android.widget.Button -import android.widget.GridLayout -import android.widget.ImageView -import android.widget.TextView -import androidx.cardview.widget.CardView -import androidx.core.content.ContextCompat -import com.zerobranch.layout.SwipeLayout -import kotlinx.serialization.json.longOrNull -import mx.trackermap.TrackerMap.android.R -import mx.trackermap.TrackerMap.android.map.MarkerTransformations -import mx.trackermap.TrackerMap.client.models.UnitInformation -import mx.trackermap.TrackerMap.utils.Formatter -import mx.trackermap.TrackerMap.utils.SpeedUnit - -typealias ActionCallback = (unit: UnitInformation, action: Action) -> Unit - -class UnitRenderData { - data class UnitRenderViewHolder( - val unitName: TextView, - val unitIcon: ImageView? = null, - val statusIcon: ImageView, - val engineStopIcon: ImageView, - val gridLayout: GridLayout, - val detailsButton: Button? = null, - val reportsButton: Button? = null, - val commandsButton: Button? = null, - val unitCard: CardView? = null, - val swipeLayout: SwipeLayout? = null - ) - - companion object { - fun render( - viewHolder: UnitRenderViewHolder, - context: Context, - unit: UnitInformation, - actionCallback: ActionCallback? - ) { - viewHolder.apply { - val details: MutableList> = mutableListOf() - - /* Device name */ - unitName.text = unit.device.name - - /* Device icon */ - unitIcon?.setImageResource( - MarkerTransformations.categoryToResourceId(unit.device.category) - ) - unitIcon?.contentDescription = context.getString( - MarkerTransformations.categoryToStringId(unit.device.category) - ) - - /* Contact */ - unit.device.contact?.let { contact -> - if (contact.isNotEmpty()) { - details.add( - Triple( - R.drawable.device_contact, - contact, - context.getString(R.string.unit_driver_name) - ) - ) - } - } - - statusIcon.visibility = View.GONE - engineStopIcon.visibility = View.GONE - - unit.position?.let { position -> - /* Status icon */ - statusIcon.visibility = View.VISIBLE - position.speed?.let { speed -> - if (speed >= 2) { - statusIcon.setColorFilter( - ContextCompat.getColor(context, R.color.colorOnline) - ) - } else { - statusIcon.setColorFilter( - ContextCompat.getColor(context, R.color.colorOffline) - ) - } - } ?: run { - statusIcon.setColorFilter(Color.GRAY) - } - - /* Engine stop */ - val attributes = position.attributes - if (attributes["out1"].toString() != "null") { - engineStopIcon.visibility = View.VISIBLE - engineStopIcon.setImageResource( - when (attributes["out1"].toString()) { - "true" -> R.drawable.device_unlocked - "false" -> R.drawable.device_locked - else -> R.drawable.device_locked - } - ) - engineStopIcon.contentDescription = when (attributes["out1"].toString()) { - "true" -> context.getString(R.string.unit_lock_on) - "false" -> context.getString(R.string.unit_lock_off) - else -> context.getString(R.string.unit_lock_on) - } - } - - /* Speed */ - position.speed?.let { speed -> - details.add( - Triple( - R.drawable.position_speed, - Formatter.formatSpeed(speed, SpeedUnit.KMH), - context.getString(R.string.unit_speed) - ) - ) - } - - /* Address */ - position.address?.let { address -> - details.add( - Triple( - R.drawable.position_address, - address, - context.getString(R.string.unit_last_address) - ) - ) - } - - /* Hourmeter */ - position.attributes["hours"]?.longOrNull?.let { - if (it > 0) { - details.add( - Triple( - R.drawable.position_hourmeter, - Formatter.formatHours(it), - context.getString(R.string.unit_hourmeter) - ) - ) - } - } - - /* Date time */ - position.fixTime?.let { fixTime -> - details.add( - Triple( - R.drawable.position_datetime, - Formatter.formatDate(fixTime), - context.getString(R.string.unit_last_date) - ) - ) - } - } - - gridLayout.removeAllViewsInLayout() - val metrics = context.resources.displayMetrics - details.forEachIndexed { i, detail -> - /* Property icon */ - val imageView = ImageView(gridLayout.context) - imageView.setImageResource(detail.first) - imageView.contentDescription = detail.third - imageView.setColorFilter( - ContextCompat.getColor( - context, - androidx.appcompat.R.color.secondary_text_default_material_light - ) - ) - - val imageLayout = GridLayout.LayoutParams() - imageLayout.width = GridLayout.LayoutParams.WRAP_CONTENT - imageLayout.height = GridLayout.LayoutParams.WRAP_CONTENT - imageLayout.marginEnd = - TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 6f, metrics).toInt() - imageLayout.rowSpec = GridLayout.spec(i) - imageLayout.columnSpec = GridLayout.spec(0) - imageView.layoutParams = imageLayout - - /* Property text */ - val textView = TextView(gridLayout.context) - textView.text = detail.second - - val textLayout = GridLayout.LayoutParams() - textLayout.width = 0 - textLayout.height = GridLayout.LayoutParams.MATCH_PARENT - textLayout.rowSpec = GridLayout.spec(i) - textLayout.columnSpec = GridLayout.spec(1, 1, 5f) - textView.layoutParams = textLayout - - gridLayout.addView(imageView) - gridLayout.addView(textView) - - imageLayout.setGravity(Gravity.CENTER) - } - - actionCallback?.let { callback -> - unitCard?.setOnClickListener { - swipeLayout?.close() - callback(unit, Action.CLICK) - } - detailsButton?.setOnClickListener { - swipeLayout?.close() - callback(unit, Action.DETAILS) - } - reportsButton?.setOnClickListener { - swipeLayout?.close() - callback(unit, Action.REPORTS) - } - commandsButton?.setOnClickListener { - swipeLayout?.close() - callback(unit, Action.COMMANDS) - } - } - } - } - } -} \ No newline at end of file diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MapFragment.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MapFragment.kt index b8ce350..6a80f95 100644 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MapFragment.kt +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MapFragment.kt @@ -17,6 +17,7 @@ import mil.nga.sf.util.SFException import mil.nga.sf.wkt.GeometryReader import java.io.File import mx.trackermap.TrackerMap.android.R +import mx.trackermap.TrackerMap.android.shared.MarkerTransformations import mx.trackermap.TrackerMap.client.models.Geofence import mx.trackermap.TrackerMap.client.models.MapLayer import mx.trackermap.TrackerMap.utils.MapCalculus diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MarkerTransformations.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MarkerTransformations.kt deleted file mode 100644 index 933cd8a..0000000 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/MarkerTransformations.kt +++ /dev/null @@ -1,142 +0,0 @@ -package mx.trackermap.TrackerMap.android.map - -import android.util.Log -import mx.trackermap.TrackerMap.android.R -import mx.trackermap.TrackerMap.client.models.Position -import mx.trackermap.TrackerMap.client.models.Stop -import mx.trackermap.TrackerMap.client.models.UnitInformation -import mx.trackermap.TrackerMap.utils.MarkerType - -object MarkerTransformations { - fun unitToMarker(unit: UnitInformation): MapFragment.Marker? { - if (unit.position == null || unit.position!!.latitude == null || unit.position!!.longitude == null) { - return null - } - - return MapFragment.Marker( - unit.position!!.id!!, - unit.device.name, - unit.position!!.latitude!!, - unit.position!!.longitude!!, - categoryToMarkerType(unit.device.category ?: "") - ) - } - - fun positionToMarker(position: Position): MapFragment.Marker? { - if (position.latitude == null || position.longitude == null) { - return null - } - - return MapFragment.Marker( - position.id!!, - "", - position.latitude!!, - position.longitude!! - ) - } - - fun stopToMarker(stop: Stop): MapFragment.Marker? { - Log.d("MarkerTransformations", "stopToMarker($stop)") - if (stop.latitude == null || stop.longitude == null) { - return null - } - - return MapFragment.Marker( - stop.deviceId!!, - stop.deviceName!!, - stop.latitude!!, - stop.longitude!! - ) - } - - private fun categoryToMarkerType(category: String?): MarkerType { - return when (category?.lowercase()) { - "animal" -> MarkerType.ANIMAL - "bicycle" -> MarkerType.BICYCLE - "boat" -> MarkerType.BOAT - "bus" -> MarkerType.BUS - "car" -> MarkerType.CAR - "crane" -> MarkerType.CRANE - "helicopter" -> MarkerType.HELICOPTER - "motorcycle" -> MarkerType.MOTORCYCLE - "offroad" -> MarkerType.OFFROAD - "person" -> MarkerType.PERSON - "pickup" -> MarkerType.PICKUP - "plane" -> MarkerType.PLANE - "scooter" -> MarkerType.SCOOTER - "ship" -> MarkerType.SHIP - "tractor" -> MarkerType.TRACTOR - "train" -> MarkerType.TRAIN - "tram" -> MarkerType.TRAM - "trolleybus" -> MarkerType.TROLLEYBUS - "truck" -> MarkerType.TRUCK - "van" -> MarkerType.VAN - else -> MarkerType.DEFAULT - } - } - - fun markerTypeToResourceId(markerType: MarkerType): Int { - return when (markerType) { - MarkerType.ANIMAL -> R.drawable.map_animal - MarkerType.BICYCLE -> R.drawable.map_bicycle - MarkerType.BOAT -> R.drawable.map_boat - MarkerType.BUS -> R.drawable.map_bus - MarkerType.CAR -> R.drawable.map_car - MarkerType.CRANE -> R.drawable.map_crane - MarkerType.DEFAULT -> R.drawable.map_default - MarkerType.HELICOPTER -> R.drawable.map_helicopter - MarkerType.MOTORCYCLE -> R.drawable.map_motorcycle - MarkerType.OFFROAD -> R.drawable.map_offroad - MarkerType.PERSON -> R.drawable.map_person - MarkerType.PICKUP -> R.drawable.map_pickup - MarkerType.PLANE -> R.drawable.map_plane - MarkerType.SCOOTER -> R.drawable.map_scooter - MarkerType.SHIP -> R.drawable.map_ship - MarkerType.TRACTOR -> R.drawable.map_tractor - MarkerType.TRAIN -> R.drawable.map_train - MarkerType.TRAM -> R.drawable.map_tram - MarkerType.TROLLEYBUS -> R.drawable.map_trolleybus - MarkerType.TRUCK -> R.drawable.map_truck - MarkerType.VAN -> R.drawable.map_van - - MarkerType.REPORT_POSITION -> R.drawable.map_report_position - MarkerType.REPORT_START -> R.drawable.map_report_start - MarkerType.REPORT_END -> R.drawable.map_report_end - } - } - - fun markerTypeToStringId(markerType: MarkerType): Int { - return when (markerType) { - MarkerType.ANIMAL -> R.string.unit_category_animal - MarkerType.BICYCLE -> R.string.unit_category_bicycle - MarkerType.BOAT -> R.string.unit_category_boat - MarkerType.BUS -> R.string.unit_category_bus - MarkerType.CAR -> R.string.unit_category_car - MarkerType.CRANE -> R.string.unit_category_crane - MarkerType.DEFAULT -> R.string.unit_category_default - MarkerType.HELICOPTER -> R.string.unit_category_helicopter - MarkerType.MOTORCYCLE -> R.string.unit_category_motorcycle - MarkerType.OFFROAD -> R.string.unit_category_offroad - MarkerType.PERSON -> R.string.unit_category_person - MarkerType.PICKUP -> R.string.unit_category_pickup - MarkerType.PLANE -> R.string.unit_category_plane - MarkerType.SCOOTER -> R.string.unit_category_scooter - MarkerType.SHIP -> R.string.unit_category_ship - MarkerType.TRACTOR -> R.string.unit_category_tractor - MarkerType.TRAIN -> R.string.unit_category_train - MarkerType.TRAM -> R.string.unit_category_tram - MarkerType.TROLLEYBUS -> R.string.unit_category_trolleybus - MarkerType.TRUCK -> R.string.unit_category_truck - MarkerType.VAN -> R.string.unit_category_van - else -> R.string.unit_category_default - } - } - - fun categoryToResourceId(category: String?): Int { - return markerTypeToResourceId(categoryToMarkerType(category)) - } - - fun categoryToStringId(category: String?): Int { - return markerTypeToResourceId(categoryToMarkerType(category)) - } -} \ No newline at end of file diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/UnitMapFragment.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/UnitMapFragment.kt index 6f6596f..6ea5f82 100644 --- a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/UnitMapFragment.kt +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/map/UnitMapFragment.kt @@ -11,8 +11,8 @@ import kotlinx.coroutines.DelicateCoroutinesApi import mx.trackermap.TrackerMap.android.R import mx.trackermap.TrackerMap.android.databinding.UnitMapFragmentBinding import mx.trackermap.TrackerMap.android.details.DetailsActivity -import mx.trackermap.TrackerMap.android.devices.Action -import mx.trackermap.TrackerMap.android.devices.UnitRenderData +import mx.trackermap.TrackerMap.android.shared.MarkerTransformations +import mx.trackermap.TrackerMap.android.shared.UnitRenderData import mx.trackermap.TrackerMap.android.units.UnitFragment import mx.trackermap.TrackerMap.android.units.UnitsViewModel import mx.trackermap.TrackerMap.client.models.UnitInformation @@ -117,10 +117,12 @@ class UnitMapFragment(private val unitsViewModel: UnitsViewModel) : UnitFragment unitsViewModel.geofences.removeObservers(viewLifecycleOwner) } - private fun itemAction(unit: UnitInformation, action: Action) { + private fun itemAction(unit: UnitInformation, action: UnitRenderData.Action) { when (action) { - Action.DETAILS, Action.REPORTS, Action.COMMANDS -> { - Log.d("DevicesFragment", "Action: $action - Unit: $unit") + UnitRenderData.Action.DETAILS, + UnitRenderData.Action.REPORTS, + UnitRenderData.Action.COMMANDS -> { + Log.d("UnitMapFragment", "Action: $action - Unit: $unit") val activity = requireActivity() val intent = Intent(activity.applicationContext, DetailsActivity::class.java) intent.putExtra(DetailsActivity.DEVICE_ID_EXTRA, unit.device.id) @@ -128,7 +130,7 @@ class UnitMapFragment(private val unitsViewModel: UnitsViewModel) : UnitFragment intent.putExtra(DetailsActivity.ACTION_EXTRA, action) startActivity(intent) } - Action.CLICK -> { + UnitRenderData.Action.CLICK -> { unitsViewModel.selectUnit(unit) } } diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/MarkerTransformations.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/MarkerTransformations.kt new file mode 100644 index 0000000..660b436 --- /dev/null +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/MarkerTransformations.kt @@ -0,0 +1,143 @@ +package mx.trackermap.TrackerMap.android.shared + +import android.util.Log +import mx.trackermap.TrackerMap.android.R +import mx.trackermap.TrackerMap.android.map.MapFragment +import mx.trackermap.TrackerMap.client.models.Position +import mx.trackermap.TrackerMap.client.models.Stop +import mx.trackermap.TrackerMap.client.models.UnitInformation +import mx.trackermap.TrackerMap.utils.MarkerType + +object MarkerTransformations { + fun unitToMarker(unit: UnitInformation): MapFragment.Marker? { + if (unit.position == null || unit.position!!.latitude == null || unit.position!!.longitude == null) { + return null + } + + return MapFragment.Marker( + unit.position!!.id!!, + unit.device.name, + unit.position!!.latitude!!, + unit.position!!.longitude!!, + categoryToMarkerType(unit.device.category ?: "") + ) + } + + fun positionToMarker(position: Position): MapFragment.Marker? { + if (position.latitude == null || position.longitude == null) { + return null + } + + return MapFragment.Marker( + position.id!!, + "", + position.latitude!!, + position.longitude!! + ) + } + + fun stopToMarker(stop: Stop): MapFragment.Marker? { + Log.d("MarkerTransformations", "stopToMarker($stop)") + if (stop.latitude == null || stop.longitude == null) { + return null + } + + return MapFragment.Marker( + stop.deviceId!!, + stop.deviceName!!, + stop.latitude!!, + stop.longitude!! + ) + } + + private fun categoryToMarkerType(category: String?): MarkerType { + return when (category?.lowercase()) { + "animal" -> MarkerType.ANIMAL + "bicycle" -> MarkerType.BICYCLE + "boat" -> MarkerType.BOAT + "bus" -> MarkerType.BUS + "car" -> MarkerType.CAR + "crane" -> MarkerType.CRANE + "helicopter" -> MarkerType.HELICOPTER + "motorcycle" -> MarkerType.MOTORCYCLE + "offroad" -> MarkerType.OFFROAD + "person" -> MarkerType.PERSON + "pickup" -> MarkerType.PICKUP + "plane" -> MarkerType.PLANE + "scooter" -> MarkerType.SCOOTER + "ship" -> MarkerType.SHIP + "tractor" -> MarkerType.TRACTOR + "train" -> MarkerType.TRAIN + "tram" -> MarkerType.TRAM + "trolleybus" -> MarkerType.TROLLEYBUS + "truck" -> MarkerType.TRUCK + "van" -> MarkerType.VAN + else -> MarkerType.DEFAULT + } + } + + fun markerTypeToResourceId(markerType: MarkerType): Int { + return when (markerType) { + MarkerType.ANIMAL -> R.drawable.map_animal + MarkerType.BICYCLE -> R.drawable.map_bicycle + MarkerType.BOAT -> R.drawable.map_boat + MarkerType.BUS -> R.drawable.map_bus + MarkerType.CAR -> R.drawable.map_car + MarkerType.CRANE -> R.drawable.map_crane + MarkerType.DEFAULT -> R.drawable.map_default + MarkerType.HELICOPTER -> R.drawable.map_helicopter + MarkerType.MOTORCYCLE -> R.drawable.map_motorcycle + MarkerType.OFFROAD -> R.drawable.map_offroad + MarkerType.PERSON -> R.drawable.map_person + MarkerType.PICKUP -> R.drawable.map_pickup + MarkerType.PLANE -> R.drawable.map_plane + MarkerType.SCOOTER -> R.drawable.map_scooter + MarkerType.SHIP -> R.drawable.map_ship + MarkerType.TRACTOR -> R.drawable.map_tractor + MarkerType.TRAIN -> R.drawable.map_train + MarkerType.TRAM -> R.drawable.map_tram + MarkerType.TROLLEYBUS -> R.drawable.map_trolleybus + MarkerType.TRUCK -> R.drawable.map_truck + MarkerType.VAN -> R.drawable.map_van + + MarkerType.REPORT_POSITION -> R.drawable.map_report_position + MarkerType.REPORT_START -> R.drawable.map_report_start + MarkerType.REPORT_END -> R.drawable.map_report_end + } + } + + fun markerTypeToStringId(markerType: MarkerType): Int { + return when (markerType) { + MarkerType.ANIMAL -> R.string.unit_category_animal + MarkerType.BICYCLE -> R.string.unit_category_bicycle + MarkerType.BOAT -> R.string.unit_category_boat + MarkerType.BUS -> R.string.unit_category_bus + MarkerType.CAR -> R.string.unit_category_car + MarkerType.CRANE -> R.string.unit_category_crane + MarkerType.DEFAULT -> R.string.unit_category_default + MarkerType.HELICOPTER -> R.string.unit_category_helicopter + MarkerType.MOTORCYCLE -> R.string.unit_category_motorcycle + MarkerType.OFFROAD -> R.string.unit_category_offroad + MarkerType.PERSON -> R.string.unit_category_person + MarkerType.PICKUP -> R.string.unit_category_pickup + MarkerType.PLANE -> R.string.unit_category_plane + MarkerType.SCOOTER -> R.string.unit_category_scooter + MarkerType.SHIP -> R.string.unit_category_ship + MarkerType.TRACTOR -> R.string.unit_category_tractor + MarkerType.TRAIN -> R.string.unit_category_train + MarkerType.TRAM -> R.string.unit_category_tram + MarkerType.TROLLEYBUS -> R.string.unit_category_trolleybus + MarkerType.TRUCK -> R.string.unit_category_truck + MarkerType.VAN -> R.string.unit_category_van + else -> R.string.unit_category_default + } + } + + fun categoryToResourceId(category: String?): Int { + return markerTypeToResourceId(categoryToMarkerType(category)) + } + + fun categoryToStringId(category: String?): Int { + return markerTypeToResourceId(categoryToMarkerType(category)) + } +} \ No newline at end of file diff --git a/androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/UnitRenderData.kt b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/UnitRenderData.kt new file mode 100644 index 0000000..e8a4bd6 --- /dev/null +++ b/androidApp/src/main/java/mx/trackermap/TrackerMap/android/shared/UnitRenderData.kt @@ -0,0 +1,221 @@ +package mx.trackermap.TrackerMap.android.shared + +import android.content.Context +import android.graphics.Color +import android.util.TypedValue +import android.view.Gravity +import android.view.View +import android.widget.Button +import android.widget.GridLayout +import android.widget.ImageView +import android.widget.TextView +import androidx.cardview.widget.CardView +import androidx.core.content.ContextCompat +import com.zerobranch.layout.SwipeLayout +import kotlinx.serialization.json.longOrNull +import mx.trackermap.TrackerMap.android.R +import mx.trackermap.TrackerMap.client.models.UnitInformation +import mx.trackermap.TrackerMap.utils.Formatter +import mx.trackermap.TrackerMap.utils.SpeedUnit + +typealias ActionCallback = (unit: UnitInformation, action: UnitRenderData.Action) -> Unit + +class UnitRenderData { + data class UnitRenderViewHolder( + val unitName: TextView, + val unitIcon: ImageView? = null, + val statusIcon: ImageView, + val engineStopIcon: ImageView, + val gridLayout: GridLayout, + val detailsButton: Button? = null, + val reportsButton: Button? = null, + val commandsButton: Button? = null, + val unitCard: CardView? = null, + val swipeLayout: SwipeLayout? = null + ) + + enum class Action { + CLICK, DETAILS, REPORTS, COMMANDS + } + + companion object { + fun render( + viewHolder: UnitRenderViewHolder, + context: Context, + unit: UnitInformation, + actionCallback: ActionCallback? + ) { + viewHolder.apply { + val details: MutableList> = mutableListOf() + + /* Device name */ + unitName.text = unit.device.name + + /* Device icon */ + unitIcon?.setImageResource( + MarkerTransformations.categoryToResourceId(unit.device.category) + ) + unitIcon?.contentDescription = context.getString( + MarkerTransformations.categoryToStringId(unit.device.category) + ) + + /* Contact */ + unit.device.contact?.let { contact -> + if (contact.isNotEmpty()) { + details.add( + Triple( + R.drawable.device_contact, + contact, + context.getString(R.string.unit_driver_name) + ) + ) + } + } + + statusIcon.visibility = View.GONE + engineStopIcon.visibility = View.GONE + + unit.position?.let { position -> + /* Status icon */ + statusIcon.visibility = View.VISIBLE + position.speed?.let { speed -> + if (speed >= 2) { + statusIcon.setColorFilter( + ContextCompat.getColor(context, R.color.colorOnline) + ) + } else { + statusIcon.setColorFilter( + ContextCompat.getColor(context, R.color.colorOffline) + ) + } + } ?: run { + statusIcon.setColorFilter(Color.GRAY) + } + + /* Engine stop */ + val attributes = position.attributes + if (attributes["out1"].toString() != "null") { + engineStopIcon.visibility = View.VISIBLE + engineStopIcon.setImageResource( + when (attributes["out1"].toString()) { + "true" -> R.drawable.device_unlocked + "false" -> R.drawable.device_locked + else -> R.drawable.device_locked + } + ) + engineStopIcon.contentDescription = when (attributes["out1"].toString()) { + "true" -> context.getString(R.string.unit_lock_on) + "false" -> context.getString(R.string.unit_lock_off) + else -> context.getString(R.string.unit_lock_on) + } + } + + /* Speed */ + position.speed?.let { speed -> + details.add( + Triple( + R.drawable.position_speed, + Formatter.formatSpeed(speed, SpeedUnit.KMH), + context.getString(R.string.unit_speed) + ) + ) + } + + /* Address */ + position.address?.let { address -> + details.add( + Triple( + R.drawable.position_address, + address, + context.getString(R.string.unit_last_address) + ) + ) + } + + /* Hourmeter */ + position.attributes["hours"]?.longOrNull?.let { + if (it > 0) { + details.add( + Triple( + R.drawable.position_hourmeter, + Formatter.formatHours(it), + context.getString(R.string.unit_hourmeter) + ) + ) + } + } + + /* Date time */ + position.fixTime?.let { fixTime -> + details.add( + Triple( + R.drawable.position_datetime, + Formatter.formatDate(fixTime), + context.getString(R.string.unit_last_date) + ) + ) + } + } + + gridLayout.removeAllViewsInLayout() + val metrics = context.resources.displayMetrics + details.forEachIndexed { i, detail -> + /* Property icon */ + val imageView = ImageView(gridLayout.context) + imageView.setImageResource(detail.first) + imageView.contentDescription = detail.third + imageView.setColorFilter( + ContextCompat.getColor( + context, + androidx.appcompat.R.color.secondary_text_default_material_light + ) + ) + + val imageLayout = GridLayout.LayoutParams() + imageLayout.width = GridLayout.LayoutParams.WRAP_CONTENT + imageLayout.height = GridLayout.LayoutParams.WRAP_CONTENT + imageLayout.marginEnd = + TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 6f, metrics).toInt() + imageLayout.rowSpec = GridLayout.spec(i) + imageLayout.columnSpec = GridLayout.spec(0) + imageView.layoutParams = imageLayout + + /* Property text */ + val textView = TextView(gridLayout.context) + textView.text = detail.second + + val textLayout = GridLayout.LayoutParams() + textLayout.width = 0 + textLayout.height = GridLayout.LayoutParams.MATCH_PARENT + textLayout.rowSpec = GridLayout.spec(i) + textLayout.columnSpec = GridLayout.spec(1, 1, 5f) + textView.layoutParams = textLayout + + gridLayout.addView(imageView) + gridLayout.addView(textView) + + imageLayout.setGravity(Gravity.CENTER) + } + + actionCallback?.let { callback -> + unitCard?.setOnClickListener { + swipeLayout?.close() + callback(unit, Action.CLICK) + } + detailsButton?.setOnClickListener { + swipeLayout?.close() + callback(unit, Action.DETAILS) + } + reportsButton?.setOnClickListener { + swipeLayout?.close() + callback(unit, Action.REPORTS) + } + commandsButton?.setOnClickListener { + swipeLayout?.close() + callback(unit, Action.COMMANDS) + } + } + } + } + } +} \ No newline at end of file -- cgit v1.2.3