Merge pull request #11242 from osmandapp/trip_recording_graphs_dynamic_update

Trip recording graphs (add dynamic update)
This commit is contained in:
Vitaliy 2021-03-29 22:18:15 +03:00 committed by GitHub
commit 211cc78189
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 298 additions and 154 deletions

View file

@ -48,9 +48,9 @@ import net.osmand.plus.activities.SavingTrackHelper;
import net.osmand.plus.base.MenuBottomSheetDialogFragment; import net.osmand.plus.base.MenuBottomSheetDialogFragment;
import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem; import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem;
import net.osmand.plus.helpers.AndroidUiHelper; import net.osmand.plus.helpers.AndroidUiHelper;
import net.osmand.plus.helpers.GpxUiHelper;
import net.osmand.plus.mapcontextmenu.other.TrackChartPoints; import net.osmand.plus.mapcontextmenu.other.TrackChartPoints;
import net.osmand.plus.myplaces.GPXItemPagerAdapter; import net.osmand.plus.myplaces.GPXItemPagerAdapter;
import net.osmand.plus.myplaces.GPXTabItemType;
import net.osmand.plus.myplaces.SegmentActionsListener; import net.osmand.plus.myplaces.SegmentActionsListener;
import net.osmand.plus.myplaces.SegmentGPXAdapter; import net.osmand.plus.myplaces.SegmentGPXAdapter;
import net.osmand.plus.settings.backend.OsmandSettings; import net.osmand.plus.settings.backend.OsmandSettings;
@ -71,18 +71,19 @@ import java.util.List;
import static net.osmand.AndroidUtils.getSecondaryTextColorId; import static net.osmand.AndroidUtils.getSecondaryTextColorId;
import static net.osmand.AndroidUtils.setPadding; import static net.osmand.AndroidUtils.setPadding;
import static net.osmand.plus.UiUtilities.CompoundButtonType.GLOBAL; import static net.osmand.plus.UiUtilities.CompoundButtonType.GLOBAL;
import static net.osmand.plus.track.GpxBlockStatisticsBuilder.INIT_BLOCKS_ALTITUDE; import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_ALTITUDE;
import static net.osmand.plus.track.GpxBlockStatisticsBuilder.INIT_BLOCKS_GENERAL; import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_GENERAL;
import static net.osmand.plus.track.GpxBlockStatisticsBuilder.INIT_BLOCKS_SPEED; import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_SPEED;
public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment implements SegmentActionsListener { public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment implements SegmentActionsListener {
public static final String TAG = TripRecordingBottomSheet.class.getSimpleName(); public static final String TAG = TripRecordingBottomSheet.class.getSimpleName();
private static final Log LOG = PlatformUtil.getLog(TripRecordingBottomSheet.class); private static final Log LOG = PlatformUtil.getLog(TripRecordingBottomSheet.class);
public static final String UPDATE_TRACK_ICON = "update_track_icon"; public static final String UPDATE_TRACK_ICON = "update_track_icon";
public static final String UPDATE_DYNAMIC_ITEMS = "update_dynamic_items";
private static final int GPS_UPDATE_INTERVAL = 1000; private static final int GPS_UPDATE_INTERVAL = 1000;
private static final String[] INIT_BLOCKS_KEYS = public static final GPXTabItemType[] INIT_TAB_ITEMS =
new String[]{INIT_BLOCKS_GENERAL, INIT_BLOCKS_ALTITUDE, INIT_BLOCKS_SPEED}; new GPXTabItemType[]{GPX_TAB_ITEM_GENERAL, GPX_TAB_ITEM_ALTITUDE, GPX_TAB_ITEM_SPEED};
private OsmandApplication app; private OsmandApplication app;
private OsmandSettings settings; private OsmandSettings settings;
@ -91,16 +92,17 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
private View statusContainer; private View statusContainer;
private AppCompatImageView trackAppearanceIcon; private AppCompatImageView trackAppearanceIcon;
private LinearLayout segmentsContainer;
private TrackDisplayHelper displayHelper;
private TrackChartPoints trackChartPoints; private TrackChartPoints trackChartPoints;
private GPXItemPagerAdapter graphsAdapter; private GPXItemPagerAdapter graphsAdapter;
private int graphTabPosition = 0;
private ViewGroup segmentsTabs;
private GpxBlockStatisticsBuilder blockStatisticsBuilder; private GpxBlockStatisticsBuilder blockStatisticsBuilder;
private SelectedGpxFile selectedGpxFile; private SelectedGpxFile selectedGpxFile;
private final Handler handler = new Handler(); private final Handler handler = new Handler();
private Runnable updatingGPS; private Runnable updatingGPS;
private Runnable updatingGraph;
private GPXFile getGPXFile() { private GPXFile getGPXFile() {
return selectedGpxFile.getGpxFile(); return selectedGpxFile.getGpxFile();
@ -153,14 +155,14 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
} }
}); });
segmentsContainer = itemView.findViewById(R.id.segments_container); segmentsTabs = itemView.findViewById(R.id.segments_container);
createSegmentsTabs(segmentsContainer); createSegmentsTabs(segmentsTabs);
RecyclerView statBlocks = itemView.findViewById(R.id.block_statistics); RecyclerView statBlocks = itemView.findViewById(R.id.block_statistics);
blockStatisticsBuilder = new GpxBlockStatisticsBuilder(app, selectedGpxFile, nightMode); blockStatisticsBuilder = new GpxBlockStatisticsBuilder(app, selectedGpxFile, nightMode);
blockStatisticsBuilder.setBlocksView(statBlocks); blockStatisticsBuilder.setBlocksView(statBlocks);
blockStatisticsBuilder.setBlocksClickable(false); blockStatisticsBuilder.setBlocksClickable(false);
blockStatisticsBuilder.setInitBlocksKey(INIT_BLOCKS_GENERAL); blockStatisticsBuilder.setTabItem(GPX_TAB_ITEM_GENERAL);
blockStatisticsBuilder.initStatBlocks(null, blockStatisticsBuilder.initStatBlocks(null,
ContextCompat.getColor(app, getActiveTextColorId(nightMode))); ContextCompat.getColor(app, getActiveTextColorId(nightMode)));
@ -181,8 +183,10 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
boolean wasTrackMonitored = !wasTrackMonitored(); boolean wasTrackMonitored = !wasTrackMonitored();
if (!wasTrackMonitored) { if (!wasTrackMonitored) {
blockStatisticsBuilder.stopUpdatingStatBlocks(); blockStatisticsBuilder.stopUpdatingStatBlocks();
stopUpdatingGraph();
} else { } else {
blockStatisticsBuilder.runUpdatingStatBlocksIfNeeded(); blockStatisticsBuilder.runUpdatingStatBlocksIfNeeded();
runUpdatingGraph();
} }
settings.SAVE_GLOBAL_TRACK_TO_GPX.set(wasTrackMonitored); settings.SAVE_GLOBAL_TRACK_TO_GPX.set(wasTrackMonitored);
updateStatus(); updateStatus();
@ -222,6 +226,7 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
super.onResume(); super.onResume();
blockStatisticsBuilder.runUpdatingStatBlocksIfNeeded(); blockStatisticsBuilder.runUpdatingStatBlocksIfNeeded();
runUpdatingGPS(); runUpdatingGPS();
runUpdatingGraph();
MapActivity mapActivity = getMapActivity(); MapActivity mapActivity = getMapActivity();
if (mapActivity != null) { if (mapActivity != null) {
mapActivity.getMapLayers().getGpxLayer().setTrackChartPoints(trackChartPoints); mapActivity.getMapLayers().getGpxLayer().setTrackChartPoints(trackChartPoints);
@ -233,6 +238,7 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
super.onPause(); super.onPause();
blockStatisticsBuilder.stopUpdatingStatBlocks(); blockStatisticsBuilder.stopUpdatingStatBlocks();
stopUpdatingGPS(); stopUpdatingGPS();
stopUpdatingGraph();
MapActivity mapActivity = getMapActivity(); MapActivity mapActivity = getMapActivity();
if (mapActivity != null) { if (mapActivity != null) {
mapActivity.getMapLayers().getGpxLayer().setTrackChartPoints(null); mapActivity.getMapLayers().getGpxLayer().setTrackChartPoints(null);
@ -248,6 +254,10 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
if (key.equals(UPDATE_TRACK_ICON)) { if (key.equals(UPDATE_TRACK_ICON)) {
updateTrackIcon(app, trackAppearanceIcon); updateTrackIcon(app, trackAppearanceIcon);
} }
if (key.equals(UPDATE_DYNAMIC_ITEMS)) {
blockStatisticsBuilder.restartUpdatingStatBlocks();
restartUpdatingGraph();
}
} }
} }
@ -258,11 +268,11 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
} }
} }
public void stopUpdatingGPS() { private void stopUpdatingGPS() {
handler.removeCallbacks(updatingGPS); handler.removeCallbacks(updatingGPS);
} }
public void runUpdatingGPS() { private void runUpdatingGPS() {
updatingGPS = new Runnable() { updatingGPS = new Runnable() {
@Override @Override
public void run() { public void run() {
@ -274,27 +284,30 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
handler.post(updatingGPS); handler.post(updatingGPS);
} }
private void recreateStatBlocks(String initBlocksKey) { private void stopUpdatingGraph() {
blockStatisticsBuilder.stopUpdatingStatBlocks(); handler.removeCallbacks(updatingGraph);
blockStatisticsBuilder.setInitBlocksKey(initBlocksKey);
blockStatisticsBuilder.runUpdatingStatBlocksIfNeeded();
} }
private void setupDisplayHelper() { private void runUpdatingGraph() {
displayHelper = new TrackDisplayHelper(app); updatingGraph = new Runnable() {
if (!selectedGpxFile.isShowCurrentTrack()) { @Override
File file = new File(getGPXFile().path); public void run() {
displayHelper.setFile(file); int interval = app.getSettings().SAVE_GLOBAL_TRACK_INTERVAL.get();
displayHelper.setGpxDataItem(app.getGpxDbHelper().getItem(file)); graphsAdapter.updateGraph(graphTabPosition);
} AndroidUiHelper.updateVisibility(segmentsTabs, graphsAdapter.isTabsVisible());
displayHelper.setGpx(getGPXFile()); handler.postDelayed(this, Math.max(GPS_UPDATE_INTERVAL, interval));
}
};
handler.post(updatingGraph);
}
private void restartUpdatingGraph() {
stopUpdatingGraph();
runUpdatingGraph();
} }
private void createSegmentsTabs(ViewGroup viewGroup) { private void createSegmentsTabs(ViewGroup viewGroup) {
viewGroup.removeAllViews(); View segmentView = SegmentGPXAdapter.createGpxTabsView(null, viewGroup, this, nightMode);
setupDisplayHelper();
View segmentView = SegmentGPXAdapter.createGpxTabsView(displayHelper, viewGroup, this, nightMode);
AndroidUiHelper.setVisibility(View.GONE, segmentView.findViewById(R.id.list_item_divider)); AndroidUiHelper.setVisibility(View.GONE, segmentView.findViewById(R.id.list_item_divider));
WrapContentHeightViewPager pager = segmentView.findViewById(R.id.pager); WrapContentHeightViewPager pager = segmentView.findViewById(R.id.pager);
PagerSlidingTabStrip tabLayout = segmentView.findViewById(R.id.sliding_tabs); PagerSlidingTabStrip tabLayout = segmentView.findViewById(R.id.sliding_tabs);
@ -304,17 +317,26 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
tabLayout.setOnTabReselectedListener(new PagerSlidingTabStrip.OnTabReselectedListener() { tabLayout.setOnTabReselectedListener(new PagerSlidingTabStrip.OnTabReselectedListener() {
@Override @Override
public void onTabSelected(int position) { public void onTabSelected(int position) {
recreateStatBlocks(INIT_BLOCKS_KEYS[position]); graphTabPosition = position;
blockStatisticsBuilder.setTabItem(INIT_TAB_ITEMS[graphTabPosition]);
blockStatisticsBuilder.restartUpdatingStatBlocks();
} }
@Override @Override
public void onTabReselected(int position) { public void onTabReselected(int position) {
recreateStatBlocks(INIT_BLOCKS_KEYS[position]); graphTabPosition = position;
blockStatisticsBuilder.setTabItem(INIT_TAB_ITEMS[graphTabPosition]);
} }
}); });
graphsAdapter = new GPXItemPagerAdapter(app, GpxUiHelper.makeGpxDisplayItem(app, TrackDisplayHelper displayHelper = new TrackDisplayHelper(app);
displayHelper.getGpx()), displayHelper, nightMode, this, true); GPXFile gpxFile = getGPXFile();
File file = new File(gpxFile.path);
displayHelper.setFile(file);
displayHelper.setGpxDataItem(app.getGpxDbHelper().getItem(file));
displayHelper.setGpx(gpxFile);
graphsAdapter = new GPXItemPagerAdapter(app, null, displayHelper, nightMode, this, true);
graphsAdapter.setChartHMargin(getResources().getDimensionPixelSize(R.dimen.content_padding)); graphsAdapter.setChartHMargin(getResources().getDimensionPixelSize(R.dimen.content_padding));
pager.setAdapter(graphsAdapter); pager.setAdapter(graphsAdapter);
@ -596,7 +618,7 @@ public class TripRecordingBottomSheet extends MenuBottomSheetDialogFragment impl
public void onPointSelected(TrkSegment segment, double lat, double lon) { public void onPointSelected(TrkSegment segment, double lat, double lon) {
if (trackChartPoints == null) { if (trackChartPoints == null) {
trackChartPoints = new TrackChartPoints(); trackChartPoints = new TrackChartPoints();
trackChartPoints.setGpx(displayHelper.getGpx()); trackChartPoints.setGpx(getGPXFile());
} }
MapActivity mapActivity = getMapActivity(); MapActivity mapActivity = getMapActivity();
if (mapActivity != null) { if (mapActivity != null) {

View file

@ -11,6 +11,7 @@ import net.osmand.plus.base.MenuBottomSheetDialogFragment;
import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem; import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem;
import net.osmand.plus.base.bottomsheetmenu.BottomSheetItemWithDescription; import net.osmand.plus.base.bottomsheetmenu.BottomSheetItemWithDescription;
import net.osmand.plus.base.bottomsheetmenu.simpleitems.DividerSpaceItem; import net.osmand.plus.base.bottomsheetmenu.simpleitems.DividerSpaceItem;
import net.osmand.plus.monitoring.TripRecordingBottomSheet.DismissTargetFragment;
import net.osmand.plus.monitoring.TripRecordingBottomSheet.ItemType; import net.osmand.plus.monitoring.TripRecordingBottomSheet.ItemType;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
@ -18,8 +19,9 @@ import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager; import androidx.fragment.app.FragmentManager;
import static net.osmand.AndroidUtils.getPrimaryTextColorId; import static net.osmand.AndroidUtils.getPrimaryTextColorId;
import static net.osmand.plus.monitoring.TripRecordingOptionsBottomSheet.ACTION_CLEAR_DATA;
public class TripRecordingClearDataBottomSheet extends MenuBottomSheetDialogFragment implements TripRecordingBottomSheet.DismissTargetFragment { public class TripRecordingClearDataBottomSheet extends MenuBottomSheetDialogFragment implements DismissTargetFragment {
public static final String TAG = TripRecordingClearDataBottomSheet.class.getSimpleName(); public static final String TAG = TripRecordingClearDataBottomSheet.class.getSimpleName();
@ -111,6 +113,14 @@ public class TripRecordingClearDataBottomSheet extends MenuBottomSheetDialogFrag
public void dismissTarget() { public void dismissTarget() {
Fragment target = getTargetFragment(); Fragment target = getTargetFragment();
if (target instanceof TripRecordingOptionsBottomSheet) { if (target instanceof TripRecordingOptionsBottomSheet) {
Bundle args = target.getArguments();
if (args != null) {
args.putBoolean(ACTION_CLEAR_DATA, true);
} else {
args = new Bundle();
args.putBoolean(ACTION_CLEAR_DATA, true);
target.setArguments(args);
}
((TripRecordingOptionsBottomSheet) target).dismiss(); ((TripRecordingOptionsBottomSheet) target).dismiss();
} }
} }

View file

@ -12,6 +12,7 @@ import net.osmand.plus.base.MenuBottomSheetDialogFragment;
import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem; import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem;
import net.osmand.plus.base.bottomsheetmenu.BottomSheetItemWithDescription; import net.osmand.plus.base.bottomsheetmenu.BottomSheetItemWithDescription;
import net.osmand.plus.base.bottomsheetmenu.simpleitems.DividerSpaceItem; import net.osmand.plus.base.bottomsheetmenu.simpleitems.DividerSpaceItem;
import net.osmand.plus.monitoring.TripRecordingBottomSheet.DismissTargetFragment;
import net.osmand.plus.monitoring.TripRecordingBottomSheet.ItemType; import net.osmand.plus.monitoring.TripRecordingBottomSheet.ItemType;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
@ -21,7 +22,7 @@ import androidx.fragment.app.FragmentManager;
import static net.osmand.AndroidUtils.getPrimaryTextColorId; import static net.osmand.AndroidUtils.getPrimaryTextColorId;
import static net.osmand.plus.monitoring.TripRecordingOptionsBottomSheet.ACTION_STOP_AND_DISMISS; import static net.osmand.plus.monitoring.TripRecordingOptionsBottomSheet.ACTION_STOP_AND_DISMISS;
public class TripRecordingDiscardBottomSheet extends MenuBottomSheetDialogFragment implements TripRecordingBottomSheet.DismissTargetFragment { public class TripRecordingDiscardBottomSheet extends MenuBottomSheetDialogFragment implements DismissTargetFragment {
public static final String TAG = TripRecordingDiscardBottomSheet.class.getSimpleName(); public static final String TAG = TripRecordingDiscardBottomSheet.class.getSimpleName();
@ -67,10 +68,15 @@ public class TripRecordingDiscardBottomSheet extends MenuBottomSheetDialogFragme
dismiss(); dismiss();
Fragment target = getTargetFragment(); Fragment target = getTargetFragment();
if (target != null) { if (target instanceof TripRecordingOptionsBottomSheet) {
Bundle args = new Bundle(); Bundle args = target.getArguments();
args.putBoolean(ACTION_STOP_AND_DISMISS, true); if (args != null) {
target.setArguments(args); args.putBoolean(ACTION_STOP_AND_DISMISS, true);
} else {
args = new Bundle();
args.putBoolean(ACTION_STOP_AND_DISMISS, true);
target.setArguments(args);
}
} }
dismissTarget(); dismissTarget();
} }

View file

@ -26,7 +26,7 @@ import net.osmand.plus.base.MenuBottomSheetDialogFragment;
import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem; import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem;
import net.osmand.plus.base.bottomsheetmenu.SimpleBottomSheetItem; import net.osmand.plus.base.bottomsheetmenu.SimpleBottomSheetItem;
import net.osmand.plus.base.bottomsheetmenu.simpleitems.DividerSpaceItem; import net.osmand.plus.base.bottomsheetmenu.simpleitems.DividerSpaceItem;
import net.osmand.plus.helpers.AndroidUiHelper; import net.osmand.plus.monitoring.TripRecordingBottomSheet.DismissTargetFragment;
import net.osmand.plus.monitoring.TripRecordingBottomSheet.ItemType; import net.osmand.plus.monitoring.TripRecordingBottomSheet.ItemType;
import net.osmand.plus.myplaces.SaveCurrentTrackTask; import net.osmand.plus.myplaces.SaveCurrentTrackTask;
import net.osmand.plus.settings.backend.OsmandSettings; import net.osmand.plus.settings.backend.OsmandSettings;
@ -34,11 +34,13 @@ import net.osmand.plus.track.SaveGpxAsyncTask.SaveGpxListener;
import net.osmand.util.Algorithms; import net.osmand.util.Algorithms;
import static net.osmand.AndroidUtils.getPrimaryTextColorId; import static net.osmand.AndroidUtils.getPrimaryTextColorId;
import static net.osmand.plus.monitoring.TripRecordingBottomSheet.UPDATE_DYNAMIC_ITEMS;
public class TripRecordingOptionsBottomSheet extends MenuBottomSheetDialogFragment implements TripRecordingBottomSheet.DismissTargetFragment { public class TripRecordingOptionsBottomSheet extends MenuBottomSheetDialogFragment implements DismissTargetFragment {
public static final String TAG = TripRecordingOptionsBottomSheet.class.getSimpleName(); public static final String TAG = TripRecordingOptionsBottomSheet.class.getSimpleName();
public static final String ACTION_STOP_AND_DISMISS = "action_stop_and_discard"; public static final String ACTION_STOP_AND_DISMISS = "action_stop_and_discard";
public static final String ACTION_CLEAR_DATA = "action_clear_data";
private static final int SAVE_UPDATE_INTERVAL = 1000; private static final int SAVE_UPDATE_INTERVAL = 1000;
private OsmandApplication app; private OsmandApplication app;
@ -210,8 +212,10 @@ public class TripRecordingOptionsBottomSheet extends MenuBottomSheetDialogFragme
@Override @Override
public void run() { public void run() {
String time = getTimeTrackSaved(); String time = getTimeTrackSaved();
TripRecordingBottomSheet.createItem(app, nightMode, buttonSave, ItemType.SAVE, hasDataToSave(), !Algorithms.isEmpty(time) ? time : null); TripRecordingBottomSheet.createItem(app, nightMode, buttonSave, ItemType.SAVE,
TripRecordingBottomSheet.createItem(app, nightMode, buttonClear, ItemType.CLEAR_DATA, hasDataToSave(), null); hasDataToSave(), !Algorithms.isEmpty(time) ? time : null);
TripRecordingBottomSheet.createItem(app, nightMode, buttonClear, ItemType.CLEAR_DATA,
hasDataToSave(), null);
handler.postDelayed(this, SAVE_UPDATE_INTERVAL); handler.postDelayed(this, SAVE_UPDATE_INTERVAL);
} }
}; };
@ -255,9 +259,14 @@ public class TripRecordingOptionsBottomSheet extends MenuBottomSheetDialogFragme
if (mapActivity != null && plugin != null) { if (mapActivity != null && plugin != null) {
stopUpdatingTimeTrackSaved(); stopUpdatingTimeTrackSaved();
plugin.saveCurrentTrack(null, mapActivity, false, true); plugin.saveCurrentTrack(null, mapActivity, false, true);
Bundle args = new Bundle(); Bundle args = getArguments();
args.putBoolean(ACTION_STOP_AND_DISMISS, true); if (args != null) {
setArguments(args); args.putBoolean(ACTION_STOP_AND_DISMISS, true);
} else {
args = new Bundle();
args.putBoolean(ACTION_STOP_AND_DISMISS, true);
setArguments(args);
}
dismiss(); dismiss();
dismissTarget(); dismissTarget();
} }
@ -273,12 +282,22 @@ public class TripRecordingOptionsBottomSheet extends MenuBottomSheetDialogFragme
return false; return false;
} }
private boolean isCleared() {
Bundle args = getArguments();
if (args != null) {
return args.getBoolean(ACTION_CLEAR_DATA);
}
return false;
}
@Override @Override
public void dismissTarget() { public void dismissTarget() {
Fragment target = getTargetFragment(); Fragment target = getTargetFragment();
if (target instanceof TripRecordingBottomSheet) { if (target instanceof TripRecordingBottomSheet) {
if (isDiscard()) { if (isDiscard()) {
((TripRecordingBottomSheet) target).dismiss(); ((TripRecordingBottomSheet) target).dismiss();
} else if (isCleared()) {
((TripRecordingBottomSheet) target).show(UPDATE_DYNAMIC_ITEMS);
} else { } else {
((TripRecordingBottomSheet) target).show(); ((TripRecordingBottomSheet) target).show();
} }

View file

@ -12,6 +12,7 @@ import android.widget.ImageView;
import android.widget.TextView; import android.widget.TextView;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.widget.SwitchCompat; import androidx.appcompat.widget.SwitchCompat;
import androidx.viewpager.widget.PagerAdapter; import androidx.viewpager.widget.PagerAdapter;
@ -33,6 +34,7 @@ import net.osmand.GPXUtilities.TrkSegment;
import net.osmand.GPXUtilities.WptPt; import net.osmand.GPXUtilities.WptPt;
import net.osmand.plus.GPXDatabase.GpxDataItem; import net.osmand.plus.GPXDatabase.GpxDataItem;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItem; import net.osmand.plus.GpxSelectionHelper.GpxDisplayItem;
import net.osmand.plus.GpxSelectionHelper.SelectedGpxFile;
import net.osmand.plus.OsmAndFormatter; import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.OsmandApplication; import net.osmand.plus.OsmandApplication;
import net.osmand.plus.R; import net.osmand.plus.R;
@ -50,6 +52,7 @@ import net.osmand.plus.views.controls.WrapContentHeightViewPager.ViewAtPositionI
import net.osmand.util.Algorithms; import net.osmand.util.Algorithms;
import net.osmand.util.MapUtils; import net.osmand.util.MapUtils;
import java.io.File;
import java.text.DateFormat; import java.text.DateFormat;
import java.text.SimpleDateFormat; import java.text.SimpleDateFormat;
import java.util.ArrayList; import java.util.ArrayList;
@ -63,10 +66,13 @@ import static net.osmand.plus.helpers.GpxUiHelper.LineGraphType.ALTITUDE;
import static net.osmand.plus.helpers.GpxUiHelper.LineGraphType.SLOPE; import static net.osmand.plus.helpers.GpxUiHelper.LineGraphType.SLOPE;
import static net.osmand.plus.helpers.GpxUiHelper.LineGraphType.SPEED; import static net.osmand.plus.helpers.GpxUiHelper.LineGraphType.SPEED;
import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_ALTITUDE; import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_ALTITUDE;
import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_GENERAL;
import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_SPEED; import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_SPEED;
public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvider, ViewAtPositionInterface { public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvider, ViewAtPositionInterface {
private static final int CHART_LABEL_COUNT = 4;
private OsmandApplication app; private OsmandApplication app;
private UiUtilities iconsCache; private UiUtilities iconsCache;
private TrackDisplayHelper displayHelper; private TrackDisplayHelper displayHelper;
@ -75,6 +81,7 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
private WptPt selectedWpt; private WptPt selectedWpt;
private TrkSegment segment; private TrkSegment segment;
private GpxDisplayItem gpxItem; private GpxDisplayItem gpxItem;
private GPXTrackAnalysis analysis;
private GPXTabItemType[] tabTypes; private GPXTabItemType[] tabTypes;
private SparseArray<View> views = new SparseArray<>(); private SparseArray<View> views = new SparseArray<>();
@ -89,8 +96,12 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
this.chartHMargin = chartHMargin; this.chartHMargin = chartHMargin;
} }
private boolean isShowCurrentTrack() {
return displayHelper.getGpx() != null && displayHelper.getGpx().showCurrentTrack;
}
public GPXItemPagerAdapter(@NonNull OsmandApplication app, public GPXItemPagerAdapter(@NonNull OsmandApplication app,
@NonNull GpxDisplayItem gpxItem, @Nullable GpxDisplayItem gpxItem,
@NonNull TrackDisplayHelper displayHelper, @NonNull TrackDisplayHelper displayHelper,
boolean nightMode, boolean nightMode,
@NonNull SegmentActionsListener actionsListener, @NonNull SegmentActionsListener actionsListener,
@ -98,22 +109,45 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
super(); super();
this.app = app; this.app = app;
this.gpxItem = gpxItem; this.gpxItem = gpxItem;
this.nightMode = nightMode;
this.displayHelper = displayHelper; this.displayHelper = displayHelper;
this.nightMode = nightMode;
this.actionsListener = actionsListener; this.actionsListener = actionsListener;
this.onlyGraphs = onlyGraphs; this.onlyGraphs = onlyGraphs;
iconsCache = app.getUIUtilities(); iconsCache = app.getUIUtilities();
updateAnalysis();
fetchTabTypes(); fetchTabTypes();
} }
private void updateAnalysis() {
analysis = null;
if (isShowCurrentTrack()) {
GPXFile gpxFile = displayHelper.getGpx();
if (gpxFile != null && !gpxFile.isEmpty()) {
analysis = gpxFile.getAnalysis(0);
gpxItem = GpxUiHelper.makeGpxDisplayItem(app, gpxFile);
}
} else {
if (gpxItem != null) {
analysis = gpxItem.analysis;
}
}
}
private void fetchTabTypes() { private void fetchTabTypes() {
List<GPXTabItemType> tabTypeList = new ArrayList<>(); List<GPXTabItemType> tabTypeList = new ArrayList<>();
tabTypeList.add(GPXTabItemType.GPX_TAB_ITEM_GENERAL); if (isShowCurrentTrack()) {
if (gpxItem != null && gpxItem.analysis != null) { if (analysis != null && (analysis.hasElevationData || analysis.hasSpeedData)) {
if (gpxItem.analysis.hasElevationData) { tabTypeList.add(GPXTabItemType.GPX_TAB_ITEM_GENERAL);
}
} else {
tabTypeList.add(GPXTabItemType.GPX_TAB_ITEM_GENERAL);
}
if (analysis != null) {
if (analysis.hasElevationData) {
tabTypeList.add(GPX_TAB_ITEM_ALTITUDE); tabTypeList.add(GPX_TAB_ITEM_ALTITUDE);
} }
if (gpxItem.analysis.isSpeedSpecified()) { if (analysis.isSpeedSpecified()) {
tabTypeList.add(GPX_TAB_ITEM_SPEED); tabTypeList.add(GPX_TAB_ITEM_SPEED);
} }
} }
@ -123,11 +157,20 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
private List<ILineDataSet> getDataSets(LineChart chart, GPXTabItemType tabType, private List<ILineDataSet> getDataSets(LineChart chart, GPXTabItemType tabType,
LineGraphType firstType, LineGraphType secondType) { LineGraphType firstType, LineGraphType secondType) {
List<ILineDataSet> dataSets = dataSetsMap.get(tabType); List<ILineDataSet> dataSets = dataSetsMap.get(tabType);
if (dataSets == null && chart != null) { boolean withoutGaps = true;
GPXTrackAnalysis analysis = gpxItem.analysis; if (isShowCurrentTrack()) {
GPXFile gpxFile = displayHelper.getGpx();
withoutGaps = !app.getSavingTrackHelper().getCurrentTrack().isJoinSegments() && gpxFile != null
&& (Algorithms.isEmpty(gpxFile.tracks) || gpxFile.tracks.get(0).generalTrack);
} else if (gpxItem != null) {
GpxDataItem gpxDataItem = displayHelper.getGpxDataItem(); GpxDataItem gpxDataItem = displayHelper.getGpxDataItem();
boolean calcWithoutGaps = gpxItem.isGeneralTrack() && gpxDataItem != null && !gpxDataItem.isJoinSegments(); withoutGaps = gpxItem.isGeneralTrack() && gpxDataItem != null && !gpxDataItem.isJoinSegments();
dataSets = GpxUiHelper.getDataSets(chart, app, analysis, firstType, secondType, calcWithoutGaps); }
if (chart != null && analysis != null) {
dataSets = GpxUiHelper.getDataSets(chart, app, analysis, firstType, secondType, withoutGaps);
if (!Algorithms.isEmpty(dataSets)) {
dataSetsMap.remove(tabType);
}
dataSetsMap.put(tabType, dataSets); dataSetsMap.put(tabType, dataSets);
} }
return dataSets; return dataSets;
@ -140,7 +183,7 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
if (ds != null && ds.size() > 0) { if (ds != null && ds.size() > 0) {
for (GPXUtilities.Track t : gpxItem.group.getGpx().tracks) { for (GPXUtilities.Track t : gpxItem.group.getGpx().tracks) {
for (TrkSegment s : t.segments) { for (TrkSegment s : t.segments) {
if (s.points.size() > 0 && s.points.get(0).equals(gpxItem.analysis.locationStart)) { if (s.points.size() > 0 && s.points.get(0).equals(analysis.locationStart)) {
segment = s; segment = s;
break; break;
} }
@ -164,7 +207,7 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
if (gpxItem.chartAxisType == GPXDataSetAxisType.TIME) { if (gpxItem.chartAxisType == GPXDataSetAxisType.TIME) {
float time = pos * 1000; float time = pos * 1000;
for (WptPt p : segment.points) { for (WptPt p : segment.points) {
if (p.time - gpxItem.analysis.startTime >= time) { if (p.time - analysis.startTime >= time) {
wpt = p; wpt = p;
break; break;
} }
@ -203,23 +246,20 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
public Object instantiateItem(@NonNull ViewGroup container, int position) { public Object instantiateItem(@NonNull ViewGroup container, int position) {
GPXTabItemType tabType = tabTypes[position]; GPXTabItemType tabType = tabTypes[position];
View view = getViewForTab(container, tabType); View view = getViewForTab(container, tabType);
GPXFile gpxFile = displayHelper.getGpx(); LineChart chart = view.findViewById(R.id.chart);
if (gpxFile != null && gpxItem != null) { ViewGroup.MarginLayoutParams lp = (ViewGroup.MarginLayoutParams) chart.getLayoutParams();
GPXTrackAnalysis analysis = gpxItem.analysis; AndroidUtils.setMargins(lp, chartHMargin, lp.topMargin, chartHMargin, lp.bottomMargin);
LineChart chart = view.findViewById(R.id.chart); if (analysis != null) {
ViewGroup.MarginLayoutParams lp = (ViewGroup.MarginLayoutParams) chart.getLayoutParams();
AndroidUtils.setMargins(lp, chartHMargin, lp.topMargin, chartHMargin, lp.bottomMargin);
setupChart(view, chart); setupChart(view, chart);
switch (tabType) { switch (tabType) {
case GPX_TAB_ITEM_GENERAL: case GPX_TAB_ITEM_GENERAL:
setupGeneralTab(view, chart, analysis, gpxFile, position); setupGeneralTab(view, chart, position);
break; break;
case GPX_TAB_ITEM_ALTITUDE: case GPX_TAB_ITEM_ALTITUDE:
setupAltitudeTab(view, chart, analysis, gpxFile, position); setupAltitudeTab(view, chart, position);
break; break;
case GPX_TAB_ITEM_SPEED: case GPX_TAB_ITEM_SPEED:
setupSpeedTab(view, chart, analysis, gpxFile, position); setupSpeedTab(view, chart, position);
break; break;
} }
} }
@ -252,10 +292,10 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
return view; return view;
} }
private void setupSpeedTab(View view, LineChart chart, GPXTrackAnalysis analysis, GPXFile gpxFile, int position) { private void setupSpeedTab(View view, LineChart chart, int position) {
if (analysis != null && analysis.isSpeedSpecified()) { if (analysis != null && analysis.isSpeedSpecified()) {
if (analysis.hasSpeedData) { if (analysis.hasSpeedData) {
GpxUiHelper.setupGPXChart(app, chart, 4); GpxUiHelper.setupGPXChart(app, chart, CHART_LABEL_COUNT);
chart.setData(new LineData(getDataSets(chart, GPX_TAB_ITEM_SPEED, SPEED, null))); chart.setData(new LineData(getDataSets(chart, GPX_TAB_ITEM_SPEED, SPEED, null)));
updateChart(chart); updateChart(chart);
chart.setVisibility(View.VISIBLE); chart.setVisibility(View.VISIBLE);
@ -324,10 +364,10 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
}); });
} }
private void setupAltitudeTab(View view, LineChart chart, GPXTrackAnalysis analysis, GPXFile gpxFile, int position) { private void setupAltitudeTab(View view, LineChart chart, int position) {
if (analysis != null) { if (analysis != null) {
if (analysis.hasElevationData) { if (analysis.hasElevationData) {
GpxUiHelper.setupGPXChart(app, chart, 4); GpxUiHelper.setupGPXChart(app, chart, CHART_LABEL_COUNT);
chart.setData(new LineData(getDataSets(chart, GPX_TAB_ITEM_ALTITUDE, ALTITUDE, SLOPE))); chart.setData(new LineData(getDataSets(chart, GPX_TAB_ITEM_ALTITUDE, ALTITUDE, SLOPE)));
updateChart(chart); updateChart(chart);
chart.setVisibility(View.VISIBLE); chart.setVisibility(View.VISIBLE);
@ -391,10 +431,10 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
} }
} }
private void setupGeneralTab(View view, LineChart chart, GPXTrackAnalysis analysis, GPXFile gpxFile, int position) { private void setupGeneralTab(View view, LineChart chart, int position) {
if (analysis != null) { if (analysis != null) {
if (analysis.hasElevationData || analysis.hasSpeedData) { if (analysis.hasElevationData || analysis.hasSpeedData) {
GpxUiHelper.setupGPXChart(app, chart, 4); GpxUiHelper.setupGPXChart(app, chart, CHART_LABEL_COUNT);
chart.setData(new LineData(getDataSets(chart, GPXTabItemType.GPX_TAB_ITEM_GENERAL, ALTITUDE, SPEED))); chart.setData(new LineData(getDataSets(chart, GPXTabItemType.GPX_TAB_ITEM_GENERAL, ALTITUDE, SPEED)));
updateChart(chart); updateChart(chart);
chart.setVisibility(View.VISIBLE); chart.setVisibility(View.VISIBLE);
@ -632,10 +672,12 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
@Override @Override
public void tabStylesUpdated(View tabsContainer, int currentPosition) { public void tabStylesUpdated(View tabsContainer, int currentPosition) {
ViewGroup.MarginLayoutParams params = (MarginLayoutParams) tabsContainer.getLayoutParams(); if (getCount() > 0) {
params.height = app.getResources().getDimensionPixelSize(!onlyGraphs ? R.dimen.dialog_button_height : R.dimen.context_menu_buttons_bottom_height); ViewGroup.MarginLayoutParams params = (MarginLayoutParams) tabsContainer.getLayoutParams();
tabsContainer.setLayoutParams(params); params.height = app.getResources().getDimensionPixelSize(!onlyGraphs ? R.dimen.dialog_button_height : R.dimen.context_menu_buttons_bottom_height);
UiUtilities.updateCustomRadioButtons(app, tabsContainer, nightMode, getCustomRadioButtonType(currentPosition)); tabsContainer.setLayoutParams(params);
UiUtilities.updateCustomRadioButtons(app, tabsContainer, nightMode, getCustomRadioButtonType(currentPosition));
}
} }
private CustomRadioButtonType getCustomRadioButtonType(int index) { private CustomRadioButtonType getCustomRadioButtonType(int index) {
@ -667,22 +709,22 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
void updateJoinGapsInfo(View view, int position) { void updateJoinGapsInfo(View view, int position) {
if (view != null) { if (view != null) {
GPXTrackAnalysis analysis = gpxItem.analysis;
GPXTabItemType tabType = tabTypes[position]; GPXTabItemType tabType = tabTypes[position];
boolean visible = gpxItem.isGeneralTrack() && analysis != null && tabType.equals(GPXTabItemType.GPX_TAB_ITEM_GENERAL); boolean generalTrack = gpxItem.isGeneralTrack();
AndroidUiHelper.updateVisibility(view.findViewById(R.id.gpx_join_gaps_container), visible);
boolean joinSegments = displayHelper.isJoinSegments(); boolean joinSegments = displayHelper.isJoinSegments();
boolean visible = generalTrack && analysis != null && tabType.equals(GPXTabItemType.GPX_TAB_ITEM_GENERAL);
AndroidUiHelper.updateVisibility(view.findViewById(R.id.gpx_join_gaps_container), visible);
((SwitchCompat) view.findViewById(R.id.gpx_join_gaps_switch)).setChecked(joinSegments); ((SwitchCompat) view.findViewById(R.id.gpx_join_gaps_switch)).setChecked(joinSegments);
if (analysis != null) { if (analysis != null) {
if (tabType.equals(GPXTabItemType.GPX_TAB_ITEM_GENERAL)) { if (tabType.equals(GPXTabItemType.GPX_TAB_ITEM_GENERAL)) {
float totalDistance = !joinSegments && gpxItem.isGeneralTrack() ? analysis.totalDistanceWithoutGaps : analysis.totalDistance; float totalDistance = !joinSegments && generalTrack ? analysis.totalDistanceWithoutGaps : analysis.totalDistance;
float timeSpan = !joinSegments && gpxItem.isGeneralTrack() ? analysis.timeSpanWithoutGaps : analysis.timeSpan; float timeSpan = !joinSegments && generalTrack ? analysis.timeSpanWithoutGaps : analysis.timeSpan;
((TextView) view.findViewById(R.id.distance_text)).setText(OsmAndFormatter.getFormattedDistance(totalDistance, app)); ((TextView) view.findViewById(R.id.distance_text)).setText(OsmAndFormatter.getFormattedDistance(totalDistance, app));
((TextView) view.findViewById(R.id.duration_text)).setText(Algorithms.formatDuration((int) (timeSpan / 1000), app.accessibilityEnabled())); ((TextView) view.findViewById(R.id.duration_text)).setText(Algorithms.formatDuration((int) (timeSpan / 1000), app.accessibilityEnabled()));
} else if (tabType.equals(GPX_TAB_ITEM_SPEED)) { } else if (tabType.equals(GPX_TAB_ITEM_SPEED)) {
long timeMoving = !joinSegments && gpxItem.isGeneralTrack() ? analysis.timeMovingWithoutGaps : analysis.timeMoving; long timeMoving = !joinSegments && generalTrack ? analysis.timeMovingWithoutGaps : analysis.timeMoving;
float totalDistanceMoving = !joinSegments && gpxItem.isGeneralTrack() ? analysis.totalDistanceMovingWithoutGaps : analysis.totalDistanceMoving; float totalDistanceMoving = !joinSegments && generalTrack ? analysis.totalDistanceMovingWithoutGaps : analysis.totalDistanceMoving;
((TextView) view.findViewById(R.id.time_moving_text)).setText(Algorithms.formatDuration((int) (timeMoving / 1000), app.accessibilityEnabled())); ((TextView) view.findViewById(R.id.time_moving_text)).setText(Algorithms.formatDuration((int) (timeMoving / 1000), app.accessibilityEnabled()));
((TextView) view.findViewById(R.id.distance_text)).setText(OsmAndFormatter.getFormattedDistance(totalDistanceMoving, app)); ((TextView) view.findViewById(R.id.distance_text)).setText(OsmAndFormatter.getFormattedDistance(totalDistanceMoving, app));
@ -693,17 +735,60 @@ public class GPXItemPagerAdapter extends PagerAdapter implements CustomTabProvid
void updateChart(LineChart chart) { void updateChart(LineChart chart) {
if (chart != null && !chart.isEmpty()) { if (chart != null && !chart.isEmpty()) {
if (gpxItem.chartMatrix != null) { if (gpxItem != null) {
chart.getViewPortHandler().refresh(new Matrix(gpxItem.chartMatrix), chart, true); if (gpxItem.chartMatrix != null) {
} chart.getViewPortHandler().refresh(new Matrix(gpxItem.chartMatrix), chart, true);
if (gpxItem.chartHighlightPos != -1) { }
chart.highlightValue(gpxItem.chartHighlightPos, 0); if (gpxItem.chartHighlightPos != -1) {
chart.highlightValue(gpxItem.chartHighlightPos, 0);
}
} else { } else {
chart.highlightValue(null); chart.highlightValue(null);
} }
} }
} }
public boolean isTabsVisible() {
GPXFile gpxFile = displayHelper.getGpx();
if (gpxFile != null && getCount() > 0 && views.size() > 0) {
for (int i = 0; i < getCount(); i++) {
LineChart lc = getViewAtPosition(i).findViewById(R.id.chart);
if (!lc.isEmpty() && !gpxFile.isEmpty()) {
return true;
}
}
}
return false;
}
public void updateGraph(int position) {
updateAnalysis();
fetchTabTypes();
if (getCount() > 0 && views.size() > 0) {
LineGraphType firstType = tabTypes[position] == GPX_TAB_ITEM_SPEED ? SPEED : ALTITUDE;
LineGraphType secondType = null;
if (tabTypes[position] == GPX_TAB_ITEM_ALTITUDE) {
secondType = SLOPE;
} else if (tabTypes[position] == GPX_TAB_ITEM_GENERAL) {
secondType = SPEED;
}
LineChart chart = getViewAtPosition(position).findViewById(R.id.chart);
List<ILineDataSet> dataSets = getDataSets(chart, tabTypes[position], firstType, secondType);
boolean isEmptyDataSets = Algorithms.isEmpty(dataSets);
AndroidUiHelper.updateVisibility(chart, !isEmptyDataSets);
chart.clear();
if (!isEmptyDataSets) {
chart.setData(new LineData(dataSets));
}
if (chart.getAxisRight().getLabelCount() != CHART_LABEL_COUNT
|| chart.getAxisLeft().getLabelCount() != CHART_LABEL_COUNT) {
GpxUiHelper.setupGPXChart(app, chart, CHART_LABEL_COUNT);
}
updateChart(chart);
}
notifyDataSetChanged();
}
private TrkSegment getTrkSegment() { private TrkSegment getTrkSegment() {
for (Track track : gpxItem.group.getGpx().tracks) { for (Track track : gpxItem.group.getGpx().tracks) {
if (!track.generalTrack && !gpxItem.isGeneralTrack() || track.generalTrack && gpxItem.isGeneralTrack()) { if (!track.generalTrack && !gpxItem.isGeneralTrack() || track.generalTrack && gpxItem.isGeneralTrack()) {

View file

@ -30,6 +30,7 @@ import net.osmand.plus.R;
import net.osmand.plus.helpers.AndroidUiHelper; import net.osmand.plus.helpers.AndroidUiHelper;
import net.osmand.plus.helpers.GpxUiHelper; import net.osmand.plus.helpers.GpxUiHelper;
import net.osmand.plus.helpers.GpxUiHelper.GPXDataSetType; import net.osmand.plus.helpers.GpxUiHelper.GPXDataSetType;
import net.osmand.plus.myplaces.GPXTabItemType;
import net.osmand.plus.myplaces.SegmentActionsListener; import net.osmand.plus.myplaces.SegmentActionsListener;
import net.osmand.plus.widgets.TextViewEx; import net.osmand.plus.widgets.TextViewEx;
import net.osmand.util.Algorithms; import net.osmand.util.Algorithms;
@ -44,15 +45,12 @@ import java.util.Date;
import java.util.List; import java.util.List;
import static net.osmand.plus.liveupdates.LiveUpdatesFragmentNew.getDefaultIconColorId; import static net.osmand.plus.liveupdates.LiveUpdatesFragmentNew.getDefaultIconColorId;
import static net.osmand.plus.myplaces.GPXTabItemType.GPX_TAB_ITEM_SPEED;
public class GpxBlockStatisticsBuilder { public class GpxBlockStatisticsBuilder {
private static final Log LOG = PlatformUtil.getLog(GpxBlockStatisticsBuilder.class); private static final Log LOG = PlatformUtil.getLog(GpxBlockStatisticsBuilder.class);
private static final int BLOCKS_UPDATE_INTERVAL = 1000; private static final int BLOCKS_UPDATE_INTERVAL = 1000;
public static final String INIT_BLOCKS_BASE = "init_blocks_base";
public static final String INIT_BLOCKS_GENERAL = "init_blocks_general";
public static final String INIT_BLOCKS_ALTITUDE = "init_blocks_altitude";
public static final String INIT_BLOCKS_SPEED = "init_blocks_speed";
private final OsmandApplication app; private final OsmandApplication app;
private final boolean nightMode; private final boolean nightMode;
@ -64,7 +62,7 @@ public class GpxBlockStatisticsBuilder {
private BlockStatisticsAdapter adapter; private BlockStatisticsAdapter adapter;
private final List<StatBlock> items = new ArrayList<>(); private final List<StatBlock> items = new ArrayList<>();
private boolean blocksClickable = true; private boolean blocksClickable = true;
private String initBlocksKey = INIT_BLOCKS_BASE; private GPXTabItemType tabItem = null;
private final Handler handler = new Handler(); private final Handler handler = new Handler();
private Runnable updatingItems; private Runnable updatingItems;
@ -88,8 +86,8 @@ public class GpxBlockStatisticsBuilder {
this.blocksView = blocksView; this.blocksView = blocksView;
} }
public void setInitBlocksKey(String initBlocksKey) { public void setTabItem(GPXTabItemType tabItem) {
this.initBlocksKey = initBlocksKey; this.tabItem = tabItem;
} }
@Nullable @Nullable
@ -133,6 +131,11 @@ public class GpxBlockStatisticsBuilder {
} }
} }
public void restartUpdatingStatBlocks() {
stopUpdatingStatBlocks();
runUpdatingStatBlocksIfNeeded();
}
public void initItems() { public void initItems() {
GPXFile gpxFile = getGPXFile(); GPXFile gpxFile = getGPXFile();
if (app == null || gpxFile == null) { if (app == null || gpxFile == null) {
@ -154,60 +157,59 @@ public class GpxBlockStatisticsBuilder {
} }
items.clear(); items.clear();
if (analysis != null) { if (analysis != null) {
switch (initBlocksKey) { if (tabItem == null) {
case INIT_BLOCKS_GENERAL: { float totalDistance = withoutGaps ? analysis.totalDistanceWithoutGaps : analysis.totalDistance;
float totalDistance = withoutGaps ? analysis.totalDistanceWithoutGaps : analysis.totalDistance; String asc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationUp, app);
float timeSpan = withoutGaps ? analysis.timeSpanWithoutGaps : analysis.timeSpan; String desc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationDown, app);
Date start = new Date(analysis.startTime); String minElevation = OsmAndFormatter.getFormattedAlt(analysis.minElevation, app);
Date end = new Date(analysis.endTime); String maxElevation = OsmAndFormatter.getFormattedAlt(analysis.maxElevation, app);
prepareDataDistance(totalDistance); String avg = OsmAndFormatter.getFormattedSpeed(analysis.avgSpeed, app);
prepareDataTimeSpan(timeSpan); String maxSpeed = OsmAndFormatter.getFormattedSpeed(analysis.maxSpeed, app);
prepareDataStartTime(start); float timeSpan = withoutGaps ? analysis.timeSpanWithoutGaps : analysis.timeSpan;
prepareDataEndTime(end); long timeMoving = withoutGaps ? analysis.timeMovingWithoutGaps : analysis.timeMoving;
break; prepareDataDistance(totalDistance);
} prepareDataAscent(asc);
case INIT_BLOCKS_ALTITUDE: { prepareDataDescent(desc);
String min = OsmAndFormatter.getFormattedAlt(analysis.minElevation, app); prepareDataAltitudeRange(minElevation, maxElevation);
String max = OsmAndFormatter.getFormattedAlt(analysis.maxElevation, app); prepareDataAverageSpeed(avg);
String asc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationUp, app); prepareDataMaximumSpeed(maxSpeed);
String desc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationDown, app); prepareDataTimeSpan(timeSpan);
prepareDataAverageAltitude(); prepareDataTimeMoving(timeMoving);
prepareDataAltitudeRange(min, max); } else {
prepareDataAscent(asc); switch (tabItem) {
prepareDataDescent(desc); case GPX_TAB_ITEM_GENERAL: {
break; float totalDistance = withoutGaps ? analysis.totalDistanceWithoutGaps : analysis.totalDistance;
} float timeSpan = withoutGaps ? analysis.timeSpanWithoutGaps : analysis.timeSpan;
case INIT_BLOCKS_SPEED: { Date start = new Date(analysis.startTime);
String avg = OsmAndFormatter.getFormattedSpeed(analysis.avgSpeed, app); Date end = new Date(analysis.endTime);
String max = OsmAndFormatter.getFormattedSpeed(analysis.maxSpeed, app); prepareDataDistance(totalDistance);
long timeMoving = withoutGaps ? analysis.timeMovingWithoutGaps : analysis.timeMoving; prepareDataTimeSpan(timeSpan);
float totalDistanceMoving = withoutGaps ? analysis.totalDistanceMovingWithoutGaps : analysis.totalDistanceMoving; prepareDataStartTime(start);
prepareDataAverageSpeed(avg); prepareDataEndTime(end);
prepareDataMaximumSpeed(max); break;
prepareDataTimeMoving(timeMoving); }
prepareDataDistanceCorrected(totalDistanceMoving); case GPX_TAB_ITEM_ALTITUDE: {
break; String min = OsmAndFormatter.getFormattedAlt(analysis.minElevation, app);
} String max = OsmAndFormatter.getFormattedAlt(analysis.maxElevation, app);
default: String asc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationUp, app);
case INIT_BLOCKS_BASE: { String desc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationDown, app);
float totalDistance = withoutGaps ? analysis.totalDistanceWithoutGaps : analysis.totalDistance; prepareDataAverageAltitude();
String asc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationUp, app); prepareDataAltitudeRange(min, max);
String desc = OsmAndFormatter.getFormattedAlt(analysis.diffElevationDown, app); prepareDataAscent(asc);
String minElevation = OsmAndFormatter.getFormattedAlt(analysis.minElevation, app); prepareDataDescent(desc);
String maxElevation = OsmAndFormatter.getFormattedAlt(analysis.maxElevation, app); break;
String avg = OsmAndFormatter.getFormattedSpeed(analysis.avgSpeed, app); }
String maxSpeed = OsmAndFormatter.getFormattedSpeed(analysis.maxSpeed, app); case GPX_TAB_ITEM_SPEED: {
float timeSpan = withoutGaps ? analysis.timeSpanWithoutGaps : analysis.timeSpan; String avg = OsmAndFormatter.getFormattedSpeed(analysis.avgSpeed, app);
long timeMoving = withoutGaps ? analysis.timeMovingWithoutGaps : analysis.timeMoving; String max = OsmAndFormatter.getFormattedSpeed(analysis.maxSpeed, app);
prepareDataDistance(totalDistance); long timeMoving = withoutGaps ? analysis.timeMovingWithoutGaps : analysis.timeMoving;
prepareDataAscent(asc); float totalDistanceMoving = withoutGaps ? analysis.totalDistanceMovingWithoutGaps : analysis.totalDistanceMoving;
prepareDataDescent(desc); prepareDataAverageSpeed(avg);
prepareDataAltitudeRange(minElevation, maxElevation); prepareDataMaximumSpeed(max);
prepareDataAverageSpeed(avg); prepareDataTimeMoving(timeMoving);
prepareDataMaximumSpeed(maxSpeed); prepareDataDistanceCorrected(totalDistanceMoving);
prepareDataTimeSpan(timeSpan); break;
prepareDataTimeMoving(timeMoving); }
break;
} }
} }
} }
@ -251,9 +253,9 @@ public class GpxBlockStatisticsBuilder {
} }
public void prepareDataTimeMoving(long timeMoving) { public void prepareDataTimeMoving(long timeMoving) {
prepareData(app.getString(initBlocksKey.equals(INIT_BLOCKS_SPEED) ? R.string.shared_string_time_moving : R.string.moving_time), prepareData(app.getString(tabItem == GPX_TAB_ITEM_SPEED ? R.string.shared_string_time_moving : R.string.moving_time),
Algorithms.formatDuration((int) (timeMoving / 1000), app.accessibilityEnabled()), Algorithms.formatDuration((int) (timeMoving / 1000), app.accessibilityEnabled()),
initBlocksKey.equals(INIT_BLOCKS_SPEED) ? R.drawable.ic_action_time_span_16 : R.drawable.ic_action_time_moving_16, tabItem == GPX_TAB_ITEM_SPEED ? R.drawable.ic_action_time_span_16 : R.drawable.ic_action_time_moving_16,
GPXDataSetType.SPEED, null, ItemType.ITEM_TIME_MOVING); GPXDataSetType.SPEED, null, ItemType.ITEM_TIME_MOVING);
} }