Rename tracksDbHelper to SavingTracksDbHelper and add ability to save as gpx

This commit is contained in:
Chumva 2019-01-10 21:28:18 +02:00
parent 17961b6331
commit 86afca198a
10 changed files with 2174 additions and 256 deletions

View file

@ -146,4 +146,6 @@ dependencies {
implementation("com.github.HITGIF:TextFieldBoxes:1.4.4") { implementation("com.github.HITGIF:TextFieldBoxes:1.4.4") {
exclude group: 'com.android.support' exclude group: 'com.android.support'
} }
implementation 'net.sf.kxml:kxml2:2.1.8'
} }

View file

@ -1,6 +1,9 @@
package net.osmand; package net.osmand;
import org.apache.commons.logging.Log; import org.apache.commons.logging.Log;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import org.xmlpull.v1.XmlSerializer;
public class PlatformUtil { public class PlatformUtil {
@ -143,4 +146,11 @@ public class PlatformUtil {
return getLog(cl.getName()); return getLog(cl.getName());
} }
public static XmlPullParser newXMLPullParser() throws XmlPullParserException {
return new org.kxml2.io.KXmlParser();
}
public static XmlSerializer newSerializer() {
return new org.kxml2.io.KXmlSerializer();
}
} }

View file

@ -25,7 +25,7 @@ class TelegramApplication : Application(), OsmandHelperListener {
lateinit var osmandAidlHelper: OsmandAidlHelper private set lateinit var osmandAidlHelper: OsmandAidlHelper private set
lateinit var locationProvider: TelegramLocationProvider private set lateinit var locationProvider: TelegramLocationProvider private set
lateinit var messagesDbHelper: MessagesDbHelper private set lateinit var messagesDbHelper: MessagesDbHelper private set
lateinit var tracksDbHelper: TracksDbHelper private set lateinit var savingTracksDbHelper: SavingTracksDbHelper private set
var telegramService: TelegramService? = null var telegramService: TelegramService? = null
@ -69,7 +69,7 @@ class TelegramApplication : Application(), OsmandHelperListener {
notificationHelper = NotificationHelper(this) notificationHelper = NotificationHelper(this)
locationProvider = TelegramLocationProvider(this) locationProvider = TelegramLocationProvider(this)
messagesDbHelper = MessagesDbHelper(this) messagesDbHelper = MessagesDbHelper(this)
tracksDbHelper = TracksDbHelper(this) savingTracksDbHelper = SavingTracksDbHelper(this)
if (settings.hasAnyChatToShareLocation() && AndroidUtils.isLocationPermissionAvailable(this)) { if (settings.hasAnyChatToShareLocation() && AndroidUtils.isLocationPermissionAvailable(this)) {
shareLocationHelper.startSharingLocation() shareLocationHelper.startSharingLocation()

View file

@ -0,0 +1,288 @@
package net.osmand.telegram.helpers;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import net.osmand.PlatformUtil;
import net.osmand.telegram.TelegramApplication;
import net.osmand.telegram.utils.GPXUtilities;
import net.osmand.telegram.utils.GPXUtilities.GPXFile;
import net.osmand.telegram.utils.GPXUtilities.Track;
import net.osmand.telegram.utils.GPXUtilities.TrkSegment;
import net.osmand.telegram.utils.GPXUtilities.WptPt;
import org.apache.commons.logging.Log;
import org.drinkless.td.libcore.telegram.TdApi;
import org.jetbrains.annotations.NotNull;
import java.io.File;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
public class SavingTracksDbHelper extends SQLiteOpenHelper {
public final static String DATABASE_NAME = "tracks"; //$NON-NLS-1$
public final static int DATABASE_VERSION = 2;
public final static String TRACK_NAME = "track"; //$NON-NLS-1$
public final static String TRACK_COL_USER_ID = "user_id"; //$NON-NLS-1$
public final static String TRACK_COL_CHAT_ID = "chat_id"; //$NON-NLS-1$
public final static String TRACK_COL_DATE = "date"; //$NON-NLS-1$
public final static String TRACK_COL_LAT = "lat"; //$NON-NLS-1$
public final static String TRACK_COL_LON = "lon"; //$NON-NLS-1$
public final static String TRACK_COL_ALTITUDE = "altitude"; //$NON-NLS-1$
public final static String TRACK_COL_SPEED = "speed"; //$NON-NLS-1$
public final static String TRACK_COL_HDOP = "hdop"; //$NON-NLS-1$
public final static String UPDATE_SCRIPT = "INSERT INTO " + TRACK_NAME + " (" + TRACK_COL_USER_ID + ", " + TRACK_COL_CHAT_ID + ", " + TRACK_COL_LAT + ", " + TRACK_COL_LON + ", "
+ TRACK_COL_ALTITUDE + ", " + TRACK_COL_SPEED + ", " + TRACK_COL_HDOP + ", " + TRACK_COL_DATE + ")"
+ " VALUES (?, ?, ?, ?, ?, ?, ?, ?)"; //$NON-NLS-1$ //$NON-NLS-2$
public final static Log log = PlatformUtil.getLog(SavingTracksDbHelper.class);
private final TelegramApplication ctx;
public SavingTracksDbHelper(TelegramApplication ctx) {
super(ctx, DATABASE_NAME, null, DATABASE_VERSION);
this.ctx = ctx;
ctx.getTelegramHelper().addIncomingMessagesListener(new TelegramHelper.TelegramIncomingMessagesListener() {
@Override
public void onReceiveChatLocationMessages(long chatId, @NotNull TdApi.Message... messages) {
for (TdApi.Message message : messages) {
updateLocationMessage(message);
}
}
@Override
public void onDeleteChatLocationMessages(long chatId, @NotNull List<? extends TdApi.Message> messages) {
}
@Override
public void updateLocationMessages() {
}
});
ctx.getTelegramHelper().addOutgoingMessagesListener(new TelegramHelper.TelegramOutgoingMessagesListener() {
@Override
public void onUpdateMessages(@NotNull List<? extends TdApi.Message> messages) {
for (TdApi.Message message : messages) {
updateLocationMessage(message);
}
}
@Override
public void onDeleteMessages(long chatId, @NotNull List<Long> messages) {
}
@Override
public void onSendLiveLocationError(int code, @NotNull String message) {
}
});
}
@Override
public void onCreate(SQLiteDatabase db) {
db.execSQL("CREATE TABLE " + TRACK_NAME + " (" + TRACK_COL_USER_ID + " long," + TRACK_COL_CHAT_ID + " long," + TRACK_COL_LAT + " double, " + TRACK_COL_LON + " double, " //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$//$NON-NLS-5$
+ TRACK_COL_ALTITUDE + " double, " + TRACK_COL_SPEED + " double, " //$NON-NLS-1$ //$NON-NLS-2$
+ TRACK_COL_HDOP + " double, " + TRACK_COL_DATE + " long )"); //$NON-NLS-1$ //$NON-NLS-2$
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
public ArrayList<Integer> getUsersIds() {
ArrayList<Integer> ids = new ArrayList<>();
try {
SQLiteDatabase db = getWritableDatabase();
if (db != null) {
try {
Cursor query = db.rawQuery("SELECT " + TRACK_COL_USER_ID + " FROM " + TRACK_NAME + " ORDER BY " + TRACK_COL_DATE + " DESC", null); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
if (query.moveToFirst()) {
do {
Integer userId = query.getInt(0);
if (!ids.contains(userId)) {
ids.add(userId);
}
} while (query.moveToNext());
}
query.close();
} finally {
db.close();
}
}
} catch (RuntimeException e) {
}
return ids;
}
/**
* @return warnings
*/
public synchronized List<String> saveDataToGpx(File dir) {
List<String> warnings = new ArrayList<String>();
dir.mkdirs();
if (dir.getParentFile().canWrite()) {
if (dir.exists()) {
Map<Integer, GPXFile> data = collectRecordedData();
// save file
for (final Integer f : data.keySet()) {
File fout = new File(dir, f + ".gpx"); //$NON-NLS-1$
if (!data.get(f).isEmpty()) {
WptPt pt = data.get(f).findPointToShow();
TdApi.User user = ctx.getTelegramHelper().getUser(pt.userId);
String fileName;
if (user != null) {
fileName = TelegramUiHelper.INSTANCE.getUserName(user)
+ "_" + new SimpleDateFormat("yyyy-MM-dd_HH-mm_EEE", Locale.US).format(new Date(pt.time)); //$NON-NLS-1$
} else {
fileName = f + "_" + new SimpleDateFormat("HH-mm_EEE", Locale.US).format(new Date(pt.time)); //$NON-NLS-1$
}
fout = new File(dir, fileName + ".gpx"); //$NON-NLS-1$
int ind = 1;
while (fout.exists()) {
fout = new File(dir, fileName + "_" + (++ind) + ".gpx"); //$NON-NLS-1$ //$NON-NLS-2$
}
}
String warn = GPXUtilities.writeGpxFile(fout, data.get(f), ctx);
if (warn != null) {
warnings.add(warn);
return warnings;
}
}
}
}
return warnings;
}
public Map<Integer, GPXFile> collectRecordedData() {
Map<Integer, GPXFile> data = new LinkedHashMap<Integer, GPXFile>();
ArrayList<Integer> usersIds = getUsersIds();
SQLiteDatabase db = getReadableDatabase();
if (db != null && db.isOpen()) {
try {
collectDBTracks(db, data, usersIds);
} finally {
db.close();
}
}
return data;
}
private void collectDBTracks(SQLiteDatabase db, Map<Integer, GPXFile> dataTracks, ArrayList<Integer> usersIds) {
for (Integer userId : usersIds) {
collectDBTracksForUser(db, dataTracks, userId);
}
}
private void collectDBTracksForUser(SQLiteDatabase db, Map<Integer, GPXFile> dataTracks, Integer userId) {
Cursor query = db.rawQuery("SELECT " + TRACK_COL_USER_ID + "," + TRACK_COL_CHAT_ID + "," + TRACK_COL_LAT + "," + TRACK_COL_LON + "," + TRACK_COL_ALTITUDE + "," //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$ //$NON-NLS-6$
+ TRACK_COL_SPEED + "," + TRACK_COL_HDOP + "," + TRACK_COL_DATE + " FROM " + TRACK_NAME +
" WHERE " + TRACK_COL_USER_ID + " = ? ORDER BY " + TRACK_COL_DATE + " ASC ", new String[]{String.valueOf(userId)}); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
long previousTime = 0;
long previousInterval = 0;
TrkSegment segment = null;
Track track = null;
if (query.moveToFirst()) {
do {
WptPt pt = new WptPt();
pt.userId = query.getInt(0);
pt.chatId = query.getLong(1);
pt.lat = query.getDouble(2);
pt.lon = query.getDouble(3);
pt.ele = query.getDouble(4);
pt.speed = query.getDouble(5);
pt.hdop = query.getDouble(6);
long time = query.getLong(7);
pt.time = time;
long currentInterval = Math.abs(time - previousTime);
boolean newInterval = pt.lat == 0 && pt.lon == 0;
if (track != null && !newInterval && (
// !ctx.getSettings().AUTO_SPLIT_RECORDING.get() ||
currentInterval < 30 * 60 * 1000 || currentInterval < 10 * previousInterval)) {
// 6 minute - same segment
segment.points.add(pt);
} else if (track != null && (
// ctx.getSettings().AUTO_SPLIT_RECORDING.get() &&
currentInterval < 2 * 60 * 60 * 1000)) {
// 2 hour - same track
segment = new TrkSegment();
if (!newInterval) {
segment.points.add(pt);
}
track.segments.add(segment);
} else {
// check if date the same - new track otherwise new file
track = new Track();
segment = new TrkSegment();
track.segments.add(segment);
if (!newInterval) {
segment.points.add(pt);
}
if (dataTracks.containsKey(pt.userId)) {
GPXFile gpx = dataTracks.get(pt.userId);
gpx.tracks.add(track);
} else {
GPXFile file = new GPXFile();
file.tracks.add(track);
dataTracks.put(pt.userId, file);
}
}
previousInterval = currentInterval;
previousTime = time;
} while (query.moveToNext());
}
query.close();
}
public void updateLocationMessage(TdApi.Message message) {
// use because there is a bug on some devices with location.getTime()
long locationTime = System.currentTimeMillis();
TdApi.MessageContent content = message.content;
if (content instanceof TdApi.MessageLocation) {
TdApi.MessageLocation messageLocation = (TdApi.MessageLocation) content;
insertData(message.senderUserId, message.chatId, messageLocation.location.latitude, messageLocation.location.longitude, 0.0, 0.0, 0.0, locationTime);
} else if (content instanceof TelegramHelper.MessageLocation) {
TelegramHelper.MessageLocation messageLocation = (TelegramHelper.MessageLocation) content;
insertData(message.senderUserId, message.chatId, messageLocation.getLat(), messageLocation.getLon(),
messageLocation.getAltitude(), messageLocation.getSpeed(), messageLocation.getHdop(), messageLocation.getLastUpdated() * 1000L);
}
}
public void insertData(int userId, long chatId, double lat, double lon, double alt, double speed, double hdop, long time) {
execWithClose(UPDATE_SCRIPT, new Object[]{userId, chatId, lat, lon, alt, speed, hdop, time});
}
private synchronized void execWithClose(String script, Object[] objects) {
SQLiteDatabase db = getWritableDatabase();
try {
if (db != null) {
db.execSQL(script, objects);
}
} catch (RuntimeException e) {
log.error(e.getMessage(), e);
} finally {
if (db != null) {
db.close();
}
}
}
}

View file

@ -1234,6 +1234,33 @@ class TelegramHelper private constructor() {
} }
} }
} }
s.startsWith(ALTITUDE_PREFIX) -> {
val altStr = s.removePrefix(ALTITUDE_PREFIX)
try {
val alt = altStr.split(" ").first()
res.altitude = alt.toDouble()
} catch (e: Exception) {
e.printStackTrace()
}
}
s.startsWith(SPEED_PREFIX) -> {
val altStr = s.removePrefix(SPEED_PREFIX)
try {
val alt = altStr.split(" ").first()
res.speed = alt.toDouble()
} catch (e: Exception) {
e.printStackTrace()
}
}
s.startsWith(HDOP_PREFIX) -> {
val altStr = s.removePrefix(HDOP_PREFIX)
try {
val alt = altStr.split(" ").first()
res.hdop = alt.toDouble()
} catch (e: Exception) {
e.printStackTrace()
}
}
s.startsWith(UPDATED_PREFIX) -> { s.startsWith(UPDATED_PREFIX) -> {
if (res.lastUpdated == 0) { if (res.lastUpdated == 0) {
val updatedStr = s.removePrefix(UPDATED_PREFIX) val updatedStr = s.removePrefix(UPDATED_PREFIX)
@ -1291,6 +1318,12 @@ class TelegramHelper private constructor() {
internal set internal set
var lastUpdated: Int = 0 var lastUpdated: Int = 0
internal set internal set
var speed: Double = 0.0
internal set
var altitude: Double = 0.0
internal set
var hdop: Double = 0.0
internal set
override fun getConstructor() = -1 override fun getConstructor() = -1

View file

@ -1,223 +0,0 @@
package net.osmand.telegram.helpers
import android.database.sqlite.SQLiteDatabase
import android.database.sqlite.SQLiteOpenHelper
import android.os.AsyncTask
import net.osmand.PlatformUtil
import net.osmand.telegram.TelegramApplication
import org.drinkless.td.libcore.telegram.TdApi
import java.io.File
import java.io.FileOutputStream
import java.io.IOException
const val TRACKS_LOG_FILE_NAME = "tracks.txt"
class TracksDbHelper(val app: TelegramApplication) :
SQLiteOpenHelper(app, DATABASE_NAME, null, DATABASE_VERSION) {
private val tracks = HashSet<Track>()
private val log = PlatformUtil.getLog(TracksDbHelper::class.java)
init {
app.telegramHelper.addIncomingMessagesListener(object :
TelegramHelper.TelegramIncomingMessagesListener {
override fun onReceiveChatLocationMessages(
chatId: Long, vararg messages: TdApi.Message
) {
messages.forEach { addMessage(chatId, it) }
}
override fun onDeleteChatLocationMessages(chatId: Long, messages: List<TdApi.Message>) {
}
override fun updateLocationMessages() {}
})
app.telegramHelper.addOutgoingMessagesListener(object :
TelegramHelper.TelegramOutgoingMessagesListener {
override fun onUpdateMessages(messages: List<TdApi.Message>) {
messages.forEach { addMessage(it.chatId, it) }
}
override fun onDeleteMessages(chatId: Long, messages: List<Long>) {
}
override fun onSendLiveLocationError(code: Int, message: String) {
}
})
}
override fun onCreate(db: SQLiteDatabase) {
db.execSQL(TRACK_TABLE_CREATE)
}
override fun onUpgrade(db: SQLiteDatabase, oldVersion: Int, newVersion: Int) {
}
private fun addMessage(chatId: Long, message: TdApi.Message) {
log.debug(message)
val content = message.content
val track = when (content) {
is TdApi.MessageLocation ->
Track(
message.senderUserId,
chatId,
content.location.latitude,
content.location.longitude,
0.0,
0.0,
0.0,
Math.max(message.date, message.editDate)
)
is TelegramHelper.MessageLocation ->
Track(
message.senderUserId,
chatId,
content.lat,
content.lon,
0.0,
0.0,
0.0,
content.lastUpdated
)
else -> {
null
}
}
if (track != null) {
synchronized(tracks) {
tracks.add(track)
}
insertData(
track.userId,
track.chatId,
track.lat,
track.lon,
track.altitude,
track.speed,
track.hdop,
track.date
)
}
}
fun insertData(
userId: Int,
chatId: Long,
lat: Double,
lon: Double,
alt: Double,
speed: Double,
hdop: Double,
time: Int
) {
execWithClose(UPDATE_SCRIPT, arrayOf(userId, chatId, lat, lon, alt, speed, hdop, time))
}
@Synchronized
private fun execWithClose(script: String, objects: Array<Any>) {
val db = writableDatabase
try {
db?.execSQL(script, objects)
} catch (e: RuntimeException) {
log.error(e.message, e)
} finally {
db?.close()
}
}
internal fun getTracks(): Set<Track> {
val res = HashSet<Track>()
readableDatabase?.rawQuery(TRACK_TABLE_SELECT, null)?.apply {
if (moveToFirst()) {
do {
val userId = getInt(0)
val chatId = getLong(1)
val lat = getDouble(2)
val lon = getDouble(3)
val altitude = getDouble(4)
val speed = getDouble(5)
val hdop = getDouble(6)
val date = getInt(7)
val track = Track(userId, chatId, lat, lon, altitude, speed, hdop, date)
res.add(track)
log.debug(track)
} while (moveToNext())
}
close()
}
return res
}
companion object {
private const val DATABASE_NAME = "tracks"
private const val DATABASE_VERSION = 1
private const val TRACK_TABLE_NAME = "track"
private const val TRACK_COL_USER_ID = "user_id"
private const val TRACK_COL_CHAT_ID = "chat_id"
private const val TRACK_COL_DATE = "date"
private const val TRACK_COL_LAT = "lat"
private const val TRACK_COL_LON = "lon"
private const val TRACK_COL_ALTITUDE = "altitude"
private const val TRACK_COL_SPEED = "speed"
private const val TRACK_COL_HDOP = "hdop"
private const val TRACK_TABLE_CREATE =
"CREATE TABLE $TRACK_TABLE_NAME ($TRACK_COL_USER_ID long, $TRACK_COL_CHAT_ID long, $TRACK_COL_LAT double, $TRACK_COL_LON double, $TRACK_COL_ALTITUDE double, $TRACK_COL_SPEED double, $TRACK_COL_HDOP double, $TRACK_COL_DATE long )"
private const val UPDATE_SCRIPT =
"INSERT INTO $TRACK_TABLE_NAME ($TRACK_COL_USER_ID, $TRACK_COL_CHAT_ID, $TRACK_COL_LAT, $TRACK_COL_LON, $TRACK_COL_ALTITUDE, $TRACK_COL_SPEED, $TRACK_COL_HDOP, $TRACK_COL_DATE) VALUES (?, ?, ?, ?, ?, ?, ?, ?)"
private const val TRACK_TABLE_SELECT =
"SELECT $TRACK_COL_USER_ID, $TRACK_COL_CHAT_ID, $TRACK_COL_LAT, $TRACK_COL_LON, $TRACK_COL_ALTITUDE, $TRACK_COL_SPEED, $TRACK_COL_HDOP, $TRACK_COL_DATE FROM $TRACK_TABLE_NAME"
private const val TRACK_TABLE_CLEAR = "DELETE FROM $TRACK_TABLE_NAME"
}
data class Track(
val userId: Int,
val chatId: Long,
val lat: Double,
val lon: Double,
val altitude: Double,
val speed: Double,
val hdop: Double,
val date: Int
)
fun writeToFile() {
var text = ""
app.tracksDbHelper.getTracks().forEach {
text += "\n--------------\n" + it.toString()
}
val path = app.getExternalFilesDir(null)
WriteTracksLogs().executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR, text, path.absolutePath)
}
private class WriteTracksLogs : AsyncTask<String, String, Void?>() {
private val log = PlatformUtil.getLog(WriteTracksLogs::class.java)
override fun doInBackground(vararg params: String?): Void? {
val text = params[0]
val path = params[1]
if (text != null && path != null) {
val file = File(path, TRACKS_LOG_FILE_NAME)
val stream = FileOutputStream(file)
try {
stream.write(text.toByteArray())
} catch (e: IOException) {
log.error(e)
} finally {
stream.close()
}
}
return null
}
}
}

View file

@ -467,7 +467,7 @@ class LiveNowTabFragment : Fragment(), TelegramListener, TelegramIncomingMessage
holder.lastTelegramUpdateTime?.visibility = View.VISIBLE holder.lastTelegramUpdateTime?.visibility = View.VISIBLE
holder.lastTelegramUpdateTime?.text = OsmandFormatter.getListItemLiveTimeDescr(app, telegramHelper.lastTelegramUpdateTime, lastTelegramUpdateStr) holder.lastTelegramUpdateTime?.text = OsmandFormatter.getListItemLiveTimeDescr(app, telegramHelper.lastTelegramUpdateTime, lastTelegramUpdateStr)
holder.lastTelegramUpdateTime?.setOnClickListener { holder.lastTelegramUpdateTime?.setOnClickListener {
app.tracksDbHelper.writeToFile() app.savingTracksDbHelper.saveDataToGpx(app.getExternalFilesDir(null))
} }
} else { } else {
holder.lastTelegramUpdateTime?.visibility = View.GONE holder.lastTelegramUpdateTime?.visibility = View.GONE

View file

@ -146,8 +146,10 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
mainView.findViewById<TextView>(R.id.status_title).apply { mainView.findViewById<TextView>(R.id.status_title).apply {
val sharingStatus = getString(R.string.sharing_enabled) val sharingStatus = getString(R.string.sharing_enabled)
val spannable = SpannableString(sharingStatus) val spannable = SpannableString(sharingStatus)
spannable.setSpan(ForegroundColorSpan(app.uiUtils.getActiveColor()), spannable.setSpan(
sharingStatus.indexOf(" "), sharingStatus.length, 0) ForegroundColorSpan(app.uiUtils.getActiveColor()),
sharingStatus.indexOf(" "), sharingStatus.length, 0
)
text = spannable text = spannable
} }
@ -450,7 +452,8 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
textContainer.visibility = if (sharingMode) View.GONE else View.VISIBLE textContainer.visibility = if (sharingMode) View.GONE else View.VISIBLE
titleContainer.visibility = if (sharingMode) View.VISIBLE else View.GONE titleContainer.visibility = if (sharingMode) View.VISIBLE else View.GONE
startSharingBtn.visibility = if (sharingMode) View.VISIBLE else View.GONE startSharingBtn.visibility = if (sharingMode) View.VISIBLE else View.GONE
headerParams.scrollFlags = if (sharingMode) 0 else AppBarLayout.LayoutParams.SCROLL_FLAG_SCROLL headerParams.scrollFlags =
if (sharingMode) 0 else AppBarLayout.LayoutParams.SCROLL_FLAG_SCROLL
stopSharingSwitcher.isChecked = true stopSharingSwitcher.isChecked = true
appBarScrollRange = -1 appBarScrollRange = -1
} }
@ -460,7 +463,12 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
settings.updateSharingStatusHistory() settings.updateSharingStatusHistory()
val sharingStatus = settings.sharingStatusChanges.last() val sharingStatus = settings.sharingStatusChanges.last()
sharingStatusTitle.text = sharingStatus.getTitle(app) sharingStatusTitle.text = sharingStatus.getTitle(app)
sharingStatusIcon.setImageDrawable(app.uiUtils.getIcon(sharingStatus.statusType.iconId, sharingStatus.statusType.iconColorRes)) sharingStatusIcon.setImageDrawable(
app.uiUtils.getIcon(
sharingStatus.statusType.iconId,
sharingStatus.statusType.iconColorRes
)
)
} }
} }
@ -490,7 +498,8 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
items.addAll(chats) items.addAll(chats)
if (!sharingMode) { if (!sharingMode) {
for (user in contacts.values) { for (user in contacts.values) {
val containsInChats = chats.any { telegramHelper.getUserIdFromChatType(it.type) == user.id } val containsInChats =
chats.any { telegramHelper.getUserIdFromChatType(it.type) == user.id }
if ((!sharingMode && settings.isSharingLocationToUser(user.id)) || user.id == currentUser?.id || containsInChats) { if ((!sharingMode && settings.isSharingLocationToUser(user.id)) || user.id == currentUser?.id || containsInChats) {
continue continue
} }
@ -521,7 +530,8 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
return list return list
} }
inner class MyLocationListAdapter : RecyclerView.Adapter<MyLocationListAdapter.BaseViewHolder>() { inner class MyLocationListAdapter :
RecyclerView.Adapter<MyLocationListAdapter.BaseViewHolder>() {
var items = mutableListOf<TdApi.Object>() var items = mutableListOf<TdApi.Object>()
set(value) { set(value) {
field = value field = value
@ -569,7 +579,8 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
} }
val lastItem = position == itemCount - 1 val lastItem = position == itemCount - 1
val placeholderId = if (isChat && telegramHelper.isGroup(item as TdApi.Chat)) R.drawable.img_group_picture else R.drawable.img_user_picture val placeholderId =
if (isChat && telegramHelper.isGroup(item as TdApi.Chat)) R.drawable.img_group_picture else R.drawable.img_user_picture
val live = (isChat && settings.isSharingLocationToChat(itemId)) val live = (isChat && settings.isSharingLocationToChat(itemId))
val shareInfo = if (isChat) settings.getChatsShareInfo()[itemId] else null val shareInfo = if (isChat) settings.getChatsShareInfo()[itemId] else null
@ -588,7 +599,12 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
} }
holder.title?.text = title holder.title?.text = title
holder.icon?.setOnClickListener {
app.forceUpdateMyLocation()
val curUser = telegramHelper.getCurrentUser()
val text = "${curUser?.id} ${curUser?.firstName} ${curUser?.lastName}"
Toast.makeText(app, text, Toast.LENGTH_LONG).show()
}
if (holder is ChatViewHolder) { if (holder is ChatViewHolder) {
holder.description?.visibility = View.GONE holder.description?.visibility = View.GONE
if (live) { if (live) {
@ -648,7 +664,8 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
val duration = shareInfo?.userSetLivePeriod val duration = shareInfo?.userSetLivePeriod
if (duration != null && duration > 0) { if (duration != null && duration > 0) {
holder.descriptionDuration?.text = OsmandFormatter.getFormattedDuration(context!!, duration) holder.descriptionDuration?.text =
OsmandFormatter.getFormattedDuration(context!!, duration)
holder.description?.apply { holder.description?.apply {
visibility = View.VISIBLE visibility = View.VISIBLE
text = "${getText(R.string.sharing_time)}:" text = "${getText(R.string.sharing_time)}:"
@ -658,17 +675,29 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
val expiresIn = shareInfo?.getChatLiveMessageExpireTime() ?: 0 val expiresIn = shareInfo?.getChatLiveMessageExpireTime() ?: 0
holder.textInArea?.apply { holder.textInArea?.apply {
val time = shareInfo?.additionalActiveTime ?: ADDITIONAL_ACTIVE_TIME_VALUES_SEC[0] val time =
shareInfo?.additionalActiveTime ?: ADDITIONAL_ACTIVE_TIME_VALUES_SEC[0]
visibility = View.VISIBLE visibility = View.VISIBLE
text = "+ ${OsmandFormatter.getFormattedDuration(context!!, time)}" text = "+ ${OsmandFormatter.getFormattedDuration(context!!, time)}"
setOnClickListener { setOnClickListener {
val expireTime = shareInfo?.getChatLiveMessageExpireTime() ?: 0 val expireTime = shareInfo?.getChatLiveMessageExpireTime() ?: 0
val newLivePeriod = expireTime + (shareInfo?.additionalActiveTime ?: ADDITIONAL_ACTIVE_TIME_VALUES_SEC[0]) val newLivePeriod = expireTime + (shareInfo?.additionalActiveTime
val nextAdditionalActiveTime = shareInfo?.getNextAdditionalActiveTime() ?: ADDITIONAL_ACTIVE_TIME_VALUES_SEC[1] ?: ADDITIONAL_ACTIVE_TIME_VALUES_SEC[0])
val nextAdditionalActiveTime = shareInfo?.getNextAdditionalActiveTime()
?: ADDITIONAL_ACTIVE_TIME_VALUES_SEC[1]
if (isChat) { if (isChat) {
settings.shareLocationToChat(itemId, true, newLivePeriod, nextAdditionalActiveTime) settings.shareLocationToChat(
itemId,
true,
newLivePeriod,
nextAdditionalActiveTime
)
} else { } else {
settings.shareLocationToUser(itemId.toInt(), newLivePeriod, nextAdditionalActiveTime) settings.shareLocationToUser(
itemId.toInt(),
newLivePeriod,
nextAdditionalActiveTime
)
} }
notifyItemChanged(position) notifyItemChanged(position)
} }
@ -686,13 +715,16 @@ class MyLocationTabFragment : Fragment(), TelegramListener {
holder.stopSharingSecondPart?.apply { holder.stopSharingSecondPart?.apply {
visibility = getStopSharingVisibility(expiresIn) visibility = getStopSharingVisibility(expiresIn)
text = "(${getString(R.string.in_time, text = "(${getString(
OsmandFormatter.getFormattedDuration(context!!, expiresIn, true))})" R.string.in_time,
OsmandFormatter.getFormattedDuration(context!!, expiresIn, true)
)})"
} }
} }
} }
private fun getStopSharingVisibility(expiresIn: Long) = if (expiresIn > 0) View.VISIBLE else View.INVISIBLE private fun getStopSharingVisibility(expiresIn: Long) =
if (expiresIn > 0) View.VISIBLE else View.INVISIBLE
private fun removeItem(chat: TdApi.Object) { private fun removeItem(chat: TdApi.Object) {
items.remove(chat) items.remove(chat)

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,24 @@
package net.osmand.telegram.utils;
import android.content.Context;
/**
*/
public interface LocationPoint {
public double getLatitude();
public double getLongitude();
public int getColor();
public boolean isVisible();
// public PointDescription getPointDescription(Context ctx);
// public String getSpeakableName();
//public void prepareCommandPlayer(CommandBuilder cmd, String names);
}