Merge remote-tracking branch 'origin/master'

This commit is contained in:
Weblate 2017-02-25 17:41:19 +01:00
commit 9b82d9af2a
11 changed files with 718 additions and 492 deletions

View file

@ -6,27 +6,14 @@
android:layout_width="match_parent"
android:layout_height="wrap_content">
<FrameLayout
<include layout="@layout/list_shadow_header"/>
<ImageView
android:id="@+id/imageView"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<FrameLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom">
<include layout="@layout/list_shadow_header"/>
</FrameLayout>
<ImageView
android:id="@+id/imageView"
android:layout_width="match_parent"
android:layout_height="152dp"
android:scaleType="center"
android:src="@drawable/audio_video_notes"/>
</FrameLayout>
android:layout_height="152dp"
android:scaleType="center"
android:visibility="gone"/>
<LinearLayout
android:layout_width="match_parent"
@ -73,6 +60,7 @@
android:gravity="center_vertical">
<LinearLayout
android:id="@+id/split_interval_view"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1.6"
@ -80,10 +68,12 @@
android:paddingLeft="16dp"
android:paddingTop="8dp"
android:paddingBottom="8dp"
android:background="?attr/selectableItemBackground"
android:orientation="horizontal"
android:gravity="center_vertical">
<TextView
android:id="@+id/split_interval_title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
@ -92,7 +82,7 @@
android:text="@string/gpx_split_interval"/>
<net.osmand.plus.widgets.TextViewEx
android:id="@+id/split_interval"
android:id="@+id/split_interval_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingLeft="8dp"
@ -111,6 +101,7 @@
</LinearLayout>
<LinearLayout
android:id="@+id/color_view"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
@ -118,10 +109,12 @@
android:paddingRight="16dp"
android:paddingTop="8dp"
android:paddingBottom="8dp"
android:background="?attr/selectableItemBackground"
android:orientation="horizontal"
android:gravity="center_vertical">
<TextView
android:id="@+id/colorText"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"

View file

@ -0,0 +1,12 @@
<?xml version="1.0" encoding="utf-8"?>
<TextView
android:id="@+id/text1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingLeft="16dp"
android:paddingRight="16dp"
android:paddingTop="12dp"
android:paddingBottom="12dp"
android:textColor="?android:attr/textColorPrimary"
android:textSize="@dimen/default_list_text_size"
xmlns:android="http://schemas.android.com/apk/res/android"/>

View file

