diff --git a/app/src/main/java/it/reyboz/bustorino/data/PreferencesHolder.java b/app/src/main/java/it/reyboz/bustorino/data/PreferencesHolder.java
index 9d40520..c223575 100644
--- a/app/src/main/java/it/reyboz/bustorino/data/PreferencesHolder.java
+++ b/app/src/main/java/it/reyboz/bustorino/data/PreferencesHolder.java
@@ -1,111 +1,111 @@
/*
BusTO - Data components
Copyright (C) 2021 Fabio Mazza
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
package it.reyboz.bustorino.data;
import android.content.Context;
import android.content.SharedPreferences;
import androidx.annotation.NonNull;
import it.reyboz.bustorino.R;
import static android.content.Context.MODE_PRIVATE;
import androidx.preference.PreferenceManager;
import it.reyboz.bustorino.fragments.SettingsFragment;
import it.reyboz.bustorino.map.MapLibreUtils;
import java.util.HashSet;
import java.util.Set;
/**
* Static class for commonly used SharedPreference operations
*/
public abstract class PreferencesHolder {
public static final String PREF_GTFS_DB_VERSION = "gtfs_db_version";
public static final String PREF_INTRO_ACTIVITY_RUN ="pref_intro_activity_run";
public static final String DB_GTT_VERSION_KEY = "NextGenDB.GTTVersion";
public static final String DB_LAST_UPDATE_KEY = "NextGenDB.LastDBUpdate";
public static final String PREF_FAVORITE_LINES = "pref_favorite_lines";
public static final Set KEYS_MERGE_SET = Set.of(PREF_FAVORITE_LINES);
public static final Set IGNORE_KEYS_LOAD_MAIN = Set.of(PREF_GTFS_DB_VERSION, PREF_INTRO_ACTIVITY_RUN, DB_GTT_VERSION_KEY, DB_LAST_UPDATE_KEY);
public static SharedPreferences getMainSharedPreferences(Context context){
return context.getSharedPreferences(context.getString(R.string.mainSharedPreferences), MODE_PRIVATE);
}
public static SharedPreferences getAppPreferences(Context con){
return PreferenceManager.getDefaultSharedPreferences(con);
}
public static int getGtfsDBVersion(SharedPreferences pref){
return pref.getInt(PREF_GTFS_DB_VERSION,-1);
}
public static void setGtfsDBVersion(SharedPreferences pref,int version){
SharedPreferences.Editor ed = pref.edit();
ed.putInt(PREF_GTFS_DB_VERSION,version);
ed.apply();
}
/**
* Check if the introduction activity has been run at least one
* @param con the context needed
* @return true if it has been run
*/
public static boolean hasIntroFinishedOneShot(Context con){
final SharedPreferences pref = getMainSharedPreferences(con);
return pref.getBoolean(PREF_INTRO_ACTIVITY_RUN, false);
}
public static boolean addOrRemoveLineToFavorites(Context con, String gtfsLineId, boolean addToFavorites){
final SharedPreferences pref = getMainSharedPreferences(con);
final HashSet favorites = new HashSet<>(pref.getStringSet(PREF_FAVORITE_LINES, new HashSet<>()));
boolean modified = true;
if(addToFavorites)
favorites.add(gtfsLineId);
else if(favorites.contains(gtfsLineId))
favorites.remove(gtfsLineId);
else
modified = false; // we are not changing anything
if(modified) {
final SharedPreferences.Editor editor = pref.edit();
editor.putStringSet(PREF_FAVORITE_LINES, favorites);
editor.apply();
}
return modified;
}
public static HashSet getFavoritesLinesGtfsIDs(@NonNull Context con){
final SharedPreferences pref = getMainSharedPreferences(con);
return new HashSet<>(pref.getStringSet(PREF_FAVORITE_LINES, new HashSet<>()));
}
public static String getMapLibreStyleFile(Context con){
final SharedPreferences pref = getAppPreferences(con);
/*final String mapStyle_val = pref.getString(SettingsFragment.LIBREMAP_STYLE_PREF_KEY, "");
return switch (mapStyle_val) {
//MUST MATCH IN keys.xml -> map_style_pref_values
case "versatiles_c" -> MapLibreUtils.STYLE_VERSATILES_COLORFUL_JSON;
case "bright" -> MapLibreUtils.STYLE_BRIGHT_DEFAULT_JSON; //default is "bright"
default -> MapLibreUtils.STYLE_VERSATILES_COLORFUL_JSON;
};
*/
- return MapLibreUtils.STYLE_VERSATILES_COLORFUL_JSON;
+ return MapLibreUtils.getDefaultStyleJson();
}
}
diff --git a/app/src/main/java/it/reyboz/bustorino/map/MapLibreUtils.kt b/app/src/main/java/it/reyboz/bustorino/map/MapLibreUtils.kt
index 8be62a1..0430d26 100644
--- a/app/src/main/java/it/reyboz/bustorino/map/MapLibreUtils.kt
+++ b/app/src/main/java/it/reyboz/bustorino/map/MapLibreUtils.kt
@@ -1,225 +1,228 @@
package it.reyboz.bustorino.map
import android.animation.TypeEvaluator
import android.content.Context
import android.util.Log
import it.reyboz.bustorino.backend.Stop
import org.maplibre.android.geometry.LatLng
import org.maplibre.android.location.LocationComponentActivationOptions
import org.maplibre.android.location.LocationComponentOptions
import org.maplibre.android.location.engine.LocationEngineRequest
import org.maplibre.android.maps.Style
import org.maplibre.geojson.Point
import org.maplibre.turf.TurfMeasurement
class MapLibreUtils {
companion object{
const val STYLE_BRIGHT_DEFAULT_JSON = "map_style_good_noshops.json"
const val STYLE_VERSATILES_COLORFUL_JSON = "versatiles_colorful_light.json"
private const val DEBUG_TAG ="BusTO-MapLibreUtils"
+ @JvmStatic
+ fun getDefaultStyleJson() = STYLE_VERSATILES_COLORFUL_JSON
+
@JvmStatic
fun shortestRotation(from: Float, to: Float): Float {
var delta = (to - from) % 360
if (delta > 180) delta -= 360
if (delta < -180) delta += 360
return from + delta
}
@JvmStatic
fun buildLocationComponentActivationOptions(
style: Style,
locationComponentOptions: LocationComponentOptions,
context: Context
): LocationComponentActivationOptions {
return LocationComponentActivationOptions
.builder(context, style)
.locationComponentOptions(locationComponentOptions)
.useDefaultLocationEngine(true)
.locationEngineRequest(
LocationEngineRequest.Builder(750)
.setFastestInterval(750)
.setPriority(LocationEngineRequest.PRIORITY_HIGH_ACCURACY)
.build()
)
.build()
}
@JvmStatic
fun calcDistanceInSegment(points: List, from: Int, to:Int): Double{
var d=0.0
var prev = points[from]
for(i in from+1..to){
d += prev.distanceTo(points[i])
prev = points[i]
}
return d
}
@JvmStatic
fun findIndexMidPoint(points: List, from: Int, to: Int, distThresh:Double): Int{
var totdist=0.0
var idx = -2
var prev = points[from]
for(i in from+1..to){
totdist += prev.distanceTo(points[i])
prev = points[i]
if (totdist >= distThresh){
idx = i
break
}
}
if(idx==-2) throw Error("Distance out of bounds, total distance is $totdist")
return idx
}
@JvmStatic
fun findPointsToPutDirectionMarkers(polyPoints: List, stops: List, distanceIcon: Double): List{
val closestIndices = findIndicesClosestPointsForStops(polyPoints, stops)
Log.d(DEBUG_TAG, "idcs: $closestIndices")
val distancesSec = mutableListOf()
var pi = closestIndices[0]
val cumulativeDist = mutableListOf()
var sum = 0.0
val pointsOutput = mutableListOf()
var nPoints = 0
var distFromLastPoint = 0.0
for(i in 1..= distanceIcon){
Log.d(DEBUG_TAG, "Add between stop ${stops[i-1]} and stop ${stops[i]}, distance between: $dd")
if(dd>100) {
val imid = findIndexMidPoint(polyPoints, pi, newi, dd / 2)
pointsOutput.add(imid)
nPoints += 1
distFromLastPoint=0.0
}
} else{
//add the last distance
//distFromLastPoint+=dd/2
}
pi= newi
}
return pointsOutput
}
/*
VERSION WITH TOTAL DISTANCE
val distancesSec = mutableListOf()
var prevk = 0
val cumulativeDist = mutableListOf()
var sum = 0.0
val pointsOutput = mutableListOf()
var nPoints = 0
//for(i in 1..= distanceIcon ){
//Log.d(DEBUG_TAG, "Add between stop ${stops[lastStopidx]} and stop ${stops[lastStopidx+1]}")
//find closest stops
var stopDist =
Math.min(polyPoints[prevk].distanceTo(polyPoints[lastStopidx]),polyPoints[k].distanceTo(polyPoints[lastStopidx]))
if(lastStopidx+1 < stops.size){
stopDist = Math.min(stopDist,
Math.min(polyPoints[prevk].distanceTo(polyPoints[lastStopidx+1]),polyPoints[k].distanceTo(polyPoints[lastStopidx+1]))
)
}
if(stopDist>100) {
val imid = findIndexMidPoint(polyPoints, prevk, k, dd / 2)
pointsOutput.add(imid)
nPoints += 1
distFromLast = 0.0
}
}
prevk = k
if (k>closestIndices[lastStopidx])
lastStopidx +=1
}
return pointsOutput
*/
@JvmStatic
fun splitPolyWhenDistanceTooBig(points: List, distMax: Double): List{
val outList = mutableListOf(points[0])
var oldP = points[0]
for(i in 1.. distMax){
val newLat = (oldP.latitude+newP.latitude)/2
val newLong = (oldP.longitude+newP.longitude)/2
val extraP = LatLng(newLat,newLong)
outList.add(extraP)
}
outList.add(newP)
oldP=newP
}
return outList
}
@JvmStatic
fun findIndicesClosestPointsForStops(points:List, stops:List): List {
val closestIndices = stops.map { s->
val p = LatLng(s.latitude!!, s.longitude!!)
var dist = 10_000_000.0 // in meters
var id = -1
for (j in points.indices){
val newd = p.distanceTo(points[j])
if (newd {
private val latLng = LatLng()
override fun evaluate(fraction: Float, startValue: LatLng, endValue: LatLng): LatLng {
latLng.latitude = startValue.latitude + (endValue.latitude - startValue.latitude) * fraction
latLng.longitude = startValue.longitude + (endValue.longitude - startValue.longitude) * fraction
return latLng
}
}
}
\ No newline at end of file