From 5d6101f23aae4c9d2324bb0a33ca688fbde06747 Mon Sep 17 00:00:00 2001 From: Skalii Date: Wed, 20 Jan 2021 17:22:44 +0200 Subject: [PATCH] set overview as default tab; add layout for overview fragment; add layouts for action items; add OverviewCard. --- OsmAnd/res/layout/gpx_overview_fragment.xml | 104 ++++++ OsmAnd/res/layout/item_gpx_action.xml | 22 ++ OsmAnd/res/layout/item_gpx_action_segment.xml | 46 +++ .../res/menu/track_menu_bottom_navigation.xml | 8 +- .../net/osmand/plus/track/OverviewCard.java | 334 ++++++++++++++++++ .../osmand/plus/track/TrackMenuFragment.java | 22 +- 6 files changed, 528 insertions(+), 8 deletions(-) create mode 100644 OsmAnd/res/layout/gpx_overview_fragment.xml create mode 100644 OsmAnd/res/layout/item_gpx_action.xml create mode 100644 OsmAnd/res/layout/item_gpx_action_segment.xml create mode 100644 OsmAnd/src/net/osmand/plus/track/OverviewCard.java diff --git a/OsmAnd/res/layout/gpx_overview_fragment.xml b/OsmAnd/res/layout/gpx_overview_fragment.xml new file mode 100644 index 0000000000..e02826fcbf --- /dev/null +++ b/OsmAnd/res/layout/gpx_overview_fragment.xml @@ -0,0 +1,104 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/OsmAnd/res/layout/item_gpx_action.xml b/OsmAnd/res/layout/item_gpx_action.xml new file mode 100644 index 0000000000..940f85d8bf --- /dev/null +++ b/OsmAnd/res/layout/item_gpx_action.xml @@ -0,0 +1,22 @@ + + + + + + + + \ No newline at end of file diff --git a/OsmAnd/res/layout/item_gpx_action_segment.xml b/OsmAnd/res/layout/item_gpx_action_segment.xml new file mode 100644 index 0000000000..962941b95c --- /dev/null +++ b/OsmAnd/res/layout/item_gpx_action_segment.xml @@ -0,0 +1,46 @@ + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/OsmAnd/res/menu/track_menu_bottom_navigation.xml b/OsmAnd/res/menu/track_menu_bottom_navigation.xml index fa07fb12a4..1b0de6b246 100644 --- a/OsmAnd/res/menu/track_menu_bottom_navigation.xml +++ b/OsmAnd/res/menu/track_menu_bottom_navigation.xml @@ -1,10 +1,10 @@ - - - - + items = new ArrayList<>(); + items.add(item1); + items.add(item2); + items.add(item3); + items.add(item4); + items.add(item5); + items.add(item6); + + rvOverview = view.findViewById(R.id.recycler_overview); + LinearLayoutManager llManager = new LinearLayoutManager(app); + llManager.setOrientation(LinearLayoutManager.HORIZONTAL); + rvOverview.setLayoutManager(llManager); + rvOverview.setItemAnimator(new DefaultItemAnimator()); + final SegmentItemAdapter oiAdapter = new SegmentItemAdapter(items); + rvOverview.setAdapter(oiAdapter); + rvOverview.addItemDecoration(new HorizontalDividerDecoration(app)); + + } + + private void initShowButton(final int iconColorDef, final int iconColorPres) { + final AppCompatImageView image = showButton.findViewById(R.id.image); + final AppCompatImageView filled = showButton.findViewById(R.id.filled); + final int iconShowResId = R.drawable.ic_action_view; + final int iconHideResId = R.drawable.ic_action_hide; + final boolean[] gpxFileSelected = {isGpxFileSelected(app, gpxFile)}; + filled.setImageResource(R.drawable.bg_topbar_shield_exit_ref); + filled.setAlpha(gpxFileSelected[0] ? 1f : 0.1f); + setImageDrawable(image, gpxFileSelected[0] ? iconShowResId : iconHideResId, + gpxFileSelected[0] ? iconColorPres : iconColorDef); + showButton.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + gpxFileSelected[0] = !gpxFileSelected[0]; + + setImageDrawable(image, gpxFileSelected[0] ? iconShowResId : iconHideResId, + gpxFileSelected[0] ? iconColorPres : iconColorDef); + + filled.setAlpha(gpxFileSelected[0] ? 1f : 0.1f); + + CardListener listener = getListener(); + if (listener != null) { + listener.onCardButtonPressed(OverviewCard.this, SHOW_ON_MAP_BUTTON_INDEX); + } + } + }); + } + + private void initAppearanceButton(int iconColorDef, int iconColorPres) { + initButton(appearanceButton, APPEARANCE_BUTTON_INDEX, R.drawable.ic_action_appearance, iconColorDef, iconColorPres); + } + + private void initEditButton(int iconColorDef, int iconColorPres) { + initButton(editButton, EDIT_BUTTON_INDEX, R.drawable.ic_action_edit_dark, iconColorDef, iconColorPres); + } + + private void initDirectionsButton(int iconColorDef, int iconColorPres) { + initButton(directionsButton, DIRECTIONS_BUTTON_INDEX, R.drawable.ic_action_gdirections_dark, iconColorDef, iconColorPres); + } + + private void initButton(View item, final int buttonIndex, int iconResId, int iconColorDef, int iconColorPres) { + final AppCompatImageView image = item.findViewById(R.id.image); + final AppCompatImageView filled = item.findViewById(R.id.filled); + filled.setImageResource(R.drawable.bg_topbar_shield_exit_ref); + filled.setAlpha(0.1f); + setImageDrawable(image, iconResId, iconColorDef); + setOnTouchItem(item, image, filled, iconResId, iconColorDef, iconColorPres); + item.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + CardListener listener = getListener(); + if (listener != null) { + listener.onCardButtonPressed(OverviewCard.this, buttonIndex); + } + } + }); + } + + private void setImageDrawable(ImageView iv, @DrawableRes int resId, @ColorRes int color) { + Drawable icon = app.getUIUtilities().getIcon(resId, color); + iv.setImageDrawable(icon); + } + + private void setOnTouchItem(View item, final ImageView image, final ImageView filled, @DrawableRes final int resId, @ColorRes final int colorDef, @ColorRes final int colorPres) { + item.setOnTouchListener(new View.OnTouchListener() { + @SuppressLint("ClickableViewAccessibility") + @Override + public boolean onTouch(View v, MotionEvent event) { + switch (event.getAction()) { + case MotionEvent.ACTION_DOWN: { + filled.setAlpha(1f); + setImageDrawable(image, resId, colorPres); + break; + } + case MotionEvent.ACTION_UP: + case MotionEvent.ACTION_CANCEL: { + filled.setAlpha(0.1f); + setImageDrawable(image, resId, colorDef); + break; + } + } + return false; + } + }); + } + + private class SegmentItemAdapter extends RecyclerView.Adapter { + private final List segmentItems; + + public SegmentItemAdapter(List segmentItems) { + this.segmentItems = segmentItems; + } + + @Override + public int getItemCount() { + return segmentItems.size(); + } + + @NonNull + @Override + public SegmentItemViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { + View itemView = LayoutInflater.from(parent.getContext()) + .inflate(R.layout.item_gpx_action_segment, parent, false); + return new SegmentItemViewHolder(itemView); + } + + @Override + public void onBindViewHolder(SegmentItemViewHolder holder, int position) { + SegmentItem item = segmentItems.get(position); + holder.bind(item); + } + + + class SegmentItemViewHolder extends RecyclerView.ViewHolder { + private final TextViewEx valueText; + private final TextView titleText; + private final AppCompatImageView imageView; + + SegmentItemViewHolder(View view) { + super(view); + valueText = view.findViewById(R.id.value); + titleText = view.findViewById(R.id.title); + imageView = view.findViewById(R.id.image); + } + + public void bind(SegmentItem overviewItem) { + valueText.setText(overviewItem.value); + titleText.setText(overviewItem.title); + setImageDrawable(imageView, overviewItem.imageResId, R.color.text_color_primary_light); //todo change color + } + } + } + + private class HorizontalDividerDecoration extends RecyclerView.ItemDecoration { + private final Drawable divider; + + public HorizontalDividerDecoration(Context context) { + int[] ATTRS = new int[]{android.R.attr.listDivider}; + final TypedArray a = context.obtainStyledAttributes(ATTRS); + divider = a.getDrawable(0); + a.recycle(); +// mDivider = getMyApplication().getUIUtilities().getIcon(R.drawable.divider_solid, R.color.divider_color_light); //todo change drawable + } + + @Override + public void onDraw(@NonNull Canvas c, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) { + drawHorizontal(c, parent); + } + + public void drawHorizontal(Canvas c, RecyclerView parent) { + final int marginV = parent.getContext().getResources().getDimensionPixelSize(R.dimen.map_small_button_margin); + final int marginH = parent.getContext().getResources().getDimensionPixelSize(R.dimen.content_padding); + final int childCount = parent.getChildCount(); + for (int i = 0; i < childCount; i++) { + final View child = parent.getChildAt(i); + final int left = child.getRight() - divider.getIntrinsicWidth() + marginH; + final int right = left + divider.getIntrinsicHeight(); + final int top = child.getTop() + marginV; + final int bottom = child.getBottom() - marginV; + divider.setBounds(left, top, right, bottom); + divider.draw(c); + } + } + + @Override + public void getItemOffsets(Rect outRect, @NonNull View view, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) { + int marginV = parent.getContext().getResources().getDimensionPixelSize(R.dimen.map_small_button_margin); + int marginH = parent.getContext().getResources().getDimensionPixelSize(R.dimen.content_padding); + outRect.set(marginH - divider.getIntrinsicWidth(), marginV, marginH + divider.getIntrinsicWidth(), marginV); + } + } + + private class SegmentItem { + private String title; + private String value; + private int imageResId; + + public SegmentItem(String title, String value, int imageResId) { + this.title = title; + this.value = value; + this.imageResId = imageResId; + } + + public String getTitle() { + return title; + } + + public void setTitle(String title) { + this.title = title; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } + + public int getImageResId() { + return imageResId; + } + + public void setImageResId(int imageResId) { + this.imageResId = imageResId; + } + } +} \ No newline at end of file diff --git a/OsmAnd/src/net/osmand/plus/track/TrackMenuFragment.java b/OsmAnd/src/net/osmand/plus/track/TrackMenuFragment.java index 03f8ab374a..f102331bfc 100644 --- a/OsmAnd/src/net/osmand/plus/track/TrackMenuFragment.java +++ b/OsmAnd/src/net/osmand/plus/track/TrackMenuFragment.java @@ -109,15 +109,17 @@ public class TrackMenuFragment extends ContextMenuScrollFragment implements Card private TextView headerTitle; private ImageView headerIcon; private BottomNavigationView bottomNav; - private TrackMenuType menuType = TrackMenuType.TRACK; + private TrackMenuType menuType = TrackMenuType.OVERVIEW; private SegmentsCard segmentsCard; private OptionsCard optionsCard; + private OverviewCard overviewCard; private TrackChartPoints trackChartPoints; private int menuTitleHeight; public enum TrackMenuType { + OVERVIEW(R.id.action_overview, R.string.shared_string_overview), TRACK(R.id.action_track, R.string.shared_string_gpx_tracks), POINTS(R.id.action_points, R.string.shared_string_gpx_points), OPTIONS(R.id.action_options, R.string.shared_string_options); @@ -234,7 +236,19 @@ public class TrackMenuFragment extends ContextMenuScrollFragment implements Card if (mapActivity != null) { ViewGroup cardsContainer = getCardsContainer(); cardsContainer.removeAllViews(); - if (menuType == TrackMenuType.TRACK) { + if (menuType == TrackMenuType.OVERVIEW) { + if (overviewCard != null && overviewCard.getView() != null) { + ViewGroup parent = (ViewGroup) overviewCard.getView().getParent(); + if (parent != null) { + parent.removeAllViews(); + } + cardsContainer.addView(overviewCard.getView()); + } else { + overviewCard = new OverviewCard(mapActivity, displayHelper, this); + overviewCard.setListener(this); + cardsContainer.addView(overviewCard.build(mapActivity)); + } + } else if (menuType == TrackMenuType.TRACK) { if (segmentsCard != null && segmentsCard.getView() != null) { ViewGroup parent = (ViewGroup) segmentsCard.getView().getParent(); if (parent != null) { @@ -415,7 +429,7 @@ public class TrackMenuFragment extends ContextMenuScrollFragment implements Card if (mapActivity == null) { return; } - if (card instanceof OptionsCard) { + if (card instanceof OptionsCard || card instanceof OverviewCard) { final GPXFile gpxFile = getGpx(); if (buttonIndex == SHOW_ON_MAP_BUTTON_INDEX) { boolean gpxFileSelected = !isGpxFileSelected(app, gpxFile); @@ -567,7 +581,7 @@ public class TrackMenuFragment extends ContextMenuScrollFragment implements Card BottomNavigationView bottomNav = view.findViewById(R.id.bottom_navigation); bottomNav.setItemIconTintList(navColorStateList); bottomNav.setItemTextColor(navColorStateList); - bottomNav.setSelectedItemId(R.id.action_track); + bottomNav.setSelectedItemId(R.id.action_overview); bottomNav.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() { @Override public boolean onNavigationItemSelected(@NonNull MenuItem item) {