@ -13,7 +13,7 @@ import java.util.List;
public class GPXDatabase {
private static final String DB_NAME = "gpx_database";
private static final int DB_VERSION = 1;
private static final int DB_VERSION = 2;
private static final String GPX_TABLE_NAME = "gpxTable";
private static final String GPX_COL_NAME = "fileName";
private static final String GPX_COL_DIR = "fileDir";
@ -37,6 +37,8 @@ public class GPXDatabase {
private static final String GPX_COL_POINTS = "points";
private static final String GPX_COL_WPT_POINTS = "wptPoints";
private static final String GPX_COL_COLOR = "color";
private static final String GPX_TABLE_CREATE = "CREATE TABLE IF NOT EXISTS " + GPX_TABLE_NAME + " (" +
GPX_COL_NAME + " TEXT, " +
GPX_COL_DIR + " TEXT, " +
@ -58,14 +60,15 @@ public class GPXDatabase {
GPX_COL_AVG_SPEED + " double, " +
GPX_COL_POINTS + " int, " +
GPX_COL_WPT_POINTS + " int);";
GPX_COL_WPT_POINTS + " int, " +
GPX_COL_COLOR + " TEXT);";
private static final String GPX_TABLE_SELECT = "SELECT " + GPX_COL_NAME + ", " + GPX_COL_DIR + "," + GPX_COL_TOTAL_DISTANCE + ", " +
GPX_COL_TOTAL_TRACKS + ", " + GPX_COL_START_TIME + ", " + GPX_COL_END_TIME + ", " +
GPX_COL_TIME_SPAN + ", " + GPX_COL_TIME_MOVING + ", " + GPX_COL_TOTAL_DISTANCE_MOVING + ", " +
GPX_COL_DIFF_ELEVATION_UP + ", " + GPX_COL_DIFF_ELEVATION_DOWN + ", " + GPX_COL_AVG_ELEVATION + ", " +
GPX_COL_MIN_ELEVATION + ", " + GPX_COL_MAX_ELEVATION + ", " + GPX_COL_MAX_SPEED + ", " +
GPX_COL_AVG_SPEED + ", " + GPX_COL_POINTS + ", " + GPX_COL_WPT_POINTS +
GPX_COL_AVG_SPEED + ", " + GPX_COL_POINTS + ", " + GPX_COL_WPT_POINTS + ", " + GPX_COL_COLOR +
" FROM " + GPX_TABLE_NAME;
private OsmandApplication context;
@ -73,6 +76,7 @@ public class GPXDatabase {
public static class GpxDataItem {
private File file;
private GPXTrackAnalysis analysis;
private int color;
public GpxDataItem(File file, GPXTrackAnalysis analysis) {
this.file = file;
@ -86,6 +90,14 @@ public class GPXDatabase {
public GPXTrackAnalysis getAnalysis() {
return analysis;
}
public int getColor() {
return color;
}
public void setColor(int color) {
this.color = color;
}
}
public GPXDatabase(OsmandApplication app) {
@ -110,22 +122,19 @@ public class GPXDatabase {
return conn;
}
public void onCreate(SQLiteConnection db) {
private void onCreate(SQLiteConnection db) {
db.execSQL(GPX_TABLE_CREATE);
}
public void onUpgrade(SQLiteConnection db, int oldVersion, int newVersion) {
/*
if (newVersion == 2) {
db.execSQL(GPX_TABLE_CREATE);
//...
private void onUpgrade(SQLiteConnection db, int oldVersion, int newVersion) {
if (oldVersion < 2) {
db.execSQL("ALTER TABLE " + GPX_TABLE_NAME + " ADD " + GPX_COL_COLOR + " TEXT");
}
*/
}
public boolean rename(File currentFile, File newFile) {
SQLiteConnection db = openConnection(false);
if(db != null){
if (db != null){
try {
String newFileName = getFileName(newFile);
String newFileDir = getFileDir(newFile);
@ -144,9 +153,28 @@ public class GPXDatabase {
return false;
}
public boolean updateColor(GpxDataItem item, int color) {
SQLiteConnection db = openConnection(false);
if (db != null){
try {
String fileName = getFileName(item.file);
String fileDir = getFileDir(item.file);
db.execSQL("UPDATE " + GPX_TABLE_NAME + " SET " +
GPX_COL_COLOR + " = ? " +
" WHERE " + GPX_COL_NAME + " = ? AND " + GPX_COL_DIR + " = ?",
new Object[] { (color == 0 ? "" : Algorithms.colorToString(color)), fileName, fileDir });
item.setColor(color);
} finally {
db.close();
}
return true;
}
return false;
}
public boolean remove(File file) {
SQLiteConnection db = openConnection(false);
if(db != null){
if (db != null){
try {
String fileName = getFileName(file);
String fileDir = getFileDir(file);
@ -166,7 +194,7 @@ public class GPXDatabase {
public boolean add(GpxDataItem item) {
SQLiteConnection db = openConnection(false);
if(db != null){
if (db != null){
try {
insert(item, db);
} finally {
@ -190,11 +218,17 @@ public class GPXDatabase {
String fileName = getFileName(item.file);
String fileDir = getFileDir(item.file);
GPXTrackAnalysis a = item.getAnalysis();
String color;
if (item.color == 0) {
color = "";
} else {
color = Algorithms.colorToString(item.color);
}
db.execSQL(
"INSERT INTO " + GPX_TABLE_NAME + " VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
"INSERT INTO " + GPX_TABLE_NAME + " VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
new Object[] { fileName, fileDir, a.totalDistance, a.totalTracks, a.startTime, a.endTime,
a.timeSpan, a.timeMoving, a.totalDistanceMoving, a.diffElevationUp, a.diffElevationDown,
a.avgElevation, a.minElevation, a.maxElevation, a.maxSpeed, a.avgSpeed, a.points, a.wptPoints });
a.avgElevation, a.minElevation, a.maxElevation, a.maxSpeed, a.avgSpeed, a.points, a.wptPoints, color });
}
private GpxDataItem readItem(SQLiteCursor query) {
@ -216,6 +250,7 @@ public class GPXDatabase {
float avgSpeed = (float)query.getDouble(15);
int points = (int)query.getInt(16);
int wptPoints = (int)query.getInt(17);
String color = query.getString(18);
GPXTrackAnalysis a = new GPXTrackAnalysis();
a.totalDistance = totalDistance;
@ -241,7 +276,13 @@ public class GPXDatabase {
} else {
dir = context.getAppPath(IndexConstants.GPX_INDEX_DIR);
}
return new GpxDataItem(new File(dir, fileName), a);
GpxDataItem item = new GpxDataItem(new File(dir, fileName), a);
try {
item.setColor(Algorithms.isEmpty(color) ? 0 : Algorithms.parseColor(color));
} catch (IllegalArgumentException e) {
item.setColor(0);
}
return item;
}
public List<GpxDataItem> getItems() {

View file

@ -3,12 +3,19 @@
*/
package net.osmand.plus.activities;
import java.io.File;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.view.ViewPager;
import android.support.v7.app.ActionBar;
import android.support.v7.widget.Toolbar;
import android.util.Log;
import android.view.MenuItem;
import android.view.View;
import net.osmand.AndroidUtils;
import net.osmand.plus.GPXDatabase.GpxDataItem;
import net.osmand.plus.GPXUtilities;
import net.osmand.plus.GPXUtilities.GPXFile;
import net.osmand.plus.GpxSelectionHelper;
@ -23,25 +30,19 @@ import net.osmand.plus.myplaces.TrackPointFragment;
import net.osmand.plus.myplaces.TrackSegmentFragment;
import net.osmand.plus.views.controls.PagerSlidingTabStrip;
import android.app.Activity;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.view.ViewPager;
import android.support.v7.widget.Toolbar;
import android.util.Log;
import android.view.MenuItem;
import android.view.View;
import java.io.File;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;
public class TrackActivity extends TabActivity {
public static final String TRACK_FILE_NAME = "TRACK_FILE_NAME";
public static final String CURRENT_RECORDING = "CURRENT_RECORDING";
public static String TAB_PARAM = "TAB_PARAM";
protected List<WeakReference<Fragment>> fragList = new ArrayList<WeakReference<Fragment>>();
protected List<WeakReference<Fragment>> fragList = new ArrayList<>();
private File file = null;
private GPXFile result;
private GPXFile gpxFile;
private GpxDataItem gpxDataItem;
ViewPager mViewPager;
private long modifiedTime = -1;
private List<GpxDisplayGroup> displayGroups;
@ -58,77 +59,88 @@ public class TrackActivity extends TabActivity {
return;
}
file = null;
if (intent.hasExtra(TRACK_FILE_NAME)) {
file = new File(intent.getStringExtra(TRACK_FILE_NAME));
String fn = file.getName().replace(".gpx", "").replace("/", " ").replace("_", " ");
getSupportActionBar().setTitle(fn);
} else {
getSupportActionBar().setTitle(getString(R.string.shared_string_currently_recording_track));
ActionBar actionBar = getSupportActionBar();
if (actionBar != null) {
if (intent.hasExtra(TRACK_FILE_NAME)) {
file = new File(intent.getStringExtra(TRACK_FILE_NAME));
String fn = file.getName().replace(".gpx", "").replace("/", " ").replace("_", " ");
actionBar.setTitle(fn);
} else {
actionBar.setTitle(getString(R.string.shared_string_currently_recording_track));
}
actionBar.setElevation(0);
}
getSupportActionBar().setElevation(0);
setContentView(R.layout.tab_content);
final PagerSlidingTabStrip mSlidingTabLayout = (PagerSlidingTabStrip) findViewById(R.id.sliding_tabs);
mSlidingTabLayout.setShouldExpand(true);
final PagerSlidingTabStrip slidingTabLayout = (PagerSlidingTabStrip) findViewById(R.id.sliding_tabs);
if (slidingTabLayout != null) {
slidingTabLayout.setShouldExpand(true);
mViewPager = (ViewPager) findViewById(R.id.pager);
mViewPager = (ViewPager) findViewById(R.id.pager);
setViewPagerAdapter(mViewPager, new ArrayList<TabActivity.TabItem>());
mSlidingTabLayout.setViewPager(mViewPager);
new AsyncTask<Void, Void, GPXFile>() {
setViewPagerAdapter(mViewPager, new ArrayList<TabActivity.TabItem>());
slidingTabLayout.setViewPager(mViewPager);
new AsyncTask<Void, Void, GPXFile>() {
protected void onPreExecute() {
setSupportProgressBarIndeterminateVisibility(true);
};
@Override
protected GPXFile doInBackground(Void... params) {
if(file == null) {
return getMyApplication().getSavingTrackHelper().getCurrentGpx();
protected void onPreExecute() {
setSupportProgressBarIndeterminateVisibility(true);
}
return GPXUtilities.loadGPXFile(TrackActivity.this, file);
}
protected void onPostExecute(GPXFile result) {
setSupportProgressBarIndeterminateVisibility(false);
setGpx(result);
for(WeakReference<Fragment> f : fragList) {
Fragment frag = f.get();
if(frag instanceof SelectedGPXFragment) {
((SelectedGPXFragment) frag).setContent();
@Override
protected GPXFile doInBackground(Void... params) {
if (file == null) {
return getMyApplication().getSavingTrackHelper().getCurrentGpx();
}
return GPXUtilities.loadGPXFile(TrackActivity.this, file);
}
protected void onPostExecute(GPXFile result) {
setSupportProgressBarIndeterminateVisibility(false);
setGpx(result);
setGpxDataItem(getMyApplication().getGpxDatabase().getItem(file));
for (WeakReference<Fragment> f : fragList) {
Fragment frag = f.get();
if (frag instanceof SelectedGPXFragment) {
((SelectedGPXFragment) frag).setContent();
}
}
((OsmandFragmentPagerAdapter) mViewPager.getAdapter()).addTab(
getTabIndicator(R.string.info_button, TrackSegmentFragment.class));
if (isHavingWayPoints() || isHavingRoutePoints()) {
((OsmandFragmentPagerAdapter) mViewPager.getAdapter()).addTab(
getTabIndicator(R.string.points, TrackPointFragment.class));
} else {
slidingTabLayout.setVisibility(View.GONE);
getSupportActionBar().setElevation(AndroidUtils.dpToPx(getMyApplication(), 4f));
}
}
((OsmandFragmentPagerAdapter) mViewPager.getAdapter()).addTab(
getTabIndicator(R.string.info_button, TrackSegmentFragment.class));
if (isHavingWayPoints() || isHavingRoutePoints()) {
((OsmandFragmentPagerAdapter) mViewPager.getAdapter()).addTab(
getTabIndicator(R.string.points, TrackPointFragment.class));
} else {
mSlidingTabLayout.setVisibility(View.GONE);
getSupportActionBar().setElevation(AndroidUtils.dpToPx(getMyApplication(), 4f));
}
};
}.execute((Void)null);
}.execute((Void) null);
}
}
protected void setGpxDataItem(GpxDataItem gpxDataItem) {
this.gpxDataItem = gpxDataItem;
}
protected void setGpx(GPXFile result) {
this.result = result;
if(file == null) {
result = getMyApplication().getSavingTrackHelper().getCurrentGpx();
this.gpxFile = result;
if (file == null) {
this.gpxFile = getMyApplication().getSavingTrackHelper().getCurrentGpx();
}
}
public List<GpxSelectionHelper.GpxDisplayGroup> getResult() {
if(result == null) {
return new ArrayList<GpxSelectionHelper.GpxDisplayGroup>();
public List<GpxDisplayGroup> getGpxFile() {
if (gpxFile == null) {
return new ArrayList<>();
}
if (result.modifiedTime != modifiedTime) {
modifiedTime = result.modifiedTime;
if (gpxFile.modifiedTime != modifiedTime) {
modifiedTime = gpxFile.modifiedTime;
GpxSelectionHelper selectedGpxHelper = ((OsmandApplication) getApplication()).getSelectedGpxHelper();
displayGroups = selectedGpxHelper.collectDisplayGroups(result);
displayGroups = selectedGpxHelper.collectDisplayGroups(gpxFile);
if (file != null) {
SelectedGpxFile sf = selectedGpxHelper.getSelectedFileByPath(result.path);
SelectedGpxFile sf = selectedGpxHelper.getSelectedFileByPath(gpxFile.path);
if (sf != null && file != null && sf.getDisplayGroups() != null) {
displayGroups = sf.getDisplayGroups();
}
@ -139,7 +151,7 @@ public class TrackActivity extends TabActivity {
@Override
public void onAttachFragment(Fragment fragment) {
fragList.add(new WeakReference<Fragment>(fragment));
fragList.add(new WeakReference<>(fragment));
}
@Override
@ -161,9 +173,11 @@ public class TrackActivity extends TabActivity {
public Toolbar getClearToolbar(boolean visible) {
final Toolbar tb = (Toolbar) findViewById(R.id.bottomControls);
tb.setTitle(null);
tb.getMenu().clear();
tb.setVisibility(visible? View.VISIBLE : View.GONE);
if (tb != null) {
tb.setTitle(null);
tb.getMenu().clear();
tb.setVisibility(visible ? View.VISIBLE : View.GONE);
}
return tb;
}
@ -195,7 +209,11 @@ public class TrackActivity extends TabActivity {
}
public GPXFile getGpx() {
return result;
return gpxFile;
}
public GpxDataItem getGpxDataItem() {
return gpxDataItem;
}
}

View file

@ -1267,17 +1267,42 @@ public class ConfigureMapMenu {
private OsmandApplication app;
private int currentColor;
private GpxAppearanceAdapterType adapterType = GpxAppearanceAdapterType.TRACK_WIDTH_COLOR;
public GpxAppearanceAdapter(Context context, String currentColorValue) {
public enum GpxAppearanceAdapterType {
TRACK_WIDTH,
TRACK_COLOR,
TRACK_WIDTH_COLOR
}
public GpxAppearanceAdapter(Context context, String currentColorValue, GpxAppearanceAdapterType adapterType) {
super(context, R.layout.rendering_prop_menu_item);
app = (OsmandApplication) getContext().getApplicationContext();
this.app = (OsmandApplication) getContext().getApplicationContext();
this.adapterType = adapterType;
RenderingRulesStorage renderer = app.getRendererRegistry().getCurrentSelectedRenderer();
this.currentColor = parseTrackColor(renderer, currentColorValue);
init();
}
public GpxAppearanceAdapter(Context context, int currentColor, GpxAppearanceAdapterType adapterType) {
super(context, R.layout.rendering_prop_menu_item);
this.app = (OsmandApplication) getContext().getApplicationContext();
this.adapterType = adapterType;
this.currentColor = currentColor;
init();
}
public void init() {
RenderingRuleProperty trackWidthProp = null;
RenderingRuleProperty trackColorProp = null;
RenderingRulesStorage renderer = app.getRendererRegistry().getCurrentSelectedRenderer();
if (renderer != null) {
trackWidthProp = renderer.PROPS.getCustomRule(CURRENT_TRACK_WIDTH_ATTR);
trackColorProp = renderer.PROPS.getCustomRule(CURRENT_TRACK_COLOR_ATTR);
if (adapterType == GpxAppearanceAdapterType.TRACK_WIDTH || adapterType == GpxAppearanceAdapterType.TRACK_WIDTH_COLOR) {
trackWidthProp = renderer.PROPS.getCustomRule(CURRENT_TRACK_WIDTH_ATTR);
}
if (adapterType == GpxAppearanceAdapterType.TRACK_COLOR || adapterType == GpxAppearanceAdapterType.TRACK_WIDTH_COLOR) {
trackColorProp = renderer.PROPS.getCustomRule(CURRENT_TRACK_COLOR_ATTR);
}
}
if (trackWidthProp != null) {
@ -1293,8 +1318,6 @@ public class ConfigureMapMenu {
item.setLastItem(true);
}
if (trackColorProp != null) {
currentColor = parseTrackColor(renderer, currentColorValue);
AppearanceListItem item = new AppearanceListItem(CURRENT_TRACK_COLOR_ATTR, "",
SettingsActivity.getStringPropertyValue(getContext(), trackColorProp.getDefaultValueDescription()),
parseTrackColor(renderer, ""));

View file

@ -556,7 +556,8 @@ public class GpxUiHelper {
popup.setVerticalOffset(AndroidUtils.dpToPx(activity, -48f));
popup.setHorizontalOffset(AndroidUtils.dpToPx(activity, -6f));
final GpxAppearanceAdapter gpxApprAdapter = new GpxAppearanceAdapter(activity,
gpxAppearanceParams.containsKey(CURRENT_TRACK_COLOR_ATTR) ? gpxAppearanceParams.get(CURRENT_TRACK_COLOR_ATTR) : prefColor.get());
gpxAppearanceParams.containsKey(CURRENT_TRACK_COLOR_ATTR) ? gpxAppearanceParams.get(CURRENT_TRACK_COLOR_ATTR) : prefColor.get(),
GpxAppearanceAdapter.GpxAppearanceAdapterType.TRACK_WIDTH_COLOR);
popup.setAdapter(gpxApprAdapter);
popup.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@ -1060,6 +1061,8 @@ public class GpxUiHelper {
dataSet.setDrawHorizontalHighlightIndicator(false);
dataSet.setHighLightColor(light ? mChart.getResources().getColor(R.color.secondary_text_light) : mChart.getResources().getColor(R.color.secondary_text_dark));
dataSet.setMode(LineDataSet.Mode.HORIZONTAL_BEZIER);
dataSet.setFillFormatter(new IFillFormatter() {
@Override
public float getFillLinePosition(ILineDataSet dataSet, LineDataProvider dataProvider) {
@ -1192,6 +1195,8 @@ public class GpxUiHelper {
dataSet.setDrawHorizontalHighlightIndicator(false);
dataSet.setHighLightColor(light ? mChart.getResources().getColor(R.color.secondary_text_light) : mChart.getResources().getColor(R.color.secondary_text_dark));
dataSet.setMode(LineDataSet.Mode.HORIZONTAL_BEZIER);
if (useRightAxis) {
dataSet.setAxisDependency(YAxis.AxisDependency.RIGHT);
}

View file

@ -1,17 +1,14 @@
package net.osmand.plus.myplaces;
import android.app.Activity;
import android.content.DialogInterface;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Handler;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.view.MenuItemCompat;
import android.support.v7.app.AlertDialog;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
@ -19,33 +16,24 @@ import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.CheckBox;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.Spinner;
import android.widget.TextView;
import net.osmand.data.FavouritePoint;
import net.osmand.data.LatLon;
import net.osmand.data.PointDescription;
import net.osmand.plus.FavouritesDbHelper;
import net.osmand.plus.GPXDatabase;
import net.osmand.plus.GPXDatabase.GpxDataItem;
import net.osmand.plus.GPXUtilities.GPXFile;
import net.osmand.plus.GPXUtilities.WptPt;
import net.osmand.plus.GpxSelectionHelper;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayGroup;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItem;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItemType;
import net.osmand.plus.GpxSelectionHelper.SelectedGpxFile;
import net.osmand.plus.MapMarkersHelper;
import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.OsmandSettings;
import net.osmand.plus.R;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.activities.TrackActivity;
import net.osmand.plus.base.OsmAndListFragment;
import net.osmand.plus.helpers.ColorDialogs;
import net.osmand.util.Algorithms;
import java.io.File;
import java.text.Collator;
@ -53,26 +41,19 @@ import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import gnu.trove.list.array.TIntArrayList;
public class SelectedGPXFragment extends OsmAndListFragment {
public static final String ARG_TO_EXPAND_TRACK_INFO = "ARG_TO_EXPAND_TRACK_INFO";
public static final String ARG_TO_FILTER_SHORT_TRACKS = "ARG_TO_FILTER_SHORT_TRACKS";
public static final String ARG_TO_HIDE_CONFIG_BTN = "ARG_TO_HIDE_CONFIG_BTN";
protected OsmandApplication app;
protected ArrayAdapter<GpxSelectionHelper.GpxDisplayItem> adapter;
protected TrackActivity activity;
protected ArrayAdapter<GpxDisplayItem> adapter;
private boolean updateEnable;
@Override
public void onAttach(Activity activity) {
this.activity = (TrackActivity) activity;
super.onAttach(activity);
public void onAttach(Context context) {
super.onAttach(context);
final Collator collator = Collator.getInstance();
collator.setStrength(Collator.SECONDARY);
app = (OsmandApplication) activity.getApplication();
app = (OsmandApplication) getActivity().getApplication();
}
@Override
@ -84,7 +65,7 @@ public class SelectedGPXFragment extends OsmAndListFragment {
}
public TrackActivity getMyActivity() {
return activity;
return (TrackActivity) getActivity();
}
@Override
@ -132,8 +113,8 @@ public class SelectedGPXFragment extends OsmAndListFragment {
protected static List<GpxDisplayGroup> filterGroups(GpxDisplayItemType[] types,
@NonNull TrackActivity trackActivity,
@Nullable Bundle args) {
List<GpxDisplayGroup> result = trackActivity.getResult();
List<GpxDisplayGroup> groups = new ArrayList<GpxSelectionHelper.GpxDisplayGroup>();
List<GpxDisplayGroup> result = trackActivity.getGpxFile();
List<GpxDisplayGroup> groups = new ArrayList<>();
for (GpxDisplayGroup group : result) {
boolean add = types == null || hasFilterType(types, group.getType());
if (isArgumentTrue(args, ARG_TO_FILTER_SHORT_TRACKS)) {
@ -157,14 +138,25 @@ public class SelectedGPXFragment extends OsmAndListFragment {
}
public void setContent() {
setContent(getListView());
}
public void setContent(ListView listView) {
adapter = createSelectedGPXAdapter();
updateContent();
setupListView(listView);
setListAdapter(adapter);
}
protected void setupListView(ListView listView) {
if (adapter.getCount() > 0) {
listView.addFooterView(getActivity().getLayoutInflater().inflate(R.layout.list_shadow_footer, null, false));
}
}
protected void updateContent() {
adapter.clear();
List<GpxSelectionHelper.GpxDisplayGroup> groups = filterGroups(filterTypes(), getMyActivity(), getArguments());
List<GpxDisplayGroup> groups = filterGroups(filterTypes(), getMyActivity(), getArguments());
adapter.setNotifyOnChange(false);
for (GpxDisplayItem i : flatten(groups)) {
adapter.add(i);
@ -196,7 +188,7 @@ public class SelectedGPXFragment extends OsmAndListFragment {
}
protected List<GpxDisplayItem> flatten(List<GpxDisplayGroup> groups) {
ArrayList<GpxDisplayItem> list = new ArrayList<GpxDisplayItem>();
ArrayList<GpxDisplayItem> list = new ArrayList<>();
for(GpxDisplayGroup g : groups) {
list.addAll(g.getModifiableList());
}
@ -211,13 +203,11 @@ public class SelectedGPXFragment extends OsmAndListFragment {
ListView listView = (ListView) view.findViewById(android.R.id.list);
listView.setDivider(null);
listView.setDividerHeight(0);
listView.addFooterView(getActivity().getLayoutInflater().inflate(R.layout.list_shadow_footer, null, false));
TextView tv = new TextView(getActivity());
tv.setText(R.string.none_selected_gpx);
tv.setTextSize(24);
listView.setEmptyView(tv);
setContent();
setContent(listView);
return view;
}
@ -228,81 +218,10 @@ public class SelectedGPXFragment extends OsmAndListFragment {
return super.onOptionsItemSelected(item);
}
protected void saveAsFavorites(final GpxDisplayItemType gpxDisplayItemType) {
AlertDialog.Builder b = new AlertDialog.Builder(getMyActivity());
final EditText editText = new EditText(getMyActivity());
final List<GpxDisplayGroup> gs = filterGroups(new GpxDisplayItemType[] { gpxDisplayItemType }, getMyActivity(), getArguments());
if (gs.size() == 0) {
return;
}
String name = gs.get(0).getName();
if(name.indexOf('\n') > 0) {
name = name.substring(0, name.indexOf('\n'));
}
editText.setText(name);
editText.setPadding(7, 3, 7, 3);
b.setTitle(R.string.save_as_favorites_points);
b.setView(editText);
b.setPositiveButton(R.string.shared_string_save, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
saveFavoritesImpl(flatten(gs), editText.getText().toString());
}
});
b.setNegativeButton(R.string.shared_string_cancel, null);
b.show();
}
protected void saveAsMapMarkers(final GpxDisplayItemType gpxDisplayItemType) {
AlertDialog.Builder b = new AlertDialog.Builder(getMyActivity());
final List<GpxDisplayGroup> gs = filterGroups(new GpxDisplayItemType[] { gpxDisplayItemType }, getMyActivity(), getArguments());
if (gs.size() == 0) {
return;
}
b.setMessage(R.string.add_points_to_map_markers_q);
b.setPositiveButton(R.string.shared_string_add, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
saveMapMarkersImpl(flatten(gs));
}
});
b.setNegativeButton(R.string.shared_string_cancel, null);
b.show();
}
protected void saveFavoritesImpl(List<GpxDisplayItem> modifiableList, String category) {
FavouritesDbHelper fdb = app.getFavorites();
for(GpxDisplayItem i : modifiableList) {
if (i.locationStart != null) {
FavouritePoint fp = new FavouritePoint(i.locationStart.lat, i.locationStart.lon, i.name, category);
if (!Algorithms.isEmpty(i.description)) {
fp.setDescription(i.description);
}
fdb.addFavourite(fp, false);
}
}
fdb.saveCurrentPointsIntoFile();
}
protected void saveMapMarkersImpl(List<GpxDisplayItem> modifiableList) {
MapMarkersHelper markersHelper = app.getMapMarkersHelper();
List<LatLon> points = new ArrayList<>();
List<PointDescription> names = new ArrayList<>();
for(GpxDisplayItem i : modifiableList) {
if (i.locationStart != null) {
points.add(new LatLon(i.locationStart.lat, i.locationStart.lon));
names.add(new PointDescription(PointDescription.POINT_TYPE_MAP_MARKER, i.name));
}
}
markersHelper.addMapMarkers(points, names);
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
menu.clear();
((TrackActivity) getActivity()).getClearToolbar(false);
getMyActivity().getClearToolbar(false);
if (getGpx() != null && getGpx().path != null && !getGpx().showCurrentTrack) {
MenuItem item = menu.add(R.string.shared_string_share).setIcon(R.drawable.ic_action_gshare_dark)
.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
@ -320,151 +239,15 @@ public class SelectedGPXFragment extends OsmAndListFragment {
}
}
protected GPXFile getGpx() {
return ((TrackActivity)getActivity()).getGpx();
return getMyActivity().getGpx();
}
protected void selectSplitDistance() {
final List<GpxDisplayGroup> groups = filterGroups(new GpxDisplayItemType[] { GpxDisplayItemType.TRACK_SEGMENT },
getMyActivity(), getArguments());
View view = getMyActivity().getLayoutInflater().inflate(R.layout.selected_track_edit, null);
final TIntArrayList list = new TIntArrayList();
final Spinner colorSpinner = (Spinner) view.findViewById(R.id.ColorSpinner);
ColorDialogs.setupColorSpinner(getActivity(), getGpx().getColor(0), colorSpinner, list);
final Spinner sp = (Spinner) view.findViewById(R.id.Spinner);
AlertDialog.Builder bld = new AlertDialog.Builder(getMyActivity());
final List<Double> distanceSplit = new ArrayList<Double>();
final TIntArrayList timeSplit = new TIntArrayList();
if (groups.size() == 0) {
sp.setVisibility(View.GONE);
view.findViewById(R.id.GpxSpinnerRow).setVisibility(View.GONE);
} else {
sp.setVisibility(View.VISIBLE);
int[] checkedItem = new int[]{!groups.get(0).isSplitDistance() && !groups.get(0).isSplitTime() ? 0 : -1};
List<String> options = new ArrayList<String>();
options.add(app.getString(R.string.shared_string_none));
distanceSplit.add(-1d);
timeSplit.add(-1);
addOptionSplit(30, true, options, distanceSplit, timeSplit, checkedItem, groups); // 50 feet, 20 yards, 20
// m
addOptionSplit(60, true, options, distanceSplit, timeSplit, checkedItem, groups); // 100 feet, 50 yards,
// 50 m
addOptionSplit(150, true, options, distanceSplit, timeSplit, checkedItem, groups); // 200 feet, 100 yards,
// 100 m
addOptionSplit(300, true, options, distanceSplit, timeSplit, checkedItem, groups); // 500 feet, 200 yards,
// 200 m
addOptionSplit(600, true, options, distanceSplit, timeSplit, checkedItem, groups); // 1000 feet, 500 yards,
// 500 m
addOptionSplit(1500, true, options, distanceSplit, timeSplit, checkedItem, groups); // 2000 feet, 1000 yards, 1 km
addOptionSplit(3000, true, options, distanceSplit, timeSplit, checkedItem, groups); // 1 mi, 2 km
addOptionSplit(6000, true, options, distanceSplit, timeSplit, checkedItem, groups); // 2 mi, 5 km
addOptionSplit(15000, true, options, distanceSplit, timeSplit, checkedItem, groups); // 5 mi, 10 km
addOptionSplit(15, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(30, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(60, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(120, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(150, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(300, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(600, false, options, distanceSplit, timeSplit, checkedItem, groups);
addOptionSplit(900, false, options, distanceSplit, timeSplit, checkedItem, groups);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(getMyActivity(),
android.R.layout.simple_spinner_item, options);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
sp.setAdapter(adapter);
if (checkedItem[0] > 0) {
sp.setSelection(checkedItem[0]);
}
}
final CheckBox vis = (CheckBox) view.findViewById(R.id.Visibility);
vis.setChecked(app.getSelectedGpxHelper().getSelectedFileByPath(getGpx().path) != null);
bld.setView(view);
bld.setNegativeButton(R.string.shared_string_cancel, null);
bld.setPositiveButton(R.string.shared_string_ok, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
SelectedGpxFile sf = app.getSelectedGpxHelper().selectGpxFile(getGpx(), vis.isChecked(), false);
int clr = list.get(colorSpinner.getSelectedItemPosition());
if (vis.isChecked() && clr != 0 && sf.getModifiableGpxFile() != null) {
sf.getModifiableGpxFile().setColor(clr);
sf.processPoints();
}
if (groups.size() > 0) {
updateSplit(groups, distanceSplit, timeSplit, sp.getSelectedItemPosition(), vis.isChecked() ? sf
: null);
}
if (vis.isChecked() && sf.getGpxFile() != null) {
if (groups.size() > 0 && groups.get(0).getModifiableList().size() > 0) {
GpxDisplayItem item = groups.get(0).getModifiableList().get(0);
app.getSettings().setMapLocationToShow(item.locationStart.lat, item.locationStart.lon,
15,
new PointDescription(PointDescription.POINT_TYPE_GPX_ITEM, item.group.getGpxName()),
false,
item); //$NON-NLS-1$
} else {
WptPt wpt = sf.getGpxFile().findPointToShow();
if (wpt != null) {
app.getSettings().setMapLocationToShow(wpt.getLatitude(), wpt.getLongitude(),
15,
new PointDescription(PointDescription.POINT_TYPE_WPT, wpt.name),
false,
wpt); //$NON-NLS-1$
}
}
MapActivity.launchMapActivityMoveToTop(activity);
}
}
});
bld.show();
protected GpxDataItem getGpxDataItem() {
return getMyActivity().getGpxDataItem();
}
private void updateSplit(List<GpxDisplayGroup> groups, List<Double> distanceSplit,
TIntArrayList timeSplit, int which, SelectedGpxFile sf) {
new SplitTrackAsyncTask(sf, this, getMyActivity(), groups, distanceSplit, timeSplit, which)
.execute((Void) null);
}
private void addOptionSplit(int value, boolean distance, List<String> options, List<Double> distanceSplit,
TIntArrayList timeSplit, int[] checkedItem, List<GpxDisplayGroup> model) {
if (distance) {
double dvalue = OsmAndFormatter.calculateRoundedDist(value, app);
options.add(OsmAndFormatter.getFormattedDistance((float) dvalue, app));
distanceSplit.add(dvalue);
timeSplit.add(-1);
if (Math.abs(model.get(0).getSplitDistance() - dvalue) < 1) {
checkedItem[0] = distanceSplit.size() - 1;
}
} else {
if (value < 60) {
options.add(value + " " + app.getString(R.string.int_seconds));
} else if (value % 60 == 0) {
options.add((value / 60) + " " + app.getString(R.string.int_min));
} else {
options.add((value / 60f) + " " + app.getString(R.string.int_min));
}
distanceSplit.add(-1d);
timeSplit.add(value);
if (model.get(0).getSplitTime() == value) {
checkedItem[0] = distanceSplit.size() - 1;
}
}
}
public ArrayAdapter<GpxSelectionHelper.GpxDisplayItem> createSelectedGPXAdapter() {
public ArrayAdapter<GpxDisplayItem> createSelectedGPXAdapter() {
return null;
}
@ -472,34 +255,35 @@ public class SelectedGPXFragment extends OsmAndListFragment {
public void onListItemClick(ListView l, View v, int position, long id) {
GpxDisplayItem child = adapter.getItem(position);
if (child != null) {
if (child.group.getGpx() != null) {
app.getSelectedGpxHelper().setGpxFileToDisplay(child.group.getGpx());
}
if (child.group.getGpx() != null) {
app.getSelectedGpxHelper().setGpxFileToDisplay(child.group.getGpx());
final OsmandSettings settings = app.getSettings();
LatLon location = new LatLon(child.locationStart.lat, child.locationStart.lon);
if (child.group.getType() == GpxDisplayItemType.TRACK_POINTS) {
settings.setMapLocationToShow(location.getLatitude(), location.getLongitude(),
settings.getLastKnownMapZoom(),
new PointDescription(PointDescription.POINT_TYPE_WPT, child.locationStart.name),
false,
child.locationStart);
} else if (child.group.getType() == GpxDisplayItemType.TRACK_ROUTE_POINTS) {
settings.setMapLocationToShow(location.getLatitude(), location.getLongitude(),
settings.getLastKnownMapZoom(),
new PointDescription(PointDescription.POINT_TYPE_WPT, child.name),
false,
child.locationStart);
} else {
settings.setMapLocationToShow(location.getLatitude(), location.getLongitude(),
settings.getLastKnownMapZoom(),
new PointDescription(PointDescription.POINT_TYPE_GPX_ITEM, child.group.getGpxName()),
false,
child);
}
MapActivity.launchMapActivityMoveToTop(getActivity());
}
final OsmandSettings settings = app.getSettings();
LatLon location = new LatLon(child.locationStart.lat, child.locationStart.lon);
if (child.group.getType() == GpxDisplayItemType.TRACK_POINTS) {
settings.setMapLocationToShow(location.getLatitude(), location.getLongitude(),
settings.getLastKnownMapZoom(),
new PointDescription(PointDescription.POINT_TYPE_WPT, child.locationStart.name),
false,
child.locationStart);
} else if (child.group.getType() == GpxDisplayItemType.TRACK_ROUTE_POINTS) {
settings.setMapLocationToShow(location.getLatitude(), location.getLongitude(),
settings.getLastKnownMapZoom(),
new PointDescription(PointDescription.POINT_TYPE_WPT, child.name),
false,
child.locationStart);
} else {
settings.setMapLocationToShow(location.getLatitude(), location.getLongitude(),
settings.getLastKnownMapZoom(),
new PointDescription(PointDescription.POINT_TYPE_GPX_ITEM, child.group.getGpxName()),
false,
child);
}
MapActivity.launchMapActivityMoveToTop(getActivity());
/*
// if(child.group.getType() == GpxDisplayItemType.TRACK_POINTS ||
// child.group.getType() == GpxDisplayItemType.TRACK_ROUTE_POINTS) {
@ -518,63 +302,4 @@ public class SelectedGPXFragment extends OsmAndListFragment {
// }
*/
}
public static class SplitTrackAsyncTask extends AsyncTask<Void, Void, Void> {
@Nullable private final SelectedGpxFile mSelectedGpxFile;
@NonNull private final SelectedGPXFragment mFragment;
@NonNull private final TrackActivity mActivity;
private final List<GpxDisplayGroup> groups;
private final List<Double> distanceSplit;
private final TIntArrayList timeSplit;
private final int which;
public SplitTrackAsyncTask(@Nullable SelectedGpxFile selectedGpxFile,
SelectedGPXFragment fragment,
TrackActivity activity,
List<GpxDisplayGroup> groups,
List<Double> distanceSplit,
TIntArrayList timeSplit,
int which) {
mSelectedGpxFile = selectedGpxFile;
mFragment = fragment;
mActivity = activity;
this.groups = groups;
this.distanceSplit = distanceSplit;
this.timeSplit = timeSplit;
this.which = which;
}
protected void onPostExecute(Void result) {
if (mSelectedGpxFile != null) {
mSelectedGpxFile.setDisplayGroups(filterGroups(null, mActivity, mFragment.getArguments()));
}
if (mFragment.isVisible()) {
mFragment.updateContent();
}
if (!mActivity.isFinishing()) {
mActivity.setProgressBarIndeterminateVisibility(false);
}
}
protected void onPreExecute() {
mActivity.setProgressBarIndeterminateVisibility(true);
}
@Override
protected Void doInBackground(Void... params) {
for (GpxDisplayGroup model : groups) {
OsmandApplication application = mActivity.getMyApplication();
if (which == 0) {
model.noSplit(application);
} else if (distanceSplit.get(which) > 0) {
model.splitByDistance(application, distanceSplit.get(which));
} else if (timeSplit.get(which) > 0) {
model.splitByTime(application, timeSplit.get(which));
}
}
return null;
}
}
}

View file

@ -1,7 +1,9 @@
package net.osmand.plus.myplaces;
import android.content.DialogInterface;
import android.support.annotation.NonNull;
import android.support.v4.view.MenuItemCompat;
import android.support.v7.app.AlertDialog;
import android.text.Html;
import android.view.LayoutInflater;
import android.view.Menu;
@ -10,12 +12,19 @@ import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.TextView;
import net.osmand.data.FavouritePoint;
import net.osmand.data.LatLon;
import net.osmand.data.PointDescription;
import net.osmand.plus.FavouritesDbHelper;
import net.osmand.plus.GpxSelectionHelper;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItem;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItemType;
import net.osmand.plus.MapMarkersHelper;
import net.osmand.plus.R;
import net.osmand.plus.base.FavoriteImageDrawable;
import net.osmand.util.Algorithms;
@ -25,6 +34,14 @@ import java.util.List;
public class TrackPointFragment extends SelectedGPXFragment {
@Override
protected void setupListView(ListView listView) {
super.setupListView(listView);
if (adapter.getCount() > 0) {
listView.addHeaderView(getActivity().getLayoutInflater().inflate(R.layout.list_shadow_header, null, false));
}
}
@Override
protected GpxDisplayItemType[] filterTypes() {
return new GpxDisplayItemType[] { GpxSelectionHelper.GpxDisplayItemType.TRACK_POINTS, GpxSelectionHelper.GpxDisplayItemType.TRACK_ROUTE_POINTS };
@ -58,6 +75,77 @@ public class TrackPointFragment extends SelectedGPXFragment {
}
}
protected void saveAsFavorites(final GpxDisplayItemType gpxDisplayItemType) {
AlertDialog.Builder b = new AlertDialog.Builder(getMyActivity());
final EditText editText = new EditText(getMyActivity());
final List<GpxSelectionHelper.GpxDisplayGroup> gs = filterGroups(new GpxDisplayItemType[] { gpxDisplayItemType }, getMyActivity(), getArguments());
if (gs.size() == 0) {
return;
}
String name = gs.get(0).getName();
if(name.indexOf('\n') > 0) {
name = name.substring(0, name.indexOf('\n'));
}
editText.setText(name);
editText.setPadding(7, 3, 7, 3);
b.setTitle(R.string.save_as_favorites_points);
b.setView(editText);
b.setPositiveButton(R.string.shared_string_save, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
saveFavoritesImpl(flatten(gs), editText.getText().toString());
}
});
b.setNegativeButton(R.string.shared_string_cancel, null);
b.show();
}
protected void saveAsMapMarkers(final GpxDisplayItemType gpxDisplayItemType) {
AlertDialog.Builder b = new AlertDialog.Builder(getMyActivity());
final List<GpxSelectionHelper.GpxDisplayGroup> gs = filterGroups(new GpxDisplayItemType[] { gpxDisplayItemType }, getMyActivity(), getArguments());
if (gs.size() == 0) {
return;
}
b.setMessage(R.string.add_points_to_map_markers_q);
b.setPositiveButton(R.string.shared_string_add, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
saveMapMarkersImpl(flatten(gs));
}
});
b.setNegativeButton(R.string.shared_string_cancel, null);
b.show();
}
protected void saveFavoritesImpl(List<GpxDisplayItem> modifiableList, String category) {
FavouritesDbHelper fdb = app.getFavorites();
for(GpxDisplayItem i : modifiableList) {
if (i.locationStart != null) {
FavouritePoint fp = new FavouritePoint(i.locationStart.lat, i.locationStart.lon, i.name, category);
if (!Algorithms.isEmpty(i.description)) {
fp.setDescription(i.description);
}
fdb.addFavourite(fp, false);
}
}
fdb.saveCurrentPointsIntoFile();
}
protected void saveMapMarkersImpl(List<GpxDisplayItem> modifiableList) {
MapMarkersHelper markersHelper = app.getMapMarkersHelper();
List<LatLon> points = new ArrayList<>();
List<PointDescription> names = new ArrayList<>();
for(GpxDisplayItem i : modifiableList) {
if (i.locationStart != null) {
points.add(new LatLon(i.locationStart.lat, i.locationStart.lon));
names.add(new PointDescription(PointDescription.POINT_TYPE_MAP_MARKER, i.name));
}
}
markersHelper.addMapMarkers(points, names);
}
@Override
public ArrayAdapter<GpxDisplayItem> createSelectedGPXAdapter() {
return new PointGPXAdapter(new ArrayList<GpxDisplayItem>());

View file

@ -2,20 +2,24 @@ package net.osmand.plus.myplaces;
import android.content.Context;
import android.graphics.Matrix;
import android.os.AsyncTask;
import android.support.annotation.NonNull;
import android.support.v4.view.MenuItemCompat;
import android.support.annotation.Nullable;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewCompat;
import android.support.v7.widget.ListPopupWindow;
import android.support.v7.widget.SwitchCompat;
import android.util.SparseArray;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.CompoundButton;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.TextView;
import com.github.mikephil.charting.charts.LineChart;
@ -26,20 +30,31 @@ import com.github.mikephil.charting.listener.ChartTouchListener.ChartGesture;
import com.github.mikephil.charting.listener.OnChartGestureListener;
import net.osmand.AndroidUtils;
import net.osmand.data.PointDescription;
import net.osmand.plus.GPXUtilities;
import net.osmand.plus.GPXUtilities.GPXTrackAnalysis;
import net.osmand.plus.GpxSelectionHelper;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayGroup;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItem;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItemType;
import net.osmand.plus.GpxSelectionHelper.SelectedGpxFile;
import net.osmand.plus.IconsCache;
import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.OsmandSettings;
import net.osmand.plus.R;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.activities.TrackActivity;
import net.osmand.plus.dialogs.ConfigureMapMenu.AppearanceListItem;
import net.osmand.plus.dialogs.ConfigureMapMenu.GpxAppearanceAdapter;
import net.osmand.plus.dialogs.ConfigureMapMenu.GpxAppearanceAdapter.GpxAppearanceAdapterType;
import net.osmand.plus.helpers.GpxUiHelper;
import net.osmand.plus.helpers.GpxUiHelper.OrderedLineDataSet;
import net.osmand.plus.views.controls.PagerSlidingTabStrip;
import net.osmand.plus.views.controls.PagerSlidingTabStrip.CustomTabProvider;
import net.osmand.plus.views.controls.WrapContentHeightViewPager;
import net.osmand.plus.views.controls.WrapContentHeightViewPager.ViewAtPositionInterface;
import net.osmand.render.RenderingRulesStorage;
import net.osmand.util.Algorithms;
import java.text.DateFormat;
@ -47,27 +62,262 @@ import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import gnu.trove.list.array.TIntArrayList;
import static net.osmand.plus.dialogs.ConfigureMapMenu.CURRENT_TRACK_COLOR_ATTR;
public class TrackSegmentFragment extends SelectedGPXFragment {
private List<String> options = new ArrayList<>();
private List<Double> distanceSplit = new ArrayList<>();
private TIntArrayList timeSplit = new TIntArrayList();
private int selectedSplitInterval;
@Override
protected void setupListView(ListView listView) {
super.setupListView(listView);
if (adapter.getCount() > 0) {
View view = getActivity().getLayoutInflater().inflate(R.layout.gpx_item_list_header, null, false);
listView.addHeaderView(view);
final ImageView imageView = (ImageView) view.findViewById(R.id.imageView);
final View splitIntervalView = view.findViewById(R.id.split_interval_view);
final View colorView = view.findViewById(R.id.color_view);
final SwitchCompat vis = (SwitchCompat) view.findViewById(R.id.showOnMapToggle);
vis.setChecked(app.getSelectedGpxHelper().getSelectedFileByPath(getGpx().path) != null);
vis.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
SelectedGpxFile sf = app.getSelectedGpxHelper().selectGpxFile(getGpx(), vis.isChecked(), false);
if (vis.isChecked() && sf.getModifiableGpxFile() != null) {
sf.processPoints();
updateColorView(colorView);
} else {
updateColorView(colorView);
}
}
});
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
SelectedGpxFile sf = app.getSelectedGpxHelper().selectGpxFile(getGpx(), vis.isChecked(), false);
if (vis.isChecked() && sf.getGpxFile() != null) {
final List<GpxDisplayGroup> groups = getGroups();
if (groups.size() > 0 && groups.get(0).getModifiableList().size() > 0) {
GpxDisplayItem item = groups.get(0).getModifiableList().get(0);
app.getSettings().setMapLocationToShow(item.locationStart.lat, item.locationStart.lon,
15,
new PointDescription(PointDescription.POINT_TYPE_GPX_ITEM, item.group.getGpxName()),
false,
item);
} else {
GPXUtilities.WptPt wpt = sf.getGpxFile().findPointToShow();
if (wpt != null) {
app.getSettings().setMapLocationToShow(wpt.getLatitude(), wpt.getLongitude(),
15,
new PointDescription(PointDescription.POINT_TYPE_WPT, wpt.name),
false,
wpt);
}
}
MapActivity.launchMapActivityMoveToTop(getMyActivity());
}
}
});
updateColorView(colorView);
colorView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final ListPopupWindow popup = new ListPopupWindow(getActivity());
popup.setAnchorView(colorView);
popup.setContentWidth(AndroidUtils.dpToPx(app, 200f));
popup.setModal(true);
popup.setDropDownGravity(Gravity.RIGHT | Gravity.TOP);
popup.setVerticalOffset(AndroidUtils.dpToPx(app, -48f));
popup.setHorizontalOffset(AndroidUtils.dpToPx(app, -6f));
final GpxAppearanceAdapter gpxApprAdapter = new GpxAppearanceAdapter(getActivity(),
getGpx().getColor(0), GpxAppearanceAdapterType.TRACK_COLOR);
popup.setAdapter(gpxApprAdapter);
popup.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
AppearanceListItem item = gpxApprAdapter.getItem(position);
if (item != null) {
if (item.getAttrName() == CURRENT_TRACK_COLOR_ATTR) {
int clr = item.getColor();
if (vis.isChecked()) {
SelectedGpxFile sf = app.getSelectedGpxHelper().selectGpxFile(getGpx(), vis.isChecked(), false);
if (clr != 0 && sf.getModifiableGpxFile() != null) {
sf.getModifiableGpxFile().setColor(clr);
app.getGpxDatabase().updateColor(getGpxDataItem(), clr);
}
} else {
app.getGpxDatabase().updateColor(getGpxDataItem(), clr);
}
}
}
popup.dismiss();
updateColorView(colorView);
}
});
popup.show();
}
});
prepareSplitIntervalAdapterData();
setupSplitIntervalView(splitIntervalView);
updateSplitIntervalView(splitIntervalView);
splitIntervalView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final ListPopupWindow popup = new ListPopupWindow(getActivity());
popup.setAnchorView(splitIntervalView);
popup.setContentWidth(AndroidUtils.dpToPx(app, 200f));
popup.setModal(true);
popup.setDropDownGravity(Gravity.RIGHT | Gravity.TOP);
popup.setVerticalOffset(AndroidUtils.dpToPx(app, -48f));
popup.setHorizontalOffset(AndroidUtils.dpToPx(app, -6f));
popup.setAdapter(new ArrayAdapter<>(getMyActivity(),
R.layout.popup_list_text_item, options));
popup.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
selectedSplitInterval = position;
SelectedGpxFile sf = app.getSelectedGpxHelper().selectGpxFile(getGpx(), vis.isChecked(), false);
final List<GpxDisplayGroup> groups = getGroups();
if (groups.size() > 0) {
updateSplit(groups, vis.isChecked() ? sf : null);
}
popup.dismiss();
updateSplitIntervalView(splitIntervalView);
}
});
popup.show();
}
});
}
}
private List<GpxDisplayGroup> getGroups() {
return filterGroups(new GpxDisplayItemType[] { GpxDisplayItemType.TRACK_SEGMENT },
getMyActivity(), getArguments());
}
private void setupSplitIntervalView(View view) {
final TextView title = (TextView) view.findViewById(R.id.split_interval_title);
final TextView text = (TextView) view.findViewById(R.id.split_interval_text);
final ImageView img = (ImageView) view.findViewById(R.id.split_interval_arrow);
int colorId;
final List<GpxDisplayGroup> groups = getGroups();
if (groups.size() > 0) {
colorId = app.getSettings().isLightContent() ?
R.color.primary_text_light : R.color.primary_text_dark;
} else {
colorId = app.getSettings().isLightContent() ?
R.color.secondary_text_light : R.color.secondary_text_dark;
}
int color = app.getResources().getColor(colorId);
title.setTextColor(color);
text.setTextColor(color);
img.setImageDrawable(app.getIconsCache().getIcon(R.drawable.ic_action_arrow_drop_down, colorId));
}
private void updateSplitIntervalView(View view) {
final TextView text = (TextView) view.findViewById(R.id.split_interval_text);
if (selectedSplitInterval == 0) {
text.setText(getString(R.string.shared_string_none));
} else {
text.setText(options.get(selectedSplitInterval));
}
}
private void updateColorView(View colorView) {
final ImageView colorImageView = (ImageView) colorView.findViewById(R.id.colorImage);
int color = getGpxDataItem().getColor();
if (color == 0) {
color = getGpx().getColor(0);
}
if (color == 0) {
final RenderingRulesStorage renderer = app.getRendererRegistry().getCurrentSelectedRenderer();
final OsmandSettings.CommonPreference<String> prefColor
= app.getSettings().getCustomRenderProperty(CURRENT_TRACK_COLOR_ATTR);
color = GpxAppearanceAdapter.parseTrackColor(renderer, prefColor.get());
}
if (color == 0) {
colorImageView.setImageDrawable(app.getIconsCache().getThemedIcon(R.drawable.ic_action_circle));
} else {
colorImageView.setImageDrawable(app.getIconsCache().getPaintedIcon(R.drawable.ic_action_circle, color));
}
}
@Override
protected GpxDisplayItemType[] filterTypes() {
return new GpxDisplayItemType[] { GpxSelectionHelper.GpxDisplayItemType.TRACK_SEGMENT };
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
super.onCreateOptionsMenu(menu, inflater);
MenuItem item = menu.add(R.string.shared_string_show_on_map).setIcon(R.drawable.ic_show_on_map).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
selectSplitDistance();
return true;
private void prepareSplitIntervalAdapterData() {
final List<GpxDisplayGroup> groups = getGroups();
options.add(app.getString(R.string.shared_string_none));
distanceSplit.add(-1d);
timeSplit.add(-1);
addOptionSplit(30, true, groups); // 50 feet, 20 yards, 20
// m
addOptionSplit(60, true, groups); // 100 feet, 50 yards,
// 50 m
addOptionSplit(150, true, groups); // 200 feet, 100 yards,
// 100 m
addOptionSplit(300, true, groups); // 500 feet, 200 yards,
// 200 m
addOptionSplit(600, true, groups); // 1000 feet, 500 yards,
// 500 m
addOptionSplit(1500, true, groups); // 2000 feet, 1000 yards, 1 km
addOptionSplit(3000, true, groups); // 1 mi, 2 km
addOptionSplit(6000, true, groups); // 2 mi, 5 km
addOptionSplit(15000, true, groups); // 5 mi, 10 km
addOptionSplit(15, false, groups);
addOptionSplit(30, false, groups);
addOptionSplit(60, false, groups);
addOptionSplit(120, false, groups);
addOptionSplit(150, false, groups);
addOptionSplit(300, false, groups);
addOptionSplit(600, false, groups);
addOptionSplit(900, false, groups);
}
private void updateSplit(List<GpxDisplayGroup> groups, SelectedGpxFile sf) {
new SplitTrackAsyncTask(sf, this, getMyActivity(), groups).execute((Void) null);
}
private void addOptionSplit(int value, boolean distance, List<GpxDisplayGroup> model) {
if (distance) {
double dvalue = OsmAndFormatter.calculateRoundedDist(value, app);
options.add(OsmAndFormatter.getFormattedDistance((float) dvalue, app));
distanceSplit.add(dvalue);
timeSplit.add(-1);
if (Math.abs(model.get(0).getSplitDistance() - dvalue) < 1) {
selectedSplitInterval = distanceSplit.size() - 1;
}
});
MenuItemCompat.setShowAsAction(item, MenuItemCompat.SHOW_AS_ACTION_ALWAYS);
} else {
if (value < 60) {
options.add(value + " " + app.getString(R.string.int_seconds));
} else if (value % 60 == 0) {
options.add((value / 60) + " " + app.getString(R.string.int_min));
} else {
options.add((value / 60f) + " " + app.getString(R.string.int_min));
}
distanceSplit.add(-1d);
timeSplit.add(value);
if (model.get(0).getSplitTime() == value) {
selectedSplitInterval = distanceSplit.size() - 1;
}
}
}
@Override
@ -102,8 +352,9 @@ public class TrackSegmentFragment extends SelectedGPXFragment {
@Override
public View getView(int position, View convertView, @NonNull ViewGroup parent) {
View row = convertView;
PagerSlidingTabStrip tabLayout = null;
PagerSlidingTabStrip tabLayout;
WrapContentHeightViewPager pager;
boolean create = false;
if (row == null) {
LayoutInflater inflater = getMyActivity().getLayoutInflater();
row = inflater.inflate(R.layout.gpx_list_item_tab_content, parent, false);
@ -120,16 +371,18 @@ public class TrackSegmentFragment extends SelectedGPXFragment {
tabLayout.setTabSelectionType(PagerSlidingTabStrip.TabSelectionType.SOLID_COLOR);
pager = (WrapContentHeightViewPager) row.findViewById(R.id.pager);
pager.setSwipeable(false);
pager.setOffscreenPageLimit(2);
create = true;
} else {
tabLayout = (PagerSlidingTabStrip) row.findViewById(R.id.sliding_tabs);
pager = (WrapContentHeightViewPager) row.findViewById(R.id.pager);
}
if (tabLayout != null) {
pager.setAdapter(getPagerAdapter(tabLayout, getItem(position)));
pager.setOffscreenPageLimit(2);
pager.setAdapter(getPagerAdapter(tabLayout, getItem(position)));
if (create) {
tabLayout.setViewPager(pager);
} else {
tabLayout.notifyDataSetChanged(true);
}
return row;
}
}
@ -277,7 +530,7 @@ public class TrackSegmentFragment extends SelectedGPXFragment {
switch (tabType) {
case GPX_TAB_ITEM_GENERAL:
if (analysis != null) {
List<ILineDataSet> dataSets = new ArrayList<>();
List<ILineDataSet> dataSets = new LinkedList<>();
if (analysis.elevationData != null || analysis.isSpeedSpecified()) {
GpxUiHelper.setupGPXChart(app, chart, 4);
OrderedLineDataSet speedDataSet = null;
@ -526,4 +779,55 @@ public class TrackSegmentFragment extends SelectedGPXFragment {
chart.highlightValue(gpxItem.chartHighlightPos, 0);
}
}
class SplitTrackAsyncTask extends AsyncTask<Void, Void, Void> {
@Nullable
private final SelectedGpxFile mSelectedGpxFile;
@NonNull private final SelectedGPXFragment mFragment;
@NonNull private final TrackActivity mActivity;
private final List<GpxDisplayGroup> groups;
SplitTrackAsyncTask(@Nullable SelectedGpxFile selectedGpxFile,
@NonNull SelectedGPXFragment fragment,
@NonNull TrackActivity activity,
List<GpxDisplayGroup> groups) {
mSelectedGpxFile = selectedGpxFile;
mFragment = fragment;
mActivity = activity;
this.groups = groups;
}
protected void onPostExecute(Void result) {
if (mSelectedGpxFile != null) {
mSelectedGpxFile.setDisplayGroups(filterGroups(null, mActivity, mFragment.getArguments()));
}
if (mFragment.isVisible()) {
mFragment.updateContent();
}
if (!mActivity.isFinishing()) {
mActivity.setProgressBarIndeterminateVisibility(false);
}
}
protected void onPreExecute() {
mActivity.setProgressBarIndeterminateVisibility(true);
}
@Override
protected Void doInBackground(Void... params) {
for (GpxDisplayGroup model : groups) {
OsmandApplication application = mActivity.getMyApplication();
if (selectedSplitInterval == 0) {
model.noSplit(application);
} else if (distanceSplit.get(selectedSplitInterval) > 0) {
model.splitByDistance(application, distanceSplit.get(selectedSplitInterval));
} else if (timeSplit.get(selectedSplitInterval) > 0) {
model.splitByTime(application, timeSplit.get(selectedSplitInterval));
}
}
return null;
}
}
}

View file

@ -23,6 +23,7 @@ import net.osmand.data.PointDescription;
import net.osmand.data.QuadRect;
import net.osmand.data.QuadTree;
import net.osmand.data.RotatedTileBox;
import net.osmand.plus.GPXDatabase.GpxDataItem;
import net.osmand.plus.GPXUtilities;
import net.osmand.plus.GPXUtilities.GPXFile;
import net.osmand.plus.GPXUtilities.TrkSegment;
@ -367,8 +368,13 @@ public class GPXLayer extends OsmandMapLayer implements ContextMenuLayer.IContex
List<SelectedGpxFile> selectedGPXFiles, DrawSettings settings) {
for (SelectedGpxFile g : selectedGPXFiles) {
GpxDataItem gpxDataItem = view.getApplication().getGpxDatabase().getItem(new File(g.getGpxFile().path));
List<TrkSegment> segments = g.getPointsToDisplay();
for (TrkSegment ts : segments) {
int color = gpxDataItem.getColor();
if (color == 0) {
color = ts.getColor(cachedColor);
}
if (ts.renders.isEmpty() // only do once (CODE HERE NEEDS TO BE UI INSTEAD)
&& !ts.points.isEmpty()) { // hmmm. 0-point tracks happen, but.... how?
if (g.isShowCurrentTrack()) {
@ -377,7 +383,7 @@ public class GPXLayer extends OsmandMapLayer implements ContextMenuLayer.IContex
ts.renders.add(new Renderable.StandardTrack(ts.points, 17.2));
}
}
updatePaints(ts.getColor(cachedColor), g.isRoutePoints(), g.isShowCurrentTrack(), settings, tileBox);
updatePaints(color, g.isRoutePoints(), g.isShowCurrentTrack(), settings, tileBox);
ts.drawRenderers(view.getZoom(), paint, canvas, tileBox);
}
}

View file

@ -247,10 +247,10 @@ public class PagerSlidingTabStrip extends HorizontalScrollView {
pager.setOnPageChangeListener(pageListener);
pager.getAdapter().registerDataSetObserver(adapterObserver);
adapterObserver.setAttached(true);
notifyDataSetChanged();
notifyDataSetChanged(false);
}
public void notifyDataSetChanged() {
public void notifyDataSetChanged(boolean forced) {
tabsContainer.removeAllViews();
tabCount = pager.getAdapter().getCount();
View tabView;
@ -266,27 +266,34 @@ public class PagerSlidingTabStrip extends HorizontalScrollView {
addTab(i, title, tabView);
}
updateTabStyles();
getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
@SuppressWarnings("deprecation")
@SuppressLint("NewApi")
@Override
public void onGlobalLayout() {
if (forced) {
currentPosition = pager.getCurrentItem();
currentPositionOffset = 0f;
scrollToChild(currentPosition, 0);
updateSelection(currentPosition);
} else {
getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
getViewTreeObserver().removeGlobalOnLayoutListener(this);
} else {
getViewTreeObserver().removeOnGlobalLayoutListener(this);
@SuppressWarnings("deprecation")
@SuppressLint("NewApi")
@Override
public void onGlobalLayout() {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
getViewTreeObserver().removeGlobalOnLayoutListener(this);
} else {
getViewTreeObserver().removeOnGlobalLayoutListener(this);
}
currentPosition = pager.getCurrentItem();
currentPositionOffset = 0f;
scrollToChild(currentPosition, 0);
updateSelection(currentPosition);
}
currentPosition = pager.getCurrentItem();
currentPositionOffset = 0f;
scrollToChild(currentPosition, 0);
updateSelection(currentPosition);
}
});
});
}
}
private void addTab(final int position, CharSequence title, View tabView) {
@ -584,7 +591,7 @@ public class PagerSlidingTabStrip extends HorizontalScrollView {
@Override
public void onChanged() {
notifyDataSetChanged();
notifyDataSetChanged(false);
}
public void setAttached(boolean attached) {
@ -612,7 +619,11 @@ public class PagerSlidingTabStrip extends HorizontalScrollView {
super.onDetachedFromWindow();
if (pager != null) {
if (adapterObserver.isAttached()) {
pager.getAdapter().unregisterDataSetObserver(adapterObserver);
try {
pager.getAdapter().unregisterDataSetObserver(adapterObserver);
} catch (IllegalStateException e) {
//ignore
}
adapterObserver.setAttached(false);
}
}