diff --git a/OsmAnd/res/layout/enough_space_warning_card.xml b/OsmAnd/res/layout/enough_space_warning_card.xml index a39076eb99..d572d20366 100644 --- a/OsmAnd/res/layout/enough_space_warning_card.xml +++ b/OsmAnd/res/layout/enough_space_warning_card.xml @@ -36,6 +36,7 @@ android:layout_width="match_parent" android:layout_height="wrap_content" android:letterSpacing="@dimen/text_button_letter_spacing" + android:paddingBottom="@dimen/measurement_tool_menu_title_padding_bottom" android:text="@string/export_not_enough_space" android:textColor="?android:textColorPrimary" android:textSize="@dimen/default_list_text_size" diff --git a/OsmAnd/res/layout/fragment_import.xml b/OsmAnd/res/layout/fragment_import.xml index 30f518cbfc..2088d2624a 100644 --- a/OsmAnd/res/layout/fragment_import.xml +++ b/OsmAnd/res/layout/fragment_import.xml @@ -82,6 +82,7 @@ android:layout_height="match_parent" /> diff --git a/OsmAnd/res/values/sizes.xml b/OsmAnd/res/values/sizes.xml index c1addc1349..f91581adf6 100644 --- a/OsmAnd/res/values/sizes.xml +++ b/OsmAnd/res/values/sizes.xml @@ -397,6 +397,7 @@ 42dp 128dp 164dp + 68dp 6dp 12dp diff --git a/OsmAnd/res/values/strings.xml b/OsmAnd/res/values/strings.xml index 72fb10e393..9da2ac6d86 100644 --- a/OsmAnd/res/values/strings.xml +++ b/OsmAnd/res/values/strings.xml @@ -11,6 +11,7 @@ Thx - Hardy --> + %1$s * %2$s OsmAnd shows photos from several sources:\nOpenPlaceReviews - POI photos;\nMapillary - street-level imagery;\nWeb / Wikimedia - POI photos specified in OpenStreetMap data. Use dev.openstreetmap.org Switch to use "dev.openstreetmap.org" instead of "openstreetmap.org" to testing uploading OSM Note / POI / GPX. diff --git a/OsmAnd/src/net/osmand/plus/settings/backend/ExportSettingsType.java b/OsmAnd/src/net/osmand/plus/settings/backend/ExportSettingsType.java index bf86c42ee6..13135c0821 100644 --- a/OsmAnd/src/net/osmand/plus/settings/backend/ExportSettingsType.java +++ b/OsmAnd/src/net/osmand/plus/settings/backend/ExportSettingsType.java @@ -10,7 +10,6 @@ public enum ExportSettingsType { GLOBAL(R.string.general_settings_2, R.drawable.ic_action_settings), QUICK_ACTIONS(R.string.configure_screen_quick_action, R.drawable.ic_quick_action), POI_TYPES(R.string.poi_dialog_poi_type, R.drawable.ic_action_info_dark), - SEARCH_HISTORY(R.string.shared_string_search_history, R.drawable.ic_action_history), AVOID_ROADS(R.string.avoid_road, R.drawable.ic_action_alert), FAVORITES(R.string.shared_string_favorites, R.drawable.ic_action_favorite), TRACKS(R.string.shared_string_tracks, R.drawable.ic_action_route_distance), @@ -19,6 +18,7 @@ public enum ExportSettingsType { MULTIMEDIA_NOTES(R.string.audionotes_plugin_name, R.drawable.ic_grouped_by_type), ACTIVE_MARKERS(R.string.map_markers, R.drawable.ic_action_flag), HISTORY_MARKERS(R.string.markers_history, R.drawable.ic_action_flag), + SEARCH_HISTORY(R.string.shared_string_search_history, R.drawable.ic_action_history), CUSTOM_RENDER_STYLE(R.string.shared_string_rendering_style, R.drawable.ic_action_map_style), CUSTOM_ROUTING(R.string.shared_string_routing, R.drawable.ic_action_route_distance), MAP_SOURCES(R.string.quick_action_map_source_title, R.drawable.ic_map), @@ -48,12 +48,13 @@ public enum ExportSettingsType { public boolean isSettingsCategory() { return this == PROFILE || this == GLOBAL || this == QUICK_ACTIONS || this == POI_TYPES - || this == SEARCH_HISTORY || this == AVOID_ROADS; + || this == AVOID_ROADS; } public boolean isMyPlacesCategory() { return this == FAVORITES || this == TRACKS || this == OSM_EDITS || this == OSM_NOTES - || this == MULTIMEDIA_NOTES || this == ACTIVE_MARKERS || this == HISTORY_MARKERS; + || this == MULTIMEDIA_NOTES || this == ACTIVE_MARKERS || this == HISTORY_MARKERS + || this == SEARCH_HISTORY; } public boolean isResourcesCategory() { diff --git a/OsmAnd/src/net/osmand/plus/settings/backend/backup/SettingsHelper.java b/OsmAnd/src/net/osmand/plus/settings/backend/backup/SettingsHelper.java index 4553cf805f..b6b7f6e5b5 100644 --- a/OsmAnd/src/net/osmand/plus/settings/backend/backup/SettingsHelper.java +++ b/OsmAnd/src/net/osmand/plus/settings/backend/backup/SettingsHelper.java @@ -539,10 +539,6 @@ public class SettingsHelper { if (!poiList.isEmpty()) { settingsItems.put(ExportSettingsType.POI_TYPES, poiList); } - List historyEntries = SearchHistoryHelper.getInstance(app).getHistoryEntries(false); - if (!historyEntries.isEmpty()) { - settingsItems.put(ExportSettingsType.SEARCH_HISTORY, historyEntries); - } Map impassableRoads = app.getAvoidSpecificRoads().getImpassableRoads(); if (!impassableRoads.isEmpty()) { settingsItems.put(ExportSettingsType.AVOID_ROADS, new ArrayList<>(impassableRoads.values())); @@ -611,6 +607,10 @@ public class SettingsHelper { markersGroup.setMarkers(markersHistory); myPlacesItems.put(ExportSettingsType.HISTORY_MARKERS, Collections.singletonList(markersGroup)); } + List historyEntries = SearchHistoryHelper.getInstance(app).getHistoryEntries(false); + if (!historyEntries.isEmpty()) { + myPlacesItems.put(ExportSettingsType.SEARCH_HISTORY, historyEntries); + } return myPlacesItems; } diff --git a/OsmAnd/src/net/osmand/plus/settings/fragments/BaseSettingsListFragment.java b/OsmAnd/src/net/osmand/plus/settings/fragments/BaseSettingsListFragment.java index d95b6cffea..912c189991 100644 --- a/OsmAnd/src/net/osmand/plus/settings/fragments/BaseSettingsListFragment.java +++ b/OsmAnd/src/net/osmand/plus/settings/fragments/BaseSettingsListFragment.java @@ -11,6 +11,7 @@ import android.view.ViewTreeObserver; import android.widget.ExpandableListView; import android.widget.LinearLayout; +import androidx.activity.OnBackPressedCallback; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.appcompat.app.AlertDialog; @@ -31,6 +32,7 @@ import net.osmand.plus.settings.backend.ExportSettingsCategory; import net.osmand.plus.settings.backend.ExportSettingsType; import net.osmand.plus.settings.fragments.ExportSettingsAdapter.OnItemSelectedListener; import net.osmand.plus.widgets.TextViewEx; +import net.osmand.util.Algorithms; import java.io.File; import java.util.ArrayList; @@ -73,6 +75,17 @@ public abstract class BaseSettingsListFragment extends BaseOsmAndFragment implem super.onCreate(savedInstanceState); app = requireMyApplication(); nightMode = !app.getSettings().isLightContent(); + + requireActivity().getOnBackPressedDispatcher().addCallback(this, new OnBackPressedCallback(true) { + @Override + public void handleOnBackPressed() { + if (!hasSelectedData()) { + dismissFragment(); + } else { + showExitDialog(); + } + } + }); } @Nullable @@ -101,10 +114,14 @@ public abstract class BaseSettingsListFragment extends BaseOsmAndFragment implem continueBtn = root.findViewById(R.id.continue_button); UiUtilities.setupDialogButton(nightMode, continueBtn, DialogButtonType.PRIMARY, getString(R.string.shared_string_continue)); - continueBtn.setOnClickListener(new View.OnClickListener() { + root.findViewById(R.id.continue_button_container).setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { - onContinueButtonClickAction(); + if (expandableList.getHeaderViewsCount() >= 2) { + onContinueButtonClickAction(); + } else { + expandableList.smoothScrollToPositionFromTop(0, 0, 100); + } } }); @@ -185,7 +202,11 @@ public abstract class BaseSettingsListFragment extends BaseOsmAndFragment implem toolbar.setNavigationOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { - showExitDialog(); + if (!hasSelectedData()) { + dismissFragment(); + } else { + showExitDialog(); + } } }); } @@ -204,16 +225,25 @@ public abstract class BaseSettingsListFragment extends BaseOsmAndFragment implem continueBtn.setEnabled(false); } else { updateWarningHeaderVisibility(false); - continueBtn.setEnabled(adapter.hasSelectedData()); + continueBtn.setEnabled(hasSelectedData()); } itemsSizeContainer.setVisibility(View.VISIBLE); } else { updateWarningHeaderVisibility(false); itemsSizeContainer.setVisibility(View.INVISIBLE); - continueBtn.setEnabled(adapter.hasSelectedData()); + continueBtn.setEnabled(hasSelectedData()); } } + public boolean hasSelectedData() { + for (List items : selectedItemsMap.values()) { + if (!Algorithms.isEmpty(items)) { + return true; + } + } + return false; + } + private void updateWarningHeaderVisibility(boolean visible) { if (visible) { if (expandableList.getHeaderViewsCount() < 2) { diff --git a/OsmAnd/src/net/osmand/plus/settings/fragments/ExportItemsBottomSheet.java b/OsmAnd/src/net/osmand/plus/settings/fragments/ExportItemsBottomSheet.java index 8c62e04ccf..49dd920841 100644 --- a/OsmAnd/src/net/osmand/plus/settings/fragments/ExportItemsBottomSheet.java +++ b/OsmAnd/src/net/osmand/plus/settings/fragments/ExportItemsBottomSheet.java @@ -153,7 +153,30 @@ public class ExportItemsBottomSheet extends MenuBottomSheetDialogFragment { int checkBoxColor = checkBox.getState() == UNCHECKED ? secondaryColorRes : activeColorRes; CompoundButtonCompat.setButtonTintList(checkBox, ColorStateList.valueOf(ContextCompat.getColor(app, checkBoxColor))); - selectedSize.setText(getString(R.string.ltr_or_rtl_combine_via_slash, selectedItems.size(), allItems.size())); + String description; + if (type == ExportSettingsType.OFFLINE_MAPS && !selectedItems.isEmpty()) { + String size = AndroidUtils.formatSize(app, calculateSelectedItemsSize()); + String selected = getString(R.string.ltr_or_rtl_combine_via_slash, selectedItems.size(), allItems.size()); + description = getString(R.string.ltr_or_rtl_combine_via_comma, selected, size); + } else { + description = getString(R.string.ltr_or_rtl_combine_via_slash, selectedItems.size(), allItems.size()); + } + selectedSize.setText(description); + } + + private long calculateSelectedItemsSize() { + long itemsSize = 0; + for (int i = 0; i < allItems.size(); i++) { + Object object = allItems.get(i); + if (selectedItems.contains(object)) { + if (object instanceof FileSettingsItem) { + itemsSize += ((FileSettingsItem) object).getSize(); + } else if (object instanceof File) { + itemsSize += ((File) object).length(); + } + } + } + return itemsSize; } private void updateItems(boolean checked) { @@ -275,6 +298,10 @@ public class ExportItemsBottomSheet extends MenuBottomSheetDialogFragment { builder.setTitle(group.getDisplayName(app)); int color = group.getColor() == 0 ? ContextCompat.getColor(app, R.color.color_favorite) : group.getColor(); builder.setIcon(uiUtilities.getPaintedIcon(R.drawable.ic_action_folder, color)); + + int points = group.getPoints().size(); + String itemsDescr = app.getString(R.string.shared_string_gpx_points); + builder.setDescription(getString(R.string.ltr_or_rtl_combine_via_colon, itemsDescr, points)); } else if (object instanceof GlobalSettingsItem) { GlobalSettingsItem globalSettingsItem = (GlobalSettingsItem) object; builder.setTitle(globalSettingsItem.getPublicName(app)); @@ -285,9 +312,12 @@ public class ExportItemsBottomSheet extends MenuBottomSheetDialogFragment { builder.setTitle(getString(R.string.map_markers)); builder.setIcon(uiUtilities.getIcon(R.drawable.ic_action_flag, activeColorRes)); } else if (ExportSettingsType.HISTORY_MARKERS.name().equals(markersGroup.getId())) { - builder.setTitle(getString(R.string.map_markers)); + builder.setTitle(getString(R.string.markers_history)); builder.setIcon(uiUtilities.getIcon(R.drawable.ic_action_history, activeColorRes)); } + int selectedMarkers = markersGroup.getMarkers().size(); + String itemsDescr = app.getString(R.string.shared_string_items); + builder.setDescription(getString(R.string.ltr_or_rtl_combine_via_colon, itemsDescr, selectedMarkers)); } else if (object instanceof HistoryEntry) { HistoryEntry historyEntry = (HistoryEntry) object; builder.setTitle(historyEntry.getName().getName()); @@ -305,6 +335,7 @@ public class ExportItemsBottomSheet extends MenuBottomSheetDialogFragment { } else if (file.getAbsolutePath().contains(IndexConstants.GPX_INDEX_DIR)) { builder.setTitle(GpxUiHelper.getGpxTitle(file.getName())); builder.setIcon(uiUtilities.getIcon(R.drawable.ic_action_route_distance, activeColorRes)); + builder.setDescription(file.getParentFile().getName()); } else if (file.getAbsolutePath().contains(IndexConstants.AV_INDEX_DIR)) { int iconId = AudioVideoNotesPlugin.getIconIdForRecordingFile(file); if (iconId == -1) { @@ -316,6 +347,31 @@ public class ExportItemsBottomSheet extends MenuBottomSheetDialogFragment { || fileSubtype == FileSettingsItem.FileSubtype.VOICE) { builder.setTitle(FileNameTranslationHelper.getFileNameWithRegion(app, file.getName())); builder.setIcon(uiUtilities.getIcon(fileSubtype.getIconId(), activeColorRes)); + + if (fileSubtype.isMap()) { + String mapDescription = getMapDescription(file); + String size = AndroidUtils.formatSize(app, file.length()); + if (mapDescription != null) { + builder.setDescription(getString(R.string.ltr_or_rtl_combine_via_star, mapDescription, size)); + } else { + builder.setDescription(size); + } + } } } + + private String getMapDescription(File file) { + if (file.isDirectory() || file.getName().endsWith(IndexConstants.BINARY_WIKIVOYAGE_MAP_INDEX_EXT)) { + return getString(R.string.online_map); + } else if (file.getName().endsWith(IndexConstants.BINARY_ROAD_MAP_INDEX_EXT)) { + return getString(R.string.download_roads_only_item); + } else if (file.getName().endsWith(IndexConstants.BINARY_WIKI_MAP_INDEX_EXT)) { + return getString(R.string.download_wikipedia_maps); + } else if (file.getName().endsWith(IndexConstants.BINARY_SRTM_MAP_INDEX_EXT)) { + return getString(R.string.download_srtm_maps); + } else if (file.getName().endsWith(IndexConstants.BINARY_MAP_INDEX_EXT)) { + return getString(R.string.download_regular_maps); + } + return null; + } } \ No newline at end of file diff --git a/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsAdapter.java b/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsAdapter.java index d479b78a7c..edd6419c74 100644 --- a/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsAdapter.java +++ b/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsAdapter.java @@ -18,6 +18,7 @@ import net.osmand.plus.UiUtilities; import net.osmand.plus.activities.OsmandBaseExpandableListAdapter; import net.osmand.plus.helpers.AndroidUiHelper; import net.osmand.plus.helpers.FontCache; +import net.osmand.plus.mapmarkers.MapMarkersGroup; import net.osmand.plus.settings.backend.ExportSettingsCategory; import net.osmand.plus.settings.backend.ExportSettingsType; import net.osmand.plus.settings.backend.backup.FileSettingsItem; @@ -70,6 +71,8 @@ public class ExportSettingsAdapter extends OsmandBaseExpandableListAdapter { View group = convertView; if (group == null) { group = themedInflater.inflate(R.layout.profile_data_list_item_group, parent, false); + int minHeight = app.getResources().getDimensionPixelSize(R.dimen.setting_list_item_group_height); + group.findViewById(R.id.item_container).setMinimumHeight(minHeight); } final ExportSettingsCategory category = itemsTypes.get(groupPosition); final SettingsCategoryItems items = itemsMap.get(category); @@ -122,6 +125,8 @@ public class ExportSettingsAdapter extends OsmandBaseExpandableListAdapter { View child = convertView; if (child == null) { child = themedInflater.inflate(R.layout.profile_data_list_item_group, parent, false); + int minHeight = app.getResources().getDimensionPixelSize(R.dimen.setting_list_item_large_height); + child.findViewById(R.id.item_container).setMinimumHeight(minHeight); } final ExportSettingsCategory category = itemsTypes.get(groupPosition); final SettingsCategoryItems categoryItems = itemsMap.get(category); @@ -247,10 +252,6 @@ public class ExportSettingsAdapter extends OsmandBaseExpandableListAdapter { notifyDataSetChanged(); } - public boolean hasSelectedData() { - return !selectedItemsMap.isEmpty(); - } - public List getData() { List selectedItems = new ArrayList<>(); for (List items : selectedItemsMap.values()) { @@ -307,6 +308,10 @@ public class ExportSettingsAdapter extends OsmandBaseExpandableListAdapter { itemsSize += ((FileSettingsItem) object).getSize(); } else if (object instanceof File) { itemsSize += ((File) object).length(); + } else if (object instanceof MapMarkersGroup) { + int selectedMarkers = ((MapMarkersGroup) object).getMarkers().size(); + String itemsDescr = app.getString(R.string.shared_string_items); + return app.getString(R.string.ltr_or_rtl_combine_via_colon, itemsDescr, selectedMarkers); } } } diff --git a/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsFragment.java b/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsFragment.java index f831fd8fdd..c46168ec67 100644 --- a/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsFragment.java +++ b/OsmAnd/src/net/osmand/plus/settings/fragments/ExportSettingsFragment.java @@ -11,7 +11,6 @@ import android.view.ViewGroup; import android.widget.TextView; import android.widget.Toast; -import androidx.activity.OnBackPressedCallback; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.fragment.app.FragmentActivity; @@ -77,13 +76,6 @@ public class ExportSettingsFragment extends BaseSettingsListFragment { progressValue = savedInstanceState.getInt(PROGRESS_VALUE_KEY); } dataList = app.getSettingsHelper().getAdditionalData(globalExport); - - requireActivity().getOnBackPressedDispatcher().addCallback(this, new OnBackPressedCallback(true) { - @Override - public void handleOnBackPressed() { - showExitDialog(); - } - }); } @Nullable diff --git a/OsmAnd/src/net/osmand/plus/settings/fragments/ImportSettingsFragment.java b/OsmAnd/src/net/osmand/plus/settings/fragments/ImportSettingsFragment.java index bb629308b9..f078d1c34b 100644 --- a/OsmAnd/src/net/osmand/plus/settings/fragments/ImportSettingsFragment.java +++ b/OsmAnd/src/net/osmand/plus/settings/fragments/ImportSettingsFragment.java @@ -12,7 +12,6 @@ import android.widget.LinearLayout; import android.widget.ProgressBar; import android.widget.TextView; -import androidx.activity.OnBackPressedCallback; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.fragment.app.FragmentManager; @@ -102,12 +101,6 @@ public class ImportSettingsFragment extends BaseSettingsListFragment { duplicateStartTime = savedInstanceState.getLong(DUPLICATES_START_TIME_KEY); } settingsHelper = app.getSettingsHelper(); - requireActivity().getOnBackPressedDispatcher().addCallback(this, new OnBackPressedCallback(true) { - @Override - public void handleOnBackPressed() { - showExitDialog(); - } - }); ImportAsyncTask importTask = settingsHelper.getImportTask(); if (importTask != null) {