Merge branch 'master' into chips-points
# Conflicts: # OsmAnd/src/net/osmand/plus/track/TrackMenuFragment.java
This commit is contained in:
commit
8f4d63dc4f
133 changed files with 4192 additions and 976 deletions
|
@ -11,6 +11,7 @@ public interface OsmAndCustomizationConstants {
|
|||
String DRAWER_MY_PLACES_ID = DRAWER_ITEM_ID_SCHEME + "my_places";
|
||||
String DRAWER_SEARCH_ID = DRAWER_ITEM_ID_SCHEME + "search";
|
||||
String DRAWER_DIRECTIONS_ID = DRAWER_ITEM_ID_SCHEME + "directions";
|
||||
String DRAWER_TRIP_RECORDING_ID = DRAWER_ITEM_ID_SCHEME + "trip_recording";
|
||||
String DRAWER_CONFIGURE_MAP_ID = DRAWER_ITEM_ID_SCHEME + "configure_map";
|
||||
String DRAWER_DOWNLOAD_MAPS_ID = DRAWER_ITEM_ID_SCHEME + "download_maps";
|
||||
String DRAWER_OSMAND_LIVE_ID = DRAWER_ITEM_ID_SCHEME + "osmand_live";
|
||||
|
|
|
@ -83,7 +83,7 @@ public class BinaryMapIndexReader {
|
|||
|
||||
public final static int TRANSPORT_STOP_ZOOM = 24;
|
||||
public static final int SHIFT_COORDINATES = 5;
|
||||
public static final int LABEL_ZOOM_ENCODE = 26;
|
||||
public static final int LABEL_ZOOM_ENCODE = 31 - SHIFT_COORDINATES;
|
||||
private final static Log log = PlatformUtil.getLog(BinaryMapIndexReader.class);
|
||||
public static boolean READ_STATS = false;
|
||||
public static final SearchPoiTypeFilter ACCEPT_ALL_POI_TYPE_FILTER = new SearchPoiTypeFilter() {
|
||||
|
|
|
@ -38,6 +38,11 @@ public class BinaryMapPoiReaderAdapter {
|
|||
private static final int ZOOM_TO_SKIP_FILTER_READ = 6;
|
||||
private static final int ZOOM_TO_SKIP_FILTER = 3;
|
||||
private static final int BUCKET_SEARCH_BY_NAME = 15; // should be bigger 100?
|
||||
private static final int BASE_POI_SHIFT = SHIFT_BITS_CATEGORY;// 7
|
||||
private static final int FINAL_POI_SHIFT = BinaryMapIndexReader.SHIFT_COORDINATES;// 5
|
||||
private static final int BASE_POI_ZOOM = 31 - BASE_POI_SHIFT;// 24 zoom
|
||||
private static final int FINAL_POI_ZOOM = 31 - FINAL_POI_SHIFT;// 26 zoom
|
||||
|
||||
|
||||
public static class PoiSubType {
|
||||
public boolean text;
|
||||
|
@ -714,6 +719,8 @@ public class BinaryMapPoiReaderAdapter {
|
|||
Amenity am = null;
|
||||
int x = 0;
|
||||
int y = 0;
|
||||
int precisionXY = 0;
|
||||
boolean hasLocation = false;
|
||||
StringBuilder retValue = new StringBuilder();
|
||||
PoiCategory amenityType = null;
|
||||
LinkedList<String> textTags = null;
|
||||
|
@ -740,12 +747,22 @@ public class BinaryMapPoiReaderAdapter {
|
|||
am.setRoutePoint(arp);
|
||||
}
|
||||
}
|
||||
if (hasLocation) {
|
||||
if (precisionXY != 0) {
|
||||
int[] xy = MapUtils.calculateFinalXYFromBaseAndPrecisionXY(BASE_POI_ZOOM, FINAL_POI_ZOOM, precisionXY, x >> BASE_POI_SHIFT, y >> BASE_POI_SHIFT, true);
|
||||
int x31 = xy[0] << FINAL_POI_SHIFT;
|
||||
int y31 = xy[1] << FINAL_POI_SHIFT;
|
||||
am.setLocation(MapUtils.get31LatitudeY(y31), MapUtils.get31LongitudeX(x31));
|
||||
} else {
|
||||
am.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x));
|
||||
}
|
||||
}
|
||||
return am;
|
||||
case OsmandOdb.OsmAndPoiBoxDataAtom.DX_FIELD_NUMBER:
|
||||
x = (codedIS.readSInt32() + (px << (24 - zoom))) << 7;
|
||||
x = (codedIS.readSInt32() + (px << (BASE_POI_ZOOM - zoom))) << BASE_POI_SHIFT;
|
||||
break;
|
||||
case OsmandOdb.OsmAndPoiBoxDataAtom.DY_FIELD_NUMBER:
|
||||
y = (codedIS.readSInt32() + (py << (24 - zoom))) << 7;
|
||||
y = (codedIS.readSInt32() + (py << (BASE_POI_ZOOM - zoom))) << BASE_POI_SHIFT;
|
||||
req.numberOfVisitedObjects++;
|
||||
if (checkBounds) {
|
||||
if (left31 > x || right31 < x || top31 > y || bottom31 < y) {
|
||||
|
@ -754,7 +771,8 @@ public class BinaryMapPoiReaderAdapter {
|
|||
}
|
||||
}
|
||||
am = new Amenity();
|
||||
am.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x));
|
||||
hasLocation = true;
|
||||
//am.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x)); // set precise coordinates
|
||||
break;
|
||||
case OsmandOdb.OsmAndPoiBoxDataAtom.SUBCATEGORIES_FIELD_NUMBER:
|
||||
int subtypev = codedIS.readUInt32();
|
||||
|
@ -827,6 +845,11 @@ public class BinaryMapPoiReaderAdapter {
|
|||
case OsmandOdb.OsmAndPoiBoxDataAtom.NOTE_FIELD_NUMBER:
|
||||
am.setDescription(codedIS.readString());
|
||||
break;
|
||||
case OsmandOdb.OsmAndPoiBoxDataAtom.PRECISIONXY_FIELD_NUMBER:
|
||||
if (hasLocation) {
|
||||
precisionXY = codedIS.readInt32();
|
||||
}
|
||||
break;
|
||||
default:
|
||||
skipUnknownField(t);
|
||||
break;
|
||||
|
|
|
@ -54371,6 +54371,24 @@ public final class OsmandOdb {
|
|||
*/
|
||||
com.google.protobuf.ByteString
|
||||
getTextValuesBytes(int index);
|
||||
|
||||
// optional int32 precisionXY = 16;
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
boolean hasPrecisionXY();
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
int getPrecisionXY();
|
||||
}
|
||||
/**
|
||||
* Protobuf type {@code OsmAnd.OBF.OsmAndPoiBoxDataAtom}
|
||||
|
@ -54539,6 +54557,11 @@ public final class OsmandOdb {
|
|||
textValues_.add(input.readBytes());
|
||||
break;
|
||||
}
|
||||
case 128: {
|
||||
bitField0_ |= 0x00000200;
|
||||
precisionXY_ = input.readInt32();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (com.google.protobuf.InvalidProtocolBufferException e) {
|
||||
|
@ -55048,6 +55071,30 @@ public final class OsmandOdb {
|
|||
return textValues_.getByteString(index);
|
||||
}
|
||||
|
||||
// optional int32 precisionXY = 16;
|
||||
public static final int PRECISIONXY_FIELD_NUMBER = 16;
|
||||
private int precisionXY_;
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
public boolean hasPrecisionXY() {
|
||||
return ((bitField0_ & 0x00000200) == 0x00000200);
|
||||
}
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
public int getPrecisionXY() {
|
||||
return precisionXY_;
|
||||
}
|
||||
|
||||
private void initFields() {
|
||||
dx_ = 0;
|
||||
dy_ = 0;
|
||||
|
@ -55062,6 +55109,7 @@ public final class OsmandOdb {
|
|||
note_ = "";
|
||||
textCategories_ = java.util.Collections.emptyList();
|
||||
textValues_ = com.google.protobuf.LazyStringArrayList.EMPTY;
|
||||
precisionXY_ = 0;
|
||||
}
|
||||
private byte memoizedIsInitialized = -1;
|
||||
public final boolean isInitialized() {
|
||||
|
@ -55122,6 +55170,9 @@ public final class OsmandOdb {
|
|||
for (int i = 0; i < textValues_.size(); i++) {
|
||||
output.writeBytes(15, textValues_.getByteString(i));
|
||||
}
|
||||
if (((bitField0_ & 0x00000200) == 0x00000200)) {
|
||||
output.writeInt32(16, precisionXY_);
|
||||
}
|
||||
getUnknownFields().writeTo(output);
|
||||
}
|
||||
|
||||
|
@ -55203,6 +55254,10 @@ public final class OsmandOdb {
|
|||
size += dataSize;
|
||||
size += 1 * getTextValuesList().size();
|
||||
}
|
||||
if (((bitField0_ & 0x00000200) == 0x00000200)) {
|
||||
size += com.google.protobuf.CodedOutputStream
|
||||
.computeInt32Size(16, precisionXY_);
|
||||
}
|
||||
size += getUnknownFields().getSerializedSize();
|
||||
memoizedSerializedSize = size;
|
||||
return size;
|
||||
|
@ -55345,6 +55400,8 @@ public final class OsmandOdb {
|
|||
bitField0_ = (bitField0_ & ~0x00000800);
|
||||
textValues_ = com.google.protobuf.LazyStringArrayList.EMPTY;
|
||||
bitField0_ = (bitField0_ & ~0x00001000);
|
||||
precisionXY_ = 0;
|
||||
bitField0_ = (bitField0_ & ~0x00002000);
|
||||
return this;
|
||||
}
|
||||
|
||||
|
@ -55430,6 +55487,10 @@ public final class OsmandOdb {
|
|||
bitField0_ = (bitField0_ & ~0x00001000);
|
||||
}
|
||||
result.textValues_ = textValues_;
|
||||
if (((from_bitField0_ & 0x00002000) == 0x00002000)) {
|
||||
to_bitField0_ |= 0x00000200;
|
||||
}
|
||||
result.precisionXY_ = precisionXY_;
|
||||
result.bitField0_ = to_bitField0_;
|
||||
onBuilt();
|
||||
return result;
|
||||
|
@ -55525,6 +55586,9 @@ public final class OsmandOdb {
|
|||
}
|
||||
onChanged();
|
||||
}
|
||||
if (other.hasPrecisionXY()) {
|
||||
setPrecisionXY(other.getPrecisionXY());
|
||||
}
|
||||
this.mergeUnknownFields(other.getUnknownFields());
|
||||
return this;
|
||||
}
|
||||
|
@ -56506,6 +56570,55 @@ public final class OsmandOdb {
|
|||
return this;
|
||||
}
|
||||
|
||||
// optional int32 precisionXY = 16;
|
||||
private int precisionXY_ ;
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
public boolean hasPrecisionXY() {
|
||||
return ((bitField0_ & 0x00002000) == 0x00002000);
|
||||
}
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
public int getPrecisionXY() {
|
||||
return precisionXY_;
|
||||
}
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
public Builder setPrecisionXY(int value) {
|
||||
bitField0_ |= 0x00002000;
|
||||
precisionXY_ = value;
|
||||
onChanged();
|
||||
return this;
|
||||
}
|
||||
/**
|
||||
* <code>optional int32 precisionXY = 16;</code>
|
||||
*
|
||||
* <pre>
|
||||
* precision in 1-xy-xy-xy binary format
|
||||
* </pre>
|
||||
*/
|
||||
public Builder clearPrecisionXY() {
|
||||
bitField0_ = (bitField0_ & ~0x00002000);
|
||||
precisionXY_ = 0;
|
||||
onChanged();
|
||||
return this;
|
||||
}
|
||||
|
||||
// @@protoc_insertion_point(builder_scope:OsmAnd.OBF.OsmAndPoiBoxDataAtom)
|
||||
}
|
||||
|
||||
|
@ -65008,37 +65121,38 @@ public final class OsmandOdb {
|
|||
"tegories\030\003 \003(\r\022\025\n\rsubcategories\030\005 \003(\r\"i\n" +
|
||||
"\020OsmAndPoiBoxData\022\014\n\004zoom\030\001 \001(\r\022\t\n\001x\030\002 \001" +
|
||||
"(\r\022\t\n\001y\030\003 \001(\r\0221\n\007poiData\030\005 \003(\0132 .OsmAnd." +
|
||||
"OBF.OsmAndPoiBoxDataAtom\"\360\001\n\024OsmAndPoiBo",
|
||||
"OBF.OsmAndPoiBoxDataAtom\"\205\002\n\024OsmAndPoiBo",
|
||||
"xDataAtom\022\n\n\002dx\030\002 \002(\021\022\n\n\002dy\030\003 \002(\021\022\022\n\ncat" +
|
||||
"egories\030\004 \003(\r\022\025\n\rsubcategories\030\005 \003(\r\022\014\n\004" +
|
||||
"name\030\006 \001(\t\022\016\n\006nameEn\030\007 \001(\t\022\n\n\002id\030\010 \001(\004\022\024" +
|
||||
"\n\014openingHours\030\n \001(\t\022\014\n\004site\030\013 \001(\t\022\r\n\005ph" +
|
||||
"one\030\014 \001(\t\022\014\n\004note\030\r \001(\t\022\026\n\016textCategorie" +
|
||||
"s\030\016 \003(\r\022\022\n\ntextValues\030\017 \003(\t\"\032\n\007IdTable\022\017" +
|
||||
"\n\007routeId\030\001 \003(\022\"F\n\017RestrictionData\022\014\n\004ty" +
|
||||
"pe\030\001 \002(\005\022\014\n\004from\030\002 \002(\005\022\n\n\002to\030\003 \002(\005\022\013\n\003vi" +
|
||||
"a\030\004 \001(\005\"x\n\tRouteData\022\016\n\006points\030\001 \002(\014\022\022\n\n" +
|
||||
"pointTypes\030\004 \001(\014\022\022\n\npointNames\030\005 \001(\014\022\r\n\005",
|
||||
"types\030\007 \002(\014\022\017\n\007routeId\030\014 \002(\005\022\023\n\013stringNa" +
|
||||
"mes\030\016 \001(\014\"\304\005\n\022OsmAndRoutingIndex\022\014\n\004name" +
|
||||
"\030\001 \002(\t\022?\n\005rules\030\002 \003(\01320.OsmAnd.OBF.OsmAn" +
|
||||
"dRoutingIndex.RouteEncodingRule\022>\n\trootB" +
|
||||
"oxes\030\003 \003(\0132+.OsmAnd.OBF.OsmAndRoutingInd" +
|
||||
"ex.RouteDataBox\022A\n\014basemapBoxes\030\004 \003(\0132+." +
|
||||
"OsmAnd.OBF.OsmAndRoutingIndex.RouteDataB" +
|
||||
"ox\022=\n\006blocks\030\005 \003(\0132-.OsmAnd.OBF.OsmAndRo" +
|
||||
"utingIndex.RouteDataBlock\032;\n\021RouteEncodi" +
|
||||
"ngRule\022\013\n\003tag\030\003 \002(\t\022\r\n\005value\030\005 \002(\t\022\n\n\002id",
|
||||
"\030\007 \001(\r\032\231\001\n\014RouteDataBox\022\014\n\004left\030\001 \002(\021\022\r\n" +
|
||||
"\005right\030\002 \002(\021\022\013\n\003top\030\003 \002(\021\022\016\n\006bottom\030\004 \002(" +
|
||||
"\021\022\023\n\013shiftToData\030\005 \001(\007\022:\n\005boxes\030\007 \003(\0132+." +
|
||||
"OsmAnd.OBF.OsmAndRoutingIndex.RouteDataB" +
|
||||
"ox\032\303\001\n\016RouteDataBlock\022$\n\007idTable\030\005 \001(\0132\023" +
|
||||
".OsmAnd.OBF.IdTable\022*\n\013dataObjects\030\006 \003(\013" +
|
||||
"2\025.OsmAnd.OBF.RouteData\0221\n\014restrictions\030" +
|
||||
"\007 \003(\0132\033.OsmAnd.OBF.RestrictionData\022,\n\013st" +
|
||||
"ringTable\030\010 \001(\0132\027.OsmAnd.OBF.StringTable" +
|
||||
"B\036\n\021net.osmand.binaryB\tOsmandOdb"
|
||||
"s\030\016 \003(\r\022\022\n\ntextValues\030\017 \003(\t\022\023\n\013precision" +
|
||||
"XY\030\020 \001(\005\"\032\n\007IdTable\022\017\n\007routeId\030\001 \003(\022\"F\n\017" +
|
||||
"RestrictionData\022\014\n\004type\030\001 \002(\005\022\014\n\004from\030\002 " +
|
||||
"\002(\005\022\n\n\002to\030\003 \002(\005\022\013\n\003via\030\004 \001(\005\"x\n\tRouteDat" +
|
||||
"a\022\016\n\006points\030\001 \002(\014\022\022\n\npointTypes\030\004 \001(\014\022\022\n",
|
||||
"\npointNames\030\005 \001(\014\022\r\n\005types\030\007 \002(\014\022\017\n\007rout" +
|
||||
"eId\030\014 \002(\005\022\023\n\013stringNames\030\016 \001(\014\"\304\005\n\022OsmAn" +
|
||||
"dRoutingIndex\022\014\n\004name\030\001 \002(\t\022?\n\005rules\030\002 \003" +
|
||||
"(\01320.OsmAnd.OBF.OsmAndRoutingIndex.Route" +
|
||||
"EncodingRule\022>\n\trootBoxes\030\003 \003(\0132+.OsmAnd" +
|
||||
".OBF.OsmAndRoutingIndex.RouteDataBox\022A\n\014" +
|
||||
"basemapBoxes\030\004 \003(\0132+.OsmAnd.OBF.OsmAndRo" +
|
||||
"utingIndex.RouteDataBox\022=\n\006blocks\030\005 \003(\0132" +
|
||||
"-.OsmAnd.OBF.OsmAndRoutingIndex.RouteDat" +
|
||||
"aBlock\032;\n\021RouteEncodingRule\022\013\n\003tag\030\003 \002(\t",
|
||||
"\022\r\n\005value\030\005 \002(\t\022\n\n\002id\030\007 \001(\r\032\231\001\n\014RouteDat" +
|
||||
"aBox\022\014\n\004left\030\001 \002(\021\022\r\n\005right\030\002 \002(\021\022\013\n\003top" +
|
||||
"\030\003 \002(\021\022\016\n\006bottom\030\004 \002(\021\022\023\n\013shiftToData\030\005 " +
|
||||
"\001(\007\022:\n\005boxes\030\007 \003(\0132+.OsmAnd.OBF.OsmAndRo" +
|
||||
"utingIndex.RouteDataBox\032\303\001\n\016RouteDataBlo" +
|
||||
"ck\022$\n\007idTable\030\005 \001(\0132\023.OsmAnd.OBF.IdTable" +
|
||||
"\022*\n\013dataObjects\030\006 \003(\0132\025.OsmAnd.OBF.Route" +
|
||||
"Data\0221\n\014restrictions\030\007 \003(\0132\033.OsmAnd.OBF." +
|
||||
"RestrictionData\022,\n\013stringTable\030\010 \001(\0132\027.O" +
|
||||
"smAnd.OBF.StringTableB\036\n\021net.osmand.bina",
|
||||
"ryB\tOsmandOdb"
|
||||
};
|
||||
com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner =
|
||||
new com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() {
|
||||
|
@ -65296,7 +65410,7 @@ public final class OsmandOdb {
|
|||
internal_static_OsmAnd_OBF_OsmAndPoiBoxDataAtom_fieldAccessorTable = new
|
||||
com.google.protobuf.GeneratedMessage.FieldAccessorTable(
|
||||
internal_static_OsmAnd_OBF_OsmAndPoiBoxDataAtom_descriptor,
|
||||
new java.lang.String[] { "Dx", "Dy", "Categories", "Subcategories", "Name", "NameEn", "Id", "OpeningHours", "Site", "Phone", "Note", "TextCategories", "TextValues", });
|
||||
new java.lang.String[] { "Dx", "Dy", "Categories", "Subcategories", "Name", "NameEn", "Id", "OpeningHours", "Site", "Phone", "Note", "TextCategories", "TextValues", "PrecisionXY", });
|
||||
internal_static_OsmAnd_OBF_IdTable_descriptor =
|
||||
getDescriptor().getMessageTypes().get(36);
|
||||
internal_static_OsmAnd_OBF_IdTable_fieldAccessorTable = new
|
||||
|
|
|
@ -436,6 +436,7 @@ public class OsmandRegions {
|
|||
cx /= object.getPointsLength();
|
||||
cy /= object.getPointsLength();
|
||||
rd.regionCenter = new LatLon(MapUtils.get31LatitudeY((int) cy), MapUtils.get31LongitudeX((int) cx));
|
||||
rd.boundingBox = findBoundingBox(object);
|
||||
}
|
||||
|
||||
rd.regionParentFullName = mapIndexFields.get(mapIndexFields.parentFullName, object);
|
||||
|
@ -461,6 +462,43 @@ public class OsmandRegions {
|
|||
return rd;
|
||||
}
|
||||
|
||||
private QuadRect findBoundingBox(BinaryMapDataObject object) {
|
||||
if (object.getPointsLength() == 0) {
|
||||
return new QuadRect(0, 0, 0, 0);
|
||||
}
|
||||
|
||||
double currentX = object.getPoint31XTile(0);
|
||||
double currentY = object.getPoint31YTile(0);
|
||||
double minX = currentX;
|
||||
double maxX = currentX;
|
||||
double minY = currentY;
|
||||
double maxY = currentY;
|
||||
|
||||
if (object.getPointsLength() > 1) {
|
||||
for (int i = 1; i < object.getPointsLength(); i++) {
|
||||
currentX = object.getPoint31XTile(i);
|
||||
currentY = object.getPoint31YTile(i);
|
||||
if (currentX > maxX) {
|
||||
maxX = currentX;
|
||||
} else if (currentX < minX) {
|
||||
minX = currentX;
|
||||
}
|
||||
if (currentY > maxY) {
|
||||
maxY = currentY;
|
||||
} else if (currentY < minY) {
|
||||
minY = currentY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
minX = MapUtils.get31LongitudeX((int) minX);
|
||||
maxX = MapUtils.get31LongitudeX((int) maxX);
|
||||
double revertedMinY = MapUtils.get31LatitudeY((int) maxY);
|
||||
double revertedMaxY = MapUtils.get31LatitudeY((int) minY);
|
||||
|
||||
return new QuadRect(minX, revertedMinY, maxX, revertedMaxY);
|
||||
}
|
||||
|
||||
private String getSearchIndex(BinaryMapDataObject object) {
|
||||
MapIndex mi = object.getMapIndex();
|
||||
TIntObjectIterator<String> it = object.getObjectNames().iterator();
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package net.osmand.map;
|
||||
|
||||
import net.osmand.data.LatLon;
|
||||
import net.osmand.data.QuadRect;
|
||||
import net.osmand.util.Algorithms;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
@ -40,6 +41,7 @@ public class WorldRegion implements Serializable {
|
|||
protected String regionDownloadName;
|
||||
protected boolean regionMapDownload;
|
||||
protected LatLon regionCenter;
|
||||
protected QuadRect boundingBox;
|
||||
|
||||
public static class RegionParams {
|
||||
protected String regionLeftHandDriving;
|
||||
|
@ -182,4 +184,20 @@ public class WorldRegion implements Serializable {
|
|||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
public boolean containsRegion(WorldRegion region) {
|
||||
if (this.boundingBox != null && region.boundingBox != null) {
|
||||
return this.boundingBox.contains(region.boundingBox);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean isContinent() {
|
||||
if (superregion != null) {
|
||||
String superRegionId = superregion.getRegionId();
|
||||
String thisRegionId = getRegionId();
|
||||
return WORLD.equals(superRegionId) && !RUSSIA_REGION_ID.equals(thisRegionId);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
|
@ -127,6 +127,17 @@ public class Algorithms {
|
|||
return def;
|
||||
}
|
||||
|
||||
public static double parseDoubleSilently(String input, double def) {
|
||||
if (input != null && input.length() > 0) {
|
||||
try {
|
||||
return Double.parseDouble(input);
|
||||
} catch (NumberFormatException e) {
|
||||
return def;
|
||||
}
|
||||
}
|
||||
return def;
|
||||
}
|
||||
|
||||
public static String getFileNameWithoutExtension(File f) {
|
||||
return getFileNameWithoutExtension(f.getName());
|
||||
}
|
||||
|
|
|
@ -49,6 +49,47 @@ public class MapUtils {
|
|||
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '_', '~'
|
||||
};
|
||||
|
||||
public static int calculateFromBaseZoomPrecisionXY(int baseZoom, int finalZoom, int xFinal, int yFinal) {
|
||||
int px = xFinal;
|
||||
int py = yFinal;
|
||||
int precisionNumber = 1;
|
||||
for (int zoom = finalZoom - 1; zoom >= baseZoom; zoom--) {
|
||||
int x = px / 2; // (int) MapUtils.getTileNumberX(zoom, lon);
|
||||
int y = py / 2; // (int) MapUtils.getTileNumberY(zoom, lat);
|
||||
int deltax = px - x * 2;
|
||||
int deltay = py - y * 2;
|
||||
precisionNumber = (precisionNumber << 2) + (deltax << 1) + deltay;
|
||||
// StringBuilder spaces = new StringBuilder();
|
||||
// for (int i = 0; i < 32 - zoom; i++) {
|
||||
// spaces.append(' ');
|
||||
// }
|
||||
// System.out.println(String.format("%d %s + %d %s %s + %d", zoom, Integer.toBinaryString(x), deltax, spaces.toString(), Integer.toBinaryString(y), deltay));
|
||||
px = x;
|
||||
py = y;
|
||||
}
|
||||
// System.out.println(String.format("Bits: %d %s (%d)", Integer.toBinaryString(precisionNumber).length(), Integer.toBinaryString(precisionNumber), precisionNumber));
|
||||
return precisionNumber;
|
||||
}
|
||||
|
||||
public static int[] calculateFinalXYFromBaseAndPrecisionXY(int bazeZoom, int finalZoom,
|
||||
int precisionXY, int xBase, int yBase, boolean ignoreNotEnoughPrecision) {
|
||||
// System.out.println(String.format("Base x, y at zoom %d: %d %d", zoomToStart, xBaseApproximation, yBaseApproximation));
|
||||
// calculate finish approximation using precisionNumber
|
||||
int finalX = xBase;
|
||||
int finalY = yBase;
|
||||
int precisionCalc = precisionXY;
|
||||
for (int zoom = bazeZoom; zoom < finalZoom; zoom++) {
|
||||
if (precisionCalc <= 1 && precisionCalc > 0 && !ignoreNotEnoughPrecision) {
|
||||
throw new IllegalArgumentException("Not enough bits to retrieve zoom approximation");
|
||||
}
|
||||
finalY = finalY * 2 + (precisionXY & 1);
|
||||
finalX = finalX * 2 + ((precisionXY & 2) >> 1);
|
||||
precisionXY = precisionXY >> 2;
|
||||
}
|
||||
// System.out.println(String.format("Calc x, y at zoom %d: %d %d", finalZoom, finalX, finalY));
|
||||
return new int[] { finalX, finalY };
|
||||
}
|
||||
|
||||
|
||||
|
||||
public static double getDistance(LatLon l, double latitude, double longitude) {
|
||||
|
|
|
@ -85,6 +85,7 @@ android {
|
|||
}
|
||||
amazonFree {
|
||||
java.srcDirs = ["src-nogms", "src-google"]
|
||||
manifest.srcFile "AndroidManifest-gplayFree.xml"
|
||||
}
|
||||
amazonFull {
|
||||
java.srcDirs = ["src-nogms", "src-google"]
|
||||
|
|
6
OsmAnd/res/drawable-mdpi/btn_background_active_dark.xml
Normal file
6
OsmAnd/res/drawable-mdpi/btn_background_active_dark.xml
Normal file
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<solid android:color="@color/active_buttons_and_links_bg_pressed_dark" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<solid android:color="@color/inactive_buttons_and_links_bg_dark" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<solid android:color="@color/inactive_buttons_and_links_bg_light" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<stroke android:width="1dp" android:color="@color/active_buttons_and_links_bg_pressed_dark" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<stroke android:width="1dp" android:color="@color/active_buttons_and_links_bg_pressed_light" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<stroke android:width="1dp" android:color="@color/inactive_buttons_and_links_bg_dark" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<stroke android:width="1dp" android:color="@color/inactive_buttons_and_links_bg_light" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
6
OsmAnd/res/drawable/btn_background_active_light.xml
Normal file
6
OsmAnd/res/drawable/btn_background_active_light.xml
Normal file
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<solid android:color="@color/active_buttons_and_links_bg_pressed_light" />
|
||||
<corners android:radius="3dp" />
|
||||
</shape>
|
15
OsmAnd/res/drawable/btn_unstroked_dark.xml
Normal file
15
OsmAnd/res/drawable/btn_unstroked_dark.xml
Normal file
|
@ -0,0 +1,15 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<selector xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<item android:state_pressed="true">
|
||||
<shape android:shape="rectangle">
|
||||
<solid android:color="@color/active_buttons_and_links_bg_pressed_dark" />
|
||||
<corners android:radius="@dimen/dlg_button_rect_rad" />
|
||||
</shape>
|
||||
</item>
|
||||
<item>
|
||||
<shape android:shape="rectangle">
|
||||
<solid android:color="@null" />
|
||||
<corners android:radius="@dimen/dlg_button_rect_rad" />
|
||||
</shape>
|
||||
</item>
|
||||
</selector>
|
15
OsmAnd/res/drawable/btn_unstroked_light.xml
Normal file
15
OsmAnd/res/drawable/btn_unstroked_light.xml
Normal file
|
@ -0,0 +1,15 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<selector xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<item android:state_pressed="true">
|
||||
<shape android:shape="rectangle">
|
||||
<solid android:color="@color/active_buttons_and_links_bg_pressed_light" />
|
||||
<corners android:radius="@dimen/dlg_button_rect_rad" />
|
||||
</shape>
|
||||
</item>
|
||||
<item>
|
||||
<shape android:shape="rectangle">
|
||||
<solid android:color="@null" />
|
||||
<corners android:radius="@dimen/dlg_button_rect_rad" />
|
||||
</shape>
|
||||
</item>
|
||||
</selector>
|
23
OsmAnd/res/drawable/ic_action_ruler_line.xml
Normal file
23
OsmAnd/res/drawable/ic_action_ruler_line.xml
Normal file
|
@ -0,0 +1,23 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportWidth="24"
|
||||
android:viewportHeight="24">
|
||||
<path
|
||||
android:pathData="M16,3C16.5523,3 17,3.4477 17,4V5.1707C17.8524,5.472 18.528,6.1476 18.8293,7H20C20.5523,7 21,7.4477 21,8C21,8.5523 20.5523,9 20,9H18.8293C18.528,9.8524 17.8524,10.528 17,10.8293V12C17,12.5523 16.5523,13 16,13C15.4477,13 15,12.5523 15,12V10.8293C14.1476,10.528 13.472,9.8524 13.1707,9H12C11.4477,9 11,8.5523 11,8C11,7.4477 11.4477,7 12,7H13.1707C13.472,6.1476 14.1476,5.472 15,5.1707V4C15,3.4477 15.4477,3 16,3ZM17,8C17,8.5523 16.5523,9 16,9C15.4477,9 15,8.5523 15,8C15,7.4477 15.4477,7 16,7C16.5523,7 17,7.4477 17,8Z"
|
||||
android:fillColor="#ffffff"
|
||||
android:fillType="evenOdd"/>
|
||||
<path
|
||||
android:pathData="M6,19.5C6,20.3284 5.3284,21 4.5,21C3.6716,21 3,20.3284 3,19.5C3,18.6716 3.6716,18 4.5,18C5.3284,18 6,18.6716 6,19.5Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M12.7071,12.7071C13.0976,12.3166 13.0976,11.6834 12.7071,11.2929C12.3166,10.9024 11.6834,10.9024 11.2929,11.2929L10.2929,12.2929C9.9024,12.6834 9.9024,13.3166 10.2929,13.7071C10.6834,14.0976 11.3166,14.0976 11.7071,13.7071L12.7071,12.7071Z"
|
||||
android:strokeAlpha="0.5"
|
||||
android:fillColor="#ffffff"
|
||||
android:fillAlpha="0.5"/>
|
||||
<path
|
||||
android:pathData="M9.7071,15.7071C10.0976,15.3166 10.0976,14.6834 9.7071,14.2929C9.3166,13.9024 8.6834,13.9024 8.2929,14.2929L7.2929,15.2929C6.9024,15.6834 6.9024,16.3166 7.2929,16.7071C7.6834,17.0976 8.3166,17.0976 8.7071,16.7071L9.7071,15.7071Z"
|
||||
android:strokeAlpha="0.5"
|
||||
android:fillColor="#ffffff"
|
||||
android:fillAlpha="0.5"/>
|
||||
</vector>
|
70
OsmAnd/res/layout/bottom_sheet_button_with_icon.xml
Normal file
70
OsmAnd/res/layout/bottom_sheet_button_with_icon.xml
Normal file
|
@ -0,0 +1,70 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/button_container"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:clickable="true"
|
||||
android:focusable="true"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:paddingStart="@dimen/content_padding_small"
|
||||
android:paddingLeft="@dimen/content_padding_small"
|
||||
android:paddingTop="@dimen/text_margin_small"
|
||||
android:paddingEnd="@dimen/content_padding_small"
|
||||
android:paddingRight="@dimen/content_padding_small"
|
||||
android:paddingBottom="@dimen/text_margin_small"
|
||||
tools:background="@drawable/btn_background_inactive_dark"
|
||||
tools:ignore="UselessParent">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:duplicateParentState="true"
|
||||
android:orientation="vertical">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/button_text"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:duplicateParentState="true"
|
||||
android:letterSpacing="@dimen/description_letter_spacing"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
tools:text="Title"
|
||||
tools:textColor="@color/active_color_primary_dark" />
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/desc"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:duplicateParentState="true"
|
||||
android:letterSpacing="@dimen/description_letter_spacing"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
android:visibility="gone"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
tools:text="Description"
|
||||
tools:textColor="@color/text_color_secondary_dark"
|
||||
tools:visibility="visible" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/icon"
|
||||
android:layout_width="@dimen/map_widget_icon"
|
||||
android:layout_height="@dimen/map_widget_icon"
|
||||
android:layout_marginStart="@dimen/context_menu_padding_margin_large"
|
||||
android:layout_marginLeft="@dimen/context_menu_padding_margin_large"
|
||||
android:duplicateParentState="true"
|
||||
tools:srcCompat="@drawable/ic_action_appearance"
|
||||
tools:tint="@color/icon_color_active_dark" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</FrameLayout>
|
72
OsmAnd/res/layout/bottom_sheet_select_segment.xml
Normal file
72
OsmAnd/res/layout/bottom_sheet_select_segment.xml
Normal file
|
@ -0,0 +1,72 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
android:paddingStart="@dimen/content_padding"
|
||||
android:paddingLeft="@dimen/content_padding"
|
||||
android:paddingTop="@dimen/measurement_tool_menu_title_padding_top"
|
||||
android:paddingEnd="@dimen/content_padding"
|
||||
android:paddingRight="@dimen/content_padding"
|
||||
android:paddingBottom="@dimen/measurement_tool_button_padding_top">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/title"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="@dimen/widget_turn_lane_margin"
|
||||
android:ellipsize="end"
|
||||
android:gravity="center_vertical"
|
||||
android:letterSpacing="@dimen/text_button_letter_spacing"
|
||||
android:lineSpacingExtra="@dimen/titleLineSpacingExtra"
|
||||
android:maxLines="1"
|
||||
android:text="@string/select_segments"
|
||||
android:textColor="?android:textColorPrimary"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium" />
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/description"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="@dimen/list_header_settings_top_margin"
|
||||
android:letterSpacing="@dimen/description_letter_spacing"
|
||||
android:lineSpacingMultiplier="@dimen/bottom_sheet_text_spacing_multiplier"
|
||||
android:lineSpacingExtra="@dimen/descriptionLineSpacingExtra"
|
||||
android:text="@string/select_segments_description"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
osmand:typeface="@string/font_roboto_regular" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/gpx_track_container"
|
||||
layout="@layout/gpx_track_item"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="@dimen/dashPluginMargin" />
|
||||
|
||||
<View
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:background="?attr/dashboard_divider" />
|
||||
|
||||
<androidx.recyclerview.widget.RecyclerView
|
||||
android:id="@+id/gpx_segment_list"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="0dp"
|
||||
android:layout_weight="1"
|
||||
tools:itemCount="1"
|
||||
tools:listitem="@layout/gpx_segment_list_item">
|
||||
|
||||
</androidx.recyclerview.widget.RecyclerView>
|
||||
|
||||
</LinearLayout>
|
|
@ -21,11 +21,13 @@
|
|||
android:layout_marginLeft="@dimen/card_padding"
|
||||
android:padding="@dimen/context_menu_padding_margin_small"
|
||||
android:paddingStart="@dimen/context_menu_padding_margin_small"
|
||||
android:paddingEnd="@dimen/context_menu_padding_margin_small">
|
||||
android:paddingEnd="@dimen/context_menu_padding_margin_small"
|
||||
android:background="@null">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:layout_width="@dimen/favorites_icon_size_small"
|
||||
android:layout_height="@dimen/favorites_icon_size_small"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
android:tint="?attr/default_icon_color"
|
||||
osmand:srcCompat="@drawable/ic_action_close" />
|
||||
</FrameLayout>
|
||||
|
@ -43,18 +45,20 @@
|
|||
osmand:typeface="@string/font_roboto_medium" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/btn_save"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginRight="@dimen/content_padding_half"
|
||||
android:layout_marginEnd="@dimen/content_padding_half"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:background="@drawable/btn_border_active">
|
||||
android:layout_gravity="center_vertical">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/btn_save"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:layout_gravity="start"
|
||||
android:gravity="center_vertical"
|
||||
android:duplicateParentState="true"
|
||||
android:background="@drawable/btn_border_active"
|
||||
android:paddingStart="@dimen/content_padding"
|
||||
android:paddingLeft="@dimen/content_padding"
|
||||
android:paddingTop="@dimen/content_padding_half"
|
||||
|
@ -77,18 +81,18 @@
|
|||
|
||||
<ScrollView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent">
|
||||
android:layout_height="match_parent"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding_half"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginBottom="@dimen/content_padding_half">
|
||||
|
||||
<net.osmand.plus.widgets.EditTextEx
|
||||
android:id="@+id/description"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding_half"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginBottom="@dimen/content_padding_half"
|
||||
android:background="?attr/card_and_list_background_basic"
|
||||
android:textColor="?android:attr/textColorPrimary"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
|
|
|
@ -1,31 +1,79 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/root"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="vertical"
|
||||
android:background="?attr/list_background_color">
|
||||
android:orientation="vertical">
|
||||
|
||||
<com.google.android.material.appbar.AppBarLayout
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="?attr/pstsTabBackground">
|
||||
android:layout_height="@dimen/action_bar_height"
|
||||
android:background="?attr/pstsTabBackground"
|
||||
android:orientation="horizontal"
|
||||
android:gravity="center_vertical">
|
||||
|
||||
<androidx.appcompat.widget.Toolbar
|
||||
android:id="@+id/toolbar"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="@dimen/action_bar_height"
|
||||
app:titleTextColor="?attr/list_background_color" />
|
||||
<FrameLayout
|
||||
android:id="@+id/toolbar_back"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding_small"
|
||||
android:layout_marginLeft="@dimen/content_padding_small"
|
||||
android:background="@null"
|
||||
android:padding="@dimen/content_padding_half"
|
||||
android:paddingStart="@dimen/content_padding_half"
|
||||
android:paddingEnd="@dimen/content_padding_half">
|
||||
|
||||
</com.google.android.material.appbar.AppBarLayout>
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:layout_width="@dimen/standard_icon_size"
|
||||
android:layout_height="@dimen/standard_icon_size"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
osmand:srcCompat="@drawable/ic_arrow_back"/>
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/toolbar_title"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/dialog_button_height"
|
||||
android:layout_marginLeft="@dimen/dialog_button_height"
|
||||
android:layout_weight="1"
|
||||
android:ellipsize="end"
|
||||
android:textColor="@color/list_background_color_light"
|
||||
android:textSize="@dimen/dialog_header_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
tools:text="Amsterdam" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/toolbar_edit"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding_small"
|
||||
android:layout_marginLeft="@dimen/content_padding_small"
|
||||
android:layout_marginRight="@dimen/content_padding_small"
|
||||
android:layout_marginEnd="@dimen/content_padding_small"
|
||||
android:background="@null"
|
||||
android:padding="@dimen/content_padding_half"
|
||||
android:paddingStart="@dimen/content_padding_half"
|
||||
android:paddingEnd="@dimen/content_padding_half">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:layout_width="@dimen/standard_icon_size"
|
||||
android:layout_height="@dimen/standard_icon_size"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
osmand:srcCompat="@drawable/ic_action_edit_dark"/>
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<ScrollView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent">
|
||||
android:layout_height="match_parent"
|
||||
android:background="?attr/activity_background_basic">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/ll"
|
||||
|
@ -61,33 +109,32 @@
|
|||
tools:visibility="visible"/>
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/btn_edit"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/context_menu_padding_margin_small"
|
||||
android:layout_marginBottom="@dimen/context_menu_padding_margin_small"
|
||||
android:background="@drawable/rounded_background_3dp">
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/btn_edit"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
android:padding="@dimen/context_menu_padding_margin_small"
|
||||
android:paddingStart="@dimen/context_menu_padding_margin_small"
|
||||
android:paddingEnd="@dimen/context_menu_padding_margin_small"
|
||||
android:duplicateParentState="true"
|
||||
android:padding="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingStart="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingEnd="@dimen/bottom_sheet_content_padding_small"
|
||||
android:drawablePadding="@dimen/list_content_padding_large"
|
||||
osmand:drawableLeftCompat="@drawable/ic_action_edit_dark"
|
||||
osmand:drawableStartCompat="@drawable/ic_action_edit_dark"
|
||||
osmand:drawableLeftCompat="@drawable/ic_action_edit_dark"
|
||||
osmand:drawableTint="?attr/active_color_basic"
|
||||
android:visibility="gone"
|
||||
android:text="@string/shared_string_edit"
|
||||
android:textColor="?attr/active_color_basic"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
tools:visibility="visible" />
|
||||
osmand:typeface="@string/font_roboto_medium" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
|
|
|
@ -1,158 +1,158 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="fill_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="?attr/expandable_list_item_background"
|
||||
android:minHeight="@dimen/favorites_list_item_height"
|
||||
android:orientation="vertical">
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="fill_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="?attr/expandable_list_item_background"
|
||||
android:minHeight="@dimen/favorites_list_item_height"
|
||||
android:orientation="vertical">
|
||||
|
||||
<View
|
||||
android:id="@+id/divider"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:background="?attr/dashboard_divider"
|
||||
android:visibility="gone"/>
|
||||
<View
|
||||
android:id="@+id/divider"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:background="?attr/dashboard_divider"
|
||||
android:visibility="gone" />
|
||||
|
||||
<View
|
||||
android:id="@+id/list_divider"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:background="?attr/dashboard_divider"
|
||||
android:visibility="gone"
|
||||
android:layout_marginLeft="@dimen/settings_divider_margin_start"
|
||||
android:layout_marginStart="@dimen/settings_divider_margin_start" />
|
||||
<View
|
||||
android:id="@+id/list_divider"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:layout_marginStart="@dimen/settings_divider_margin_start"
|
||||
android:layout_marginLeft="@dimen/settings_divider_margin_start"
|
||||
android:background="?attr/dashboard_divider"
|
||||
android:visibility="gone" />
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:minHeight="@dimen/favorites_list_item_height"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:paddingStart="@dimen/favorites_my_places_icon_left_padding"
|
||||
android:paddingLeft="@dimen/favorites_my_places_icon_left_padding"
|
||||
android:paddingEnd="@dimen/favorites_my_places_icon_left_padding"
|
||||
android:paddingRight="@dimen/favorites_my_places_icon_left_padding">
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:minHeight="@dimen/favorites_list_item_height"
|
||||
android:orientation="horizontal"
|
||||
android:paddingStart="@dimen/favorites_my_places_icon_left_padding"
|
||||
android:paddingLeft="@dimen/favorites_my_places_icon_left_padding"
|
||||
android:paddingEnd="@dimen/favorites_my_places_icon_left_padding"
|
||||
android:paddingRight="@dimen/favorites_my_places_icon_left_padding">
|
||||
|
||||
<FrameLayout
|
||||
android:layout_width="@dimen/favorites_my_places_icon_size"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_gravity="center_vertical">
|
||||
<FrameLayout
|
||||
android:layout_width="@dimen/favorites_my_places_icon_size"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_gravity="center_vertical">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatCheckBox
|
||||
android:id="@+id/toggle_item"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center"
|
||||
android:focusable="false"
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible" />
|
||||
<androidx.appcompat.widget.AppCompatCheckBox
|
||||
android:id="@+id/toggle_item"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center"
|
||||
android:focusable="false"
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/favourite_icon"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center"
|
||||
android:contentDescription="@string/favorite"
|
||||
tools:src="@drawable/bg_point_circle"/>
|
||||
</FrameLayout>
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/favourite_icon"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center"
|
||||
android:contentDescription="@string/favorite"
|
||||
tools:src="@drawable/bg_point_circle" />
|
||||
</FrameLayout>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_weight="1"
|
||||
android:orientation="vertical"
|
||||
android:layout_marginStart="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_marginLeft="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_marginEnd="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_marginRight="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:paddingTop="@dimen/context_menu_padding_margin_small"
|
||||
android:paddingBottom="@dimen/context_menu_padding_margin_small">
|
||||
<LinearLayout
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_marginLeft="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_marginEnd="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_marginRight="@dimen/favorites_my_places_icon_right_padding"
|
||||
android:layout_weight="1"
|
||||
android:orientation="vertical"
|
||||
android:paddingTop="@dimen/context_menu_padding_margin_small"
|
||||
android:paddingBottom="@dimen/context_menu_padding_margin_small">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/favourite_label"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:maxLines="2"
|
||||
android:scrollbars="none"
|
||||
android:textColor="?android:textColorPrimary"
|
||||
android:layout_marginBottom="@dimen/subHeaderPadding"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
tools:text="@string/lorem_ipsum" />
|
||||
<TextView
|
||||
android:id="@+id/favourite_label"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="@dimen/subHeaderPadding"
|
||||
android:maxLines="2"
|
||||
android:scrollbars="none"
|
||||
android:textColor="?android:textColorPrimary"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
tools:text="@string/lorem_ipsum" />
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/direction"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:contentDescription="@string/show_view_angle"
|
||||
osmand:srcCompat="@drawable/ic_direction_arrow" />
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/direction"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginTop="1sp"
|
||||
android:contentDescription="@string/show_view_angle"
|
||||
osmand:srcCompat="@drawable/ic_direction_arrow" />
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/distance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/gpx_small_icon_margin"
|
||||
android:layout_marginLeft="@dimen/gpx_small_icon_margin"
|
||||
android:maxLines="1"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
tools:text="100500 km" />
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/distance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/gpx_small_icon_margin"
|
||||
android:layout_marginLeft="@dimen/gpx_small_icon_margin"
|
||||
android:maxLines="1"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
tools:text="100500 km" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/group_image"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/list_item_button_padding"
|
||||
android:layout_marginLeft="@dimen/list_item_button_padding"
|
||||
android:contentDescription="@string/favorite_category_name"
|
||||
osmand:srcCompat="@drawable/ic_action_group_name_16" />
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/group_image"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/list_item_button_padding"
|
||||
android:layout_marginLeft="@dimen/list_item_button_padding"
|
||||
android:contentDescription="@string/favorite_category_name"
|
||||
osmand:srcCompat="@drawable/ic_action_group_name_16" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/group_name"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/gpx_small_icon_margin"
|
||||
android:layout_marginLeft="@dimen/gpx_small_icon_margin"
|
||||
android:ellipsize="end"
|
||||
android:maxLines="1"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
<TextView
|
||||
android:id="@+id/group_name"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/gpx_small_icon_margin"
|
||||
android:layout_marginLeft="@dimen/gpx_small_icon_margin"
|
||||
android:ellipsize="end"
|
||||
android:maxLines="1"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
||||
<ImageButton
|
||||
android:id="@+id/navigate_to"
|
||||
android:layout_width="@dimen/list_item_height"
|
||||
android:layout_height="@dimen/list_item_height"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/dashFavIconMargin"
|
||||
android:layout_marginLeft="@dimen/dashFavIconMargin"
|
||||
android:background="?attr/dashboard_button"
|
||||
android:contentDescription="@string/context_menu_item_directions_to"
|
||||
osmand:srcCompat="@drawable/ic_action_remove_dark"
|
||||
android:visibility="gone" />
|
||||
<ImageButton
|
||||
android:id="@+id/navigate_to"
|
||||
android:layout_width="@dimen/list_item_height"
|
||||
android:layout_height="@dimen/list_item_height"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/dashFavIconMargin"
|
||||
android:layout_marginLeft="@dimen/dashFavIconMargin"
|
||||
android:background="?attr/dashboard_button"
|
||||
android:contentDescription="@string/context_menu_item_directions_to"
|
||||
android:visibility="gone"
|
||||
osmand:srcCompat="@drawable/ic_action_remove_dark" />
|
||||
|
||||
<ImageButton
|
||||
android:id="@+id/options"
|
||||
android:layout_width="@dimen/list_item_height"
|
||||
android:layout_height="@dimen/list_item_height"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:background="?attr/dashboard_button"
|
||||
android:contentDescription="@string/shared_string_more"
|
||||
osmand:srcCompat="@drawable/ic_overflow_menu_white"
|
||||
android:visibility="gone" />
|
||||
</LinearLayout>
|
||||
<ImageButton
|
||||
android:id="@+id/options"
|
||||
android:layout_width="@dimen/list_item_height"
|
||||
android:layout_height="@dimen/list_item_height"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:background="?attr/dashboard_button"
|
||||
android:contentDescription="@string/shared_string_more"
|
||||
android:visibility="gone"
|
||||
osmand:srcCompat="@drawable/ic_overflow_menu_white" />
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
|
@ -68,19 +68,18 @@
|
|||
android:orientation="horizontal">
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/btn_read_full"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/context_menu_padding_margin_small"
|
||||
android:layout_marginLeft="@dimen/context_menu_padding_margin_small"
|
||||
android:background="@drawable/rounded_background_3dp">
|
||||
android:layout_marginStart="@dimen/content_padding_half"
|
||||
android:layout_marginLeft="@dimen/content_padding_half">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/btn_read_full"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="start"
|
||||
android:gravity="center_vertical"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
android:duplicateParentState="true"
|
||||
android:padding="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingStart="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingEnd="@dimen/bottom_sheet_content_padding_small"
|
||||
|
@ -96,19 +95,19 @@
|
|||
</FrameLayout>
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/btn_edit"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginRight="@dimen/context_menu_padding_margin_small"
|
||||
android:layout_marginEnd="@dimen/context_menu_padding_margin_small"
|
||||
android:layout_gravity="end"
|
||||
android:background="@drawable/rounded_background_3dp">
|
||||
android:layout_marginRight="@dimen/content_padding_half"
|
||||
android:layout_marginEnd="@dimen/content_padding_half"
|
||||
android:layout_gravity="end">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/btn_edit"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="start"
|
||||
android:gravity="center_vertical"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
android:duplicateParentState="true"
|
||||
android:padding="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingStart="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingEnd="@dimen/bottom_sheet_content_padding_small"
|
||||
|
@ -134,7 +133,6 @@
|
|||
android:layout_marginStart="@dimen/card_padding"
|
||||
android:layout_marginLeft="@dimen/card_padding"
|
||||
android:layout_marginTop="@dimen/content_padding"
|
||||
android:background="@drawable/rounded_background_3dp"
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible">
|
||||
|
||||
|
@ -142,7 +140,7 @@
|
|||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
android:duplicateParentState="true"
|
||||
android:padding="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingStart="@dimen/bottom_sheet_content_padding_small"
|
||||
android:paddingEnd="@dimen/bottom_sheet_content_padding_small"
|
||||
|
|
|
@ -38,21 +38,23 @@
|
|||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:gravity="center"
|
||||
android:orientation="horizontal"
|
||||
android:paddingTop="@dimen/dash_margin"
|
||||
android:paddingBottom="@dimen/dash_margin">
|
||||
android:layout_marginTop="@dimen/dash_margin"
|
||||
android:layout_marginBottom="@dimen/dash_margin"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/direction"
|
||||
android:layout_width="@dimen/context_menu_transport_icon_size"
|
||||
android:layout_height="@dimen/context_menu_transport_icon_size"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginTop="1sp"
|
||||
osmand:srcCompat="@drawable/ic_direction_arrow" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/distance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/content_padding_small_half"
|
||||
android:layout_marginLeft="@dimen/content_padding_small_half"
|
||||
android:maxLines="1"
|
||||
|
|
98
OsmAnd/res/layout/gpx_segment_list_item.xml
Normal file
98
OsmAnd/res/layout/gpx_segment_list_item.xml
Normal file
|
@ -0,0 +1,98 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:minHeight="@dimen/favorites_list_item_height"
|
||||
android:paddingTop="@dimen/list_header_settings_top_margin"
|
||||
android:paddingBottom="@dimen/list_header_settings_top_margin"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/icon"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/list_content_padding"
|
||||
android:layout_marginLeft="@dimen/list_content_padding"
|
||||
android:layout_marginEnd="@dimen/list_content_padding"
|
||||
android:layout_marginRight="@dimen/list_content_padding"
|
||||
android:contentDescription="@string/shared_string_icon"
|
||||
android:visibility="visible"
|
||||
osmand:srcCompat="@drawable/ic_action_split_interval" />
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="@dimen/list_content_padding"
|
||||
android:layout_marginLeft="@dimen/list_content_padding"
|
||||
android:layout_marginEnd="@dimen/list_content_padding"
|
||||
android:layout_marginRight="@dimen/list_content_padding"
|
||||
android:layout_weight="1"
|
||||
android:orientation="vertical">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/name"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="start"
|
||||
android:textColor="?android:textColorPrimary"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
tools:text="Segment" />
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/read_section"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:paddingTop="@dimen/subHeaderPadding"
|
||||
android:paddingBottom="@dimen/subHeaderPadding"
|
||||
android:visibility="visible">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/distance_icon"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="@dimen/content_padding_half"
|
||||
android:layout_marginRight="@dimen/content_padding_half"
|
||||
android:contentDescription="@string/distance"
|
||||
osmand:srcCompat="@drawable/ic_action_distance_16" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/distance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
tools:text="0" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/time_icon"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="@dimen/content_padding_half"
|
||||
android:layout_marginRight="@dimen/content_padding_half"
|
||||
android:contentDescription="@string/track_points"
|
||||
osmand:srcCompat="@drawable/ic_action_time_moving_16" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/time_interval"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:textColor="?android:textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
tools:text="0" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
|
@ -51,6 +51,7 @@
|
|||
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/name_and_read_section_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:paddingTop="@dimen/gpx_text_top_margin"
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
android:layout_height="@dimen/list_header_height"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:gravity="center_vertical"
|
||||
android:gravity="start|center_vertical"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<LinearLayout
|
||||
|
@ -14,14 +14,13 @@
|
|||
android:layout_height="match_parent"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:gravity="center_vertical"
|
||||
android:maxWidth="@dimen/grid_menu_item_width"
|
||||
android:gravity="start|center_vertical"
|
||||
android:orientation="vertical">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:gravity="start|center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:weightSum="2">
|
||||
|
||||
|
@ -31,6 +30,7 @@
|
|||
android:layout_height="match_parent"
|
||||
android:layout_weight="1"
|
||||
android:background="@null"
|
||||
android:letterSpacing="@dimen/description_letter_spacing"
|
||||
android:lines="1"
|
||||
android:textColor="?android:attr/textColorPrimary"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
|
@ -61,8 +61,11 @@
|
|||
android:layout_height="wrap_content"
|
||||
android:background="@null"
|
||||
android:ellipsize="end"
|
||||
android:letterSpacing="@dimen/description_letter_spacing"
|
||||
android:gravity="start|center_vertical"
|
||||
android:lines="1"
|
||||
android:maxWidth="@dimen/grid_menu_item_width"
|
||||
android:minWidth="@dimen/map_route_buttons_width"
|
||||
android:textColor="?android:attr/textColorSecondary"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
tools:text="@string/distance" />
|
||||
|
|
|
@ -73,6 +73,7 @@
|
|||
android:paddingBottom="@dimen/content_padding_small">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/check_box_title"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
|
|
159
OsmAnd/res/layout/trip_recording_active_fragment.xml
Normal file
159
OsmAnd/res/layout/trip_recording_active_fragment.xml
Normal file
|
@ -0,0 +1,159 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:osmand="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:paddingStart="@dimen/content_padding"
|
||||
android:paddingLeft="@dimen/content_padding"
|
||||
android:paddingTop="@dimen/content_padding_small"
|
||||
android:paddingEnd="@dimen/content_padding"
|
||||
android:paddingRight="@dimen/content_padding"
|
||||
android:paddingBottom="@dimen/content_padding_small"
|
||||
android:weightSum="2">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/title"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:letterSpacing="@dimen/text_button_letter_spacing"
|
||||
android:text="@string/monitoring_settings"
|
||||
android:textSize="@dimen/default_list_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium" />
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/status_container"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:clickable="true"
|
||||
android:focusable="true"
|
||||
android:gravity="end|center_vertical"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<net.osmand.plus.widgets.TextViewEx
|
||||
android:id="@+id/text_status"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:letterSpacing="@dimen/description_letter_spacing"
|
||||
android:textSize="@dimen/default_desc_text_size"
|
||||
osmand:typeface="@string/font_roboto_medium"
|
||||
tools:text="@string/recording_default_name"
|
||||
tools:textColor="@color/icon_color_osmand_light" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/icon_status"
|
||||
android:layout_width="@dimen/map_widget_icon"
|
||||
android:layout_height="@dimen/map_widget_icon"
|
||||
android:layout_marginStart="@dimen/content_padding_small"
|
||||
android:layout_marginLeft="@dimen/content_padding_small"
|
||||
tools:srcCompat="@drawable/ic_action_polygom_dark"
|
||||
tools:tint="@color/icon_color_osmand_light" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<androidx.recyclerview.widget.RecyclerView
|
||||
android:id="@+id/block_statistics"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="@dimen/list_header_height"
|
||||
android:layout_marginTop="@dimen/content_padding_small_half"
|
||||
android:clipToPadding="false"
|
||||
android:orientation="horizontal"
|
||||
tools:itemCount="4"
|
||||
tools:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
|
||||
tools:listitem="@layout/item_gpx_stat_block" />
|
||||
|
||||
<include
|
||||
android:id="@+id/show_track_on_map"
|
||||
layout="@layout/bottom_sheet_with_switch_divider_and_additional_button"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding_half"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:layout_marginBottom="@dimen/content_padding" />
|
||||
|
||||
<View
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:background="?attr/dashboard_divider" />
|
||||
|
||||
<include
|
||||
android:id="@+id/button_clear"
|
||||
layout="@layout/bottom_sheet_button_with_icon"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:layout_marginBottom="@dimen/content_padding" />
|
||||
|
||||
<include
|
||||
android:id="@+id/button_segment"
|
||||
layout="@layout/bottom_sheet_button_with_icon"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding_half"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding" />
|
||||
|
||||
<include
|
||||
android:id="@+id/button_save"
|
||||
layout="@layout/bottom_sheet_button_with_icon"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding_small"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:layout_marginBottom="@dimen/content_padding" />
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_marginTop="@dimen/content_padding_half"
|
||||
android:layout_marginEnd="@dimen/content_padding"
|
||||
android:layout_marginRight="@dimen/content_padding"
|
||||
android:layout_marginBottom="@dimen/content_padding"
|
||||
android:baselineAligned="false"
|
||||
android:orientation="horizontal"
|
||||
android:weightSum="2">
|
||||
|
||||
<include
|
||||
android:id="@+id/button_pause"
|
||||
layout="@layout/bottom_sheet_button_with_icon"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1" />
|
||||
|
||||
<include
|
||||
android:id="@+id/button_stop"
|
||||
layout="@layout/bottom_sheet_button_with_icon"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/content_padding"
|
||||
android:layout_marginLeft="@dimen/content_padding"
|
||||
android:layout_weight="1" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
|
@ -2309,7 +2309,7 @@
|
|||
<string name="relief_smoothness_factor_descr">التضاريس المفضلة : مسطحة أو تلال.</string>
|
||||
<string name="shared_string_slope">الانحدار</string>
|
||||
<string name="shared_string_move">نقل</string>
|
||||
<string name="routing_attr_height_obstacles_description">استخدام بيانات ارتفاع التضاريس المقدمة بواسطة SRTM, ASTER, EU-DEM.</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">إظهار نقاط ومعالم العمق.</string>
|
||||
<string name="auto_split_recording_descr">بدء مقطع جديدة بعد فارق 6 دقائق، مسار جديد بعد فارق 2 ساعة، أو ملف جديد بعد فارق أطول إذا تغير التاريخ.</string>
|
||||
<string name="shared_string_paused">متوقف مؤقتاً</string>
|
||||
|
|
|
@ -779,7 +779,7 @@
|
|||
<string name="altitude_descent">Eniş</string>
|
||||
<string name="altitude_ascent">Yoxuş</string>
|
||||
<string name="routing_attr_height_obstacles_name">Yüksəklik məlumatlarını istifadə et</string>
|
||||
<string name="routing_attr_height_obstacles_description">SRTM, ASTER və EU-DEM tərəfindən təmin edilən ərazi yüksəklik məlumatlarını istifadə et.</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Dərinlik konturlarını və nöqtələrini göstər.</string>
|
||||
<string name="rendering_attr_depthContours_name">Dəniz dərinliyi konturları</string>
|
||||
<string name="rendering_attr_contourDensity_description">Kontur xəttinin sıxlığı</string>
|
||||
|
|
|
@ -519,7 +519,7 @@
|
|||
<string name="shared_string_time">Tiempu</string>
|
||||
<string name="total_distance">Distancia total</string>
|
||||
<string name="routing_attr_height_obstacles_name">Usar datos d\'elevación</string>
|
||||
<string name="routing_attr_height_obstacles_description">Inclúi la elevación del tarrén (pelos datos de SRTM, ASTER y EU-DEM).</string>
|
||||
|
||||
<string name="search_another_country">Esbillar otra rexón</string>
|
||||
<string name="shared_string_change">Camudar</string>
|
||||
<string name="mapillary_image">Imaxe de Mapillary</string>
|
||||
|
|
|
@ -2189,7 +2189,7 @@ Praparcyjnaj pamiacі %4$s MB (Abmiežavańnie Android %5$s MB, Dalvik %6$s MB).
|
|||
<string name="mapillary_image">Vyjava Mapillary</string>
|
||||
<string name="mapillary_widget_descr">Dazvaliaje chutki ŭniosak ŭ Mapillary.</string>
|
||||
<string name="relief_smoothness_factor_descr">Pieravažny reĺjef: raŭninny ci harysty.</string>
|
||||
<string name="routing_attr_height_obstacles_description">Faktar vyšyni ziamnoj pavierchni (danyja z SRTM, ASTER i EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Pakazvać kontury i punkty hlybini.</string>
|
||||
<string name="rendering_attr_contourDensity_description">Ščyĺnasć haryzantaliaŭ</string>
|
||||
<string name="rendering_attr_contourWidth_description">Taŭščynia haryzantaliaŭ (izahipsy)</string>
|
||||
|
|
|
@ -2194,7 +2194,7 @@
|
|||
<string name="shared_string_time">Час</string>
|
||||
<string name="total_distance">Агульная даўжыня</string>
|
||||
<string name="routing_attr_height_obstacles_name">Выкарыстоўваць даныя вышыні</string>
|
||||
<string name="routing_attr_height_obstacles_description">Фактар вышыні зямной паверхні (даныя з SRTM, ASTER і EU-DEM).</string>
|
||||
|
||||
<string name="auto_split_recording_title">Аўтаматычнае дзяленне запісаў пасля перапынку</string>
|
||||
<string name="auto_split_recording_descr">Пачаць новы сегмент пасля 6-хвіліннага перапынку, новы след — пасля 2-гадзіннага перапынку, ці новы файл пасля доўгага перапынку (як змяніляся дата).</string>
|
||||
<string name="lang_ber">Берберская</string>
|
||||
|
|
|
@ -2162,7 +2162,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Mostra isòbates i fondàries puntuals.</string>
|
||||
<string name="rendering_attr_depthContours_name">Isòbates</string>
|
||||
<string name="routing_attr_height_obstacles_name">Utilitza les cotes d\'elevació</string>
|
||||
<string name="routing_attr_height_obstacles_description">Revisa l\'elevació del terreny (mitjançant dades SRTM, ASTER i EU-DEM).</string>
|
||||
|
||||
<string name="route_altitude">Alçat de la ruta</string>
|
||||
<string name="altitude_descent">Descens</string>
|
||||
<string name="altitude_ascent">Ascens</string>
|
||||
|
|
|
@ -2174,7 +2174,7 @@
|
|||
<string name="shared_string_time">Čas</string>
|
||||
<string name="total_distance">Celková vzdálenost</string>
|
||||
<string name="routing_attr_height_obstacles_name">Použít údaje o nadmořské výšce</string>
|
||||
<string name="routing_attr_height_obstacles_description">Zohlednit převýšení terénu (data od SRTM, ASTER a EU-DEM).</string>
|
||||
|
||||
<string name="routing_attr_driving_style_name">Styl jízdy</string>
|
||||
<string name="select_gpx_folder">Vyberte složku pro soubor GPX</string>
|
||||
<string name="file_can_not_be_moved">Soubor se nepodařilo přesunout.</string>
|
||||
|
|
|
@ -2172,7 +2172,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Vis dybdekonturer og -punkter.</string>
|
||||
<string name="rendering_attr_depthContours_name">Havdybdekonturer</string>
|
||||
<string name="routing_attr_height_obstacles_name">Brug højdedata</string>
|
||||
<string name="routing_attr_height_obstacles_description">Terrænhøjde-faktor (via SRTM, ASTER og EU-DEM data).</string>
|
||||
|
||||
<string name="route_altitude">Rutehøjde</string>
|
||||
<string name="altitude_descent">Fald</string>
|
||||
<string name="altitude_ascent">Stigning</string>
|
||||
|
|
|
@ -2171,7 +2171,7 @@
|
|||
<string name="navigate_point_olc">Offener Standortcode (OLC)</string>
|
||||
<string name="quick_action_page_list_descr">Eine Schaltfläche, um durch die Liste unten zu blättern.</string>
|
||||
<string name="routing_attr_height_obstacles_name">Höhendaten berücksichtigen</string>
|
||||
<string name="routing_attr_height_obstacles_description">Faktor im Geländeprofil (über SRTM, ASTER und EU-DEM-Daten).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_name">Nautische Tiefenlinien</string>
|
||||
<string name="rendering_attr_depthContours_description">Tiefenlinien und -punkte einblenden.</string>
|
||||
<string name="route_altitude">Routenhöhenprofil</string>
|
||||
|
|
|
@ -1876,7 +1876,7 @@
|
|||
<string name="total_distance">Συνολική απόσταση</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Επιλέξτε διακύμανση ανύψωσης</string>
|
||||
<string name="routing_attr_height_obstacles_name">Χρήση υψομετρικών δεδομένων</string>
|
||||
<string name="routing_attr_height_obstacles_description">Συντελεστής σε ανύψωση εδάφους (μέσω SRTM, ASTER και δεδομένων EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Εμφάνιση ισοβαθών καμπυλών και σημείων.</string>
|
||||
<string name="rendering_attr_depthContours_name">Ναυτικές ισοβαθείς καμπύλες</string>
|
||||
<string name="auto_split_recording_title">Αυτόματος διαχωρισμός καταγραφών μετά από κενό</string>
|
||||
|
|
|
@ -2166,7 +2166,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Montri punktojn kaj kurbojn de profundo.</string>
|
||||
<string name="rendering_attr_depthContours_name">Maraj profundec-kurboj</string>
|
||||
<string name="routing_attr_height_obstacles_name">Uzi datumojn pri altitudo</string>
|
||||
<string name="routing_attr_height_obstacles_description">Konsideri nivelon de tereno (laŭ datumoj el SRTM, ASTER kaj EU-DEM).</string>
|
||||
|
||||
<string name="route_altitude">Kursa altitudo</string>
|
||||
<string name="altitude_descent">Malsupreniro</string>
|
||||
<string name="altitude_ascent">Supreniro</string>
|
||||
|
|
|
@ -2175,7 +2175,7 @@
|
|||
<string name="shared_string_time">Tiempo</string>
|
||||
<string name="total_distance">Distancia total</string>
|
||||
<string name="routing_attr_height_obstacles_name">Usar datos de elevación</string>
|
||||
<string name="routing_attr_height_obstacles_description">Incluye como factor, la elevación del terreno (según datos de SRTM, ASTER y EU-DEM).</string>
|
||||
|
||||
<string name="routing_attr_driving_style_name">Estilo de conducción</string>
|
||||
<string name="select_gpx_folder">Marcar la carpeta del archivo GPX</string>
|
||||
<string name="file_can_not_be_moved">No se pudo mover el archivo.</string>
|
||||
|
|
|
@ -2175,7 +2175,7 @@
|
|||
<string name="shared_string_time">Tiempo</string>
|
||||
<string name="total_distance">Distancia total</string>
|
||||
<string name="routing_attr_height_obstacles_name">Usar datos de elevación</string>
|
||||
<string name="routing_attr_height_obstacles_description">Incluye como factor, la elevación del terreno (según datos de SRTM, ASTER y EU-DEM).</string>
|
||||
|
||||
<string name="routing_attr_driving_style_name">Estilo de conducción</string>
|
||||
<string name="select_gpx_folder">Marcar la carpeta del archivo GPX</string>
|
||||
<string name="file_can_not_be_moved">No se pudo mover el archivo.</string>
|
||||
|
|
|
@ -2163,7 +2163,7 @@
|
|||
<string name="shared_string_time">Tiempo</string>
|
||||
<string name="total_distance">Distancia total</string>
|
||||
<string name="routing_attr_height_obstacles_name">Usar datos de elevación</string>
|
||||
<string name="routing_attr_height_obstacles_description">Incluye como factor, la elevación del terreno (según datos de SRTM, ASTER y EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Mostrar curvas y puntos de profundidad.</string>
|
||||
<string name="rendering_attr_depthContours_name">Curvas de profundidad náuticas</string>
|
||||
<string name="auto_split_recording_title">División automática de grabaciones en intervalos</string>
|
||||
|
|
|
@ -2504,7 +2504,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Kuva sügavuskontuurid ja -punktid.</string>
|
||||
<string name="rendering_attr_depthContours_name">Meresügavuse kontuurid</string>
|
||||
<string name="routing_attr_height_obstacles_name">Kasuta kõrgusandmeid</string>
|
||||
<string name="routing_attr_height_obstacles_description">Maastiku kõrguse tegur (SRTM, ASTER ja EU-DEM andmestikust).</string>
|
||||
|
||||
<string name="altitude_descent">Laskumine</string>
|
||||
<string name="altitude_ascent">Tõus</string>
|
||||
<string name="altitude_range">Kõrgusevahe</string>
|
||||
|
|
|
@ -2197,7 +2197,7 @@ Area honi dagokio: %1$s x %2$s</string>
|
|||
<string name="shared_string_time">Denbora</string>
|
||||
<string name="total_distance">Distantzia guztira</string>
|
||||
<string name="routing_attr_height_obstacles_name">Erabili elebazio kotak</string>
|
||||
<string name="routing_attr_height_obstacles_description">Kontuan izan terrenoaren elebazioa (SRTM, ASTER, eta EU-DEM datuen bidez).</string>
|
||||
|
||||
<string name="shared_string_slope">Malda</string>
|
||||
<string name="lang_ber">Berberera</string>
|
||||
<string name="right_side_navigation">Eskumatik gidatzea</string>
|
||||
|
|
|
@ -1811,7 +1811,7 @@
|
|||
<string name="average_altitude">میانگین ارتفاع</string>
|
||||
<string name="total_distance">مسافت کل</string>
|
||||
<string name="routing_attr_height_obstacles_name">استفاده از دادهٔ ارتفاعی</string>
|
||||
<string name="routing_attr_height_obstacles_description">فاکتور ارتفاعدهی عارضهها (با استفاده از دادههای SRTM، ASTER و EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">نمایش نقاط و منحنیهای میزان عمقی.</string>
|
||||
<string name="rendering_attr_depthContours_name">منحنیهای میزان عمق دریا</string>
|
||||
<string name="rendering_attr_contourDensity_description">تراکم منحنی میزان</string>
|
||||
|
|
|
@ -1898,7 +1898,7 @@ Jos pidät OsmAndista ja OSMsta ja haluat tukea niitä, on tämä täydellinen t
|
|||
<string name="shared_string_time">Aika</string>
|
||||
<string name="total_distance">Kokonaisetäisyys</string>
|
||||
<string name="routing_attr_height_obstacles_name">Käytä korkeustietoja</string>
|
||||
<string name="routing_attr_height_obstacles_description">Käytä maaston korkeustietoja jotka saadaan SRTM, ASTER ja EU-DEM lähteistä</string>
|
||||
|
||||
<string name="auto_split_recording_title">Jaa automaattisesti nauhoitukset tauon jälkeen</string>
|
||||
<string name="rendering_attr_hideWaterPolygons_name">Piilota vesi</string>
|
||||
<string name="shared_string_action_name">Toiminnon nimi</string>
|
||||
|
|
|
@ -2158,7 +2158,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Afficher les lignes et points de sonde.</string>
|
||||
<string name="rendering_attr_depthContours_name">Lignes de sonde maritimes</string>
|
||||
<string name="routing_attr_height_obstacles_name">Utiliser les données d\'altitude</string>
|
||||
<string name="routing_attr_height_obstacles_description">Facteur pour les données d\'altitude fournies par SRTM, ASTER et EU-DEM.</string>
|
||||
|
||||
<string name="average_altitude">Altitude moyenne</string>
|
||||
<string name="total_distance">Distance totale</string>
|
||||
<string name="shared_string_time">Durée</string>
|
||||
|
|
|
@ -2572,7 +2572,7 @@ Lon %2$s</string>
|
|||
<string name="do_not_send_anonymous_app_usage_desc">O OsmAnd recompila información sobre as lapelas que abres na aplicación. Non estamos a recompilar datos da localización, datos inseridos na aplicación ou datos relacionados coas áreas que ollas, procuras ou baixas.</string>
|
||||
<string name="do_not_show_startup_messages_desc">Agocha os descontos da aplicación e as mensaxes especiais dos acontecementos locais.</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Escoller variación da altitude</string>
|
||||
<string name="routing_attr_height_obstacles_description">Inclúe coma factor, a altitude do terreo (segundo datos do SRTM, ASTER e EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Amosar curvas e puntos do afundimento.</string>
|
||||
<string name="rendering_attr_depthContours_name">Curvas do afundimento náuticos</string>
|
||||
<string name="auto_split_recording_title">División automática das gravacións en intres</string>
|
||||
|
|
|
@ -2168,7 +2168,7 @@
|
|||
<string name="shared_string_time">Idő</string>
|
||||
<string name="total_distance">Teljes táv</string>
|
||||
<string name="routing_attr_height_obstacles_name">Magasságadatok használata</string>
|
||||
<string name="routing_attr_height_obstacles_description">Terepmagasság figyelembe vétele (SRTM, ASTER és EU-DEM domborzatmodellekből).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Mélységvonalak és pontok megjelenítése.</string>
|
||||
<string name="rendering_attr_depthContours_name">Tengeri mélységvonalak</string>
|
||||
<string name="auto_split_recording_title">Felvételek automatikus szétvágása szünet után</string>
|
||||
|
|
|
@ -341,7 +341,7 @@
|
|||
<string name="total_distance">Ընդհանուր հեռավորությունը</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Ընտրել բարձունքների տատանումը</string>
|
||||
<string name="routing_attr_height_obstacles_name">Օգտագործել բարձրության տվյալները</string>
|
||||
<string name="routing_attr_height_obstacles_description">Օգտագործել բարձրության տվյալներ տրամադրված SRTM, ASTER և EU-DEM։</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Ցույց տալ խորության տվյալները։</string>
|
||||
<string name="rendering_attr_depthContours_name">Ծովային խորքային ուրվագծեր</string>
|
||||
<string name="rendering_attr_contourDensity_description">Եզրագծերի խտությունը</string>
|
||||
|
|
|
@ -333,7 +333,7 @@
|
|||
<string name="total_distance">Jarak Total</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Pilih fluktuasi ketinggian</string>
|
||||
<string name="routing_attr_height_obstacles_name">Gunakan Data Ketinggian</string>
|
||||
<string name="routing_attr_height_obstacles_description">Gunakan data elevasi medan yang disediakan oleh SRTM, ASTER, dan EU-DEM.</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Tampilkan kontur dan titik kedalaman.</string>
|
||||
<string name="rendering_attr_depthContours_name">Kontur kedalaman bahari</string>
|
||||
<string name="auto_split_recording_title">Rekaman split otomatis setelah jeda</string>
|
||||
|
|
|
@ -1994,7 +1994,7 @@
|
|||
<string name="fonts_header">Letur fyrir kort</string>
|
||||
<string name="right_side_navigation">Ekið á hægri akrein</string>
|
||||
<string name="driving_region_automatic">Sjálfvirkt</string>
|
||||
<string name="routing_attr_height_obstacles_description">Nota yfirborðshæðargögn (í gegnum SRTM, ASTER og EU-DEM).</string>
|
||||
|
||||
<string name="auto_split_recording_title">Skipta skráningu sjálfvirkt eftir bil</string>
|
||||
<string name="incremental_search_city">Stigvaxandi leit í borg</string>
|
||||
<string name="rendering_attr_showRoadMaps_description">Veldu þegar birta á kort einungis með vegum:</string>
|
||||
|
|
|
@ -2167,7 +2167,7 @@
|
|||
<string name="shared_string_time">Tempo</string>
|
||||
<string name="total_distance">Distanza totale</string>
|
||||
<string name="routing_attr_height_obstacles_name">Utilizza dati altitudine</string>
|
||||
<string name="routing_attr_height_obstacles_description">Fattore di elevazione del terreno (tramite i dati SRTM, ASTER e EU-DEM).</string>
|
||||
|
||||
<string name="shared_string_time_span">Intervallo di tempo</string>
|
||||
<string name="shared_string_max">Massimo</string>
|
||||
<string name="shared_string_start_time">Ora d\'inizio</string>
|
||||
|
|
|
@ -2712,7 +2712,7 @@
|
|||
\n ניתן לקבל נווט אמין למדינה שלך - בין אם זו ישראל, צרפת, גרמניה, מקסיקו, אנגליה, ספרד, הולנד, ארה״ב, רוסיה, ברזיל או כל מדינה אחרת.</string>
|
||||
<string name="nm">מייל ימי</string>
|
||||
<string name="rendering_attr_hikingRoutesOSMC_description">עיבוד מסלולים לפי עקבות OSMC.</string>
|
||||
<string name="routing_attr_height_obstacles_description">מקדם נתוני גובה פני קרקע (נתונים של SRTM, ASTER ו־EU-DEM).</string>
|
||||
|
||||
<string name="plugin_nautical_descr">תוסף זה מעשיר את המפה ואת הניווט של יישומון OsmAnd ומאפשר לייצר מפות ימיות לחתירה, הפלגה וסוגים נוספים של ספורט ימי.
|
||||
\n
|
||||
\nתוסף מפה מיוחד ל־OsmAnd יספק את כל סימוני הניווט הימיים והסימנים הימיים המוסכמים, לניווט במקווי מים פנימיים לרבות ניווט באזורים הקרובים לחוף. התיאור של כל סימון ניווט מספק את הפרטים הנדרשים כדי לזהות אותם ואת המשמעות שלהם (קטגוריה, צורה, צבע, רצף, הפניה וכו׳).
|
||||
|
|
|
@ -2084,7 +2084,7 @@ POIの更新は利用できません</string>
|
|||
<string name="shared_string_time">時間</string>
|
||||
<string name="total_distance">総走行距離</string>
|
||||
<string name="routing_attr_height_obstacles_name">標高データを使用</string>
|
||||
<string name="routing_attr_height_obstacles_description">SRTM、ASTER、EU-DEMによる地形標高データを使用します。</string>
|
||||
|
||||
<string name="rendering_attr_hideWaterPolygons_description">水域</string>
|
||||
<string name="rendering_attr_hideWaterPolygons_name">水域ポリゴン</string>
|
||||
<string name="wiki_around">近隣のWikipedia記事</string>
|
||||
|
|
|
@ -2231,7 +2231,7 @@ Tai yra puikus būdas paremti OsmAnd ir OSM, jei jie jums patinka.</string>
|
|||
<string name="total_distance">Bendras atstumas</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Pasirinkite aukščio kaitos diapazoną</string>
|
||||
<string name="routing_attr_height_obstacles_name">Naudoti aukščio informaciją</string>
|
||||
<string name="routing_attr_height_obstacles_description">Vietovės reljefo faktorius (SRTM, ASTER ir EU-DEM duomenimis).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Rodyti gylio kontūrus ir taškus.</string>
|
||||
<string name="rendering_attr_depthContours_name">Vandenyno gylio kontūrai</string>
|
||||
<string name="auto_split_recording_title">Automatinis įrašo padalinimas po pertraukimo</string>
|
||||
|
|
|
@ -2166,7 +2166,7 @@ Apraksta laukumu: %1$s x %2$s</string>
|
|||
<string name="shared_string_time">Laiks</string>
|
||||
<string name="total_distance">Maršruta garums</string>
|
||||
<string name="routing_attr_height_obstacles_name">Lietot elevācijas datus</string>
|
||||
<string name="routing_attr_height_obstacles_description">Lietot apgabala elevācijas datus no SRTM, ASTER un EU-DEM.</string>
|
||||
|
||||
<string name="relief_smoothness_factor_descr">Ieteicamais reljefs: līdzens vai kalnains.</string>
|
||||
<string name="shared_string_slope">Slīpums</string>
|
||||
<string name="lang_ber">Berberu</string>
|
||||
|
|
|
@ -2015,7 +2015,7 @@
|
|||
<string name="add_new_folder">Legg til ny mappe</string>
|
||||
<string name="shared_string_gpx_track">Spor</string>
|
||||
<string name="routing_attr_height_obstacles_name">Bruk høydedata</string>
|
||||
<string name="routing_attr_height_obstacles_description">Ta hensyn til terrenghøyde (data fra SRTM, ASTER og EU-DEM).</string>
|
||||
|
||||
<string name="quick_action_bug_message">Melding</string>
|
||||
<string name="shared_string_permissions">Tillatelser</string>
|
||||
<string name="import_gpx_failed_descr">Kunne ikke importere filen. Kontroller at OsmAnd har tillatelse til å lese den.</string>
|
||||
|
|
|
@ -2177,7 +2177,7 @@
|
|||
<string name="shared_string_time_moving">Tijd in beweging</string>
|
||||
<string name="routing_attr_driving_style_name">Rijstijl</string>
|
||||
<string name="routing_attr_height_obstacles_name">Hoogtegegevens gebruiken</string>
|
||||
<string name="routing_attr_height_obstacles_description">Gebruik hoogtegegevens (van SRTM, ASTER en EU-DEM data) bij bepalen route.</string>
|
||||
|
||||
<string name="shared_string_gpx_track">Track</string>
|
||||
<string name="right_side_navigation">Rechts rijdend</string>
|
||||
<string name="driving_region_automatic">Automatisch</string>
|
||||
|
|
|
@ -2169,7 +2169,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Wyświetla kontury i punkty głębi.</string>
|
||||
<string name="rendering_attr_depthContours_name">Morskie kontury głębokości</string>
|
||||
<string name="routing_attr_height_obstacles_name">Używanie danych wysokościowych</string>
|
||||
<string name="routing_attr_height_obstacles_description">Używa danych wysokościowych (dane z SRTM, ASTER i EU-DEM).</string>
|
||||
|
||||
<string name="route_altitude">Wysokość trasy</string>
|
||||
<string name="altitude_descent">W dół</string>
|
||||
<string name="altitude_ascent">W górę</string>
|
||||
|
|
|
@ -2207,7 +2207,7 @@
|
|||
<string name="route_altitude">Altitude da rota</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Selecionar a flutuação de altimetria</string>
|
||||
<string name="routing_attr_height_obstacles_name">Usar dados altimétricos</string>
|
||||
<string name="routing_attr_height_obstacles_description">Considerar altimetria do terreno (via dados SRTM, ASTER e EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Mostrar curvas e pontos batimétricos.</string>
|
||||
<string name="rendering_attr_depthContours_name">Batimetria náutica</string>
|
||||
<string name="rendering_attr_contourDensity_description">Densidade das curvas de nível</string>
|
||||
|
|
|
@ -2011,7 +2011,7 @@
|
|||
<string name="total_distance">Distância total</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Selecionar flutuação de elevação</string>
|
||||
<string name="routing_attr_height_obstacles_name">Utilizar dados de elevação</string>
|
||||
<string name="routing_attr_height_obstacles_description">Utilizar elevação de terreno (dos dados do SRTM, ASTER e EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Mostrar pontos e contornos de profundidade.</string>
|
||||
<string name="rendering_attr_depthContours_name">Contornos de profundidade náuticos</string>
|
||||
<string name="show_transparency_seekbar">Mostra a transparência da barra de navegação</string>
|
||||
|
|
|
@ -142,7 +142,7 @@
|
|||
<string name="routing_attr_driving_style_name">Стиль езды</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Колебания высоты ландшафта</string>
|
||||
<string name="routing_attr_height_obstacles_name">Использовать данные о высотах</string>
|
||||
<string name="routing_attr_height_obstacles_description">Фактор рельефа местности (по данным SRTM, ASTER и EU-DEM).</string>
|
||||
|
||||
<string name="quick_action_duplicates">Действие переименовано в %1$s, чтобы избежать дублирования.</string>
|
||||
<string name="quick_action_duplicate">Обнаружен дубликат имени</string>
|
||||
<string name="quick_action_showhide_favorites_descr">Переключатель, чтобы показать или скрыть избранные точки на карте.</string>
|
||||
|
|
|
@ -2167,7 +2167,7 @@
|
|||
<string name="rendering_attr_depthContours_name">Curvas de profondidade nàuticas</string>
|
||||
<string name="rendering_attr_depthContours_description">Ammustra sas lìnias de profondidade.</string>
|
||||
<string name="routing_attr_height_obstacles_name">Imprea sos datos de s\'artària</string>
|
||||
<string name="routing_attr_height_obstacles_description">Fatore pro s\'artària de su terrinu (dae datos SRTM, ASTER e EU-DEM).</string>
|
||||
|
||||
<string name="routing_attr_driving_style_name">Istile de ghia</string>
|
||||
<string name="route_altitude">Artària de su caminu</string>
|
||||
<string name="altitude_descent">Falada</string>
|
||||
|
|
|
@ -2165,7 +2165,7 @@
|
|||
<string name="rendering_attr_depthContours_description">Zobraziť hĺbkové úrovne a body.</string>
|
||||
<string name="rendering_attr_depthContours_name">Námorné hĺbkové vrstevnice</string>
|
||||
<string name="routing_attr_height_obstacles_name">Použiť údaje nadmorskej výšky</string>
|
||||
<string name="routing_attr_height_obstacles_description">Zohľadniť prevýšenie terénu (z údajov SRTM, ASTER a EU-DEM).</string>
|
||||
|
||||
<string name="route_altitude">Prevýšenie trasy</string>
|
||||
<string name="altitude_descent">Klesanie</string>
|
||||
<string name="altitude_ascent">Stúpanie</string>
|
||||
|
|
|
@ -2169,7 +2169,7 @@
|
|||
<string name="shared_string_time">Čas</string>
|
||||
<string name="total_distance">Skupna razdalja</string>
|
||||
<string name="routing_attr_height_obstacles_name">Uporabi podatke višine</string>
|
||||
<string name="routing_attr_height_obstacles_description">Faktor podatkov spreminjanja višine terena (po podatkih SRTM, ASTER in EU-DEM).</string>
|
||||
|
||||
<string name="routing_attr_driving_style_name">Način vožnje</string>
|
||||
<string name="select_gpx_folder">Izbor mape datotek GPX</string>
|
||||
<string name="file_can_not_be_moved">Datoteke ni mogoče premakniti.</string>
|
||||
|
|
|
@ -1525,7 +1525,7 @@
|
|||
<string name="index_item_depth_points_northern_hemisphere">Поморске дубинске тачке северне полулопте</string>
|
||||
<string name="download_depth_countours">Поморске изобате</string>
|
||||
<string name="shared_string_color">Боја</string>
|
||||
<string name="routing_attr_height_obstacles_description">Урачунај и податке висине земљишта (обезбеђених помоћу СРМ, АСТЕР и ЕУ-ДЕМ података).</string>
|
||||
|
||||
<string name="auto_split_recording_title">Самоподели снимке после размака</string>
|
||||
<string name="auto_split_recording_descr">Почни нови одсечак после размака од 6 минута, нову путању после размака од 2 сата, или нови фајл после дужег размака ако је дан измењен.</string>
|
||||
<string name="rendering_attr_showMtbRoutes_name">Прикажи путеве планинских бицикли</string>
|
||||
|
|
|
@ -2097,7 +2097,7 @@ Vänligen tillhandahåll fullständig kod</string>
|
|||
<string name="quick_action_map_overlay_switch">"Kartöverlägget har ändrats till \"%s\"."</string>
|
||||
<string name="quick_action_btn_tutorial_descr">Tryck länge och dra knappen för att ändra dess position på skärmen.</string>
|
||||
<string name="routing_attr_height_obstacles_name">Använd höjddata</string>
|
||||
<string name="routing_attr_height_obstacles_description">Använd terränghöjddata från SRTM, ASTER och EU-DEM.</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Visa djupkonturer och punkter.</string>
|
||||
<string name="shared_string_slope">Sluttning</string>
|
||||
<string name="altitude_range">Höjdområde</string>
|
||||
|
|
|
@ -2307,7 +2307,7 @@
|
|||
<string name="average_altitude">Ortalama yükseklik</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Yükseklikte dalgalanma seçin</string>
|
||||
<string name="routing_attr_height_obstacles_name">Yükseklik verisi kullan</string>
|
||||
<string name="routing_attr_height_obstacles_description">Arazi kotunda faktör (SRTM, ASTER ve EU-DEM verileri aracılığıyla).</string>
|
||||
|
||||
<string name="search_map_hint">Şehir veya bölge</string>
|
||||
<string name="route_roundabout_short">%1$d çıkışa gir ve ilerle</string>
|
||||
<string name="gpx_no_tracks_title">Henüz yol dosyanız yok</string>
|
||||
|
|
|
@ -2130,7 +2130,7 @@
|
|||
<string name="shared_string_time">Час</string>
|
||||
<string name="total_distance">Загальна відстань</string>
|
||||
<string name="routing_attr_height_obstacles_name">Використовувати дані висоти</string>
|
||||
<string name="routing_attr_height_obstacles_description">Фактор висоти рельєфу земної поверхні (дані від SRTM, ASTER та EU-DEM).</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">Показати контури глибини і точки.</string>
|
||||
<string name="rendering_attr_depthContours_name">Контури морських глибин</string>
|
||||
<string name="auto_split_recording_title">Авто-розрив запису після перерви</string>
|
||||
|
|
|
@ -1382,7 +1382,7 @@
|
|||
<string name="average_altitude">平均海拔</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">选择海拔波动</string>
|
||||
<string name="routing_attr_height_obstacles_name">使用标高数据</string>
|
||||
<string name="routing_attr_height_obstacles_description">地形高程因素(通过 SRTM、ASTER 和欧盟 DEM 数据)。</string>
|
||||
|
||||
<string name="rendering_attr_depthContours_description">显示等深线和标记。</string>
|
||||
<string name="rendering_attr_depthContours_name">航海等深线</string>
|
||||
<string name="auto_split_recording_title">自动拆分录音后的间隙</string>
|
||||
|
|
|
@ -2161,7 +2161,7 @@
|
|||
<string name="rendering_attr_depthContours_description">顯示等深線和標記。</string>
|
||||
<string name="rendering_attr_depthContours_name">航海等深線</string>
|
||||
<string name="routing_attr_height_obstacles_name">使用海拔資料</string>
|
||||
<string name="routing_attr_height_obstacles_description">將地勢海拔納入 (透過 SRTM、ASTER 和 EU-DEM 的資料)。</string>
|
||||
|
||||
<string name="route_altitude">路線的海拔</string>
|
||||
<string name="altitude_descent">下坡</string>
|
||||
<string name="altitude_ascent">上坡</string>
|
||||
|
|
|
@ -4339,10 +4339,10 @@
|
|||
<string name="poi_patrolled_no">Patrolled: no</string>
|
||||
<string name="poi_piste_status_open">Piste status: open</string>
|
||||
<string name="poi_piste_status_closed">Piste status: closed</string>
|
||||
|
||||
<string name="poi_summit_register_yes">Summit register: yes</string>
|
||||
<string name="poi_summit_register_no">Summit register: no</string>
|
||||
|
||||
<string name="poi_mobile_library">Mobile library stop position</string>
|
||||
<string name="poi_conference_centre">Conference centre</string>
|
||||
<string name="poi_geodesist">Geodesist</string>
|
||||
|
||||
</resources>
|
||||
|
|
|
@ -413,4 +413,7 @@
|
|||
|
||||
<dimen name="radioButtonSize">32dp</dimen>
|
||||
<dimen name="checkBoxSize">24dp</dimen>
|
||||
|
||||
<dimen name="titleLineSpacingExtra">5sp</dimen>
|
||||
<dimen name="descriptionLineSpacingExtra">3sp</dimen>
|
||||
</resources>
|
|
@ -12,8 +12,16 @@
|
|||
|
||||
-->
|
||||
|
||||
<string name="routing_attr_height_obstacles_description">Routing could avoid strong uphills.</string>
|
||||
<string name="app_restart_required">Application restart required to apply some settings.</string>
|
||||
<string name="on_pause">On pause</string>
|
||||
<string name="track_recording_description">Are you sure you want to stop recording?\nAll unsaved data will be lost.</string>
|
||||
<string name="track_recording_title">Track recording stopped</string>
|
||||
<string name="track_recording_save_and_stop">Save and stop recording</string>
|
||||
<string name="track_recording_stop_without_saving">Stop without saving</string>
|
||||
<string name="delete_number_files_question">Delete %1$d files?</string>
|
||||
<string name="shared_strings_all_regions">All regions</string>
|
||||
<string name="restart">Restart</string>
|
||||
<string name="elevation_data_descr">Routing could avoid strong uphills</string>
|
||||
<string name="map_orientation_threshold_descr">Don\'t rotate map view if speed is less than a threshold</string>
|
||||
<string name="snap_to_road_descr">Current location icon will be snapped to the current navigation route</string>
|
||||
<string name="routing_attr_driving_style_description">Select driving purpose to get shorter, faster or safer route</string>
|
||||
|
@ -39,6 +47,9 @@
|
|||
<string name="hillshade_slope_contour_lines">Hillshade / Slope / Contour lines</string>
|
||||
<string name="toast_select_edits_for_upload">Select edits for upload</string>
|
||||
<string name="uploaded_count">Uploaded %1$d of %2$d</string>
|
||||
<string name="segments_count">Segment %1$d</string>
|
||||
<string name="select_segments_description">%1$s contains more than one segment, you need to select the needed part for the navigation.</string>
|
||||
<string name="select_segments">Select segments</string>
|
||||
<string name="uploading_count">Uploading %1$d of %2$d</string>
|
||||
<string name="upload_photo_completed">Upload completed</string>
|
||||
<string name="upload_photo">Uploading</string>
|
||||
|
@ -1613,7 +1624,6 @@
|
|||
<string name="total_distance">Total distance</string>
|
||||
<string name="routing_attr_relief_smoothness_factor_name">Select elevation fluctuation</string>
|
||||
<string name="routing_attr_height_obstacles_name">Use elevation data</string>
|
||||
<string name="routing_attr_height_obstacles_description">Factor in terrain elevation (via SRTM, ASTER, and EU-DEM data).</string>
|
||||
<string name="rendering_attr_depthContours_description">Show depth contours and points.</string>
|
||||
<string name="rendering_attr_depthContours_name">Nautical depth contours</string>
|
||||
<!-- string name="release_2_6">
|
||||
|
|
|
@ -62,6 +62,8 @@ import net.osmand.plus.mapmarkers.MarkersPlanRouteContext;
|
|||
import net.osmand.plus.measurementtool.MeasurementToolFragment;
|
||||
import net.osmand.plus.measurementtool.StartPlanRouteBottomSheet;
|
||||
import net.osmand.plus.monitoring.OsmandMonitoringPlugin;
|
||||
import net.osmand.plus.monitoring.TripRecordingActiveBottomSheet;
|
||||
import net.osmand.plus.monitoring.TripRecordingBottomSheet;
|
||||
import net.osmand.plus.osmedit.dialogs.DismissRouteBottomSheetFragment;
|
||||
import net.osmand.plus.profiles.ProfileDataObject;
|
||||
import net.osmand.plus.profiles.ProfileDataUtils;
|
||||
|
@ -98,6 +100,7 @@ import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_CONFIGURE_P
|
|||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_CONFIGURE_SCREEN_ID;
|
||||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_DASHBOARD_ID;
|
||||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_DIRECTIONS_ID;
|
||||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_TRIP_RECORDING_ID;
|
||||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_DIVIDER_ID;
|
||||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_DOWNLOAD_MAPS_ID;
|
||||
import static net.osmand.aidlapi.OsmAndCustomizationConstants.DRAWER_HELP_ID;
|
||||
|
@ -356,10 +359,10 @@ public class MapActivityActions implements DialogProvider {
|
|||
}
|
||||
|
||||
public void addActionsToAdapter(final double latitude,
|
||||
final double longitude,
|
||||
final ContextMenuAdapter adapter,
|
||||
Object selectedObj,
|
||||
boolean configureMenu) {
|
||||
final double longitude,
|
||||
final ContextMenuAdapter adapter,
|
||||
Object selectedObj,
|
||||
boolean configureMenu) {
|
||||
ItemBuilder itemBuilder = new ItemBuilder();
|
||||
|
||||
adapter.addItem(itemBuilder
|
||||
|
@ -522,6 +525,7 @@ public class MapActivityActions implements DialogProvider {
|
|||
GPXRouteParamsBuilder params = new GPXRouteParamsBuilder(result, settings);
|
||||
params.setCalculateOsmAndRouteParts(settings.GPX_ROUTE_CALC_OSMAND_PARTS.get());
|
||||
params.setCalculateOsmAndRoute(settings.GPX_ROUTE_CALC.get());
|
||||
params.setSelectedSegment(settings.GPX_ROUTE_SEGMENT.get());
|
||||
List<Location> ps = params.getPoints(settings.getContext());
|
||||
mapActivity.getRoutingHelper().setGpxParams(params);
|
||||
settings.FOLLOW_THE_GPX_ROUTE.set(result.path);
|
||||
|
@ -539,17 +543,17 @@ public class MapActivityActions implements DialogProvider {
|
|||
}
|
||||
|
||||
public void enterRoutePlanningModeGivenGpx(GPXFile gpxFile, LatLon from, PointDescription fromName,
|
||||
boolean useIntermediatePointsByDefault, boolean showMenu) {
|
||||
boolean useIntermediatePointsByDefault, boolean showMenu) {
|
||||
enterRoutePlanningModeGivenGpx(gpxFile, from, fromName, useIntermediatePointsByDefault, showMenu, MapRouteInfoMenu.DEFAULT_MENU_STATE);
|
||||
}
|
||||
|
||||
public void enterRoutePlanningModeGivenGpx(GPXFile gpxFile, LatLon from, PointDescription fromName,
|
||||
boolean useIntermediatePointsByDefault, boolean showMenu, int menuState) {
|
||||
boolean useIntermediatePointsByDefault, boolean showMenu, int menuState) {
|
||||
enterRoutePlanningModeGivenGpx(gpxFile, null, from, fromName, useIntermediatePointsByDefault, showMenu, menuState);
|
||||
}
|
||||
|
||||
public void enterRoutePlanningModeGivenGpx(GPXFile gpxFile, ApplicationMode appMode, LatLon from, PointDescription fromName,
|
||||
boolean useIntermediatePointsByDefault, boolean showMenu, int menuState) {
|
||||
boolean useIntermediatePointsByDefault, boolean showMenu, int menuState) {
|
||||
settings.USE_INTERMEDIATE_POINTS_NAVIGATION.set(useIntermediatePointsByDefault);
|
||||
OsmandApplication app = mapActivity.getMyApplication();
|
||||
TargetPointsHelper targets = app.getTargetPointsHelper();
|
||||
|
@ -839,6 +843,26 @@ public class MapActivityActions implements DialogProvider {
|
|||
}
|
||||
}).createItem());
|
||||
|
||||
final OsmandMonitoringPlugin monitoringPlugin = OsmandPlugin.getEnabledPlugin(OsmandMonitoringPlugin.class);
|
||||
if (monitoringPlugin != null) {
|
||||
optionsMenuHelper.addItem(new ItemBuilder().setTitleId(R.string.map_widget_monitoring, mapActivity)
|
||||
.setId(DRAWER_TRIP_RECORDING_ID)
|
||||
.setIcon(R.drawable.ic_action_track_recordable)
|
||||
.setListener(new ItemClickListener() {
|
||||
@Override
|
||||
public boolean onContextMenuClick(ArrayAdapter<ContextMenuItem> adapter, int itemId, int pos, boolean isChecked, int[] viewCoordinates) {
|
||||
app.logEvent("trip_recording_open");
|
||||
MapActivity.clearPrevActivityIntent();
|
||||
if (monitoringPlugin.hasDataToSave() || monitoringPlugin.wasTrackMonitored()) {
|
||||
TripRecordingActiveBottomSheet.showInstance(mapActivity.getSupportFragmentManager(), monitoringPlugin.getCurrentTrack());
|
||||
} else {
|
||||
TripRecordingBottomSheet.showInstance(mapActivity.getSupportFragmentManager());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}).createItem());
|
||||
}
|
||||
|
||||
|
||||
optionsMenuHelper.addItem(new ItemBuilder().setTitleId(R.string.get_directions, mapActivity)
|
||||
.setId(DRAWER_DIRECTIONS_ID)
|
||||
|
@ -1087,7 +1111,7 @@ public class MapActivityActions implements DialogProvider {
|
|||
}
|
||||
|
||||
private String getProfileDescription(OsmandApplication app, ApplicationMode mode,
|
||||
Map<String, ProfileDataObject> profilesObjects, String defaultDescription) {
|
||||
Map<String, ProfileDataObject> profilesObjects, String defaultDescription) {
|
||||
String description = defaultDescription;
|
||||
|
||||
String routingProfileKey = mode.getRoutingProfile();
|
||||
|
|
|
@ -19,6 +19,7 @@ import net.osmand.plus.GpxSelectionHelper.SelectedGpxFile;
|
|||
import net.osmand.plus.OsmAndLocationProvider;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.OsmandPlugin;
|
||||
import net.osmand.plus.settings.backend.ApplicationMode;
|
||||
import net.osmand.plus.settings.backend.OsmandSettings;
|
||||
import net.osmand.plus.Version;
|
||||
import net.osmand.plus.monitoring.OsmandMonitoringPlugin;
|
||||
|
@ -78,6 +79,9 @@ public class SavingTrackHelper extends SQLiteOpenHelper {
|
|||
private SelectedGpxFile currentTrack;
|
||||
private int points;
|
||||
private int trkPoints = 0;
|
||||
private long lastTimeFileSaved;
|
||||
|
||||
private ApplicationMode lastRoutingApplicationMode;
|
||||
|
||||
public SavingTrackHelper(OsmandApplication ctx) {
|
||||
super(ctx, DATABASE_NAME, null, DATABASE_VERSION);
|
||||
|
@ -255,6 +259,7 @@ public class SavingTrackHelper extends SQLiteOpenHelper {
|
|||
GPXTrackAnalysis analysis = gpx.getAnalysis(fout.lastModified());
|
||||
GpxDataItem item = new GpxDataItem(fout, analysis);
|
||||
ctx.getGpxDbHelper().add(item);
|
||||
lastTimeFileSaved = fout.lastModified();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -440,12 +445,15 @@ public class SavingTrackHelper extends SQLiteOpenHelper {
|
|||
} else {
|
||||
heading = NO_HEADING;
|
||||
}
|
||||
if (ctx.getRoutingHelper().isFollowingMode()) {
|
||||
lastRoutingApplicationMode = settings.getApplicationMode();
|
||||
}
|
||||
boolean record = false;
|
||||
if (location != null && OsmAndLocationProvider.isNotSimulatedLocation(location)
|
||||
&& OsmandPlugin.getEnabledPlugin(OsmandMonitoringPlugin.class) != null) {
|
||||
if (settings.SAVE_TRACK_TO_GPX.get()
|
||||
&& locationTime - lastTimeUpdated > settings.SAVE_TRACK_INTERVAL.get()
|
||||
&& ctx.getRoutingHelper().isFollowingMode()) {
|
||||
&& lastRoutingApplicationMode == settings.getApplicationMode()) {
|
||||
record = true;
|
||||
} else if (settings.SAVE_GLOBAL_TRACK_TO_GPX.get()
|
||||
&& locationTime - lastTimeUpdated > settings.SAVE_GLOBAL_TRACK_INTERVAL.get()) {
|
||||
|
@ -705,9 +713,10 @@ public class SavingTrackHelper extends SQLiteOpenHelper {
|
|||
}
|
||||
|
||||
public boolean getIsRecording() {
|
||||
OsmandSettings settings = ctx.getSettings();
|
||||
return OsmandPlugin.getEnabledPlugin(OsmandMonitoringPlugin.class) != null
|
||||
&& ctx.getSettings().SAVE_GLOBAL_TRACK_TO_GPX.get()
|
||||
|| (ctx.getSettings().SAVE_TRACK_TO_GPX.get() && ctx.getRoutingHelper().isFollowingMode());
|
||||
&& settings.SAVE_GLOBAL_TRACK_TO_GPX.get() || settings.SAVE_TRACK_TO_GPX.get()
|
||||
&& lastRoutingApplicationMode == settings.getApplicationMode();
|
||||
}
|
||||
|
||||
public float getDistance() {
|
||||
|
@ -730,6 +739,14 @@ public class SavingTrackHelper extends SQLiteOpenHelper {
|
|||
return lastTimeUpdated;
|
||||
}
|
||||
|
||||
public long getLastTimeFileSaved() {
|
||||
return lastTimeFileSaved;
|
||||
}
|
||||
|
||||
public void setLastTimeFileSaved(long lastTimeFileSaved) {
|
||||
this.lastTimeFileSaved = lastTimeFileSaved;
|
||||
}
|
||||
|
||||
public GPXFile getCurrentGpx() {
|
||||
return currentTrack.getGpxFile();
|
||||
}
|
||||
|
|
|
@ -134,6 +134,9 @@ public class FailSafeFuntions {
|
|||
if(settings.GPX_ROUTE_CALC.get()) {
|
||||
gpxRoute.setCalculateOsmAndRoute(true);
|
||||
}
|
||||
if (settings.GPX_ROUTE_SEGMENT.get() != -1) {
|
||||
gpxRoute.setSelectedSegment(settings.GPX_ROUTE_SEGMENT.get());
|
||||
}
|
||||
} else {
|
||||
gpxRoute = null;
|
||||
}
|
||||
|
|
|
@ -380,7 +380,7 @@ public abstract class MenuBottomSheetDialogFragment extends BottomSheetDialogFra
|
|||
AndroidUiHelper.updateVisibility(dismissButton, buttonTextId != DEFAULT_VALUE);
|
||||
}
|
||||
|
||||
private void setupRightButton() {
|
||||
protected void setupRightButton() {
|
||||
rightButton = buttonsContainer.findViewById(R.id.right_bottom_button);
|
||||
rightButton.getLayoutParams().height = getRightButtonHeight();
|
||||
int buttonTextId = getRightBottomButtonTextId();
|
||||
|
|
|
@ -0,0 +1,301 @@
|
|||
package net.osmand.plus.base;
|
||||
|
||||
import android.content.res.ColorStateList;
|
||||
import android.os.Bundle;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.TextView;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.appcompat.app.AppCompatActivity;
|
||||
import androidx.core.content.ContextCompat;
|
||||
import androidx.core.widget.CompoundButtonCompat;
|
||||
import androidx.fragment.app.FragmentManager;
|
||||
|
||||
import net.osmand.AndroidUtils;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
import net.osmand.plus.UiUtilities;
|
||||
import net.osmand.plus.base.bottomsheetmenu.BaseBottomSheetItem;
|
||||
import net.osmand.plus.base.bottomsheetmenu.BottomSheetItemWithCompoundButton;
|
||||
import net.osmand.plus.base.bottomsheetmenu.BottomSheetItemWithCompoundButton.Builder;
|
||||
import net.osmand.plus.base.bottomsheetmenu.SimpleBottomSheetItem;
|
||||
import net.osmand.plus.base.bottomsheetmenu.simpleitems.SimpleDividerItem;
|
||||
import net.osmand.util.Algorithms;
|
||||
import net.osmand.view.ThreeStateCheckbox;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import static net.osmand.view.ThreeStateCheckbox.State.CHECKED;
|
||||
import static net.osmand.view.ThreeStateCheckbox.State.MISC;
|
||||
import static net.osmand.view.ThreeStateCheckbox.State.UNCHECKED;
|
||||
|
||||
public class SelectMultipleItemsBottomSheet extends MenuBottomSheetDialogFragment {
|
||||
|
||||
private OsmandApplication app;
|
||||
private UiUtilities uiUtilities;
|
||||
|
||||
private TextView title;
|
||||
private TextView description;
|
||||
private TextView applyButtonTitle;
|
||||
private TextView checkBoxTitle;
|
||||
private TextView selectedSize;
|
||||
private ThreeStateCheckbox checkBox;
|
||||
|
||||
private int activeColorRes;
|
||||
private int secondaryColorRes;
|
||||
|
||||
private final List<SelectableItem> allItems = new ArrayList<>();
|
||||
private final List<SelectableItem> selectedItems = new ArrayList<>();
|
||||
private SelectionUpdateListener selectionUpdateListener;
|
||||
private OnApplySelectionListener onApplySelectionListener;
|
||||
|
||||
public static final String TAG = SelectMultipleItemsBottomSheet.class.getSimpleName();
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup parent, Bundle savedInstanceState) {
|
||||
View mainView = super.onCreateView(inflater, parent, savedInstanceState);
|
||||
onSelectedItemsChanged();
|
||||
return mainView;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createMenuItems(Bundle savedInstanceState) {
|
||||
app = requiredMyApplication();
|
||||
uiUtilities = app.getUIUtilities();
|
||||
activeColorRes = nightMode ? R.color.icon_color_active_dark : R.color.icon_color_active_light;
|
||||
secondaryColorRes = nightMode ? R.color.icon_color_secondary_dark : R.color.icon_color_secondary_light;
|
||||
|
||||
items.add(createTitleItem());
|
||||
items.add(new SimpleDividerItem(app));
|
||||
createListItems();
|
||||
}
|
||||
|
||||
private BaseBottomSheetItem createTitleItem() {
|
||||
LayoutInflater themedInflater = UiUtilities.getInflater(requireContext(), nightMode);
|
||||
View view = themedInflater.inflate(R.layout.settings_group_title, null);
|
||||
|
||||
checkBox = view.findViewById(R.id.check_box);
|
||||
checkBoxTitle = view.findViewById(R.id.check_box_title);
|
||||
description = view.findViewById(R.id.description);
|
||||
selectedSize = view.findViewById(R.id.selected_size);
|
||||
title = view.findViewById(R.id.title);
|
||||
View selectAllButton = view.findViewById(R.id.select_all_button);
|
||||
selectAllButton.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
checkBox.performClick();
|
||||
boolean checked = checkBox.getState() == CHECKED;
|
||||
if (checked) {
|
||||
selectedItems.addAll(allItems);
|
||||
} else {
|
||||
selectedItems.clear();
|
||||
}
|
||||
onSelectedItemsChanged();
|
||||
updateItems(checked);
|
||||
}
|
||||
});
|
||||
return new SimpleBottomSheetItem.Builder().setCustomView(view).create();
|
||||
}
|
||||
|
||||
private void createListItems() {
|
||||
for (final SelectableItem item : allItems) {
|
||||
boolean checked = selectedItems.contains(item);
|
||||
final BottomSheetItemWithCompoundButton[] uiItem = new BottomSheetItemWithCompoundButton[1];
|
||||
final Builder builder = (BottomSheetItemWithCompoundButton.Builder) new Builder();
|
||||
builder.setChecked(checked)
|
||||
.setButtonTintList(AndroidUtils.createCheckedColorStateList(app, secondaryColorRes, activeColorRes))
|
||||
.setLayoutId(R.layout.bottom_sheet_item_with_descr_and_checkbox_56dp)
|
||||
.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
boolean checked = !uiItem[0].isChecked();
|
||||
uiItem[0].setChecked(checked);
|
||||
SelectableItem tag = (SelectableItem) uiItem[0].getTag();
|
||||
if (checked) {
|
||||
selectedItems.add(tag);
|
||||
} else {
|
||||
selectedItems.remove(tag);
|
||||
}
|
||||
onSelectedItemsChanged();
|
||||
}
|
||||
})
|
||||
.setTag(item);
|
||||
setupListItem(builder, item);
|
||||
uiItem[0] = builder.create();
|
||||
items.add(uiItem[0]);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void setupRightButton() {
|
||||
super.setupRightButton();
|
||||
applyButtonTitle = rightButton.findViewById(R.id.button_text);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onRightBottomButtonClick() {
|
||||
if (onApplySelectionListener != null) {
|
||||
onApplySelectionListener.onSelectionApplied(selectedItems);
|
||||
}
|
||||
dismiss();
|
||||
}
|
||||
|
||||
private void onSelectedItemsChanged() {
|
||||
updateSelectAllButton();
|
||||
updateSelectedSizeView();
|
||||
updateApplyButtonEnable();
|
||||
if (selectionUpdateListener != null) {
|
||||
selectionUpdateListener.onSelectionUpdate();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected int getRightBottomButtonTextId() {
|
||||
return R.string.shared_string_apply;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean useVerticalButtons() {
|
||||
return true;
|
||||
}
|
||||
|
||||
private void setupListItem(Builder builder, SelectableItem item) {
|
||||
builder.setTitle(item.title);
|
||||
builder.setDescription(item.description);
|
||||
builder.setIcon(uiUtilities.getIcon(item.iconId, activeColorRes));
|
||||
}
|
||||
|
||||
private void updateSelectAllButton() {
|
||||
String checkBoxTitle;
|
||||
if (Algorithms.isEmpty(selectedItems)) {
|
||||
checkBox.setState(UNCHECKED);
|
||||
checkBoxTitle = getString(R.string.shared_string_select_all);
|
||||
} else {
|
||||
checkBox.setState(selectedItems.containsAll(allItems) ? CHECKED : MISC);
|
||||
checkBoxTitle = getString(R.string.shared_string_deselect_all);
|
||||
}
|
||||
int checkBoxColor = checkBox.getState() == UNCHECKED ? secondaryColorRes : activeColorRes;
|
||||
CompoundButtonCompat.setButtonTintList(checkBox, ColorStateList.valueOf(ContextCompat.getColor(app, checkBoxColor)));
|
||||
this.checkBoxTitle.setText(checkBoxTitle);
|
||||
}
|
||||
|
||||
private void updateSelectedSizeView() {
|
||||
String selected = String.valueOf(selectedItems.size());
|
||||
String all = String.valueOf(allItems.size());
|
||||
selectedSize.setText(getString(R.string.ltr_or_rtl_combine_via_slash, selected, all));
|
||||
}
|
||||
|
||||
private void updateApplyButtonEnable() {
|
||||
if (Algorithms.isEmpty(selectedItems)) {
|
||||
rightButton.setEnabled(false);
|
||||
} else {
|
||||
rightButton.setEnabled(true);
|
||||
}
|
||||
}
|
||||
|
||||
private void updateItems(boolean checked) {
|
||||
for (BaseBottomSheetItem item : items) {
|
||||
if (item instanceof BottomSheetItemWithCompoundButton) {
|
||||
((BottomSheetItemWithCompoundButton) item).setChecked(checked);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setTitle(@NonNull String title) {
|
||||
this.title.setText(title);
|
||||
}
|
||||
|
||||
public void setDescription(@NonNull String description) {
|
||||
this.description.setText(description);
|
||||
}
|
||||
|
||||
public void setConfirmButtonTitle(@NonNull String confirmButtonTitle) {
|
||||
applyButtonTitle.setText(confirmButtonTitle);
|
||||
}
|
||||
|
||||
private void setItems(List<SelectableItem> allItems) {
|
||||
if (!Algorithms.isEmpty(allItems)) {
|
||||
this.allItems.addAll(allItems);
|
||||
}
|
||||
}
|
||||
|
||||
private void setSelectedItems(List<SelectableItem> selected) {
|
||||
if (!Algorithms.isEmpty(selected)) {
|
||||
this.selectedItems.addAll(selected);
|
||||
}
|
||||
}
|
||||
|
||||
public List<SelectableItem> getSelectedItems() {
|
||||
return selectedItems;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPause() {
|
||||
super.onPause();
|
||||
if (requireActivity().isChangingConfigurations()) {
|
||||
dismiss();
|
||||
}
|
||||
}
|
||||
|
||||
public static SelectMultipleItemsBottomSheet showInstance(@NonNull AppCompatActivity activity,
|
||||
@NonNull List<SelectableItem> items,
|
||||
@Nullable List<SelectableItem> selected,
|
||||
boolean usedOnMap) {
|
||||
SelectMultipleItemsBottomSheet fragment = new SelectMultipleItemsBottomSheet();
|
||||
fragment.setUsedOnMap(usedOnMap);
|
||||
fragment.setItems(items);
|
||||
fragment.setSelectedItems(selected);
|
||||
FragmentManager fm = activity.getSupportFragmentManager();
|
||||
fragment.show(fm, TAG);
|
||||
return fragment;
|
||||
}
|
||||
|
||||
public void setSelectionUpdateListener(SelectionUpdateListener selectionUpdateListener) {
|
||||
this.selectionUpdateListener = selectionUpdateListener;
|
||||
}
|
||||
|
||||
public void setOnApplySelectionListener(OnApplySelectionListener onApplySelectionListener) {
|
||||
this.onApplySelectionListener = onApplySelectionListener;
|
||||
}
|
||||
|
||||
public interface SelectionUpdateListener {
|
||||
void onSelectionUpdate();
|
||||
}
|
||||
|
||||
public interface OnApplySelectionListener {
|
||||
void onSelectionApplied(List<SelectableItem> selectedItems);
|
||||
}
|
||||
|
||||
public static class SelectableItem {
|
||||
private String title;
|
||||
private String description;
|
||||
private int iconId;
|
||||
private Object object;
|
||||
|
||||
public void setTitle(String title) {
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
public void setIconId(int iconId) {
|
||||
this.iconId = iconId;
|
||||
}
|
||||
|
||||
public void setObject(Object object) {
|
||||
this.object = object;
|
||||
}
|
||||
|
||||
public Object getObject() {
|
||||
return object;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -17,7 +17,7 @@ public class AbstractDownloadActivity extends ActionBarProgressActivity {
|
|||
downloadValidationManager.startDownload(this, indexItem);
|
||||
}
|
||||
|
||||
public void makeSureUserCancelDownload(IndexItem item) {
|
||||
public void makeSureUserCancelDownload(DownloadItem item) {
|
||||
downloadValidationManager.makeSureUserCancelDownload(this, item);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -56,7 +56,8 @@ public class CustomIndexItem extends IndexItem {
|
|||
}
|
||||
|
||||
@Override
|
||||
public File getTargetFile(OsmandApplication ctx) {
|
||||
@NonNull
|
||||
public File getTargetFile(@NonNull OsmandApplication ctx) {
|
||||
String basename = getTranslatedBasename();
|
||||
if (!Algorithms.isEmpty(subfolder)) {
|
||||
basename = subfolder + "/" + basename;
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
package net.osmand.plus.download;
|
||||
|
||||
import android.Manifest;
|
||||
import android.annotation.SuppressLint;
|
||||
import android.content.Context;
|
||||
import android.content.DialogInterface;
|
||||
import android.content.Intent;
|
||||
|
|
|
@ -2,6 +2,8 @@ package net.osmand.plus.download;
|
|||
|
||||
import android.content.Context;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import net.osmand.AndroidUtils;
|
||||
import net.osmand.IndexConstants;
|
||||
import net.osmand.map.OsmandRegions;
|
||||
|
@ -18,6 +20,7 @@ import java.io.IOException;
|
|||
import java.net.URLEncoder;
|
||||
import java.text.ParseException;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.Collection;
|
||||
import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.Locale;
|
||||
|
@ -114,6 +117,10 @@ public class DownloadActivityType {
|
|||
return byTag.get(tagName);
|
||||
}
|
||||
|
||||
public static Collection<DownloadActivityType> values() {
|
||||
return byTag.values();
|
||||
}
|
||||
|
||||
protected static String addVersionToExt(String ext, int version) {
|
||||
return "_" + version + ext;
|
||||
}
|
||||
|
@ -318,7 +325,7 @@ public class DownloadActivityType {
|
|||
}
|
||||
}
|
||||
|
||||
public String getVisibleDescription(IndexItem indexItem, Context ctx) {
|
||||
public String getVisibleDescription(DownloadItem downloadItem, Context ctx) {
|
||||
if (this == SRTM_COUNTRY_FILE) {
|
||||
return ctx.getString(R.string.download_srtm_maps);
|
||||
} else if (this == WIKIPEDIA_FILE) {
|
||||
|
@ -337,20 +344,20 @@ public class DownloadActivityType {
|
|||
return "";
|
||||
}
|
||||
|
||||
public String getVisibleName(IndexItem indexItem, Context ctx, OsmandRegions osmandRegions, boolean includingParent) {
|
||||
public String getVisibleName(DownloadItem downloadItem, Context ctx, OsmandRegions osmandRegions, boolean includingParent) {
|
||||
if (this == VOICE_FILE) {
|
||||
String fileName = indexItem.fileName;
|
||||
String fileName = downloadItem.getFileName();
|
||||
if (fileName.endsWith(IndexConstants.VOICE_INDEX_EXT_ZIP)) {
|
||||
return FileNameTranslationHelper.getVoiceName(ctx, getBasename(indexItem));
|
||||
return FileNameTranslationHelper.getVoiceName(ctx, getBasename(downloadItem));
|
||||
} else if (fileName.endsWith(IndexConstants.TTSVOICE_INDEX_EXT_JS)) {
|
||||
return FileNameTranslationHelper.getVoiceName(ctx, getBasename(indexItem));
|
||||
return FileNameTranslationHelper.getVoiceName(ctx, getBasename(downloadItem));
|
||||
}
|
||||
return getBasename(indexItem);
|
||||
return getBasename(downloadItem);
|
||||
}
|
||||
if (this == FONT_FILE) {
|
||||
return FileNameTranslationHelper.getFontName(ctx, getBasename(indexItem));
|
||||
return FileNameTranslationHelper.getFontName(ctx, getBasename(downloadItem));
|
||||
}
|
||||
final String basename = getBasename(indexItem);
|
||||
final String basename = getBasename(downloadItem);
|
||||
if (basename.endsWith(FileNameTranslationHelper.WIKI_NAME)) {
|
||||
return FileNameTranslationHelper.getWikiName(ctx, basename);
|
||||
}
|
||||
|
@ -441,9 +448,11 @@ public class DownloadActivityType {
|
|||
return fileName;
|
||||
}
|
||||
|
||||
@NonNull
|
||||
public String getBasename(@NonNull DownloadItem downloadItem) {
|
||||
String fileName = downloadItem.getFileName();
|
||||
if (Algorithms.isEmpty(fileName)) return fileName;
|
||||
|
||||
public String getBasename(IndexItem indexItem) {
|
||||
String fileName = indexItem.fileName;
|
||||
if (fileName.endsWith(IndexConstants.EXTRA_ZIP_EXT)) {
|
||||
return fileName.substring(0, fileName.length() - IndexConstants.EXTRA_ZIP_EXT.length());
|
||||
}
|
||||
|
@ -458,7 +467,7 @@ public class DownloadActivityType {
|
|||
if (fileName.endsWith(IndexConstants.SQLITE_EXT)) {
|
||||
return fileName.substring(0, fileName.length() - IndexConstants.SQLITE_EXT.length());
|
||||
}
|
||||
if (indexItem.getType() == WIKIVOYAGE_FILE &&
|
||||
if (downloadItem.getType() == WIKIVOYAGE_FILE &&
|
||||
fileName.endsWith(IndexConstants.BINARY_WIKIVOYAGE_MAP_INDEX_EXT)) {
|
||||
return fileName.substring(0, fileName.length() - IndexConstants.BINARY_WIKIVOYAGE_MAP_INDEX_EXT.length());
|
||||
}
|
||||
|
|
|
@ -239,6 +239,16 @@ public class DownloadIndexesThread {
|
|||
}
|
||||
}
|
||||
|
||||
public void cancelDownload(DownloadItem item) {
|
||||
if (item instanceof MultipleIndexItem) {
|
||||
MultipleIndexItem multipleIndexItem = (MultipleIndexItem) item;
|
||||
cancelDownload(multipleIndexItem.getAllIndexes());
|
||||
} else if (item instanceof IndexItem) {
|
||||
IndexItem indexItem = (IndexItem) item;
|
||||
cancelDownload(indexItem);
|
||||
}
|
||||
}
|
||||
|
||||
public void cancelDownload(IndexItem item) {
|
||||
app.logMapDownloadEvent("cancel", item);
|
||||
if (currentDownloadingItem == item) {
|
||||
|
|
81
OsmAnd/src/net/osmand/plus/download/DownloadItem.java
Normal file
81
OsmAnd/src/net/osmand/plus/download/DownloadItem.java
Normal file
|
@ -0,0 +1,81 @@
|
|||
package net.osmand.plus.download;
|
||||
|
||||
import android.content.Context;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import net.osmand.map.OsmandRegions;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
|
||||
public abstract class DownloadItem {
|
||||
|
||||
protected DownloadActivityType type;
|
||||
protected DownloadResourceGroup relatedGroup;
|
||||
|
||||
public DownloadItem(DownloadActivityType type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
public DownloadActivityType getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public void setRelatedGroup(DownloadResourceGroup relatedGroup) {
|
||||
this.relatedGroup = relatedGroup;
|
||||
}
|
||||
|
||||
public DownloadResourceGroup getRelatedGroup() {
|
||||
return relatedGroup;
|
||||
}
|
||||
|
||||
@NonNull
|
||||
public String getSizeDescription(Context ctx) {
|
||||
return getFormattedMb(ctx, getSizeToDownloadInMb());
|
||||
}
|
||||
|
||||
public String getVisibleName(Context ctx, OsmandRegions osmandRegions) {
|
||||
return type.getVisibleName(this, ctx, osmandRegions, true);
|
||||
}
|
||||
|
||||
public String getVisibleName(Context ctx, OsmandRegions osmandRegions, boolean includingParent) {
|
||||
return type.getVisibleName(this, ctx, osmandRegions, includingParent);
|
||||
}
|
||||
|
||||
public String getVisibleDescription(OsmandApplication ctx) {
|
||||
return type.getVisibleDescription(this, ctx);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
public String getBasename() {
|
||||
return type.getBasename(this);
|
||||
}
|
||||
|
||||
protected abstract double getSizeToDownloadInMb();
|
||||
|
||||
public abstract double getArchiveSizeMB();
|
||||
|
||||
public abstract boolean isDownloaded();
|
||||
|
||||
public abstract boolean isOutdated();
|
||||
|
||||
public abstract boolean hasActualDataToDownload();
|
||||
|
||||
public abstract boolean isDownloading(@NonNull DownloadIndexesThread thread);
|
||||
|
||||
public abstract String getFileName();
|
||||
|
||||
@NonNull
|
||||
public abstract List<File> getDownloadedFiles(@NonNull OsmandApplication app);
|
||||
|
||||
@NonNull
|
||||
public static String getFormattedMb(@NonNull Context ctx, double sizeInMb) {
|
||||
String size = String.format(Locale.US, "%.2f", sizeInMb);
|
||||
return ctx.getString(R.string.ltr_or_rtl_combine_via_space, size, "MB");
|
||||
}
|
||||
|
||||
}
|
|
@ -8,6 +8,7 @@ import net.osmand.map.OsmandRegions;
|
|||
import net.osmand.map.WorldRegion;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
import net.osmand.util.Algorithms;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
|
@ -20,8 +21,8 @@ public class DownloadResourceGroup {
|
|||
|
||||
private final DownloadResourceGroupType type;
|
||||
private final DownloadResourceGroup parentGroup;
|
||||
// ASSERT: individualResources are not empty if and only if groups are empty
|
||||
private final List<IndexItem> individualResources;
|
||||
// ASSERT: individualDownloadItems are not empty if and only if groups are empty
|
||||
private final List<DownloadItem> individualDownloadItems;
|
||||
private final List<DownloadResourceGroup> groups;
|
||||
protected final String id;
|
||||
|
||||
|
@ -107,10 +108,10 @@ public class DownloadResourceGroup {
|
|||
public DownloadResourceGroup(DownloadResourceGroup parentGroup, DownloadResourceGroupType type, String id) {
|
||||
boolean flat = type.containsIndexItem();
|
||||
if (flat) {
|
||||
this.individualResources = new ArrayList<IndexItem>();
|
||||
this.individualDownloadItems = new ArrayList<DownloadItem>();
|
||||
this.groups = null;
|
||||
} else {
|
||||
this.individualResources = null;
|
||||
this.individualDownloadItems = null;
|
||||
this.groups = new ArrayList<DownloadResourceGroup>();
|
||||
}
|
||||
this.id = id;
|
||||
|
@ -173,7 +174,7 @@ public class DownloadResourceGroup {
|
|||
DownloadResourceGroup regionMaps = getSubGroupById(DownloadResourceGroupType.REGION_MAPS.getDefaultId());
|
||||
if(regionMaps != null && regionMaps.size() == 1 && parentGroup != null && parentGroup.getParentGroup() != null &&
|
||||
isEmpty(getSubGroupById(DownloadResourceGroupType.SUBREGIONS.getDefaultId()))) {
|
||||
IndexItem item = regionMaps.individualResources.get(0);
|
||||
IndexItem item = regionMaps.getIndividualResources().get(0);
|
||||
DownloadResourceGroup screenParent = parentGroup.getParentGroup();
|
||||
if(item.getType() == DownloadActivityType.HILLSHADE_FILE) {
|
||||
DownloadResourceGroup hillshades =
|
||||
|
@ -183,7 +184,7 @@ public class DownloadResourceGroup {
|
|||
screenParent.addGroup(hillshades);
|
||||
}
|
||||
hillshades.addItem(item);
|
||||
regionMaps.individualResources.remove(0);
|
||||
regionMaps.individualDownloadItems.remove(0);
|
||||
} else if (item.getType() == DownloadActivityType.SRTM_COUNTRY_FILE) {
|
||||
DownloadResourceGroup hillshades = screenParent
|
||||
.getSubGroupById(DownloadResourceGroupType.SRTM_HEADER.getDefaultId());
|
||||
|
@ -192,7 +193,7 @@ public class DownloadResourceGroup {
|
|||
screenParent.addGroup(hillshades);
|
||||
}
|
||||
hillshades.addItem(item);
|
||||
regionMaps.individualResources.remove(0);
|
||||
regionMaps.individualDownloadItems.remove(0);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -221,35 +222,38 @@ public class DownloadResourceGroup {
|
|||
}
|
||||
}
|
||||
groups.add(g);
|
||||
if (g.individualResources != null) {
|
||||
final net.osmand.Collator collator = OsmAndCollator.primaryCollator();
|
||||
final OsmandApplication app = getRoot().app;
|
||||
final OsmandRegions osmandRegions = app.getRegions();
|
||||
Collections.sort(g.individualResources, new Comparator<IndexItem>() {
|
||||
@Override
|
||||
public int compare(IndexItem lhs, IndexItem rhs) {
|
||||
int lli = lhs.getType().getOrderIndex();
|
||||
int rri = rhs.getType().getOrderIndex();
|
||||
if(lli < rri) {
|
||||
return -1;
|
||||
} else if(lli > rri) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
return collator.compare(lhs.getVisibleName(app.getApplicationContext(), osmandRegions),
|
||||
rhs.getVisibleName(app.getApplicationContext(), osmandRegions));
|
||||
}
|
||||
});
|
||||
}
|
||||
sortDownloadItems(g.individualDownloadItems);
|
||||
}
|
||||
|
||||
public void addItem(IndexItem i) {
|
||||
protected void sortDownloadItems(List<DownloadItem> items) {
|
||||
if (Algorithms.isEmpty(items)) return;
|
||||
final net.osmand.Collator collator = OsmAndCollator.primaryCollator();
|
||||
final OsmandApplication app = getRoot().app;
|
||||
final OsmandRegions osmandRegions = app.getRegions();
|
||||
Collections.sort(items, new Comparator<DownloadItem>() {
|
||||
@Override
|
||||
public int compare(DownloadItem firstItem, DownloadItem secondItem) {
|
||||
int firstOrder = firstItem.getType().getOrderIndex();
|
||||
int secondOrder = secondItem.getType().getOrderIndex();
|
||||
if(firstOrder < secondOrder) {
|
||||
return -1;
|
||||
} else if(firstOrder > secondOrder) {
|
||||
return 1;
|
||||
}
|
||||
String firstName = firstItem.getVisibleName(app, osmandRegions);
|
||||
String secondName = secondItem.getVisibleName(app, osmandRegions);
|
||||
return collator.compare(firstName, secondName);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void addItem(DownloadItem i) {
|
||||
i.setRelatedGroup(this);
|
||||
individualResources.add(i);
|
||||
individualDownloadItems.add(i);
|
||||
}
|
||||
|
||||
public boolean isEmpty() {
|
||||
return isEmpty(individualResources) && isEmpty(groups);
|
||||
return isEmpty(individualDownloadItems) && isEmpty(groups);
|
||||
}
|
||||
|
||||
private boolean isEmpty(List<?> l) {
|
||||
|
@ -265,7 +269,7 @@ public class DownloadResourceGroup {
|
|||
}
|
||||
|
||||
public int size() {
|
||||
return groups != null ? groups.size() : individualResources.size();
|
||||
return groups != null ? groups.size() : individualDownloadItems.size();
|
||||
}
|
||||
|
||||
public DownloadResourceGroup getGroupByIndex(int ind) {
|
||||
|
@ -275,9 +279,9 @@ public class DownloadResourceGroup {
|
|||
return null;
|
||||
}
|
||||
|
||||
public IndexItem getItemByIndex(int ind) {
|
||||
if (individualResources != null && ind >= 0 && ind < individualResources.size()) {
|
||||
return individualResources.get(ind);
|
||||
public DownloadItem getItemByIndex(int ind) {
|
||||
if (individualDownloadItems != null && ind >= 0 && ind < individualDownloadItems.size()) {
|
||||
return individualDownloadItems.get(ind);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -306,9 +310,21 @@ public class DownloadResourceGroup {
|
|||
}
|
||||
|
||||
public List<IndexItem> getIndividualResources() {
|
||||
List<IndexItem> individualResources = new ArrayList<>();
|
||||
if (individualDownloadItems != null) {
|
||||
for (DownloadItem item : individualDownloadItems) {
|
||||
if (item instanceof IndexItem) {
|
||||
individualResources.add((IndexItem) item);
|
||||
}
|
||||
}
|
||||
}
|
||||
return individualResources;
|
||||
}
|
||||
|
||||
public List<DownloadItem> getIndividualDownloadItems() {
|
||||
return individualDownloadItems;
|
||||
}
|
||||
|
||||
public WorldRegion getRegion() {
|
||||
return region;
|
||||
}
|
||||
|
|
|
@ -25,10 +25,14 @@ import java.io.InputStream;
|
|||
import java.text.DateFormat;
|
||||
import java.text.ParseException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashSet;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import static net.osmand.plus.download.DownloadResourceGroup.DownloadResourceGroupType.REGION_MAPS;
|
||||
|
||||
public class DownloadResources extends DownloadResourceGroup {
|
||||
private static final String TAG = DownloadResources.class.getSimpleName();
|
||||
|
@ -40,7 +44,7 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
private Map<String, String> indexFileNames = new LinkedHashMap<>();
|
||||
private Map<String, String> indexActivatedFileNames = new LinkedHashMap<>();
|
||||
private List<IndexItem> rawResources;
|
||||
private Map<WorldRegion, List<IndexItem> > groupByRegion;
|
||||
private Map<WorldRegion, List<IndexItem>> groupByRegion;
|
||||
private List<IndexItem> itemsToUpdate = new ArrayList<>();
|
||||
public static final String WORLD_SEAMARKS_KEY = "world_seamarks";
|
||||
public static final String WORLD_SEAMARKS_NAME = "World_seamarks";
|
||||
|
@ -260,7 +264,7 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
}
|
||||
|
||||
private Map<String, String> listWithAlternatives(final java.text.DateFormat dateFormat, File file,
|
||||
final String ext, final Map<String, String> files) {
|
||||
final String ext, final Map<String, String> files) {
|
||||
if (file.isDirectory()) {
|
||||
file.list(new FilenameFilter() {
|
||||
@Override
|
||||
|
@ -337,13 +341,13 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
DownloadResourceGroup wikivoyageMapsScreen = new DownloadResourceGroup(wikivoyageMapsGroup, DownloadResourceGroupType.WIKIVOYAGE_MAPS);
|
||||
DownloadResourceGroup wikivoyageMaps = new DownloadResourceGroup(wikivoyageMapsGroup, DownloadResourceGroupType.WIKIVOYAGE_HEADER);
|
||||
|
||||
Map<WorldRegion, List<IndexItem> > groupByRegion = new LinkedHashMap<WorldRegion, List<IndexItem>>();
|
||||
Map<WorldRegion, List<IndexItem>> groupByRegion = new LinkedHashMap<>();
|
||||
OsmandRegions regs = app.getRegions();
|
||||
for (IndexItem ii : resources) {
|
||||
if (ii.getType() == DownloadActivityType.VOICE_FILE) {
|
||||
if (ii.getFileName().endsWith(IndexConstants.TTSVOICE_INDEX_EXT_JS)){
|
||||
if (ii.getFileName().endsWith(IndexConstants.TTSVOICE_INDEX_EXT_JS)) {
|
||||
voiceTTS.addItem(ii);
|
||||
} else if (ii.getFileName().endsWith(IndexConstants.VOICE_INDEX_EXT_ZIP)){
|
||||
} else if (ii.getFileName().endsWith(IndexConstants.VOICE_INDEX_EXT_ZIP)) {
|
||||
voiceRec.addItem(ii);
|
||||
}
|
||||
continue;
|
||||
|
@ -402,11 +406,11 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
LinkedList<DownloadResourceGroup> parent = new LinkedList<DownloadResourceGroup>();
|
||||
DownloadResourceGroup worldSubregions = new DownloadResourceGroup(this, DownloadResourceGroupType.SUBREGIONS);
|
||||
addGroup(worldSubregions);
|
||||
for(WorldRegion rg : region.getSubregions()) {
|
||||
for (WorldRegion rg : region.getSubregions()) {
|
||||
queue.add(rg);
|
||||
parent.add(worldSubregions);
|
||||
}
|
||||
while(!queue.isEmpty()) {
|
||||
while (!queue.isEmpty()) {
|
||||
WorldRegion reg = queue.pollFirst();
|
||||
DownloadResourceGroup parentGroup = parent.pollFirst();
|
||||
List<WorldRegion> subregions = reg.getSubregions();
|
||||
|
@ -414,18 +418,20 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
mainGrp.region = reg;
|
||||
parentGroup.addGroup(mainGrp);
|
||||
|
||||
DownloadResourceGroup flatFiles = new DownloadResourceGroup(mainGrp, REGION_MAPS);
|
||||
List<IndexItem> list = groupByRegion.get(reg);
|
||||
if(list != null) {
|
||||
DownloadResourceGroup flatFiles = new DownloadResourceGroup(mainGrp, DownloadResourceGroupType.REGION_MAPS);
|
||||
for(IndexItem ii : list) {
|
||||
if (list != null) {
|
||||
for (IndexItem ii : list) {
|
||||
flatFiles.addItem(ii);
|
||||
}
|
||||
}
|
||||
if (list != null || !reg.isContinent()) {
|
||||
mainGrp.addGroup(flatFiles);
|
||||
}
|
||||
DownloadResourceGroup subRegions = new DownloadResourceGroup(mainGrp, DownloadResourceGroupType.SUBREGIONS);
|
||||
mainGrp.addGroup(subRegions);
|
||||
// add to processing queue
|
||||
for(WorldRegion rg : subregions) {
|
||||
for (WorldRegion rg : subregions) {
|
||||
queue.add(rg);
|
||||
parent.add(subRegions);
|
||||
}
|
||||
|
@ -463,11 +469,91 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
addGroup(otherGroup);
|
||||
|
||||
createHillshadeSRTMGroups();
|
||||
collectMultipleIndexesItems();
|
||||
trimEmptyGroups();
|
||||
updateLoadedFiles();
|
||||
return true;
|
||||
}
|
||||
|
||||
private void collectMultipleIndexesItems() {
|
||||
collectMultipleIndexesItems(region);
|
||||
}
|
||||
|
||||
private void collectMultipleIndexesItems(@NonNull WorldRegion region) {
|
||||
List<WorldRegion> subRegions = region.getSubregions();
|
||||
if (Algorithms.isEmpty(subRegions)) return;
|
||||
|
||||
DownloadResourceGroup group = getRegionMapsGroup(region);
|
||||
if (group != null) {
|
||||
boolean listModified = false;
|
||||
List<IndexItem> indexesList = group.getIndividualResources();
|
||||
List<WorldRegion> regionsToCollect = removeDuplicateRegions(subRegions);
|
||||
for (DownloadActivityType type : DownloadActivityType.values()) {
|
||||
if (!doesListContainIndexWithType(indexesList, type)) {
|
||||
List<IndexItem> indexesFromSubRegions = collectIndexesOfType(regionsToCollect, type);
|
||||
if (indexesFromSubRegions != null) {
|
||||
group.addItem(new MultipleIndexItem(region, indexesFromSubRegions, type));
|
||||
listModified = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (listModified) {
|
||||
sortDownloadItems(group.getIndividualDownloadItems());
|
||||
}
|
||||
}
|
||||
for (WorldRegion subRegion : subRegions) {
|
||||
collectMultipleIndexesItems(subRegion);
|
||||
}
|
||||
}
|
||||
|
||||
private DownloadResourceGroup getRegionMapsGroup(WorldRegion region) {
|
||||
DownloadResourceGroup group = getRegionGroup(region);
|
||||
if (group != null) {
|
||||
return group.getSubGroupById(REGION_MAPS.getDefaultId());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private List<IndexItem> collectIndexesOfType(@NonNull List<WorldRegion> regions,
|
||||
@NonNull DownloadActivityType type) {
|
||||
List<IndexItem> collectedIndexes = new ArrayList<>();
|
||||
for (WorldRegion region : regions) {
|
||||
List<IndexItem> regionIndexes = getIndexItems(region);
|
||||
boolean found = false;
|
||||
if (regionIndexes != null) {
|
||||
for (IndexItem index : regionIndexes) {
|
||||
if (index.getType() == type) {
|
||||
found = true;
|
||||
collectedIndexes.add(index);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!found) return null;
|
||||
}
|
||||
return collectedIndexes;
|
||||
}
|
||||
|
||||
private List<WorldRegion> removeDuplicateRegions(List<WorldRegion> regions) {
|
||||
Set<WorldRegion> duplicates = new HashSet<>();
|
||||
for (int i = 0; i < regions.size() - 1; i++) {
|
||||
WorldRegion r1 = regions.get(i);
|
||||
for (int j = i + 1; j < regions.size(); j++) {
|
||||
WorldRegion r2 = regions.get(j);
|
||||
if (r1.containsRegion(r2)) {
|
||||
duplicates.add(r2);
|
||||
} else if (r2.containsRegion(r1)) {
|
||||
duplicates.add(r1);
|
||||
}
|
||||
}
|
||||
}
|
||||
for (WorldRegion region : duplicates) {
|
||||
regions.remove(region);
|
||||
}
|
||||
return regions;
|
||||
}
|
||||
|
||||
private void buildRegionsGroups(WorldRegion region, DownloadResourceGroup group) {
|
||||
LinkedList<WorldRegion> queue = new LinkedList<WorldRegion>();
|
||||
LinkedList<DownloadResourceGroup> parent = new LinkedList<DownloadResourceGroup>();
|
||||
|
@ -485,7 +571,7 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
CustomRegion customRegion = (CustomRegion) reg;
|
||||
List<IndexItem> indexItems = customRegion.loadIndexItems();
|
||||
if (!Algorithms.isEmpty(indexItems)) {
|
||||
DownloadResourceGroup flatFiles = new DownloadResourceGroup(mainGrp, DownloadResourceGroupType.REGION_MAPS);
|
||||
DownloadResourceGroup flatFiles = new DownloadResourceGroup(mainGrp, REGION_MAPS);
|
||||
for (IndexItem ii : indexItems) {
|
||||
flatFiles.addItem(ii);
|
||||
}
|
||||
|
@ -557,7 +643,11 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
return res;
|
||||
}
|
||||
|
||||
public static List<IndexItem> findIndexItemsAt(OsmandApplication app, List<String> names, DownloadActivityType type, boolean includeDownloaded, int limit) {
|
||||
public static List<IndexItem> findIndexItemsAt(OsmandApplication app,
|
||||
List<String> names,
|
||||
DownloadActivityType type,
|
||||
boolean includeDownloaded,
|
||||
int limit) {
|
||||
List<IndexItem> res = new ArrayList<>();
|
||||
OsmandRegions regions = app.getRegions();
|
||||
DownloadIndexesThread downloadThread = app.getDownloadThread();
|
||||
|
@ -573,8 +663,12 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
return res;
|
||||
}
|
||||
|
||||
private static boolean isIndexItemDownloaded(DownloadIndexesThread downloadThread, DownloadActivityType type, WorldRegion downloadRegion, List<IndexItem> res) {
|
||||
List<IndexItem> otherIndexItems = new ArrayList<>(downloadThread.getIndexes().getIndexItems(downloadRegion));
|
||||
private static boolean isIndexItemDownloaded(DownloadIndexesThread downloadThread,
|
||||
DownloadActivityType type,
|
||||
WorldRegion downloadRegion,
|
||||
List<IndexItem> res) {
|
||||
List<IndexItem> otherIndexItems =
|
||||
new ArrayList<>(downloadThread.getIndexes().getIndexItems(downloadRegion));
|
||||
for (IndexItem indexItem : otherIndexItems) {
|
||||
if (indexItem.getType() == type && indexItem.isDownloaded()) {
|
||||
return true;
|
||||
|
@ -584,8 +678,24 @@ public class DownloadResources extends DownloadResourceGroup {
|
|||
&& isIndexItemDownloaded(downloadThread, type, downloadRegion.getSuperregion(), res);
|
||||
}
|
||||
|
||||
private static boolean addIndexItem(DownloadIndexesThread downloadThread, DownloadActivityType type, WorldRegion downloadRegion, List<IndexItem> res) {
|
||||
List<IndexItem> otherIndexItems = new ArrayList<>(downloadThread.getIndexes().getIndexItems(downloadRegion));
|
||||
private boolean doesListContainIndexWithType(List<IndexItem> indexItems,
|
||||
DownloadActivityType type) {
|
||||
if (indexItems != null) {
|
||||
for (IndexItem indexItem : indexItems) {
|
||||
if (indexItem.getType() == type) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private static boolean addIndexItem(DownloadIndexesThread downloadThread,
|
||||
DownloadActivityType type,
|
||||
WorldRegion downloadRegion,
|
||||
List<IndexItem> res) {
|
||||
List<IndexItem> otherIndexItems =
|
||||
new ArrayList<>(downloadThread.getIndexes().getIndexItems(downloadRegion));
|
||||
for (IndexItem indexItem : otherIndexItems) {
|
||||
if (indexItem.getType() == type
|
||||
&& !res.contains(indexItem)) {
|
||||
|
|
|
@ -192,7 +192,7 @@ public class DownloadValidationManager {
|
|||
}
|
||||
|
||||
|
||||
public void makeSureUserCancelDownload(FragmentActivity ctx, final IndexItem item) {
|
||||
public void makeSureUserCancelDownload(FragmentActivity ctx, final DownloadItem item) {
|
||||
AlertDialog.Builder bld = new AlertDialog.Builder(ctx);
|
||||
bld.setTitle(ctx.getString(R.string.shared_string_cancel));
|
||||
bld.setMessage(R.string.confirm_interrupt_download);
|
||||
|
|
|
@ -1,24 +1,24 @@
|
|||
package net.osmand.plus.download;
|
||||
|
||||
import android.content.Context;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import net.osmand.IndexConstants;
|
||||
import net.osmand.PlatformUtil;
|
||||
import net.osmand.map.OsmandRegions;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
import net.osmand.plus.helpers.FileNameTranslationHelper;
|
||||
import net.osmand.util.Algorithms;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.text.DateFormat;
|
||||
import java.util.Collections;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
public class IndexItem implements Comparable<IndexItem> {
|
||||
public class IndexItem extends DownloadItem implements Comparable<IndexItem> {
|
||||
private static final Log log = PlatformUtil.getLog(IndexItem.class);
|
||||
|
||||
String description;
|
||||
|
@ -27,43 +27,43 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
long timestamp;
|
||||
long contentSize;
|
||||
long containerSize;
|
||||
DownloadActivityType type;
|
||||
boolean extra;
|
||||
|
||||
// Update information
|
||||
boolean outdated;
|
||||
boolean downloaded;
|
||||
long localTimestamp;
|
||||
DownloadResourceGroup relatedGroup;
|
||||
|
||||
|
||||
public IndexItem(String fileName, String description, long timestamp, String size, long contentSize,
|
||||
long containerSize, @NonNull DownloadActivityType tp) {
|
||||
public IndexItem(String fileName,
|
||||
String description,
|
||||
long timestamp,
|
||||
String size,
|
||||
long contentSize,
|
||||
long containerSize,
|
||||
@NonNull DownloadActivityType type) {
|
||||
super(type);
|
||||
this.fileName = fileName;
|
||||
this.description = description;
|
||||
this.timestamp = timestamp;
|
||||
this.size = size;
|
||||
this.contentSize = contentSize;
|
||||
this.containerSize = containerSize;
|
||||
this.type = tp;
|
||||
}
|
||||
|
||||
public DownloadActivityType getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public void setRelatedGroup(DownloadResourceGroup relatedGroup) {
|
||||
this.relatedGroup = relatedGroup;
|
||||
}
|
||||
|
||||
public DownloadResourceGroup getRelatedGroup() {
|
||||
return relatedGroup;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getFileName() {
|
||||
return fileName;
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public List<File> getDownloadedFiles(@NonNull OsmandApplication app) {
|
||||
File targetFile = getTargetFile(app);
|
||||
if (targetFile.exists()) {
|
||||
return Collections.singletonList(targetFile);
|
||||
}
|
||||
return Collections.emptyList();
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
|
@ -89,11 +89,11 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
return ((double)containerSize) / (1 << 20);
|
||||
}
|
||||
|
||||
public String getSizeDescription(Context ctx) {
|
||||
return ctx.getString(R.string.ltr_or_rtl_combine_via_space, size, "MB");
|
||||
@Override
|
||||
protected double getSizeToDownloadInMb() {
|
||||
return Algorithms.parseDoubleSilently(size, 0.0);
|
||||
}
|
||||
|
||||
|
||||
public DownloadEntry createDownloadEntry(OsmandApplication ctx) {
|
||||
String fileName = this.fileName;
|
||||
File parent = type.getDownloadFolder(ctx, this);
|
||||
|
@ -132,11 +132,8 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
return type.getTargetFileName(this);
|
||||
}
|
||||
|
||||
public String getBasename() {
|
||||
return type.getBasename(this);
|
||||
}
|
||||
|
||||
public File getTargetFile(OsmandApplication ctx) {
|
||||
@NonNull
|
||||
public File getTargetFile(@NonNull OsmandApplication ctx) {
|
||||
String basename = getTranslatedBasename();
|
||||
return new File(type.getDownloadFolder(ctx, this), basename + type.getUnzipExtension(ctx, this));
|
||||
}
|
||||
|
@ -170,6 +167,10 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
return "";
|
||||
}
|
||||
|
||||
public String getDate(@NonNull DateFormat dateFormat, boolean remote) {
|
||||
return remote ? getRemoteDate(dateFormat) : getLocalDate(dateFormat);
|
||||
}
|
||||
|
||||
public String getRemoteDate(DateFormat dateFormat) {
|
||||
if(timestamp <= 0) {
|
||||
return "";
|
||||
|
@ -178,7 +179,7 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
}
|
||||
|
||||
|
||||
public String getLocalDate(DateFormat dateFormat) {
|
||||
private String getLocalDate(@NonNull DateFormat dateFormat) {
|
||||
if(localTimestamp <= 0) {
|
||||
return "";
|
||||
}
|
||||
|
@ -199,6 +200,11 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
this.downloaded = downloaded;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasActualDataToDownload() {
|
||||
return !isDownloaded() || isOutdated();
|
||||
}
|
||||
|
||||
public void setLocalTimestamp(long localTimestamp) {
|
||||
this.localTimestamp = localTimestamp;
|
||||
}
|
||||
|
@ -211,20 +217,11 @@ public class IndexItem implements Comparable<IndexItem> {
|
|||
return downloaded;
|
||||
}
|
||||
|
||||
public String getVisibleName(Context ctx, OsmandRegions osmandRegions) {
|
||||
return type.getVisibleName(this, ctx, osmandRegions, true);
|
||||
@Override
|
||||
public boolean isDownloading(@NonNull DownloadIndexesThread thread) {
|
||||
return thread.isDownloading(this);
|
||||
}
|
||||
|
||||
public String getVisibleName(Context ctx, OsmandRegions osmandRegions, boolean includingParent) {
|
||||
return type.getVisibleName(this, ctx, osmandRegions, includingParent);
|
||||
}
|
||||
|
||||
public String getVisibleDescription(OsmandApplication clctx) {
|
||||
return type.getVisibleDescription(this, clctx);
|
||||
}
|
||||
|
||||
|
||||
|
||||
public String getDate(java.text.DateFormat format) {
|
||||
return format.format(new Date(timestamp));
|
||||
}
|
||||
|
|
122
OsmAnd/src/net/osmand/plus/download/MultipleIndexItem.java
Normal file
122
OsmAnd/src/net/osmand/plus/download/MultipleIndexItem.java
Normal file
|
@ -0,0 +1,122 @@
|
|||
package net.osmand.plus.download;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import net.osmand.map.WorldRegion;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class MultipleIndexItem extends DownloadItem {
|
||||
|
||||
private final List<IndexItem> items;
|
||||
|
||||
public MultipleIndexItem(@NonNull WorldRegion region,
|
||||
@NonNull List<IndexItem> items,
|
||||
@NonNull DownloadActivityType type) {
|
||||
super(type);
|
||||
this.items = items;
|
||||
}
|
||||
|
||||
public List<IndexItem> getAllIndexes() {
|
||||
return items;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isOutdated() {
|
||||
for (IndexItem item : items) {
|
||||
if (item.isOutdated()) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDownloaded() {
|
||||
for (IndexItem item : items) {
|
||||
if (item.isDownloaded()) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDownloading(@NonNull DownloadIndexesThread thread) {
|
||||
for (IndexItem item : items) {
|
||||
if (thread.isDownloading(item)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getFileName() {
|
||||
// The file name is used in many places.
|
||||
// But in the case of a Multiple Indexes element it's not use in most cases.
|
||||
// File is not created for Multiple Indexes element,
|
||||
// and all file names are available in internal IndexItem elements.
|
||||
|
||||
// The only one place where a filename may be needed
|
||||
// is to generate the base and display names.
|
||||
// Since these names are generated based on the filename.
|
||||
// But now we don't need a name for display,
|
||||
// because on all screens where we now use multiple elements item,
|
||||
// for display used a type name instead of a file name.
|
||||
|
||||
// Later, if you need a file name,
|
||||
// you can try to create it based on the WorldRegion
|
||||
// and file name of one of the internal IndexItem elements.
|
||||
return "";
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public List<File> getDownloadedFiles(@NonNull OsmandApplication app) {
|
||||
List<File> result = new ArrayList<>();
|
||||
for (IndexItem item : items) {
|
||||
result.addAll(item.getDownloadedFiles(app));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public List<IndexItem> getIndexesToDownload() {
|
||||
List<IndexItem> indexesToDownload = new ArrayList<>();
|
||||
for (IndexItem item : items) {
|
||||
if (item.hasActualDataToDownload()) {
|
||||
indexesToDownload.add(item);
|
||||
}
|
||||
}
|
||||
return indexesToDownload;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasActualDataToDownload() {
|
||||
return getIndexesToDownload().size() > 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getSizeToDownloadInMb() {
|
||||
double totalSizeMb = 0.0d;
|
||||
for (IndexItem item : items) {
|
||||
if (item.hasActualDataToDownload()) {
|
||||
totalSizeMb += item.getSizeToDownloadInMb();
|
||||
}
|
||||
}
|
||||
return totalSizeMb;
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getArchiveSizeMB() {
|
||||
double result = 0.0d;
|
||||
for (IndexItem item : items) {
|
||||
result += item.getArchiveSizeMB();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
113
OsmAnd/src/net/osmand/plus/download/MultipleIndexesUiHelper.java
Normal file
113
OsmAnd/src/net/osmand/plus/download/MultipleIndexesUiHelper.java
Normal file
|
@ -0,0 +1,113 @@
|
|||
package net.osmand.plus.download;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.appcompat.app.AppCompatActivity;
|
||||
|
||||
import net.osmand.map.OsmandRegions;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
import net.osmand.plus.base.SelectMultipleItemsBottomSheet;
|
||||
import net.osmand.plus.base.SelectMultipleItemsBottomSheet.OnApplySelectionListener;
|
||||
import net.osmand.plus.base.SelectMultipleItemsBottomSheet.SelectableItem;
|
||||
import net.osmand.plus.base.SelectMultipleItemsBottomSheet.SelectionUpdateListener;
|
||||
|
||||
import java.text.DateFormat;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class MultipleIndexesUiHelper {
|
||||
|
||||
public static void showDialog(@NonNull MultipleIndexItem multipleIndexItem,
|
||||
@NonNull AppCompatActivity activity,
|
||||
@NonNull final OsmandApplication app,
|
||||
@NonNull DateFormat dateFormat,
|
||||
boolean showRemoteDate,
|
||||
@NonNull final SelectItemsToDownloadListener listener) {
|
||||
List<IndexItem> indexesToDownload = getIndexesToDownload(multipleIndexItem);
|
||||
List<SelectableItem> allItems = new ArrayList<>();
|
||||
List<SelectableItem> selectedItems = new ArrayList<>();
|
||||
OsmandRegions osmandRegions = app.getRegions();
|
||||
for (IndexItem indexItem : multipleIndexItem.getAllIndexes()) {
|
||||
SelectableItem selectableItem = new SelectableItem();
|
||||
selectableItem.setTitle(indexItem.getVisibleName(app, osmandRegions, false));
|
||||
|
||||
String size = indexItem.getSizeDescription(app);
|
||||
String date = indexItem.getDate(dateFormat, showRemoteDate);
|
||||
String description = app.getString(R.string.ltr_or_rtl_combine_via_bold_point, size, date);
|
||||
selectableItem.setDescription(description);
|
||||
|
||||
selectableItem.setIconId(indexItem.getType().getIconResource());
|
||||
selectableItem.setObject(indexItem);
|
||||
allItems.add(selectableItem);
|
||||
|
||||
if (indexesToDownload.contains(indexItem)) {
|
||||
selectedItems.add(selectableItem);
|
||||
}
|
||||
}
|
||||
|
||||
final SelectMultipleItemsBottomSheet dialog =
|
||||
SelectMultipleItemsBottomSheet.showInstance(activity, allItems, selectedItems, true);
|
||||
|
||||
dialog.setSelectionUpdateListener(new SelectionUpdateListener() {
|
||||
@Override
|
||||
public void onSelectionUpdate() {
|
||||
dialog.setTitle(app.getString(R.string.welmode_download_maps));
|
||||
String total = app.getString(R.string.shared_string_total);
|
||||
double sizeToDownload = getDownloadSizeInMb(dialog.getSelectedItems());
|
||||
String size = DownloadItem.getFormattedMb(app, sizeToDownload);
|
||||
String description =
|
||||
app.getString(R.string.ltr_or_rtl_combine_via_colon, total, size);
|
||||
dialog.setDescription(description);
|
||||
String btnTitle = app.getString(R.string.shared_string_download);
|
||||
if (sizeToDownload > 0) {
|
||||
btnTitle = app.getString(R.string.ltr_or_rtl_combine_via_dash, btnTitle, size);
|
||||
}
|
||||
dialog.setConfirmButtonTitle(btnTitle);
|
||||
}
|
||||
});
|
||||
|
||||
dialog.setOnApplySelectionListener(new OnApplySelectionListener() {
|
||||
@Override
|
||||
public void onSelectionApplied(List<SelectableItem> selectedItems) {
|
||||
List<IndexItem> indexItems = new ArrayList<>();
|
||||
for (SelectableItem item : selectedItems) {
|
||||
Object obj = item.getObject();
|
||||
if (obj instanceof IndexItem) {
|
||||
indexItems.add((IndexItem) obj);
|
||||
}
|
||||
}
|
||||
listener.onItemsToDownloadSelected(indexItems);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private static List<IndexItem> getIndexesToDownload(MultipleIndexItem multipleIndexItem) {
|
||||
if (multipleIndexItem.hasActualDataToDownload()) {
|
||||
// download left regions
|
||||
return multipleIndexItem.getIndexesToDownload();
|
||||
} else {
|
||||
// download all regions again
|
||||
return multipleIndexItem.getAllIndexes();
|
||||
}
|
||||
}
|
||||
|
||||
private static double getDownloadSizeInMb(@NonNull List<SelectableItem> selectableItems) {
|
||||
List<IndexItem> indexItems = new ArrayList<>();
|
||||
for (SelectableItem i : selectableItems) {
|
||||
Object obj = i.getObject();
|
||||
if (obj instanceof IndexItem) {
|
||||
indexItems.add((IndexItem) obj);
|
||||
}
|
||||
}
|
||||
double totalSizeMb = 0.0d;
|
||||
for (IndexItem item : indexItems) {
|
||||
totalSizeMb += item.getSizeToDownloadInMb();
|
||||
}
|
||||
return totalSizeMb;
|
||||
}
|
||||
|
||||
public interface SelectItemsToDownloadListener {
|
||||
void onItemsToDownloadSelected(List<IndexItem> items);
|
||||
}
|
||||
|
||||
}
|
|
@ -10,9 +10,9 @@ import android.widget.TextView;
|
|||
import net.osmand.plus.R;
|
||||
import net.osmand.plus.activities.OsmandBaseExpandableListAdapter;
|
||||
import net.osmand.plus.download.CustomIndexItem;
|
||||
import net.osmand.plus.download.DownloadItem;
|
||||
import net.osmand.plus.download.DownloadActivity;
|
||||
import net.osmand.plus.download.DownloadResourceGroup;
|
||||
import net.osmand.plus.download.IndexItem;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
@ -52,9 +52,9 @@ public class DownloadResourceGroupAdapter extends OsmandBaseExpandableListAdapte
|
|||
public View getChildView(final int groupPosition, final int childPosition, boolean isLastChild,
|
||||
View convertView, ViewGroup parent) {
|
||||
final Object child = getChild(groupPosition, childPosition);
|
||||
if (child instanceof IndexItem) {
|
||||
if (child instanceof DownloadItem) {
|
||||
|
||||
IndexItem item = (IndexItem) child;
|
||||
DownloadItem item = (DownloadItem) child;
|
||||
DownloadResourceGroup group = getGroupObj(groupPosition);
|
||||
ItemViewHolder viewHolder;
|
||||
if (convertView != null && convertView.getTag() instanceof ItemViewHolder) {
|
||||
|
|
|
@ -35,6 +35,7 @@ import net.osmand.plus.download.DownloadActivity;
|
|||
import net.osmand.plus.download.DownloadActivity.BannerAndDownloadFreeVersion;
|
||||
import net.osmand.plus.download.DownloadActivityType;
|
||||
import net.osmand.plus.download.DownloadIndexesThread.DownloadEvents;
|
||||
import net.osmand.plus.download.DownloadItem;
|
||||
import net.osmand.plus.download.DownloadResourceGroup;
|
||||
import net.osmand.plus.download.DownloadResources;
|
||||
import net.osmand.plus.download.DownloadValidationManager;
|
||||
|
@ -504,10 +505,10 @@ public class DownloadResourceGroupFragment extends DialogFragment implements Dow
|
|||
|
||||
DownloadItemFragment downloadItemFragment = DownloadItemFragment.createInstance(regionId, childPosition);
|
||||
((DownloadActivity) getActivity()).showDialog(getActivity(), downloadItemFragment);
|
||||
} else if (child instanceof IndexItem) {
|
||||
IndexItem indexItem = (IndexItem) child;
|
||||
} else if (child instanceof DownloadItem) {
|
||||
DownloadItem downloadItem = (DownloadItem) child;
|
||||
ItemViewHolder vh = (ItemViewHolder) v.getTag();
|
||||
OnClickListener ls = vh.getRightButtonAction(indexItem, vh.getClickAction(indexItem));
|
||||
OnClickListener ls = vh.getRightButtonAction(downloadItem, vh.getClickAction(downloadItem));
|
||||
ls.onClick(v);
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -17,11 +17,14 @@ import android.widget.ProgressBar;
|
|||
import android.widget.TextView;
|
||||
import android.widget.Toast;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.appcompat.app.AlertDialog;
|
||||
import androidx.appcompat.widget.PopupMenu;
|
||||
import androidx.core.view.ViewCompat;
|
||||
|
||||
import net.osmand.map.OsmandRegions;
|
||||
import net.osmand.map.WorldRegion;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
import net.osmand.plus.Version;
|
||||
import net.osmand.plus.activities.LocalIndexHelper.LocalIndexType;
|
||||
|
@ -31,11 +34,15 @@ import net.osmand.plus.activities.PluginsFragment;
|
|||
import net.osmand.plus.chooseplan.ChoosePlanDialogFragment;
|
||||
import net.osmand.plus.download.CityItem;
|
||||
import net.osmand.plus.download.CustomIndexItem;
|
||||
import net.osmand.plus.download.DownloadItem;
|
||||
import net.osmand.plus.download.DownloadActivity;
|
||||
import net.osmand.plus.download.DownloadActivityType;
|
||||
import net.osmand.plus.download.DownloadResourceGroup;
|
||||
import net.osmand.plus.download.DownloadResources;
|
||||
import net.osmand.plus.download.IndexItem;
|
||||
import net.osmand.plus.download.MultipleIndexesUiHelper;
|
||||
import net.osmand.plus.download.MultipleIndexesUiHelper.SelectItemsToDownloadListener;
|
||||
import net.osmand.plus.download.MultipleIndexItem;
|
||||
import net.osmand.plus.download.ui.LocalIndexesFragment.LocalIndexOperationTask;
|
||||
import net.osmand.plus.helpers.FileNameTranslationHelper;
|
||||
import net.osmand.plus.inapp.InAppPurchaseHelper;
|
||||
|
@ -43,6 +50,7 @@ import net.osmand.util.Algorithms;
|
|||
|
||||
import java.io.File;
|
||||
import java.text.DateFormat;
|
||||
import java.util.List;
|
||||
|
||||
public class ItemViewHolder {
|
||||
|
||||
|
@ -137,24 +145,24 @@ public class ItemViewHolder {
|
|||
depthContoursPurchased = InAppPurchaseHelper.isDepthContoursPurchased(context.getMyApplication());
|
||||
}
|
||||
|
||||
public void bindIndexItem(final IndexItem indexItem) {
|
||||
bindIndexItem(indexItem, null);
|
||||
public void bindIndexItem(final DownloadItem downloadItem) {
|
||||
bindIndexItem(downloadItem, null);
|
||||
}
|
||||
|
||||
public void bindIndexItem(final IndexItem indexItem, final String cityName) {
|
||||
public void bindIndexItem(final DownloadItem downloadItem, final String cityName) {
|
||||
initAppStatusVariables();
|
||||
boolean isDownloading = context.getDownloadThread().isDownloading(indexItem);
|
||||
boolean isDownloading = downloadItem.isDownloading(context.getDownloadThread());
|
||||
int progress = -1;
|
||||
if (context.getDownloadThread().getCurrentDownloadingItem() == indexItem) {
|
||||
if (context.getDownloadThread().getCurrentDownloadingItem() == downloadItem) {
|
||||
progress = context.getDownloadThread().getCurrentDownloadingItemProgress();
|
||||
}
|
||||
boolean disabled = checkDisabledAndClickAction(indexItem);
|
||||
boolean disabled = checkDisabledAndClickAction(downloadItem);
|
||||
/// name and left item
|
||||
String name;
|
||||
if(showTypeInName) {
|
||||
name = indexItem.getType().getString(context);
|
||||
name = downloadItem.getType().getString(context);
|
||||
} else {
|
||||
name = indexItem.getVisibleName(context, context.getMyApplication().getRegions(), showParentRegionName);
|
||||
name = downloadItem.getVisibleName(context, context.getMyApplication().getRegions(), showParentRegionName);
|
||||
}
|
||||
String text = (!Algorithms.isEmpty(cityName) && !cityName.equals(name) ? cityName + "\n" : "") + name;
|
||||
nameTextView.setText(text);
|
||||
|
@ -164,43 +172,78 @@ public class ItemViewHolder {
|
|||
nameTextView.setTextColor(textColorSecondary);
|
||||
}
|
||||
int color = textColorSecondary;
|
||||
if(indexItem.isDownloaded() && !isDownloading) {
|
||||
int colorId = indexItem.isOutdated() ? R.color.color_distance : R.color.color_ok;
|
||||
if(downloadItem.isDownloaded() && !isDownloading) {
|
||||
int colorId = downloadItem.isOutdated() ? R.color.color_distance : R.color.color_ok;
|
||||
color = context.getResources().getColor(colorId);
|
||||
}
|
||||
if (indexItem.isDownloaded()) {
|
||||
if (downloadItem.isDownloaded()) {
|
||||
leftImageView.setImageDrawable(getContentIcon(context,
|
||||
indexItem.getType().getIconResource(), color));
|
||||
downloadItem.getType().getIconResource(), color));
|
||||
} else if (disabled) {
|
||||
leftImageView.setImageDrawable(getContentIcon(context,
|
||||
indexItem.getType().getIconResource(), textColorSecondary));
|
||||
downloadItem.getType().getIconResource(), textColorSecondary));
|
||||
} else {
|
||||
leftImageView.setImageDrawable(getContentIcon(context,
|
||||
indexItem.getType().getIconResource()));
|
||||
downloadItem.getType().getIconResource()));
|
||||
}
|
||||
descrTextView.setTextColor(textColorSecondary);
|
||||
if (!isDownloading) {
|
||||
progressBar.setVisibility(View.GONE);
|
||||
descrTextView.setVisibility(View.VISIBLE);
|
||||
if (indexItem instanceof CustomIndexItem && (((CustomIndexItem) indexItem).getSubName(context) != null)) {
|
||||
descrTextView.setText(((CustomIndexItem) indexItem).getSubName(context));
|
||||
} else if (indexItem.getType() == DownloadActivityType.DEPTH_CONTOUR_FILE && !depthContoursPurchased) {
|
||||
if (downloadItem instanceof CustomIndexItem && (((CustomIndexItem) downloadItem).getSubName(context) != null)) {
|
||||
descrTextView.setText(((CustomIndexItem) downloadItem).getSubName(context));
|
||||
} else if (downloadItem.getType() == DownloadActivityType.DEPTH_CONTOUR_FILE && !depthContoursPurchased) {
|
||||
descrTextView.setText(context.getString(R.string.depth_contour_descr));
|
||||
} else if ((indexItem.getType() == DownloadActivityType.SRTM_COUNTRY_FILE
|
||||
|| indexItem.getType() == DownloadActivityType.HILLSHADE_FILE
|
||||
|| indexItem.getType() == DownloadActivityType.SLOPE_FILE) && srtmDisabled) {
|
||||
} else if ((downloadItem.getType() == DownloadActivityType.SRTM_COUNTRY_FILE
|
||||
|| downloadItem.getType() == DownloadActivityType.HILLSHADE_FILE
|
||||
|| downloadItem.getType() == DownloadActivityType.SLOPE_FILE) && srtmDisabled) {
|
||||
if (showTypeInName) {
|
||||
descrTextView.setText("");
|
||||
} else {
|
||||
descrTextView.setText(indexItem.getType().getString(context));
|
||||
descrTextView.setText(downloadItem.getType().getString(context));
|
||||
}
|
||||
} else if (showTypeInDesc) {
|
||||
descrTextView.setText(indexItem.getType().getString(context) +
|
||||
" • " + indexItem.getSizeDescription(context) +
|
||||
" • " + (showRemoteDate ? indexItem.getRemoteDate(dateFormat) : indexItem.getLocalDate(dateFormat)));
|
||||
} else if (downloadItem instanceof MultipleIndexItem) {
|
||||
MultipleIndexItem item = (MultipleIndexItem) downloadItem;
|
||||
String allRegionsHeader = context.getString(R.string.shared_strings_all_regions);
|
||||
String regionsHeader = context.getString(R.string.regions);
|
||||
String allRegionsCount = String.valueOf(item.getAllIndexes().size());
|
||||
String leftToDownloadCount = String.valueOf(item.getIndexesToDownload().size());
|
||||
String header;
|
||||
String count;
|
||||
if (item.hasActualDataToDownload()) {
|
||||
if (!item.isDownloaded()) {
|
||||
header = allRegionsHeader;
|
||||
count = leftToDownloadCount;
|
||||
} else {
|
||||
header = regionsHeader;
|
||||
count = String.format(
|
||||
context.getString(R.string.ltr_or_rtl_combine_via_slash),
|
||||
leftToDownloadCount,
|
||||
allRegionsCount);
|
||||
}
|
||||
} else {
|
||||
header = allRegionsHeader;
|
||||
count = allRegionsCount;
|
||||
}
|
||||
String fullDescription =
|
||||
context.getString(R.string.ltr_or_rtl_combine_via_colon, header, count);
|
||||
if (item.hasActualDataToDownload()) {
|
||||
fullDescription = context.getString(
|
||||
R.string.ltr_or_rtl_combine_via_bold_point, fullDescription,
|
||||
item.getSizeDescription(context));
|
||||
}
|
||||
descrTextView.setText(fullDescription);
|
||||
} else {
|
||||
descrTextView.setText(indexItem.getSizeDescription(context) + " • " +
|
||||
(showRemoteDate ? indexItem.getRemoteDate(dateFormat) : indexItem.getLocalDate(dateFormat)));
|
||||
IndexItem item = (IndexItem) downloadItem;
|
||||
String pattern = context.getString(R.string.ltr_or_rtl_combine_via_bold_point);
|
||||
String type = item.getType().getString(context);
|
||||
String size = item.getSizeDescription(context);
|
||||
String date = item.getDate(dateFormat, showRemoteDate);
|
||||
String fullDescription = String.format(pattern, size, date);
|
||||
if (showTypeInDesc) {
|
||||
fullDescription = String.format(pattern, type, fullDescription);
|
||||
}
|
||||
descrTextView.setText(fullDescription);
|
||||
}
|
||||
|
||||
} else {
|
||||
|
@ -209,18 +252,19 @@ public class ItemViewHolder {
|
|||
progressBar.setProgress(progress);
|
||||
|
||||
if (showProgressInDesc) {
|
||||
double mb = indexItem.getArchiveSizeMB();
|
||||
double mb = downloadItem.getArchiveSizeMB();
|
||||
String v ;
|
||||
if (progress != -1) {
|
||||
v = context.getString(R.string.value_downloaded_of_max, mb * progress / 100, mb);
|
||||
} else {
|
||||
v = context.getString(R.string.file_size_in_mb, mb);
|
||||
}
|
||||
if(showTypeInDesc && indexItem.getType() == DownloadActivityType.ROADS_FILE) {
|
||||
descrTextView.setText(indexItem.getType().getString(context) + " • " + v);
|
||||
} else {
|
||||
descrTextView.setText(v);
|
||||
String fullDescription = v;
|
||||
if(showTypeInDesc && downloadItem.getType() == DownloadActivityType.ROADS_FILE) {
|
||||
fullDescription = context.getString(R.string.ltr_or_rtl_combine_via_bold_point,
|
||||
downloadItem.getType().getString(context), fullDescription);
|
||||
}
|
||||
descrTextView.setText(fullDescription);
|
||||
descrTextView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
descrTextView.setVisibility(View.GONE);
|
||||
|
@ -241,44 +285,7 @@ public class ItemViewHolder {
|
|||
}
|
||||
}
|
||||
|
||||
protected void download(IndexItem indexItem, DownloadResourceGroup parentOptional) {
|
||||
boolean handled = false;
|
||||
if(parentOptional != null) {
|
||||
WorldRegion region = DownloadResourceGroup.getRegion(parentOptional);
|
||||
context.setDownloadItem(region, indexItem.getTargetFile(context.getMyApplication()).getAbsolutePath());
|
||||
}
|
||||
if (indexItem.getType() == DownloadActivityType.ROADS_FILE && parentOptional != null) {
|
||||
for (IndexItem ii : parentOptional.getIndividualResources()) {
|
||||
if (ii.getType() == DownloadActivityType.NORMAL_FILE) {
|
||||
if (ii.isDownloaded()) {
|
||||
handled = true;
|
||||
confirmDownload(indexItem);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if(!handled) {
|
||||
context.startDownload(indexItem);
|
||||
}
|
||||
}
|
||||
private void confirmDownload(final IndexItem indexItem) {
|
||||
AlertDialog.Builder builder = new AlertDialog.Builder(context);
|
||||
builder.setTitle(R.string.are_you_sure);
|
||||
builder.setMessage(R.string.confirm_download_roadmaps);
|
||||
builder.setNegativeButton(R.string.shared_string_cancel, null).setPositiveButton(
|
||||
R.string.shared_string_download, new DialogInterface.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(DialogInterface dialog, int which) {
|
||||
if (indexItem != null) {
|
||||
context.startDownload(indexItem);
|
||||
}
|
||||
}
|
||||
});
|
||||
builder.show();
|
||||
}
|
||||
|
||||
private boolean checkDisabledAndClickAction(final IndexItem item) {
|
||||
private boolean checkDisabledAndClickAction(final DownloadItem item) {
|
||||
RightButtonAction clickAction = getClickAction(item);
|
||||
boolean disabled = clickAction != RightButtonAction.DOWNLOAD;
|
||||
OnClickListener action = getRightButtonAction(item, clickAction);
|
||||
|
@ -290,15 +297,15 @@ public class ItemViewHolder {
|
|||
} else {
|
||||
rightButton.setVisibility(View.GONE);
|
||||
rightImageButton.setVisibility(View.VISIBLE);
|
||||
final boolean isDownloading = context.getDownloadThread().isDownloading(item);
|
||||
final boolean isDownloading = item.isDownloading(context.getDownloadThread());
|
||||
if (isDownloading) {
|
||||
rightImageButton.setImageDrawable(getContentIcon(context, R.drawable.ic_action_remove_dark));
|
||||
rightImageButton.setContentDescription(context.getString(R.string.shared_string_cancel));
|
||||
} else if(item.isDownloaded() && !item.isOutdated()) {
|
||||
} else if(!item.hasActualDataToDownload()) {
|
||||
rightImageButton.setImageDrawable(getContentIcon(context, R.drawable.ic_overflow_menu_white));
|
||||
rightImageButton.setContentDescription(context.getString(R.string.shared_string_more));
|
||||
} else {
|
||||
rightImageButton.setImageDrawable(getContentIcon(context, R.drawable.ic_action_import));
|
||||
rightImageButton.setImageDrawable(getContentIcon(context, getDownloadActionIconId(item)));
|
||||
rightImageButton.setContentDescription(context.getString(R.string.shared_string_download));
|
||||
}
|
||||
rightImageButton.setOnClickListener(action);
|
||||
|
@ -307,31 +314,37 @@ public class ItemViewHolder {
|
|||
return disabled;
|
||||
}
|
||||
|
||||
private int getDownloadActionIconId(@NonNull DownloadItem item) {
|
||||
return item instanceof MultipleIndexItem ?
|
||||
R.drawable.ic_action_multi_download :
|
||||
R.drawable.ic_action_import;
|
||||
}
|
||||
|
||||
@SuppressLint("DefaultLocale")
|
||||
public RightButtonAction getClickAction(final IndexItem indexItem) {
|
||||
public RightButtonAction getClickAction(final DownloadItem item) {
|
||||
RightButtonAction clickAction = RightButtonAction.DOWNLOAD;
|
||||
if (indexItem.getBasename().toLowerCase().equals(DownloadResources.WORLD_SEAMARKS_KEY)
|
||||
if (item.getBasename().toLowerCase().equals(DownloadResources.WORLD_SEAMARKS_KEY)
|
||||
&& nauticalPluginDisabled) {
|
||||
clickAction = RightButtonAction.ASK_FOR_SEAMARKS_PLUGIN;
|
||||
} else if ((indexItem.getType() == DownloadActivityType.SRTM_COUNTRY_FILE
|
||||
|| indexItem.getType() == DownloadActivityType.HILLSHADE_FILE
|
||||
|| indexItem.getType() == DownloadActivityType.SLOPE_FILE) && srtmDisabled) {
|
||||
} else if ((item.getType() == DownloadActivityType.SRTM_COUNTRY_FILE
|
||||
|| item.getType() == DownloadActivityType.HILLSHADE_FILE
|
||||
|| item.getType() == DownloadActivityType.SLOPE_FILE) && srtmDisabled) {
|
||||
if (srtmNeedsInstallation) {
|
||||
clickAction = RightButtonAction.ASK_FOR_SRTM_PLUGIN_PURCHASE;
|
||||
} else {
|
||||
clickAction = RightButtonAction.ASK_FOR_SRTM_PLUGIN_ENABLE;
|
||||
}
|
||||
|
||||
} else if (indexItem.getType() == DownloadActivityType.WIKIPEDIA_FILE
|
||||
} else if (item.getType() == DownloadActivityType.WIKIPEDIA_FILE
|
||||
&& !Version.isPaidVersion(context.getMyApplication())) {
|
||||
clickAction = RightButtonAction.ASK_FOR_FULL_VERSION_PURCHASE;
|
||||
} else if (indexItem.getType() == DownloadActivityType.DEPTH_CONTOUR_FILE && !depthContoursPurchased) {
|
||||
} else if (item.getType() == DownloadActivityType.DEPTH_CONTOUR_FILE && !depthContoursPurchased) {
|
||||
clickAction = RightButtonAction.ASK_FOR_DEPTH_CONTOURS_PURCHASE;
|
||||
}
|
||||
return clickAction;
|
||||
}
|
||||
|
||||
public OnClickListener getRightButtonAction(final IndexItem item, final RightButtonAction clickAction) {
|
||||
public OnClickListener getRightButtonAction(final DownloadItem item, final RightButtonAction clickAction) {
|
||||
if (clickAction != RightButtonAction.DOWNLOAD) {
|
||||
return new View.OnClickListener() {
|
||||
@Override
|
||||
|
@ -370,7 +383,7 @@ public class ItemViewHolder {
|
|||
}
|
||||
};
|
||||
} else {
|
||||
final boolean isDownloading = context.getDownloadThread().isDownloading(item);
|
||||
final boolean isDownloading = item.isDownloading(context.getDownloadThread());
|
||||
return new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
|
@ -380,8 +393,8 @@ public class ItemViewHolder {
|
|||
} else {
|
||||
context.makeSureUserCancelDownload(item);
|
||||
}
|
||||
} else if(item.isDownloaded() && !item.isOutdated()){
|
||||
contextMenu(v, item, item.getRelatedGroup());
|
||||
} else if(!item.hasActualDataToDownload()){
|
||||
showContextMenu(v, item, item.getRelatedGroup());
|
||||
} else {
|
||||
download(item, item.getRelatedGroup());
|
||||
}
|
||||
|
@ -390,52 +403,21 @@ public class ItemViewHolder {
|
|||
}
|
||||
}
|
||||
|
||||
protected void contextMenu(View v, final IndexItem indexItem, final DownloadResourceGroup parentOptional) {
|
||||
final PopupMenu optionsMenu = new PopupMenu(context, v);
|
||||
protected void showContextMenu(View v,
|
||||
final DownloadItem downloadItem,
|
||||
final DownloadResourceGroup parentOptional) {
|
||||
OsmandApplication app = context.getMyApplication();
|
||||
PopupMenu optionsMenu = new PopupMenu(context, v);
|
||||
MenuItem item;
|
||||
|
||||
final File fl = indexItem.getTargetFile(context.getMyApplication());
|
||||
if (fl.exists()) {
|
||||
item = optionsMenu.getMenu().add(R.string.shared_string_remove).setIcon(
|
||||
context.getMyApplication().getUIUtilities().getThemedIcon(R.drawable.ic_action_remove_dark));
|
||||
final List<File> downloadedFiles = downloadItem.getDownloadedFiles(app);
|
||||
if (!Algorithms.isEmpty(downloadedFiles)) {
|
||||
item = optionsMenu.getMenu().add(R.string.shared_string_remove)
|
||||
.setIcon(getContentIcon(context, R.drawable.ic_action_remove_dark));
|
||||
item.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
|
||||
@Override
|
||||
public boolean onMenuItemClick(MenuItem item) {
|
||||
LocalIndexType tp = LocalIndexType.MAP_DATA;
|
||||
if (indexItem.getType() == DownloadActivityType.HILLSHADE_FILE) {
|
||||
tp = LocalIndexType.TILES_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.SLOPE_FILE) {
|
||||
tp = LocalIndexType.TILES_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.ROADS_FILE) {
|
||||
tp = LocalIndexType.MAP_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.SRTM_COUNTRY_FILE) {
|
||||
tp = LocalIndexType.SRTM_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.WIKIPEDIA_FILE) {
|
||||
tp = LocalIndexType.MAP_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.WIKIVOYAGE_FILE) {
|
||||
tp = LocalIndexType.MAP_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.TRAVEL_FILE) {
|
||||
tp = LocalIndexType.MAP_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.FONT_FILE) {
|
||||
tp = LocalIndexType.FONT_DATA;
|
||||
} else if (indexItem.getType() == DownloadActivityType.VOICE_FILE) {
|
||||
tp = indexItem.getBasename().contains("tts") ? LocalIndexType.TTS_VOICE_DATA
|
||||
: LocalIndexType.VOICE_DATA;
|
||||
}
|
||||
final LocalIndexInfo info = new LocalIndexInfo(tp, fl, false, context.getMyApplication());
|
||||
AlertDialog.Builder confirm = new AlertDialog.Builder(context);
|
||||
confirm.setPositiveButton(R.string.shared_string_yes, new DialogInterface.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(DialogInterface dialog, int which) {
|
||||
new LocalIndexOperationTask(context, null, LocalIndexOperationTask.DELETE_OPERATION)
|
||||
.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR, info);
|
||||
}
|
||||
});
|
||||
confirm.setNegativeButton(R.string.shared_string_no, null);
|
||||
String fn = FileNameTranslationHelper.getFileName(context, context.getMyApplication().getRegions(),
|
||||
indexItem.getVisibleName(context, context.getMyApplication().getRegions()));
|
||||
confirm.setMessage(context.getString(R.string.delete_confirmation_msg, fn));
|
||||
confirm.show();
|
||||
confirmRemove(downloadItem, downloadedFiles);
|
||||
return true;
|
||||
}
|
||||
});
|
||||
|
@ -445,7 +427,7 @@ public class ItemViewHolder {
|
|||
item.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
|
||||
@Override
|
||||
public boolean onMenuItemClick(MenuItem item) {
|
||||
download(indexItem, parentOptional);
|
||||
download(downloadItem, parentOptional);
|
||||
return true;
|
||||
}
|
||||
});
|
||||
|
@ -453,6 +435,135 @@ public class ItemViewHolder {
|
|||
optionsMenu.show();
|
||||
}
|
||||
|
||||
protected void download(DownloadItem item, DownloadResourceGroup parentOptional) {
|
||||
boolean handled = false;
|
||||
if (parentOptional != null && item instanceof IndexItem) {
|
||||
IndexItem indexItem = (IndexItem) item;
|
||||
WorldRegion region = DownloadResourceGroup.getRegion(parentOptional);
|
||||
context.setDownloadItem(region, indexItem.getTargetFile(context.getMyApplication()).getAbsolutePath());
|
||||
}
|
||||
if (item.getType() == DownloadActivityType.ROADS_FILE && parentOptional != null) {
|
||||
for (IndexItem ii : parentOptional.getIndividualResources()) {
|
||||
if (ii.getType() == DownloadActivityType.NORMAL_FILE) {
|
||||
if (ii.isDownloaded()) {
|
||||
handled = true;
|
||||
confirmDownload(item);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if(!handled) {
|
||||
startDownload(item);
|
||||
}
|
||||
}
|
||||
private void confirmDownload(final DownloadItem item) {
|
||||
AlertDialog.Builder builder = new AlertDialog.Builder(context);
|
||||
builder.setTitle(R.string.are_you_sure);
|
||||
builder.setMessage(R.string.confirm_download_roadmaps);
|
||||
builder.setNegativeButton(R.string.shared_string_cancel, null).setPositiveButton(
|
||||
R.string.shared_string_download, new DialogInterface.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(DialogInterface dialog, int which) {
|
||||
if (item != null) {
|
||||
startDownload(item);
|
||||
}
|
||||
}
|
||||
});
|
||||
builder.show();
|
||||
}
|
||||
|
||||
private void startDownload(DownloadItem item) {
|
||||
if (item instanceof MultipleIndexItem) {
|
||||
selectIndexesToDownload((MultipleIndexItem) item);
|
||||
} else if (item instanceof IndexItem) {
|
||||
IndexItem indexItem = (IndexItem) item;
|
||||
context.startDownload(indexItem);
|
||||
}
|
||||
}
|
||||
|
||||
private void selectIndexesToDownload(MultipleIndexItem item) {
|
||||
OsmandApplication app = context.getMyApplication();
|
||||
MultipleIndexesUiHelper.showDialog(item, context, app, dateFormat, showRemoteDate,
|
||||
new SelectItemsToDownloadListener() {
|
||||
@Override
|
||||
public void onItemsToDownloadSelected(List<IndexItem> indexes) {
|
||||
IndexItem[] indexesArray = new IndexItem[indexes.size()];
|
||||
context.startDownload(indexes.toArray(indexesArray));
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
private void confirmRemove(@NonNull final DownloadItem downloadItem,
|
||||
@NonNull final List<File> downloadedFiles) {
|
||||
OsmandApplication app = context.getMyApplication();
|
||||
AlertDialog.Builder confirm = new AlertDialog.Builder(context);
|
||||
|
||||
String message;
|
||||
if (downloadedFiles.size() > 1) {
|
||||
message = context.getString(R.string.delete_number_files_question, downloadedFiles.size());
|
||||
} else {
|
||||
OsmandRegions regions = app.getRegions();
|
||||
String visibleName = downloadItem.getVisibleName(context, regions);
|
||||
String fileName = FileNameTranslationHelper.getFileName(context, regions, visibleName);
|
||||
message = context.getString(R.string.delete_confirmation_msg, fileName);
|
||||
}
|
||||
confirm.setMessage(message);
|
||||
|
||||
confirm.setPositiveButton(R.string.shared_string_yes, new DialogInterface.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(DialogInterface dialog, int which) {
|
||||
LocalIndexType type = getLocalIndexType(downloadItem);
|
||||
remove(type, downloadedFiles);
|
||||
}
|
||||
});
|
||||
confirm.setNegativeButton(R.string.shared_string_no, null);
|
||||
|
||||
confirm.show();
|
||||
}
|
||||
|
||||
private void remove(@NonNull LocalIndexType type,
|
||||
@NonNull List<File> filesToDelete) {
|
||||
OsmandApplication app = context.getMyApplication();
|
||||
LocalIndexOperationTask removeTask = new LocalIndexOperationTask(
|
||||
context,
|
||||
null,
|
||||
LocalIndexOperationTask.DELETE_OPERATION);
|
||||
LocalIndexInfo[] params = new LocalIndexInfo[filesToDelete.size()];
|
||||
for (int i = 0; i < filesToDelete.size(); i++) {
|
||||
File file = filesToDelete.get(i);
|
||||
params[i] = new LocalIndexInfo(type, file, false, app);
|
||||
}
|
||||
removeTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR, params);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
private LocalIndexType getLocalIndexType(@NonNull DownloadItem downloadItem) {
|
||||
LocalIndexType type = LocalIndexType.MAP_DATA;
|
||||
if (downloadItem.getType() == DownloadActivityType.HILLSHADE_FILE) {
|
||||
type = LocalIndexType.TILES_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.SLOPE_FILE) {
|
||||
type = LocalIndexType.TILES_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.ROADS_FILE) {
|
||||
type = LocalIndexType.MAP_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.SRTM_COUNTRY_FILE) {
|
||||
type = LocalIndexType.SRTM_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.WIKIPEDIA_FILE) {
|
||||
type = LocalIndexType.MAP_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.WIKIVOYAGE_FILE) {
|
||||
type = LocalIndexType.MAP_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.TRAVEL_FILE) {
|
||||
type = LocalIndexType.MAP_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.FONT_FILE) {
|
||||
type = LocalIndexType.FONT_DATA;
|
||||
} else if (downloadItem.getType() == DownloadActivityType.VOICE_FILE) {
|
||||
type = downloadItem.getBasename().contains("tts") ? LocalIndexType.TTS_VOICE_DATA
|
||||
: LocalIndexType.VOICE_DATA;
|
||||
}
|
||||
return type;
|
||||
}
|
||||
|
||||
private Drawable getContentIcon(DownloadActivity context, int resourceId) {
|
||||
return context.getMyApplication().getUIUtilities().getThemedIcon(resourceId);
|
||||
}
|
||||
|
|
|
@ -153,7 +153,8 @@ public class UpdatesIndexFragment extends OsmAndListFragment implements Download
|
|||
for (IndexItem indexItem : indexItems) {
|
||||
downloadsSize += indexItem.getSize();
|
||||
}
|
||||
String updateAllText = getActivity().getString(R.string.update_all, downloadsSize >> 20);
|
||||
String updateAllText = getActivity().getString(
|
||||
R.string.update_all, String.valueOf(downloadsSize >> 20));
|
||||
updateAllButton.setText(updateAllText);
|
||||
updateAllButton.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue