Route preparation / details UI fixes

This commit is contained in:
crimean 2019-03-27 19:56:07 +03:00
parent efaa13c129
commit 9370dc6c2b
16 changed files with 482 additions and 831 deletions

View file

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/context_menu_top_shadow"
android:layout_width="match_parent"
android:layout_height="@dimen/contex_menu_top_shadow_height"
android:orientation="vertical">
<ImageView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:scaleType="fitXY"
android:src="@drawable/bg_shadow_onmap" />
</FrameLayout>

View file

@ -12,19 +12,7 @@
android:layout_height="match_parent"
android:orientation="vertical">
<FrameLayout
android:id="@+id/top_shadow"
android:layout_width="match_parent"
android:layout_height="16dp">
<ImageView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:scaleType="fitXY"
android:src="@drawable/bg_shadow_onmap" />
</FrameLayout>
<include layout="@layout/context_menu_top_shadow" />
<LinearLayout
android:id="@+id/route_menu_top_shadow_all"
@ -41,6 +29,7 @@
android:id="@+id/modes_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="?attr/route_info_bg"
tools:ignore="UselessParent">
<LinearLayout
@ -60,6 +49,7 @@
android:id="@+id/app_modes_fold_container"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:background="@color/color_transparent"
android:layout_gravity="start"
android:orientation="horizontal">
@ -79,6 +69,7 @@
android:id="@+id/app_modes_options_container"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:background="@color/color_transparent"
android:layout_gravity="end">
<ImageView
@ -527,22 +518,22 @@
android:id="@+id/bottom_container"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:foregroundGravity="top|fill_horizontal"
android:foreground="@drawable/bg_contextmenu_shadow">
android:foreground="@drawable/bg_contextmenu_shadow"
android:foregroundGravity="top|fill_horizontal">
<net.osmand.plus.LockableScrollView
android:id="@+id/route_menu_bottom_scroll"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:background="?attr/ctx_menu_info_view_bg">
android:background="?attr/activity_background_basic">
<LinearLayout
android:id="@+id/route_menu_cards_container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/activity_background_basic"
android:orientation="vertical"
android:paddingBottom="60dp"
tools:background="?attr/ctx_menu_info_view_bg">
android:paddingBottom="30dp">
</LinearLayout>
@ -582,6 +573,7 @@
android:orientation="vertical">
<ImageView
android:id="@+id/buttons_shadow"
android:layout_width="match_parent"
android:layout_height="10dp"
android:layout_gravity="bottom"

View file

@ -10,23 +10,28 @@
android:layout_height="match_parent"
android:orientation="vertical">
<include layout="@layout/context_menu_top_shadow" />
<FrameLayout
android:id="@+id/bottom_container"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="?attr/route_info_bg"
android:foregroundGravity="top|fill_horizontal">
<net.osmand.plus.LockableScrollView
android:id="@+id/route_menu_bottom_scroll"
android:layout_width="match_parent"
android:layout_height="match_parent">
android:layout_height="match_parent"
android:background="?attr/route_info_bg">
<LinearLayout
android:id="@+id/route_menu_cards_container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/route_info_bg"
android:orientation="vertical"
android:paddingBottom="60dp">
android:paddingBottom="24dp">
</LinearLayout>

View file

@ -5,7 +5,6 @@
android:id="@+id/route_info_details_card"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/card_and_list_background_basic"
android:orientation="vertical">
<View
@ -19,6 +18,7 @@
android:id="@+id/RouteInfoControls"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/card_and_list_background_basic"
android:orientation="vertical">
<LinearLayout
@ -33,8 +33,8 @@
android:layout_height="wrap_content"
android:minHeight="@dimen/route_info_list_item_height"
android:orientation="horizontal"
android:paddingBottom="@dimen/route_info_details_padding"
android:paddingTop="@dimen/route_info_details_padding">
android:paddingTop="@dimen/route_info_details_padding"
android:paddingBottom="@dimen/route_info_details_padding">
<LinearLayout
android:layout_width="0dp"
@ -148,10 +148,10 @@
android:layout_width="match_parent"
android:layout_height="36dp"
android:layout_gravity="center_vertical"
android:layout_marginBottom="@dimen/route_info_details_padding"
android:layout_marginLeft="@dimen/route_info_buttons_padding_top_bottom"
android:layout_marginRight="@dimen/route_info_buttons_padding_top_bottom"
android:layout_marginTop="@dimen/route_info_details_padding"
android:layout_marginRight="@dimen/route_info_buttons_padding_top_bottom"
android:layout_marginBottom="@dimen/route_info_details_padding"
android:orientation="horizontal">
<net.osmand.plus.widgets.TextViewEx

View file

@ -112,6 +112,7 @@
<attr name="main_font_color_basic" format="reference" />
<attr name="active_color_basic" format="reference" />
<attr name="card_and_list_background_basic" format="reference" />
<attr name="activity_background_basic" format="reference" />
</declare-styleable>
<declare-styleable name="PagerSlidingTabStrip">

View file

@ -1,6 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<dimen name="contex_menu_top_shadow_height">16dp</dimen>
<dimen name="dialog_button_ex_height">60dp</dimen>
<dimen name="dialog_button_ex_min_width">72dp</dimen>
<dimen name="dialog_button_ex_max_width">120dp</dimen>

View file

@ -244,6 +244,7 @@
<item name="main_font_color_basic">@color/main_font_light</item>
<item name="active_color_basic">@color/active_buttons_and_links_light</item>
<item name="card_and_list_background_basic">@color/card_and_list_background_light</item>
<item name="activity_background_basic">@color/activity_background_light</item>
</style>
<style name="OverflowMenuButton" parent="@style/Widget.AppCompat.ActionButton.Overflow">
@ -474,6 +475,7 @@
<item name="main_font_color_basic">@color/main_font_dark</item>
<item name="active_color_basic">@color/active_buttons_and_links_dark</item>
<item name="card_and_list_background_basic">@color/card_and_list_background_dark</item>
<item name="activity_background_basic">@color/activity_background_dark</item>
</style>
<style name="FreeVersionBanner" parent="OsmandDarkTheme">

View file

@ -29,6 +29,7 @@ import android.view.ViewParent;
import android.view.ViewTreeObserver;
import android.view.animation.DecelerateInterpolator;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import android.widget.OverScroller;
import android.widget.Toast;
@ -46,7 +47,6 @@ import net.osmand.plus.mapcontextmenu.InterceptorLinearLayout;
import net.osmand.plus.views.controls.HorizontalSwipeConfirm;
import static net.osmand.plus.mapcontextmenu.MapContextMenuFragment.CURRENT_Y_UNDEFINED;
import static net.osmand.plus.mapcontextmenu.MenuBuilder.SHADOW_HEIGHT_TOP_DP;
public abstract class ContextMenuFragment extends BaseOsmAndFragment {
@ -57,11 +57,16 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
}
public static final int ANIMATION_DURATION = 200;
public static final float MIDDLE_STATE_KOEF = .75f;
public static final String MENU_STATE_KEY = "menu_state_key";
private InterceptorLinearLayout mainView;
private View view;
private OnLayoutChangeListener containerLayoutListener;
private View topShadow;
private LinearLayout cardsContainer;
private FrameLayout bottomContainer;
private LockableScrollView bottomScrollView;
private boolean portrait;
private boolean nightMode;
@ -75,13 +80,11 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
private int topScreenPosY;
private int topToolbarPosY;
private int bottomToolbarPosY;
private int topPadding;
private int menuFullHeightMax;
private int menuBottomViewHeight;
private int menuFullHeight;
private int screenHeight;
private int viewHeight;
private int topShadowMargin;
private int currentMenuState;
private int shadowHeight;
private int statusBarHeight;
@ -92,7 +95,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
private ContextMenuFragmentListener listener;
public interface ContextMenuFragmentListener {
void onContextMenuYPosChanged(@NonNull ContextMenuFragment fragment, int y, boolean animated);
void onContextMenuYPosChanged(@NonNull ContextMenuFragment fragment, int y, boolean needMapAdjust, boolean animated);
void onContextMenuStateChanged(@NonNull ContextMenuFragment fragment, int menuState);
void onContextMenuDismiss(@NonNull ContextMenuFragment fragment);
}
@ -101,13 +104,43 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
public abstract int getMainLayoutId();
@IdRes
public abstract int getMainViewId();
public int getMainViewId() {
return R.id.main_view;
}
@IdRes
public abstract int getBottomScrollViewId();
public int getTopShadowViewId() {
return R.id.context_menu_top_shadow;
}
@IdRes
public int getBottomContainerViewId() {
return R.id.bottom_container;
}
@IdRes
public int getCardsContainerViewId() {
return R.id.route_menu_cards_container;
}
@IdRes
public int getBottomScrollViewId() {
return R.id.route_menu_bottom_scroll;
}
@IdRes
public int getTopViewId() {
return 0;
}
public abstract int getHeaderViewHeight();
public abstract boolean isHeaderViewDetached();
public int getLandscapeWidth() {
return getResources().getDimensionPixelSize(R.dimen.dashboard_land_width);
}
public abstract int getToolbarHeight();
public boolean isSingleFragment() {
@ -170,6 +203,22 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
return portrait;
}
public View getTopShadow() {
return topShadow;
}
public LinearLayout getCardsContainer() {
return cardsContainer;
}
public FrameLayout getBottomContainer() {
return bottomContainer;
}
public LockableScrollView getBottomScrollView() {
return bottomScrollView;
}
@Override
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
@ -193,39 +242,37 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
}
portrait = AndroidUiHelper.isOrientationPortrait(mapActivity);
topShadowMargin = AndroidUtils.dpToPx(mapActivity, 9f);
statusBarHeight = AndroidUtils.getStatusBarHeight(mapActivity);
shadowHeight = portrait ? AndroidUtils.dpToPx(mapActivity, SHADOW_HEIGHT_TOP_DP) : 0;
topScreenPosY = addStatusBarHeightIfNeeded(-shadowHeight);
shadowHeight = getResources().getDimensionPixelSize(R.dimen.contex_menu_top_shadow_height);
topScreenPosY = addStatusBarHeightIfNeeded(-shadowHeight) + getToolbarHeight();
topToolbarPosY = getMenuStatePosY(MenuState.FULL_SCREEN);
bottomToolbarPosY = topToolbarPosY + getToolbarHeight();
mainView = view.findViewById(getMainViewId());
nightMode = app.getDaynightHelper().isNightModeForMapControls();
LockableScrollView bottomScrollView = (LockableScrollView) view.findViewById(getBottomScrollViewId());
bottomScrollView.setScrollingEnabled(false);
AndroidUtils.setBackground(app, bottomScrollView, nightMode, R.color.route_info_bg_light, R.color.route_info_bg_dark);
AndroidUtils.setBackground(app, mainView, nightMode, R.drawable.bg_map_context_menu_light, R.drawable.bg_map_context_menu_dark);
mainView = view.findViewById(getMainViewId());
topShadow = view.findViewById(getTopShadowViewId());
cardsContainer = (LinearLayout) view.findViewById(getCardsContainerViewId());
bottomContainer = (FrameLayout) view.findViewById(getBottomContainerViewId());
bottomScrollView = (LockableScrollView) view.findViewById(getBottomScrollViewId());
bottomScrollView.setScrollingEnabled(false);
if (getTopViewId() != 0) {
View topView = view.findViewById(getTopViewId());
AndroidUtils.setBackground(app, topView, nightMode, R.color.route_info_bg_light, R.color.route_info_bg_dark);
}
if (!portrait) {
currentMenuState = MenuState.FULL_SCREEN;
if (isSingleFragment()) {
topPadding = getToolbarHeight() - topScreenPosY;
final TypedValue typedValueAttr = new TypedValue();
mapActivity.getTheme().resolveAttribute(R.attr.left_menu_view_bg, typedValueAttr, true);
mainView.setBackgroundResource(typedValueAttr.resourceId);
mainView.setLayoutParams(new FrameLayout.LayoutParams(getResources().getDimensionPixelSize(R.dimen.dashboard_land_width), ViewGroup.LayoutParams.MATCH_PARENT));
} else {
topPadding = getToolbarHeight() + topShadowMargin;
mainView.setLayoutParams(new FrameLayout.LayoutParams(AndroidUtils.dpToPx(mapActivity, 345f), ViewGroup.LayoutParams.MATCH_PARENT));
}
bottomScrollView.setPadding(0, topPadding, 0, 0);
mainView.setLayoutParams(new FrameLayout.LayoutParams(getLandscapeWidth(), ViewGroup.LayoutParams.MATCH_PARENT));
}
processScreenHeight(container);
minHalfY = viewHeight - (int) (viewHeight * .75f);
minHalfY = viewHeight - (int) (viewHeight * MIDDLE_STATE_KOEF);
final GestureDetector swipeDetector = new GestureDetector(app, new HorizontalSwipeConfirm(true));
@ -426,15 +473,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
private int addStatusBarHeightIfNeeded(int res) {
MapActivity mapActivity = getMapActivity();
if (Build.VERSION.SDK_INT >= 21 && mapActivity != null) {
return res + (isSingleFragment() ? statusBarHeight : -statusBarHeight);
}
return res;
}
public int getTopShadowMargin() {
int res = topShadowMargin;
if (Build.VERSION.SDK_INT >= 21 && !isSingleFragment()) {
res -= statusBarHeight;
return res + (isSingleFragment() ? statusBarHeight : 0);
}
return res;
}
@ -525,7 +564,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
mainView.setY(y);
ContextMenuFragmentListener listener = this.listener;
if (listener != null) {
listener.onContextMenuYPosChanged(this, y, false);
listener.onContextMenuYPosChanged(this, y, adjustMapPos, false);
}
}
@ -534,27 +573,50 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
screenHeight = container.getHeight() + statusBarHeight;
viewHeight = screenHeight - statusBarHeight - topPadding;
minHalfY = viewHeight - (int) (viewHeight * .75f);
viewHeight = screenHeight - statusBarHeight;
minHalfY = viewHeight - (int) (viewHeight * MIDDLE_STATE_KOEF);
}
}
private int getFullScreenTopPosY() {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
int res = topShadowMargin + getToolbarHeight();
if (Build.VERSION.SDK_INT >= 21 && !isSingleFragment()) {
res -= statusBarHeight;
public boolean isMoving() {
return moving;
}
return res;
public int getWidth() {
InterceptorLinearLayout mainView = getMainView();
if (mainView != null) {
return mainView.getWidth();
} else {
return 0;
}
}
private int getHeaderOnlyTopY() {
public int getHeight() {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
int height = getMenuStatePosY(getCurrentMenuState());
return viewHeight - height - AndroidUtils.getStatusBarHeight(mapActivity);
} else {
return 0;
}
}
public int getViewHeight() {
return viewHeight;
}
public int getShadowHeight() {
return shadowHeight;
}
public int getFullScreenTopPosY() {
return topScreenPosY;
}
public int getHeaderOnlyTopY() {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
int shadowHeight = getShadowHeight();
if (getHeaderViewHeight() > 0) {
return viewHeight - getHeaderViewHeight() - shadowHeight;
} else {
@ -566,9 +628,6 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
}
public int getMenuStatePosY(int menuState) {
if (!portrait) {
return topScreenPosY;
}
switch (menuState) {
case MenuState.HEADER_ONLY:
return getHeaderOnlyTopY();
@ -712,7 +771,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
return posY;
}
private void updateMainViewLayout(int posY) {
protected void updateMainViewLayout(int posY) {
MapActivity mapActivity = getMapActivity();
if (view != null && mapActivity != null) {
ViewGroup.LayoutParams lp = mainView.getLayoutParams();
@ -722,7 +781,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
}
}
protected void applyPosY(final int currentY, final boolean needCloseMenu, boolean needMapAdjust,
protected int applyPosY(final int currentY, final boolean needCloseMenu, boolean needMapAdjust,
final int previousMenuState, final int newMenuState, int dZoom, final boolean animated) {
final int posY = getPosY(currentY, needCloseMenu, previousMenuState);
if (getViewY() != posY || dZoom != 0) {
@ -769,9 +828,10 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
}
ContextMenuFragmentListener listener = this.listener;
if (listener != null) {
listener.onContextMenuYPosChanged(this, posY, true);
listener.onContextMenuYPosChanged(this, posY, needMapAdjust, true);
}
}
return posY;
}
public void animateView(@NonNull View view, int y) {
@ -803,10 +863,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
if (getActivity() == null) {
return;
}
menuFullHeight = mainView.getHeight();
menuBottomViewHeight = menuFullHeight;
menuFullHeightMax = view.findViewById(R.id.route_menu_cards_container).getHeight();
calculateLayout(view);
if (!moving) {
doLayoutMenu();
@ -823,6 +880,13 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
}
}
protected void calculateLayout(View view) {
menuFullHeight = mainView.getHeight();
menuBottomViewHeight = menuFullHeight;
menuFullHeightMax = view.findViewById(R.id.route_menu_cards_container).getHeight() +
(isHeaderViewDetached() ? getHeaderViewHeight() : 0);
}
private void doLayoutMenu() {
final int posY = getPosY(initLayout ? CURRENT_Y_UNDEFINED : getViewY(), false, getCurrentMenuState());
setViewY(posY, true, !initLayout);
@ -888,7 +952,7 @@ public abstract class ContextMenuFragment extends BaseOsmAndFragment {
if (!portrait) {
tileBoxWidthPx = tb.getPixWidth() - view.getWidth();
} else {
tileBoxHeightPx = getHeaderOnlyTopY();
tileBoxHeightPx = getHeaderOnlyTopY() - getShadowHeight();
}
if (tileBoxHeightPx > 0 || tileBoxWidthPx > 0) {
int topMarginPx = getToolbarHeight();

View file

@ -86,6 +86,7 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
private boolean portrait;
private boolean nightMode;
private boolean wasDrawerDisabled;
private int currentMenuState;
private boolean publicTransportMode;
private int routeInfoMenuState = -1;
@ -107,8 +108,10 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
routeInfoMenuState = args.getInt(ROUTE_INFO_STATE_KEY, -1);
initialMenuState = args.getInt(INITIAL_MENU_STATE_KEY, initialMenuState);
}
int routesCount = 1;
if (routes != null && !routes.isEmpty()) {
publicTransportMode = true;
routesCount = routes.size();
}
ContextThemeWrapper context =
new ContextThemeWrapper(mapActivity, !nightMode ? R.style.OsmandLightTheme : R.style.OsmandDarkTheme);
@ -129,9 +132,11 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
view.setLayoutParams(new FrameLayout.LayoutParams(getResources().getDimensionPixelSize(R.dimen.dashboard_land_width), ViewGroup.LayoutParams.MATCH_PARENT));
}
viewPager.setClipToPadding(false);
final RoutesPagerAdapter pagerAdapter = new RoutesPagerAdapter(getChildFragmentManager(), publicTransportMode ? routes.size() : 1, initialMenuState);
currentMenuState = initialMenuState;
final RoutesPagerAdapter pagerAdapter = new RoutesPagerAdapter(getChildFragmentManager(), routesCount);
viewPager.setAdapter(pagerAdapter);
viewPager.setCurrentItem(routeIndex);
viewPager.setOffscreenPageLimit(routesCount);
viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
public void onPageScrollStateChanged(int state) {
}
@ -150,7 +155,10 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
if (f != null) {
PublicTransportCard card = f.getTransportCard();
if (card != null) {
card.update();
card.updateButtons();
}
if (f == getCurrentFragment()) {
updateZoomButtonsPos(f, f.getViewY(), true);
}
}
}
@ -647,7 +655,7 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
public void updateZoomButtonsPos(@NonNull ContextMenuFragment fragment, int y, boolean animated) {
View zoomButtonsView = this.zoomButtonsView;
if (zoomButtonsView != null) {
int zoomY = y - getZoomButtonsHeight() - fragment.getTopShadowMargin();
int zoomY = y - getZoomButtonsHeight();
if (animated) {
fragment.animateView(zoomButtonsView, zoomY);
} else {
@ -660,6 +668,7 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
int visibility = visible ? View.VISIBLE : View.GONE;
mapActivity.findViewById(R.id.map_top_bar).setVisibility(visibility);
mapActivity.findViewById(R.id.map_center_info).setVisibility(visibility);
mapActivity.findViewById(R.id.map_left_widgets_panel).setVisibility(visibility);
if (!openingRouteInfo) {
@ -668,13 +677,12 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
mapActivity.getMapView().setMapPositionX(visible ? 0 : 1);
}
}
mapActivity.findViewById(R.id.bottom_controls_container).setVisibility(visibility);
mapActivity.refreshMap();
}
}
@Override
public void onContextMenuYPosChanged(@NonNull ContextMenuFragment fragment, int y, boolean animated) {
public void onContextMenuYPosChanged(@NonNull ContextMenuFragment fragment, int y, boolean needMapAdjust, boolean animated) {
if (fragment == getCurrentFragment()) {
updateToolbars(fragment, y, animated);
updateZoomButtonsPos(fragment, y, animated);
@ -685,17 +693,17 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
@Override
public void onContextMenuStateChanged(@NonNull ContextMenuFragment fragment, int menuState) {
LockableViewPager viewPager = this.viewPager;
if (viewPager != null) {
int currentItem = viewPager.getCurrentItem();
RouteDetailsFragment current = getCurrentFragment();
if (viewPager != null && current != null && fragment == current) {
currentMenuState = menuState;
List<WeakReference<RouteDetailsFragment>> routeDetailsFragments = this.routeDetailsFragments;
for (WeakReference<RouteDetailsFragment> ref : routeDetailsFragments) {
RouteDetailsFragment f = ref.get();
if (f != null) {
boolean current = f.getRouteId() == currentItem;
if (!current && f.getCurrentMenuState() != menuState) {
if (f != current && f.getCurrentMenuState() != menuState) {
f.openMenuScreen(menuState, false);
}
if (current) {
if (f == current) {
updateZoomButtonsVisibility(menuState);
updateViewPager(fragment.getViewY());
}
@ -748,12 +756,10 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
public class RoutesPagerAdapter extends FragmentPagerAdapter {
private int routesCount;
private int initialMenuState;
RoutesPagerAdapter(FragmentManager fm, int routesCount, int initialMenuState) {
RoutesPagerAdapter(FragmentManager fm, int routesCount) {
super(fm);
this.routesCount = routesCount;
this.initialMenuState = initialMenuState;
}
@Override
@ -764,7 +770,7 @@ public class ChooseRouteFragment extends BaseOsmAndFragment implements ContextMe
@Override
public Fragment getItem(int position) {
Bundle args = new Bundle();
args.putInt(ContextMenuFragment.MENU_STATE_KEY, initialMenuState);
args.putInt(ContextMenuFragment.MENU_STATE_KEY, currentMenuState);
args.putInt(RouteDetailsFragment.ROUTE_ID_KEY, position);
return Fragment.instantiate(ChooseRouteFragment.this.getContext(), RouteDetailsFragment.class.getName(), args);
}

View file

@ -78,6 +78,7 @@ import net.osmand.plus.routing.IRouteInformationListener;
import net.osmand.plus.routing.RoutingHelper;
import net.osmand.plus.routing.TransportRoutingHelper;
import net.osmand.plus.search.QuickSearchHelper;
import net.osmand.plus.widgets.TextViewExProgress;
import net.osmand.router.GeneralRouter;
import net.osmand.router.GeneralRouter.RoutingParameter;
import net.osmand.router.TransportRoutePlanner.TransportRouteResult;
@ -135,7 +136,6 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
@Nullable
private View mainView;
private int currentMenuState;
private boolean portraitMode;
private boolean swapButtonCollapsing;
@ -162,7 +162,6 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
}
public MapRouteInfoMenu() {
currentMenuState = getInitialMenuState();
onMarkerSelectListener = new OnMarkerSelectListener() {
@Override
public void onSelect(int index, PointType pointType) {
@ -209,7 +208,7 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
return animationsHandler;
}
private int getInitialMenuState() {
public int getInitialMenuState() {
return MenuState.FULL_SCREEN;
}
@ -321,7 +320,11 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
}
public int getCurrentMenuState() {
return currentMenuState;
WeakReference<MapRouteInfoMenuFragment> fragmentRef = findMenuFragment();
if (fragmentRef != null) {
return fragmentRef.get().getCurrentMenuState();
}
return 0;
}
public int getSupportedMenuStates() {
@ -340,30 +343,6 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
return MenuState.HEADER_ONLY | MenuState.HALF_SCREEN | MenuState.FULL_SCREEN;
}
public boolean slideUp() {
int v = currentMenuState;
for (int i = 0; i < 2; i++) {
v = v << 1;
if ((v & getSupportedMenuStates()) != 0) {
currentMenuState = v;
return true;
}
}
return false;
}
public boolean slideDown() {
int v = currentMenuState;
for (int i = 0; i < 2; i++) {
v = v >> 1;
if ((v & getSupportedMenuStates()) != 0) {
currentMenuState = v;
return true;
}
}
return false;
}
public void showHideMenu(int menuState) {
intermediateRequestsLatLon.clear();
if (isVisible()) {
@ -672,7 +651,7 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
View mainView = getMainView();
if (mainView != null) {
AppCompatImageView foldButtonView = (AppCompatImageView) mainView.findViewById(R.id.fold_button);
foldButtonView.setImageResource(currentMenuState == MenuState.HEADER_ONLY ?
foldButtonView.setImageResource(getCurrentMenuState() == MenuState.HEADER_ONLY ?
R.drawable.ic_action_arrow_up : R.drawable.ic_action_arrow_down);
foldButtonView.setOnClickListener(new OnClickListener() {
@Override
@ -691,7 +670,7 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
}
private void expandCollapse() {
if (currentMenuState == MenuState.HEADER_ONLY) {
if (getCurrentMenuState() == MenuState.HEADER_ONLY) {
openMenuFullScreen();
} else {
openMenuHeaderOnly();
@ -834,22 +813,19 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
int margin = AndroidUtils.dpToPx(app, 3);
View startButton = mainView.findViewById(R.id.start_button);
TextView startButtonText = (TextView) mainView.findViewById(R.id.start_button_descr);
TextViewExProgress startButtonText = (TextViewExProgress) mainView.findViewById(R.id.start_button_descr);
boolean publicTransportMode = routingHelper.getAppMode() == ApplicationMode.PUBLIC_TRANSPORT;
int iconId = publicTransportMode ? R.drawable.ic_map : R.drawable.ic_action_start_navigation;
int color;
if (isRouteCalculated()) {
AndroidUtils.setBackground(app, startButton, nightMode, R.color.active_buttons_and_links_light, R.color.active_buttons_and_links_dark);
int color = nightMode ? R.color.main_font_dark : R.color.card_and_list_background_light;
startButtonText.setTextColor(ContextCompat.getColor(app, color));
Drawable icon = app.getUIUtilities().getIcon(iconId, color);
startButtonText.setCompoundDrawablesWithIntrinsicBounds(icon, null, null, null);
color = nightMode ? R.color.main_font_dark : R.color.card_and_list_background_light;
} else {
AndroidUtils.setBackground(app, startButton, nightMode, R.color.activity_background_light, R.color.activity_background_dark);
int color = R.color.description_font_and_bottom_sheet_icons;
startButtonText.setTextColor(ContextCompat.getColor(app, color));
Drawable icon = app.getUIUtilities().getIcon(iconId, color);
startButtonText.setCompoundDrawablesWithIntrinsicBounds(icon, null, null, null);
color = R.color.description_font_and_bottom_sheet_icons;
}
startButtonText.color2 = ContextCompat.getColor(app, color);
startButtonText.setCompoundDrawablesWithIntrinsicBounds(app.getUIUtilities().getIcon(iconId, color), null, null, null);
if (publicTransportMode) {
startButtonText.setText(R.string.shared_string_show_on_map);
} else if (routingHelper.isFollowingMode() || routingHelper.isPauseNavigation()) {
@ -1576,7 +1552,7 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
public void selectOnScreen(PointType pointType) {
selectFromMapTouch = true;
selectFromMapPointType = pointType;
selectFromMapMenuState = currentMenuState;
selectFromMapMenuState = getCurrentMenuState();
hide();
}
@ -1897,12 +1873,12 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
}
MapActivity mapActivity = getMapActivity();
if (!isVisible() && mapActivity != null) {
currentMenuState = menuState;
int initialMenuState = menuState;
switched = mapActivity.getMapLayers().getMapControlsLayer().switchToRoutePlanningLayout();
boolean refreshMap = !switched;
boolean portrait = AndroidUiHelper.isOrientationPortrait(mapActivity);
if (!portrait) {
currentMenuState = MenuState.FULL_SCREEN;
initialMenuState = MenuState.FULL_SCREEN;
mapActivity.getMapView().setMapPositionX(1);
refreshMap = true;
}
@ -1911,7 +1887,7 @@ public class MapRouteInfoMenu implements IRouteInformationListener, CardListener
mapActivity.refreshMap();
}
MapRouteInfoMenuFragment.showInstance(mapActivity);
MapRouteInfoMenuFragment.showInstance(mapActivity, initialMenuState);
if (!AndroidUiHelper.isXLargeDevice(mapActivity)) {
AndroidUiHelper.updateVisibility(mapActivity.findViewById(R.id.map_right_widgets_panel), false);

View file

@ -1,8 +1,5 @@
package net.osmand.plus.routepreparationmenu;
import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.annotation.TargetApi;
import android.os.Build;
import android.os.Bundle;
import android.support.annotation.NonNull;
@ -10,21 +7,12 @@ import android.support.annotation.Nullable;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.content.ContextCompat;
import android.util.TypedValue;
import android.view.GestureDetector;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.VelocityTracker;
import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.view.ViewParent;
import android.view.ViewTreeObserver;
import android.view.animation.DecelerateInterpolator;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import android.widget.OverScroller;
import android.widget.ProgressBar;
import android.widget.TextView;
@ -33,108 +21,109 @@ import net.osmand.Location;
import net.osmand.data.QuadRect;
import net.osmand.data.RotatedTileBox;
import net.osmand.plus.ApplicationMode;
import net.osmand.plus.LockableScrollView;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.R;
import net.osmand.plus.TargetPointsHelper.TargetPoint;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.base.BaseOsmAndFragment;
import net.osmand.plus.base.ContextMenuFragment.MenuState;
import net.osmand.plus.base.ContextMenuFragment;
import net.osmand.plus.helpers.AndroidUiHelper;
import net.osmand.plus.mapcontextmenu.InterceptorLinearLayout;
import net.osmand.plus.routing.RoutingHelper;
import net.osmand.plus.routing.TransportRoutingHelper;
import net.osmand.plus.views.controls.HorizontalSwipeConfirm;
import net.osmand.plus.widgets.TextViewExProgress;
import net.osmand.router.TransportRoutePlanner.TransportRouteResult;
import net.osmand.util.MapUtils;
import java.util.List;
import static net.osmand.plus.mapcontextmenu.MapContextMenuFragment.CURRENT_Y_UNDEFINED;
public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
public class MapRouteInfoMenuFragment extends ContextMenuFragment {
public static final String TAG = "MapRouteInfoMenuFragment";
@Nullable
private MapRouteInfoMenu menu;
private InterceptorLinearLayout mainView;
private FrameLayout bottomContainer;
private View modesLayoutToolbar;
private View modesLayoutToolbarContainer;
private View modesLayoutListContainer;
private View modesLayout;
private View view;
private LinearLayout cardsContainer;
private View.OnLayoutChangeListener containerLayoutListener;
private boolean portrait;
private boolean nightMode;
private boolean moving;
private boolean forceUpdateLayout;
private boolean initLayout = true;
private boolean wasDrawerDisabled;
private int menuFullHeight;
private int minHalfY;
private int menuTopShadowAllHeight;
private int topScreenPosY;
private int menuBottomViewHeight;
private int menuFullHeightMax;
private int menuTitleHeight;
private int shadowHeight;
private int screenHeight;
private int viewHeight;
private boolean paused;
@Override
public int getMainLayoutId() {
return R.layout.plan_route_info;
}
@Nullable
private MapActivity getMapActivity() {
FragmentActivity activity = getActivity();
if (activity instanceof MapActivity) {
return (MapActivity) activity;
@Override
public int getTopViewId() {
return R.id.route_menu_top_shadow_all;
}
@Override
public int getHeaderViewHeight() {
return menuTitleHeight;
}
@Override
public boolean isHeaderViewDetached() {
return true;
}
@Override
public int getLandscapeWidth() {
return getResources().getDimensionPixelSize(R.dimen.dashboard_land_width);
}
@Override
public int getToolbarHeight() {
return 0;
}
@Override
public boolean isSingleFragment() {
return true;
}
@Override
public int getInitialMenuState() {
if (menu != null) {
if (isPortrait()) {
return menu.getInitialMenuStatePortrait();
} else {
return null;
return menu.getInitialMenuState();
}
}
return super.getInitialMenuState();
}
@NonNull
private MapActivity requireMapActivity() {
FragmentActivity activity = getActivity();
if (!(activity instanceof MapActivity)) {
throw new IllegalStateException("Fragment " + this + " not attached to an activity.");
@Override
public int getSupportedMenuStates() {
if (menu != null) {
return menu.getSupportedMenuStates();
}
return (MapActivity) activity;
return super.getSupportedMenuStates();
}
@Override
public int getSupportedMenuStatesPortrait() {
if (menu != null) {
return menu.getSupportedMenuStatesPortrait();
}
return super.getSupportedMenuStatesPortrait();
}
@Override
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
MapActivity mapActivity = requireMapActivity();
processScreenHeight(container);
portrait = AndroidUiHelper.isOrientationPortrait(mapActivity);
menu = mapActivity.getMapRouteInfoMenu();
shadowHeight = AndroidUtils.getStatusBarHeight(mapActivity);
topScreenPosY = addStatusBarHeightIfNeeded(0);
minHalfY = viewHeight - (int) (viewHeight * .75f);
view = inflater.inflate(R.layout.plan_route_info, container, false);
if (menu == null) {
return view;
}
AndroidUtils.addStatusBarPadding21v(getActivity(), view);
mainView = view.findViewById(R.id.main_view);
View view = super.onCreateView(inflater, container, savedInstanceState);
if (view != null) {
bottomContainer = (FrameLayout) view.findViewById(R.id.bottom_container);
modesLayoutToolbar = view.findViewById(R.id.modes_layout_toolbar);
modesLayoutToolbarContainer = view.findViewById(R.id.modes_layout_toolbar_container);
modesLayoutListContainer = view.findViewById(R.id.modes_layout_list_container);
modesLayout = view.findViewById(R.id.modes_layout);
nightMode = mapActivity.getMyApplication().getDaynightHelper().isNightModeForMapControls();
View topShadowView = mainView.findViewById(R.id.top_shadow);
topShadowView.setLayoutParams(new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, shadowHeight));
view.setOnClickListener(new View.OnClickListener() {
@Override
@ -143,23 +132,10 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
}
});
LockableScrollView bottomScrollView = (LockableScrollView) view.findViewById(R.id.route_menu_bottom_scroll);
bottomScrollView.setScrollingEnabled(false);
bottomScrollView.setBackgroundColor(getResources().getColor(nightMode ? R.color.activity_background_dark : R.color.activity_background_light));
cardsContainer = (LinearLayout) view.findViewById(R.id.route_menu_cards_container);
buildBottomView();
if (!portrait) {
topShadowView.setVisibility(View.GONE);
if (!isPortrait()) {
view.findViewById(R.id.app_modes_fold_container).setVisibility(View.GONE);
final TypedValue typedValueAttr = new TypedValue();
mapActivity.getTheme().resolveAttribute(R.attr.left_menu_view_bg, typedValueAttr, true);
mainView.setBackgroundResource(typedValueAttr.resourceId);
mainView.setLayoutParams(new FrameLayout.LayoutParams(getResources().getDimensionPixelSize(R.dimen.dashboard_land_width), ViewGroup.LayoutParams.MATCH_PARENT));
int widthNoShadow = AndroidUtils.dpToPx(mapActivity, 345f);
modesLayoutToolbar.setLayoutParams(new FrameLayout.LayoutParams(widthNoShadow, ViewGroup.LayoutParams.WRAP_CONTENT));
FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(widthNoShadow, ViewGroup.LayoutParams.WRAP_CONTENT);
@ -169,195 +145,24 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
appModesView.setPadding(0, 0, appModesView.getPaddingRight(), 0);
}
runLayoutListener();
final GestureDetector swipeDetector = new GestureDetector(getMapActivity(), new HorizontalSwipeConfirm(true));
final View.OnTouchListener slideTouchListener = new View.OnTouchListener() {
private float dy;
private float dyMain;
private float mDownY;
private int minimumVelocity;
private int maximumVelocity;
private VelocityTracker velocityTracker;
private OverScroller scroller;
private boolean slidingUp;
private boolean slidingDown;
{
scroller = new OverScroller(getMapActivity());
final ViewConfiguration configuration = ViewConfiguration.get(getMapActivity());
minimumVelocity = configuration.getScaledMinimumFlingVelocity();
maximumVelocity = configuration.getScaledMaximumFlingVelocity();
}
@Override
public boolean onTouch(View v, MotionEvent event) {
if (!portrait) {
if (swipeDetector.onTouchEvent(event)) {
menu.hide();
recycleVelocityTracker();
return true;
}
}
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
mDownY = event.getRawY();
dy = event.getY();
dyMain = getViewY();
initOrResetVelocityTracker();
velocityTracker.addMovement(event);
break;
case MotionEvent.ACTION_MOVE:
if (Math.abs(event.getRawY() - mDownY) > mainView.getTouchSlop()) {
moving = true;
}
if (moving) {
float y = event.getY();
float newY = getViewY() + (y - dy);
if (!portrait && newY > topScreenPosY) {
newY = topScreenPosY;
}
setViewY((int) newY, false, false);
menuFullHeight = view.getHeight() - (int) newY + 10;
ViewGroup.LayoutParams lp = mainView.getLayoutParams();
lp.height = Math.max(menuFullHeight, menuTitleHeight);
mainView.setLayoutParams(lp);
mainView.requestLayout();
float newEventY = newY - (dyMain - dy);
MotionEvent ev = MotionEvent.obtain(event.getDownTime(), event.getEventTime(), event.getAction(),
event.getX(), newEventY, event.getMetaState());
initVelocityTrackerIfNotExists();
velocityTracker.addMovement(ev);
updateToolbar();
}
break;
case MotionEvent.ACTION_UP:
if (moving) {
moving = false;
int currentY = getViewY();
int fullScreenTopPosY = getFullScreenTopPosY();
final VelocityTracker velocityTracker = this.velocityTracker;
velocityTracker.computeCurrentVelocity(1000, maximumVelocity);
int initialVelocity = (int) velocityTracker.getYVelocity();
if ((Math.abs(initialVelocity) > minimumVelocity) && currentY != fullScreenTopPosY) {
scroller.abortAnimation();
scroller.fling(0, currentY, 0, initialVelocity, 0, 0,
Math.min(viewHeight - menuFullHeightMax, fullScreenTopPosY),
screenHeight,
0, 0);
currentY = scroller.getFinalY();
scroller.abortAnimation();
slidingUp = initialVelocity < -2000;
slidingDown = initialVelocity > 2000;
} else {
slidingUp = false;
slidingDown = false;
}
changeMenuState(currentY, slidingUp, slidingDown);
}
recycleVelocityTracker();
break;
case MotionEvent.ACTION_CANCEL:
moving = false;
recycleVelocityTracker();
break;
}
return true;
}
private void initOrResetVelocityTracker() {
if (velocityTracker == null) {
velocityTracker = VelocityTracker.obtain();
} else {
velocityTracker.clear();
}
}
private void initVelocityTrackerIfNotExists() {
if (velocityTracker == null) {
velocityTracker = VelocityTracker.obtain();
velocityTracker.clear();
}
}
private void recycleVelocityTracker() {
if (velocityTracker != null) {
velocityTracker.recycle();
velocityTracker = null;
}
}
};
((InterceptorLinearLayout) mainView).setListener(slideTouchListener);
mainView.setOnTouchListener(slideTouchListener);
containerLayoutListener = new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View view, int left, int top, int right, int bottom,
int oldLeft, int oldTop, int oldRight, int oldBottom) {
if (forceUpdateLayout || bottom != oldBottom) {
forceUpdateLayout = false;
processScreenHeight(view.getParent());
updateInfo(view);
runLayoutListener();
}
}
};
updateInfo();
return view;
}
@Override
public void onResume() {
super.onResume();
paused = false;
if (menu == null) {
dismiss();
}
menu.addTargetPointListener();
ViewParent parent = view.getParent();
if (parent != null && containerLayoutListener != null) {
((View) parent).addOnLayoutChangeListener(containerLayoutListener);
}
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
mapActivity.getMapLayers().getMapControlsLayer().showMapControlsIfHidden();
wasDrawerDisabled = mapActivity.isDrawerDisabled();
if (!wasDrawerDisabled) {
mapActivity.disableDrawer();
}
}
}
@Override
public void onPause() {
super.onPause();
paused = true;
if (view != null) {
ViewParent parent = view.getParent();
if (parent != null && containerLayoutListener != null) {
((View) parent).removeOnLayoutChangeListener(containerLayoutListener);
}
}
MapActivity mapActivity = getMapActivity();
if (!wasDrawerDisabled && mapActivity != null) {
mapActivity.enableDrawer();
}
}
@Override
@ -368,10 +173,40 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
}
}
private void buildBottomView() {
LinearLayout cardsContainer = getCardsContainer();
if (cardsContainer != null && menu != null) {
menu.build(cardsContainer);
}
}
@Override
protected void setViewY(int y, boolean animated, boolean adjustMapPos) {
super.setViewY(y, animated, adjustMapPos);
updateToolbar();
}
@Override
protected void updateMainViewLayout(int posY) {
super.updateMainViewLayout(posY);
updateToolbar();
}
@Override
protected int applyPosY(int currentY, boolean needCloseMenu, boolean needMapAdjust, int previousMenuState, int newMenuState, int dZoom, boolean animated) {
int y = super.applyPosY(currentY, needCloseMenu, needMapAdjust, previousMenuState, newMenuState, dZoom, animated);
if (needMapAdjust) {
adjustMapPosition(y);
}
return y;
}
@Override
public int getStatusBarColorId() {
View view = getView();
if (view != null) {
if (menu != null && (getViewY() <= 0 || !portrait)) {
boolean nightMode = isNightMode();
if (getViewY() <= getFullScreenTopPosY() || !isPortrait()) {
if (Build.VERSION.SDK_INT >= 23 && !nightMode) {
view.setSystemUiVisibility(view.getSystemUiVisibility() | View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);
}
@ -385,24 +220,6 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
return -1;
}
public boolean isPaused() {
return paused;
}
private void buildBottomView() {
if (cardsContainer != null) {
menu.build(cardsContainer);
}
}
private int getViewY() {
return (int) mainView.getY();
}
private void setViewY(int y, boolean animated, boolean adjustMapPos) {
mainView.setY(y);
}
private void updateToolbar() {
MapActivity mapActivity = getMapActivity();
if (menu == null || mapActivity == null) {
@ -428,305 +245,18 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
menu.updateApplicationModesOptions();
}
private void processScreenHeight(ViewParent parent) {
View container = (View) parent;
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
screenHeight = container.getHeight() + AndroidUtils.getStatusBarHeight(mapActivity);
viewHeight = screenHeight - AndroidUtils.getStatusBarHeight(mapActivity);
}
}
private int getFullScreenTopPosY() {
return !portrait ? topScreenPosY : 0;
}
private int addStatusBarHeightIfNeeded(int res) {
MapActivity mapActivity = getMapActivity();
if (Build.VERSION.SDK_INT >= 21 && mapActivity != null) {
return res + AndroidUtils.getStatusBarHeight(mapActivity);
}
return res;
}
private int getHeaderOnlyTopY() {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
return viewHeight - menuTitleHeight - AndroidUtils.dpToPx(mapActivity, 50f);
} else {
return 0;
}
}
public void openMenuFullScreen() {
changeMenuState(getMenuStatePosY(MenuState.FULL_SCREEN), false, false);
}
public void openMenuHeaderOnly() {
if (portrait) {
changeMenuState(getMenuStatePosY(MenuState.HEADER_ONLY), false, false);
}
}
public void openMenuHalfScreen() {
if (portrait) {
changeMenuState(getMenuStatePosY(MenuState.HALF_SCREEN), false, false);
}
}
private int getMenuStatePosY(int menuState) {
if (!portrait) {
return topScreenPosY;
}
switch (menuState) {
case MenuState.HEADER_ONLY:
return getHeaderOnlyTopY();
case MenuState.HALF_SCREEN:
return minHalfY;
case MenuState.FULL_SCREEN:
return getFullScreenTopPosY();
default:
return 0;
}
}
private void changeMenuState(int currentY, boolean slidingUp, boolean slidingDown) {
boolean needCloseMenu = false;
int currentMenuState = menu.getCurrentMenuState();
if (portrait) {
int headerDist = Math.abs(currentY - getMenuStatePosY(MenuState.HEADER_ONLY));
int halfDist = Math.abs(currentY - getMenuStatePosY(MenuState.HALF_SCREEN));
int fullDist = Math.abs(currentY - getMenuStatePosY(MenuState.FULL_SCREEN));
int newState;
if (headerDist < halfDist && headerDist < fullDist) {
newState = MenuState.HEADER_ONLY;
} else if (halfDist < headerDist && halfDist < fullDist) {
newState = MenuState.HALF_SCREEN;
} else {
newState = MenuState.FULL_SCREEN;
}
if (slidingDown && currentMenuState == MenuState.FULL_SCREEN && getViewY() < getFullScreenTopPosY()) {
slidingDown = false;
newState = MenuState.FULL_SCREEN;
}
if (menuBottomViewHeight > 0 && slidingUp) {
while (menu.getCurrentMenuState() != newState) {
if (!menu.slideUp()) {
break;
}
}
} else if (slidingDown) {
if (currentMenuState == MenuState.HEADER_ONLY) {
needCloseMenu = true;
} else {
while (menu.getCurrentMenuState() != newState) {
if (!menu.slideDown()) {
needCloseMenu = true;
break;
}
}
}
} else {
if (currentMenuState < newState) {
while (menu.getCurrentMenuState() != newState) {
if (!menu.slideUp()) {
break;
}
}
} else {
while (menu.getCurrentMenuState() != newState) {
if (!menu.slideDown()) {
break;
}
}
}
}
}
int newMenuState = menu.getCurrentMenuState();
boolean needMapAdjust = currentMenuState != newMenuState && newMenuState != MenuState.FULL_SCREEN;
applyPosY(currentY, needCloseMenu, needMapAdjust, currentMenuState, newMenuState, 0);
}
private int getPosY(final int currentY, boolean needCloseMenu, int previousState) {
if (needCloseMenu) {
return screenHeight;
}
MapActivity mapActivity = getMapActivity();
if (mapActivity == null) {
return 0;
}
int destinationState;
destinationState = menu.getCurrentMenuState();
int posY = 0;
switch (destinationState) {
case MenuState.HEADER_ONLY:
posY = getMenuStatePosY(MenuState.HEADER_ONLY);
break;
case MenuState.HALF_SCREEN:
posY = getMenuStatePosY(MenuState.HALF_SCREEN);
break;
case MenuState.FULL_SCREEN:
if (currentY != CURRENT_Y_UNDEFINED) {
int maxPosY = viewHeight - menuFullHeightMax;
int minPosY = getMenuStatePosY(MenuState.FULL_SCREEN);
if (maxPosY > minPosY) {
maxPosY = minPosY;
}
if (currentY > minPosY || previousState != MenuState.FULL_SCREEN) {
posY = minPosY;
} else if (currentY < maxPosY) {
posY = maxPosY;
} else {
posY = currentY;
}
} else {
posY = getMenuStatePosY(MenuState.FULL_SCREEN);
}
break;
default:
break;
}
if (portrait) {
mapActivity.updateStatusBarColor();
}
return posY;
}
private void updateMainViewLayout(int posY) {
MapActivity mapActivity = getMapActivity();
if (view != null && mapActivity != null) {
menuFullHeight = view.getHeight() - posY;
menuTopShadowAllHeight = menuTitleHeight;
ViewGroup.LayoutParams lp = mainView.getLayoutParams();
lp.height = Math.max(menuFullHeight, menuTitleHeight);
mainView.setLayoutParams(lp);
mainView.requestLayout();
updateToolbar();
}
}
private void applyPosY(final int currentY, final boolean needCloseMenu, boolean needMapAdjust,
final int previousMenuState, final int newMenuState, int dZoom) {
final int posY = getPosY(currentY, needCloseMenu, previousMenuState);
if (getViewY() != posY || dZoom != 0) {
if (posY < getViewY()) {
updateMainViewLayout(posY);
}
mainView.animate().y(posY)
.setDuration(200)
.setInterpolator(new DecelerateInterpolator())
.setListener(new AnimatorListenerAdapter() {
boolean canceled = false;
@Override
public void onAnimationStart(Animator animation) {
moving = true;
}
@Override
public void onAnimationCancel(Animator animation) {
canceled = true;
}
@Override
public void onAnimationEnd(Animator animation) {
moving = false;
if (!canceled) {
if (needCloseMenu) {
menu.hide();
} else {
updateMainViewLayout(posY);
if (previousMenuState != 0 && newMenuState != 0 && previousMenuState != newMenuState) {
doAfterMenuStateChange(previousMenuState, newMenuState);
}
}
}
}
})
.start();
if (needMapAdjust) {
adjustMapPosition(posY);
}
}
}
private void doAfterMenuStateChange(int previousState, int newState) {
runLayoutListener();
}
@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
private void runLayoutListener() {
if (view != null) {
ViewTreeObserver vto = view.getViewTreeObserver();
vto.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
if (view != null) {
ViewTreeObserver obs = view.getViewTreeObserver();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
obs.removeOnGlobalLayoutListener(this);
} else {
obs.removeGlobalOnLayoutListener(this);
}
if (getActivity() == null) {
return;
}
menuFullHeight = view.findViewById(R.id.main_view).getHeight();
int newMenuTopShadowAllHeight = view.findViewById(R.id.route_menu_top_shadow_all).getHeight();
int dy = shadowHeight;
menuTopShadowAllHeight = newMenuTopShadowAllHeight;
menuTitleHeight = menuTopShadowAllHeight + dy;
menuBottomViewHeight = view.findViewById(R.id.route_menu_cards_container).getHeight();
menuFullHeightMax = menuTitleHeight + menuBottomViewHeight;
if (!moving) {
doLayoutMenu();
}
initLayout = false;
}
}
});
}
}
private void doLayoutMenu() {
final int posY = getPosY(getViewY(), false, menu.getCurrentMenuState());
setViewY(posY, true, !initLayout);
updateMainViewLayout(posY);
}
public int getHeight() {
MapActivity mapActivity = getMapActivity();
if (menu != null && mapActivity != null) {
int height = getMenuStatePosY(menu.getCurrentMenuState());
return viewHeight - height - AndroidUtils.getStatusBarHeight(mapActivity);
} else {
return 0;
}
protected void calculateLayout(View view) {
super.calculateLayout(view);
menuTitleHeight = view.findViewById(R.id.route_menu_top_shadow_all).getHeight()
+ view.findViewById(R.id.control_buttons).getHeight()
- view.findViewById(R.id.buttons_shadow).getHeight();
}
private void adjustMapPosition(int y) {
OsmandApplication app = getMyApplication();
MapActivity mapActivity = getMapActivity();
if (menu.isSelectFromMapTouch() || app == null || mapActivity == null) {
if (menu == null || menu.isSelectFromMapTouch() || app == null || mapActivity == null) {
return;
}
@ -766,10 +296,10 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
int tileBoxWidthPx = 0;
int tileBoxHeightPx = 0;
if (!portrait) {
if (!isPortrait()) {
tileBoxWidthPx = tb.getPixWidth() - getWidth();
} else {
int fHeight = viewHeight - y - AndroidUtils.getStatusBarHeight(app);
int fHeight = getViewHeight() - y - AndroidUtils.getStatusBarHeight(app);
tileBoxHeightPx = tb.getPixHeight() - fHeight;
}
if (r.left != 0 && r.right != 0) {
@ -778,19 +308,11 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
}
}
public int getWidth() {
if (mainView != null) {
return mainView.getWidth();
} else {
return 0;
}
}
public void setBottomShadowVisible(boolean visible) {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null && bottomContainer != null) {
if (visible) {
AndroidUtils.setForeground(mapActivity, bottomContainer, nightMode,
AndroidUtils.setForeground(mapActivity, bottomContainer, isNightMode(),
R.drawable.bg_contextmenu_shadow, R.drawable.bg_contextmenu_shadow);
} else {
bottomContainer.setForeground(null);
@ -799,10 +321,14 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
}
public void updateInfo() {
if (menu != null) {
updateInfo(getView());
}
public void updateInfo(View view) {
if (menu != null && view != null) {
menu.updateInfo(view);
applyDayNightMode();
if (!moving) {
if (!isMoving()) {
runLayoutListener();
}
}
@ -815,14 +341,17 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
}
public void updateFromIcon() {
if (menu != null) {
View mainView = getMainView();
if (menu != null && mainView != null) {
menu.updateFromIcon(mainView);
}
}
public void updateRouteCalculationProgress(int progress) {
MapActivity mapActivity = getMapActivity();
if (mapActivity == null) {
View mainView = getMainView();
View view = getView();
if (mapActivity == null || mainView == null || view == null) {
return;
}
@ -847,7 +376,9 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
public void hideRouteCalculationProgressBar() {
MapActivity mapActivity = getMapActivity();
if (mapActivity == null) {
View mainView = getMainView();
View view = getView();
if (mapActivity == null || mainView == null || view == null) {
return;
}
@ -859,26 +390,27 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
if (progressBarButton != null) {
progressBarButton.setVisibility(View.GONE);
}
int color = nightMode ? R.color.main_font_dark : R.color.card_and_list_background_light;
int color = isNightMode() ? R.color.main_font_dark : R.color.card_and_list_background_light;
((TextView) view.findViewById(R.id.start_button_descr)).setTextColor(ContextCompat.getColor(mapActivity, color));
}
public void updateControlButtons() {
OsmandApplication app = getMyApplication();
MapActivity mapActivity = getMapActivity();
if (app != null && mapActivity != null) {
View view = getView();
if (app != null && mapActivity != null && view != null) {
TextViewExProgress textViewExProgress = (TextViewExProgress) view.findViewById(R.id.start_button_descr);
textViewExProgress.color1 = ContextCompat.getColor(mapActivity, nightMode ? R.color.main_font_dark : R.color.card_and_list_background_light);
textViewExProgress.color1 = ContextCompat.getColor(mapActivity, isNightMode() ? R.color.main_font_dark : R.color.card_and_list_background_light);
textViewExProgress.color2 = ContextCompat.getColor(mapActivity, R.color.description_font_and_bottom_sheet_icons);
boolean publicTransportMode = app.getRoutingHelper().getAppMode() == ApplicationMode.PUBLIC_TRANSPORT;
if (menu.isRouteCalculated()) {
if (menu != null && menu.isRouteCalculated()) {
if (publicTransportMode) {
AndroidUtils.setBackground(app, view.findViewById(R.id.start_button), nightMode, R.color.card_and_list_background_light, R.color.card_and_list_background_dark);
textViewExProgress.color1 = ContextCompat.getColor(mapActivity, nightMode ? R.color.active_buttons_and_links_dark : R.color.active_buttons_and_links_light);
AndroidUtils.setBackground(app, view.findViewById(R.id.start_button), isNightMode(), R.color.card_and_list_background_light, R.color.card_and_list_background_dark);
textViewExProgress.color1 = ContextCompat.getColor(mapActivity, isNightMode() ? R.color.active_buttons_and_links_dark : R.color.active_buttons_and_links_light);
} else {
AndroidUtils.setBackground(app, view.findViewById(R.id.start_button), nightMode, R.color.active_buttons_and_links_light, R.color.active_buttons_and_links_dark);
textViewExProgress.color1 = ContextCompat.getColor(mapActivity, nightMode ? R.color.main_font_dark : R.color.card_and_list_background_light);
AndroidUtils.setBackground(app, view.findViewById(R.id.start_button), isNightMode(), R.color.active_buttons_and_links_light, R.color.active_buttons_and_links_dark);
textViewExProgress.color1 = ContextCompat.getColor(mapActivity, isNightMode() ? R.color.main_font_dark : R.color.card_and_list_background_light);
}
textViewExProgress.percent = 1;
}
@ -914,13 +446,15 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
public void applyDayNightMode() {
MapActivity ctx = getMapActivity();
if (ctx == null) {
View mainView = getMainView();
View view = getView();
if (ctx == null || mainView == null || view == null) {
return;
}
boolean portraitMode = AndroidUiHelper.isOrientationPortrait(ctx);
boolean landscapeLayout = !portraitMode;
boolean nightMode = ctx.getMyApplication().getDaynightHelper().isNightModeForMapControls();
boolean nightMode = isNightMode();
if (!landscapeLayout) {
View menuView = view.findViewById(R.id.route_menu_top_shadow_all);
AndroidUtils.setBackground(ctx, menuView, nightMode, R.color.card_and_list_background_light, R.color.card_and_list_background_dark);
@ -963,7 +497,7 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
updateControlButtons();
}
public static boolean showInstance(final MapActivity mapActivity) {
public static boolean showInstance(final MapActivity mapActivity, int initialMenuState) {
boolean portrait = AndroidUiHelper.isOrientationPortrait(mapActivity);
int slideInAnim = 0;
int slideOutAnim = 0;
@ -981,6 +515,9 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
mapActivity.getContextMenu().hideMenues();
MapRouteInfoMenuFragment fragment = new MapRouteInfoMenuFragment();
Bundle args = new Bundle();
fragment.setArguments(args);
args.putInt(ContextMenuFragment.MENU_STATE_KEY, initialMenuState);
mapActivity.getSupportFragmentManager()
.beginTransaction()
.setCustomAnimations(slideInAnim, slideOutAnim, slideInAnim, slideOutAnim)
@ -998,8 +535,8 @@ public class MapRouteInfoMenuFragment extends BaseOsmAndFragment {
public void setupRouteCalculationButtonProgressBar(@NonNull ProgressBar pb) {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
int bgColor = ContextCompat.getColor(mapActivity, nightMode ? R.color.activity_background_dark : R.color.activity_background_light);
int progressColor = ContextCompat.getColor(mapActivity, nightMode ? R.color.active_buttons_and_links_dark : R.color.active_buttons_and_links_light);
int bgColor = ContextCompat.getColor(mapActivity, isNightMode() ? R.color.activity_background_dark : R.color.activity_background_light);
int progressColor = ContextCompat.getColor(mapActivity, isNightMode() ? R.color.active_buttons_and_links_dark : R.color.active_buttons_and_links_light);
pb.setProgressDrawable(AndroidUtils.createProgressDrawable(bgColor, progressColor));
}
}

View file

@ -26,8 +26,6 @@ import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnLongClickListener;
import android.view.ViewGroup;
import android.view.animation.Animation;
import android.view.animation.Transformation;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
@ -102,9 +100,12 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
private String destinationStreetStr = "";
private int pageMarginPx;
private int toolbarHeightPx;
private int landscapeWidthPx;
private GPXFile gpx;
@Nullable
private OrderedLineDataSet slopeDataSet;
@Nullable
private OrderedLineDataSet elevationDataSet;
private GpxDisplayItem gpxItem;
private List<BaseCard> menuCards = new ArrayList<>();
@ -116,21 +117,16 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
return R.layout.route_info_layout;
}
@Override
public int getMainViewId() {
return R.id.main_view;
}
@Override
public int getBottomScrollViewId() {
return R.id.route_menu_bottom_scroll;
}
@Override
public int getHeaderViewHeight() {
return !menuCards.isEmpty() ? menuCards.get(0).getViewHeight() : 0;
}
@Override
public boolean isHeaderViewDetached() {
return false;
}
@Override
public int getToolbarHeight() {
return toolbarHeightPx;
@ -141,6 +137,11 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
return false;
}
@Override
public int getLandscapeWidth() {
return landscapeWidthPx;
}
public int getRouteId() {
return routeId;
}
@ -154,18 +155,28 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
}
pageMarginPx = dpToPx(PAGE_MARGIN);
toolbarHeightPx = getResources().getDimensionPixelSize(R.dimen.dashboard_map_toolbar);
landscapeWidthPx = dpToPx(345f);
View view = super.onCreateView(inflater, container, savedInstanceState);
if (view != null) {
if (isPortrait()) {
view.findViewById(getBottomScrollViewId()).setBackgroundDrawable(null);
}
updateCards(view);
updateCards();
runLayoutListener();
}
return view;
}
@Override
public int getShadowHeight() {
int res = super.getShadowHeight();
if (getCurrentMenuState() == MenuState.HEADER_ONLY) {
res += pageMarginPx;
}
return res;
}
@Nullable
public PublicTransportCard getTransportCard() {
return transportCard;
@ -176,7 +187,9 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
super.changeMenuState(currentY, slidingUp, slidingDown, animated);
View mainView = getMainView();
if (mainView != null && isPortrait()) {
final LinearLayout cardsContainer = (LinearLayout) mainView.findViewById(R.id.route_menu_cards_container);
updateCardsLayout();
/*
LinearLayout cardsContainer = getCardsContainer();
final FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) cardsContainer.getLayoutParams();
final int currentMenuState = getCurrentMenuState();
if (animated) {
@ -186,6 +199,7 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
Animation a = new Animation() {
@Override
protected void applyTransformation(float interpolatedTime, Transformation t) {
LinearLayout cardsContainer = getCardsContainer();
int margin = marginStart + (int) ((marginEnd - marginStart) * interpolatedTime);
layoutParams.setMargins(margin, 0, margin, 0);
cardsContainer.setLayoutParams(layoutParams);
@ -211,22 +225,27 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
} else {
updateCardsLayout();
}
*/
}
}
private void updateCardsLayout() {
View mainView = getMainView();
if (mainView != null) {
LinearLayout cardsContainer = (LinearLayout) mainView.findViewById(R.id.route_menu_cards_container);
LinearLayout cardsContainer = getCardsContainer();
View topShadow = getTopShadow();
FrameLayout bottomContainer = getBottomContainer();
FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) cardsContainer.getLayoutParams();
if (getCurrentMenuState() == MenuState.HEADER_ONLY) {
layoutParams.setMargins(pageMarginPx, 0, pageMarginPx, 0);
topShadow.setVisibility(View.INVISIBLE);
bottomContainer.setBackgroundDrawable(null);
AndroidUtils.setBackground(mainView.getContext(), cardsContainer, isNightMode(), R.drawable.travel_card_bg_light, R.drawable.travel_card_bg_dark);
mainView.setBackgroundDrawable(null);
} else {
layoutParams.setMargins(0, 0, 0, 0);
cardsContainer.setBackgroundDrawable(null);
AndroidUtils.setBackground(mainView.getContext(), mainView, isNightMode(), R.drawable.bg_map_route_menu_light, R.drawable.bg_map_route_menu_dark);
topShadow.setVisibility(View.VISIBLE);
AndroidUtils.setBackground(mainView.getContext(), bottomContainer, isNightMode(), R.color.route_info_bg_light, R.color.route_info_bg_dark);
AndroidUtils.setBackground(mainView.getContext(), cardsContainer, isNightMode(), R.color.route_info_bg_light, R.color.route_info_bg_dark);
}
cardsContainer.setLayoutParams(layoutParams);
}
@ -237,36 +256,40 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
super.setViewY(y, animated, adjustMapPos);
View mainView = getMainView();
if (mainView != null && isPortrait()) {
LinearLayout cardsContainer = getCardsContainer();
View topShadow = getTopShadow();
FrameLayout bottomContainer = getBottomContainer();
int headerOnlyY = getMenuStatePosY(MenuState.HEADER_ONLY);
int halfScreenY = getMenuStatePosY(MenuState.HALF_SCREEN);
float margin = 0;
if (y > headerOnlyY) {
margin = PAGE_MARGIN;
} else if (y > halfScreenY) {
margin = PAGE_MARGIN * (1f - (float)(headerOnlyY - y) / (headerOnlyY - halfScreenY));
margin = PAGE_MARGIN;//* (1f - (float)(headerOnlyY - y) / (headerOnlyY - halfScreenY));
}
int marginPx = dpToPx(margin);
LinearLayout cardsContainer = (LinearLayout) mainView.findViewById(R.id.route_menu_cards_container);
FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) cardsContainer.getLayoutParams();
if (layoutParams.leftMargin != marginPx) {
layoutParams.setMargins(marginPx, 0, marginPx, 0);
}
if (y > halfScreenY) {
topShadow.setVisibility(View.INVISIBLE);
bottomContainer.setBackgroundDrawable(null);
AndroidUtils.setBackground(mainView.getContext(), cardsContainer, isNightMode(), R.drawable.travel_card_bg_light, R.drawable.travel_card_bg_dark);
mainView.setBackgroundDrawable(null);
} else {
cardsContainer.setBackgroundDrawable(null);
AndroidUtils.setBackground(mainView.getContext(),mainView, isNightMode(), R.drawable.bg_map_route_menu_light, R.drawable.bg_map_route_menu_dark);
topShadow.setVisibility(View.VISIBLE);
AndroidUtils.setBackground(mainView.getContext(), bottomContainer, isNightMode(), R.color.route_info_bg_light, R.color.route_info_bg_dark);
AndroidUtils.setBackground(mainView.getContext(), cardsContainer, isNightMode(), R.color.route_info_bg_light, R.color.route_info_bg_dark);
}
}
}
private void updateCards(@NonNull View view) {
private void updateCards() {
MapActivity mapActivity = getMapActivity();
if (mapActivity != null) {
OsmandApplication app = mapActivity.getMyApplication();
RoutingHelper routingHelper = app.getRoutingHelper();
LinearLayout cardsContainer = (LinearLayout) view.findViewById(R.id.route_menu_cards_container);
LinearLayout cardsContainer = getCardsContainer();
cardsContainer.removeAllViews();
if (routeId != -1) {
List<TransportRouteResult> routes = routingHelper.getTransportRoutingHelper().getRoutes();
@ -355,6 +378,7 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
return false;
}
});
statisticCard.setTransparentBackground(true);
menuCards.add(statisticCard);
cardsContainer.addView(statisticCard.build(mapActivity));
buildRowDivider(cardsContainer, false);
@ -1046,10 +1070,10 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
@Override
public void geocodingDone(String address) {
RouteDetailsFragment fragment = fragmentRef.get();
View view = getView();
if (!TextUtils.isEmpty(address) && fragment != null && !fragment.isPaused() && view != null) {
if (!TextUtils.isEmpty(address) && fragment != null && !fragment.isPaused()) {
fragment.destinationStreetStr = address;
fragment.updateCards(view);
fragment.updateCards();
doAfterMenuStateChange(0, 0);
}
}
}, null);
@ -1449,11 +1473,13 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
float distance = i * 5;
inclines.add(i, new Incline(0f, distance));
}
if (slopeDataSet != null) {
float lastDistance = slopeDataSet.getEntryForIndex(size - 1).getX();
for (int i = 1; i <= 10; i++) {
float distance = lastDistance * 1000f + i * 5f;
inclines.add(new Incline(0f, distance));
}
}
for (Incline incline : inclines) {
incline.computeBoundaries(minIncline, maxIncline);
}
@ -1474,7 +1500,7 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
}
void openDetails() {
if (gpxItem != null) {
if (gpxItem != null && elevationDataSet != null) {
OsmandApplication app = requireMyApplication();
LatLon location = null;
WptPt wpt = null;

View file

@ -86,6 +86,18 @@ public class PublicTransportCard extends BaseCard {
fromLine.setText(getFirstLineDescrSpan());
wayLine.setText(getSecondLineDescrSpan(segments));
updateButtons();
view.findViewById(R.id.bottom_shadow).setVisibility(showBottomShadow ? View.VISIBLE : View.GONE);
view.findViewById(R.id.card_divider).setVisibility(showTopShadow ? View.VISIBLE : View.GONE);
view.findViewById(R.id.top_divider).setVisibility(!showTopShadow && showDivider ? View.VISIBLE : View.GONE);
if (transparentBackground) {
view.findViewById(R.id.routes_info_container).setBackgroundDrawable(null);
}
}
public void updateButtons() {
int color = getActiveColor();
FrameLayout detailsButton = (FrameLayout) view.findViewById(R.id.details_button);
TextView detailsButtonDescr = (TextView) view.findViewById(R.id.details_button_descr);
@ -95,7 +107,6 @@ public class PublicTransportCard extends BaseCard {
} else {
AndroidUtils.setBackground(app, detailsButton, nightMode, R.drawable.btn_border_trans_light, R.drawable.btn_border_trans_dark);
}
int color = getActiveColor();
detailsButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
@ -107,7 +118,6 @@ public class PublicTransportCard extends BaseCard {
}
}
});
FrameLayout showButton = (FrameLayout) view.findViewById(R.id.show_button);
TextView showButtonDescr = (TextView) view.findViewById(R.id.show_button_descr);
if (isCurrentRoute()) {
@ -136,13 +146,6 @@ public class PublicTransportCard extends BaseCard {
});
}
showButtonDescr.setTextColor(color);
view.findViewById(R.id.bottom_shadow).setVisibility(showBottomShadow ? View.VISIBLE : View.GONE);
view.findViewById(R.id.card_divider).setVisibility(showTopShadow ? View.VISIBLE : View.GONE);
view.findViewById(R.id.top_divider).setVisibility(!showTopShadow && showDivider ? View.VISIBLE : View.GONE);
if (transparentBackground) {
view.findViewById(R.id.routes_info_container).setBackgroundDrawable(null);
}
}
public int getRouteId() {

View file

@ -1,6 +1,7 @@
package net.osmand.plus.routepreparationmenu.cards;
import android.graphics.Matrix;
import android.support.annotation.Nullable;
import android.support.v4.content.ContextCompat;
import android.text.SpannableStringBuilder;
import android.text.style.ForegroundColorSpan;
@ -13,17 +14,20 @@ import com.github.mikephil.charting.charts.LineChart;
import com.github.mikephil.charting.data.LineData;
import com.github.mikephil.charting.highlight.Highlight;
import com.github.mikephil.charting.interfaces.datasets.ILineDataSet;
import com.github.mikephil.charting.listener.ChartTouchListener;
import com.github.mikephil.charting.listener.ChartTouchListener.ChartGesture;
import com.github.mikephil.charting.listener.OnChartGestureListener;
import net.osmand.GPXUtilities;
import net.osmand.GPXUtilities.GPXFile;
import net.osmand.GPXUtilities.GPXTrackAnalysis;
import net.osmand.plus.GpxSelectionHelper;
import net.osmand.plus.GpxSelectionHelper.GpxDisplayItem;
import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.R;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.helpers.GpxUiHelper;
import net.osmand.plus.helpers.GpxUiHelper.GPXDataSetAxisType;
import net.osmand.plus.helpers.GpxUiHelper.OrderedLineDataSet;
import net.osmand.plus.routing.RoutingHelper;
import java.util.ArrayList;
@ -32,9 +36,11 @@ import java.util.List;
public class RouteStatisticCard extends BaseCard {
private GPXFile gpx;
private GpxSelectionHelper.GpxDisplayItem gpxItem;
private GpxUiHelper.OrderedLineDataSet slopeDataSet;
private GpxUiHelper.OrderedLineDataSet elevationDataSet;
private GpxDisplayItem gpxItem;
@Nullable
private OrderedLineDataSet slopeDataSet;
@Nullable
private OrderedLineDataSet elevationDataSet;
private View.OnTouchListener onTouchListener;
public RouteStatisticCard(MapActivity mapActivity, GPXFile gpx, View.OnTouchListener onTouchListener) {
@ -87,7 +93,7 @@ public class RouteStatisticCard extends BaseCard {
String arriveStr = app.getString(R.string.arrive_at_time, OsmAndFormatter.getFormattedTime(time, true));
arriveTimeTv.setText(arriveStr);
GPXUtilities.GPXTrackAnalysis analysis = gpx.getAnalysis(0);
GPXTrackAnalysis analysis = gpx.getAnalysis(0);
buildHeader(analysis);
@ -106,13 +112,19 @@ public class RouteStatisticCard extends BaseCard {
((ImageView) view.findViewById(R.id.range_icon)).setImageDrawable(getContentIcon(R.drawable.ic_action_altitude_average));
((ImageView) view.findViewById(R.id.descent_icon)).setImageDrawable(getContentIcon(R.drawable.ic_action_altitude_descent));
((ImageView) view.findViewById(R.id.ascent_icon)).setImageDrawable(getContentIcon(R.drawable.ic_action_altitude_ascent));
if (isTransparentBackground()) {
view.setBackgroundDrawable(null);
}
}
public GpxUiHelper.OrderedLineDataSet getSlopeDataSet() {
@Nullable
public OrderedLineDataSet getSlopeDataSet() {
return slopeDataSet;
}
public GpxUiHelper.OrderedLineDataSet getElevationDataSet() {
@Nullable
public OrderedLineDataSet getElevationDataSet() {
return elevationDataSet;
}
@ -127,23 +139,27 @@ public class RouteStatisticCard extends BaseCard {
}
}
private void buildHeader(GPXUtilities.GPXTrackAnalysis analysis) {
private void buildHeader(GPXTrackAnalysis analysis) {
final LineChart mChart = (LineChart) view.findViewById(R.id.chart);
GpxUiHelper.setupGPXChart(mChart, 4, 24f, 16f, !nightMode, true);
mChart.setOnTouchListener(onTouchListener);
if (analysis.hasElevationData) {
List<ILineDataSet> dataSets = new ArrayList<>();
elevationDataSet = GpxUiHelper.createGPXElevationDataSet(app, mChart, analysis,
GpxUiHelper.GPXDataSetAxisType.DISTANCE, false, true);
OrderedLineDataSet slopeDataSet = null;
OrderedLineDataSet elevationDataSet = GpxUiHelper.createGPXElevationDataSet(app, mChart, analysis,
GPXDataSetAxisType.DISTANCE, false, true);
if (elevationDataSet != null) {
dataSets.add(elevationDataSet);
}
slopeDataSet = GpxUiHelper.createGPXSlopeDataSet(app, mChart, analysis,
GpxUiHelper.GPXDataSetAxisType.DISTANCE, elevationDataSet.getValues(), true, true);
GPXDataSetAxisType.DISTANCE, elevationDataSet.getValues(), true, true);
}
if (slopeDataSet != null) {
dataSets.add(slopeDataSet);
}
this.elevationDataSet = elevationDataSet;
this.slopeDataSet = slopeDataSet;
LineData data = new LineData(dataSets);
mChart.setData(data);
@ -152,7 +168,7 @@ public class RouteStatisticCard extends BaseCard {
float highlightDrawX = -1;
@Override
public void onChartGestureStart(MotionEvent me, ChartTouchListener.ChartGesture lastPerformedGesture) {
public void onChartGestureStart(MotionEvent me, ChartGesture lastPerformedGesture) {
if (mChart.getHighlighted() != null && mChart.getHighlighted().length > 0) {
highlightDrawX = mChart.getHighlighted()[0].getDrawX();
} else {
@ -161,7 +177,7 @@ public class RouteStatisticCard extends BaseCard {
}
@Override
public void onChartGestureEnd(MotionEvent me, ChartTouchListener.ChartGesture lastPerformedGesture) {
public void onChartGestureEnd(MotionEvent me, ChartGesture lastPerformedGesture) {
gpxItem.chartMatrix = new Matrix(mChart.getViewPortHandler().getMatrixTouch());
Highlight[] highlights = mChart.getHighlighted();
if (highlights != null && highlights.length > 0) {

View file

@ -17,6 +17,7 @@ import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.R;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.helpers.GpxUiHelper;
import net.osmand.plus.helpers.GpxUiHelper.OrderedLineDataSet;
import net.osmand.plus.routing.RoutingHelper;
import java.util.ArrayList;
@ -112,17 +113,16 @@ public class SimpleRouteCard extends BaseCard {
final GPXUtilities.GPXTrackAnalysis analysis = gpx.getAnalysis(0);
GpxUiHelper.setupGPXChart(mChart, 4, 4f, 4f, !nightMode, false);
GpxUiHelper.OrderedLineDataSet elevationDataSet;
GpxUiHelper.OrderedLineDataSet slopeDataSet;
if (analysis.hasElevationData) {
List<ILineDataSet> dataSets = new ArrayList<>();
elevationDataSet = GpxUiHelper.createGPXElevationDataSet(app, mChart, analysis,
OrderedLineDataSet slopeDataSet = null;
OrderedLineDataSet elevationDataSet = GpxUiHelper.createGPXElevationDataSet(app, mChart, analysis,
GpxUiHelper.GPXDataSetAxisType.DISTANCE, false, true);
if (elevationDataSet != null) {
dataSets.add(elevationDataSet);
}
slopeDataSet = GpxUiHelper.createGPXSlopeDataSet(app, mChart, analysis,
GpxUiHelper.GPXDataSetAxisType.DISTANCE, elevationDataSet.getValues(), true, true);
}
if (slopeDataSet != null) {
dataSets.add(slopeDataSet);
}

View file

@ -48,6 +48,7 @@ import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.activities.MapActivity.ShowQuickSearchMode;
import net.osmand.plus.dashboard.DashboardOnMap.DashboardType;
import net.osmand.plus.dialogs.DirectionsDialogs;
import net.osmand.plus.helpers.AndroidUiHelper;
import net.osmand.plus.mapcontextmenu.MapContextMenu;
import net.osmand.plus.mapcontextmenu.other.TrackDetailsMenu;
import net.osmand.plus.rastermaps.OsmandRasterMapsPlugin;
@ -728,9 +729,14 @@ public class MapControlsLayer extends OsmandMapLayer {
updateControls(tileBox, nightMode);
}
public boolean isPotrait() {
return AndroidUiHelper.isOrientationPortrait(mapActivity);
}
@SuppressWarnings("deprecation")
private void updateControls(@NonNull RotatedTileBox tileBox, DrawSettings drawSettings) {
boolean isNight = drawSettings != null && drawSettings.isNightMode();
boolean portrait = isPotrait();
int shadw = isNight ? Color.TRANSPARENT : Color.WHITE;
int textColor = isNight ? mapActivity.getResources().getColor(R.color.widgettext_night) : Color.BLACK;
if (shadowColor != shadw) {
@ -769,8 +775,8 @@ public class MapControlsLayer extends OsmandMapLayer {
routePlanningBtn.updateVisibility(showButtons);
menuControl.updateVisibility(showButtons);
mapZoomIn.updateVisibility(!routeDialogOpened && !contextMenuOpened && !isInChoosingRoutesMode());
mapZoomOut.updateVisibility(!routeDialogOpened && !contextMenuOpened && !isInChoosingRoutesMode());
mapZoomIn.updateVisibility(!routeDialogOpened && !contextMenuOpened && (!isInChoosingRoutesMode() || !portrait));
mapZoomOut.updateVisibility(!routeDialogOpened && !contextMenuOpened && (!isInChoosingRoutesMode() || !portrait));
boolean forceHideCompass = routeDialogOpened || trackDialogOpened
|| isInMeasurementToolMode() || isInPlanRouteMode() || contextMenuOpened || isInChoosingRoutesMode();
compassHud.forceHideCompass = forceHideCompass;
@ -844,6 +850,7 @@ public class MapControlsLayer extends OsmandMapLayer {
}
private void updateMyLocation(RoutingHelper rh, boolean dialogOpened) {
boolean portrait = isPotrait();
Location lastKnownLocation = mapActivity.getMyApplication().getLocationProvider().getLastKnownLocation();
boolean enabled = lastKnownLocation != null;
boolean tracked = mapActivity.getMapViewTrackingUtilities().isMapLinkedToLocation();
@ -862,7 +869,7 @@ public class MapControlsLayer extends OsmandMapLayer {
backToLocationControl.iv.setContentDescription(mapActivity.getString(R.string.map_widget_back_to_loc));
}
boolean visible = !(tracked && rh.isFollowingMode());
backToLocationControl.updateVisibility(visible && !dialogOpened && !isInPlanRouteMode() && !isInChoosingRoutesMode());
backToLocationControl.updateVisibility(visible && !dialogOpened && !isInPlanRouteMode() && (!isInChoosingRoutesMode() || !portrait));
if (app.accessibilityEnabled()) {
backToLocationControl.iv.setClickable(enabled && visible);
}