Partial implementation
This commit is contained in:
parent
3e0350a963
commit
890277dd4b
13 changed files with 245 additions and 182 deletions
15
DataExtractionOSM/src/net/osmand/ResultMatcher.java
Normal file
15
DataExtractionOSM/src/net/osmand/ResultMatcher.java
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
package net.osmand;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Easy matcher to be able to publish results immediately
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public interface ResultMatcher<T> {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param name
|
||||||
|
* @return true if result should be added to final list
|
||||||
|
*/
|
||||||
|
boolean publish(T object);
|
||||||
|
|
||||||
|
}
|
|
@ -3,9 +3,11 @@ package net.osmand.binary;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.StringMatcher;
|
import net.osmand.StringMatcher;
|
||||||
import net.osmand.data.Building;
|
import net.osmand.data.Building;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
|
import net.osmand.data.MapObject;
|
||||||
import net.osmand.data.PostCode;
|
import net.osmand.data.PostCode;
|
||||||
import net.osmand.data.Street;
|
import net.osmand.data.Street;
|
||||||
import net.osmand.data.City.CityType;
|
import net.osmand.data.City.CityType;
|
||||||
|
@ -83,7 +85,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void readCities(List<City> cities, StringMatcher matcher, boolean useEn) throws IOException {
|
protected void readCities(List<City> cities, ResultMatcher<MapObject> resultMatcher, StringMatcher matcher, boolean useEn) throws IOException {
|
||||||
while(true){
|
while(true){
|
||||||
int t = codedIS.readTag();
|
int t = codedIS.readTag();
|
||||||
int tag = WireFormat.getTagFieldNumber(t);
|
int tag = WireFormat.getTagFieldNumber(t);
|
||||||
|
@ -95,10 +97,12 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
int length = codedIS.readRawVarint32();
|
int length = codedIS.readRawVarint32();
|
||||||
|
|
||||||
int oldLimit = codedIS.pushLimit(length);
|
int oldLimit = codedIS.pushLimit(length);
|
||||||
City c = readCity(null, offset, false, matcher, useEn);
|
City c = readCity(null, offset, false, null, matcher, useEn);
|
||||||
if(c != null){
|
if(c != null){
|
||||||
|
if (resultMatcher == null || resultMatcher.publish(c)) {
|
||||||
cities.add(c);
|
cities.add(c);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
codedIS.popLimit(oldLimit);
|
codedIS.popLimit(oldLimit);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
@ -109,7 +113,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
protected PostCode readPostcode(PostCode p, int fileOffset, boolean loadStreets, String postcodeFilter) throws IOException{
|
protected PostCode readPostcode(PostCode p, int fileOffset, ResultMatcher<Street> resultMatcher, boolean loadStreets, String postcodeFilter) throws IOException{
|
||||||
int x = 0;
|
int x = 0;
|
||||||
int y = 0;
|
int y = 0;
|
||||||
while(true){
|
while(true){
|
||||||
|
@ -117,8 +121,6 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
int tag = WireFormat.getTagFieldNumber(t);
|
int tag = WireFormat.getTagFieldNumber(t);
|
||||||
switch (tag) {
|
switch (tag) {
|
||||||
case 0:
|
case 0:
|
||||||
p.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x));
|
|
||||||
p.setFileOffset(fileOffset);
|
|
||||||
return p;
|
return p;
|
||||||
case OsmandOdb.PostcodeIndex.POSTCODE_FIELD_NUMBER :
|
case OsmandOdb.PostcodeIndex.POSTCODE_FIELD_NUMBER :
|
||||||
String name = codedIS.readString();
|
String name = codedIS.readString();
|
||||||
|
@ -128,6 +130,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
}
|
}
|
||||||
if(p == null){
|
if(p == null){
|
||||||
p = new PostCode(name);
|
p = new PostCode(name);
|
||||||
|
p.setFileOffset(fileOffset);
|
||||||
}
|
}
|
||||||
p.setName(name);
|
p.setName(name);
|
||||||
break;
|
break;
|
||||||
|
@ -136,6 +139,12 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
break;
|
break;
|
||||||
case OsmandOdb.PostcodeIndex.Y_FIELD_NUMBER :
|
case OsmandOdb.PostcodeIndex.Y_FIELD_NUMBER :
|
||||||
y = codedIS.readFixed32();
|
y = codedIS.readFixed32();
|
||||||
|
p.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x));
|
||||||
|
if(!loadStreets){
|
||||||
|
// skip everything
|
||||||
|
codedIS.skipRawBytes(codedIS.getBytesUntilLimit());
|
||||||
|
return p;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case OsmandOdb.PostcodeIndex.STREETS_FIELD_NUMBER :
|
case OsmandOdb.PostcodeIndex.STREETS_FIELD_NUMBER :
|
||||||
int offset = codedIS.getTotalBytesRead();
|
int offset = codedIS.getTotalBytesRead();
|
||||||
|
@ -144,8 +153,10 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
Street s = new Street(null);
|
Street s = new Street(null);
|
||||||
int oldLimit = codedIS.pushLimit(length);
|
int oldLimit = codedIS.pushLimit(length);
|
||||||
s.setFileOffset(offset);
|
s.setFileOffset(offset);
|
||||||
readStreet(s, true, x >> 7, y >> 7, p.getName());
|
readStreet(s, null, true, x >> 7, y >> 7, p.getName());
|
||||||
|
if (resultMatcher == null || resultMatcher.publish(s)) {
|
||||||
p.registerStreet(s, false);
|
p.registerStreet(s, false);
|
||||||
|
}
|
||||||
codedIS.popLimit(oldLimit);
|
codedIS.popLimit(oldLimit);
|
||||||
} else {
|
} else {
|
||||||
codedIS.skipRawBytes(length);
|
codedIS.skipRawBytes(length);
|
||||||
|
@ -159,7 +170,8 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
protected City readCity(City c, int fileOffset, boolean loadStreets, StringMatcher nameMatcher, boolean useEn) throws IOException{
|
protected City readCity(City c, int fileOffset, boolean loadStreets, ResultMatcher<Street> resultMatcher,
|
||||||
|
StringMatcher nameMatcher, boolean useEn) throws IOException{
|
||||||
int x = 0;
|
int x = 0;
|
||||||
int y = 0;
|
int y = 0;
|
||||||
int streetInd = 0;
|
int streetInd = 0;
|
||||||
|
@ -169,10 +181,6 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
boolean englishNameMatched = false;
|
boolean englishNameMatched = false;
|
||||||
switch (tag) {
|
switch (tag) {
|
||||||
case 0:
|
case 0:
|
||||||
c.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x));
|
|
||||||
if(c.getEnName().length() == 0){
|
|
||||||
c.setEnName(Junidecode.unidecode(c.getName()));
|
|
||||||
}
|
|
||||||
return c;
|
return c;
|
||||||
case OsmandOdb.CityIndex.CITY_TYPE_FIELD_NUMBER :
|
case OsmandOdb.CityIndex.CITY_TYPE_FIELD_NUMBER :
|
||||||
int type = codedIS.readUInt32();
|
int type = codedIS.readUInt32();
|
||||||
|
@ -221,6 +229,15 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
break;
|
break;
|
||||||
case OsmandOdb.CityIndex.Y_FIELD_NUMBER :
|
case OsmandOdb.CityIndex.Y_FIELD_NUMBER :
|
||||||
y = codedIS.readFixed32();
|
y = codedIS.readFixed32();
|
||||||
|
c.setLocation(MapUtils.get31LatitudeY(y), MapUtils.get31LongitudeX(x));
|
||||||
|
if(c.getEnName().length() == 0){
|
||||||
|
c.setEnName(Junidecode.unidecode(c.getName()));
|
||||||
|
}
|
||||||
|
if(!loadStreets){
|
||||||
|
// skip everything
|
||||||
|
codedIS.skipRawBytes(codedIS.getBytesUntilLimit());
|
||||||
|
return c;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case OsmandOdb.CityIndex.INTERSECTIONS_FIELD_NUMBER :
|
case OsmandOdb.CityIndex.INTERSECTIONS_FIELD_NUMBER :
|
||||||
codedIS.skipRawBytes(codedIS.readRawVarint32());
|
codedIS.skipRawBytes(codedIS.readRawVarint32());
|
||||||
|
@ -233,8 +250,10 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
int oldLimit = codedIS.pushLimit(length);
|
int oldLimit = codedIS.pushLimit(length);
|
||||||
s.setFileOffset(offset);
|
s.setFileOffset(offset);
|
||||||
s.setIndexInCity(streetInd++);
|
s.setIndexInCity(streetInd++);
|
||||||
readStreet(s, false, x >> 7, y >> 7, null);
|
readStreet(s, null, false, x >> 7, y >> 7, null);
|
||||||
|
if (resultMatcher == null || resultMatcher.publish(s)) {
|
||||||
c.registerStreet(s);
|
c.registerStreet(s);
|
||||||
|
}
|
||||||
codedIS.popLimit(oldLimit);
|
codedIS.popLimit(oldLimit);
|
||||||
} else {
|
} else {
|
||||||
codedIS.skipRawBytes(length);
|
codedIS.skipRawBytes(length);
|
||||||
|
@ -247,7 +266,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected Street readStreet(Street s, boolean loadBuildings, int city24X, int city24Y, String postcodeFilter) throws IOException{
|
protected Street readStreet(Street s, ResultMatcher<Building> resultMatcher, boolean loadBuildings, int city24X, int city24Y, String postcodeFilter) throws IOException{
|
||||||
int x = 0;
|
int x = 0;
|
||||||
int y = 0;
|
int y = 0;
|
||||||
boolean loadLocation = city24X != 0 || city24Y != 0;
|
boolean loadLocation = city24X != 0 || city24Y != 0;
|
||||||
|
@ -295,8 +314,10 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
int oldLimit = codedIS.pushLimit(length);
|
int oldLimit = codedIS.pushLimit(length);
|
||||||
Building b = readBuilding(offset, x, y);
|
Building b = readBuilding(offset, x, y);
|
||||||
if (postcodeFilter == null || postcodeFilter.equalsIgnoreCase(b.getPostcode())) {
|
if (postcodeFilter == null || postcodeFilter.equalsIgnoreCase(b.getPostcode())) {
|
||||||
|
if (resultMatcher == null || resultMatcher.publish(b)) {
|
||||||
s.registerBuilding(b);
|
s.registerBuilding(b);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
codedIS.popLimit(oldLimit);
|
codedIS.popLimit(oldLimit);
|
||||||
} else {
|
} else {
|
||||||
codedIS.skipRawBytes(length);
|
codedIS.skipRawBytes(length);
|
||||||
|
@ -453,7 +474,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void readPostcodes(List<PostCode> postcodes, StringMatcher nameMatcher) throws IOException{
|
protected void readPostcodes(List<PostCode> postcodes, ResultMatcher<MapObject> resultMatcher, StringMatcher nameMatcher) throws IOException{
|
||||||
while(true){
|
while(true){
|
||||||
int t = codedIS.readTag();
|
int t = codedIS.readTag();
|
||||||
int tag = WireFormat.getTagFieldNumber(t);
|
int tag = WireFormat.getTagFieldNumber(t);
|
||||||
|
@ -464,11 +485,13 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
int offset = codedIS.getTotalBytesRead();
|
int offset = codedIS.getTotalBytesRead();
|
||||||
int length = codedIS.readRawVarint32();
|
int length = codedIS.readRawVarint32();
|
||||||
int oldLimit = codedIS.pushLimit(length);
|
int oldLimit = codedIS.pushLimit(length);
|
||||||
final PostCode postCode = readPostcode(null, offset, false, null);
|
final PostCode postCode = readPostcode(null, offset, null, false, null);
|
||||||
//TODO support getEnName??
|
// support getEnName??
|
||||||
if (nameMatcher == null || nameMatcher.matches(postCode.getName())) {
|
if (nameMatcher == null || nameMatcher.matches(postCode.getName())) {
|
||||||
|
if (resultMatcher == null || resultMatcher.publish(postCode)) {
|
||||||
postcodes.add(postCode);
|
postcodes.add(postCode);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
codedIS.popLimit(oldLimit);
|
codedIS.popLimit(oldLimit);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
@ -478,7 +501,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PostCode findPostcode(String name) throws IOException{
|
protected PostCode findPostcode(String name) throws IOException{
|
||||||
while(true){
|
while(true){
|
||||||
int t = codedIS.readTag();
|
int t = codedIS.readTag();
|
||||||
int tag = WireFormat.getTagFieldNumber(t);
|
int tag = WireFormat.getTagFieldNumber(t);
|
||||||
|
@ -489,7 +512,7 @@ public class BinaryMapAddressReaderAdapter {
|
||||||
int offset = codedIS.getTotalBytesRead();
|
int offset = codedIS.getTotalBytesRead();
|
||||||
int length = codedIS.readRawVarint32();
|
int length = codedIS.readRawVarint32();
|
||||||
int oldLimit = codedIS.pushLimit(length);
|
int oldLimit = codedIS.pushLimit(length);
|
||||||
PostCode p = readPostcode(null, offset, true, name);
|
PostCode p = readPostcode(null, offset, null, false, name);
|
||||||
codedIS.popLimit(oldLimit);
|
codedIS.popLimit(oldLimit);
|
||||||
if(p != null){
|
if(p != null){
|
||||||
return p;
|
return p;
|
||||||
|
|
|
@ -15,10 +15,13 @@ import java.util.Map;
|
||||||
|
|
||||||
import net.osmand.Algoritms;
|
import net.osmand.Algoritms;
|
||||||
import net.osmand.LogUtil;
|
import net.osmand.LogUtil;
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.StringMatcher;
|
import net.osmand.StringMatcher;
|
||||||
import net.osmand.binary.BinaryMapAddressReaderAdapter.AddressRegion;
|
import net.osmand.binary.BinaryMapAddressReaderAdapter.AddressRegion;
|
||||||
import net.osmand.binary.BinaryMapTransportReaderAdapter.TransportIndex;
|
import net.osmand.binary.BinaryMapTransportReaderAdapter.TransportIndex;
|
||||||
|
import net.osmand.data.Building;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
|
import net.osmand.data.MapObject;
|
||||||
import net.osmand.data.PostCode;
|
import net.osmand.data.PostCode;
|
||||||
import net.osmand.data.Street;
|
import net.osmand.data.Street;
|
||||||
import net.osmand.data.TransportStop;
|
import net.osmand.data.TransportStop;
|
||||||
|
@ -327,14 +330,14 @@ public class BinaryMapIndexReader {
|
||||||
throw new IllegalArgumentException(name);
|
throw new IllegalArgumentException(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<PostCode> getPostcodes(String region, StringMatcher nameMatcher) throws IOException {
|
public List<PostCode> getPostcodes(String region, ResultMatcher<MapObject> resultMatcher, StringMatcher nameMatcher) throws IOException {
|
||||||
List<PostCode> postcodes = new ArrayList<PostCode>();
|
List<PostCode> postcodes = new ArrayList<PostCode>();
|
||||||
AddressRegion r = getRegionByName(region);
|
AddressRegion r = getRegionByName(region);
|
||||||
if(r.postcodesOffset != -1){
|
if(r.postcodesOffset != -1){
|
||||||
codedIS.seek(r.postcodesOffset);
|
codedIS.seek(r.postcodesOffset);
|
||||||
int len = readInt();
|
int len = readInt();
|
||||||
int old = codedIS.pushLimit(len);
|
int old = codedIS.pushLimit(len);
|
||||||
addressAdapter.readPostcodes(postcodes,nameMatcher);
|
addressAdapter.readPostcodes(postcodes, resultMatcher, nameMatcher);
|
||||||
codedIS.popLimit(old);
|
codedIS.popLimit(old);
|
||||||
}
|
}
|
||||||
return postcodes;
|
return postcodes;
|
||||||
|
@ -355,42 +358,39 @@ public class BinaryMapIndexReader {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<City> getCities(String region) throws IOException {
|
public List<City> getCities(String region, ResultMatcher<MapObject> resultMatcher) throws IOException {
|
||||||
List<City> cities = new ArrayList<City>();
|
List<City> cities = new ArrayList<City>();
|
||||||
AddressRegion r = getRegionByName(region);
|
AddressRegion r = getRegionByName(region);
|
||||||
if(r.citiesOffset != -1){
|
if(r.citiesOffset != -1){
|
||||||
codedIS.seek(r.citiesOffset);
|
codedIS.seek(r.citiesOffset);
|
||||||
int len = readInt();
|
int len = readInt();
|
||||||
int old = codedIS.pushLimit(len);
|
int old = codedIS.pushLimit(len);
|
||||||
addressAdapter.readCities(cities, null, false);
|
addressAdapter.readCities(cities, resultMatcher, null, false);
|
||||||
codedIS.popLimit(old);
|
codedIS.popLimit(old);
|
||||||
}
|
}
|
||||||
return cities;
|
return cities;
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<City> getVillages(String region) throws IOException {
|
public List<City> getVillages(String region, ResultMatcher<MapObject> resultMatcher, StringMatcher nameMatcher, boolean useEn) throws IOException {
|
||||||
return getVillages(region, null, false);
|
|
||||||
}
|
|
||||||
public List<City> getVillages(String region, StringMatcher nameMatcher, boolean useEn) throws IOException {
|
|
||||||
List<City> cities = new ArrayList<City>();
|
List<City> cities = new ArrayList<City>();
|
||||||
AddressRegion r = getRegionByName(region);
|
AddressRegion r = getRegionByName(region);
|
||||||
if(r.villagesOffset != -1){
|
if(r.villagesOffset != -1){
|
||||||
codedIS.seek(r.villagesOffset);
|
codedIS.seek(r.villagesOffset);
|
||||||
int len = readInt();
|
int len = readInt();
|
||||||
int old = codedIS.pushLimit(len);
|
int old = codedIS.pushLimit(len);
|
||||||
addressAdapter.readCities(cities, nameMatcher, useEn);
|
addressAdapter.readCities(cities, resultMatcher, nameMatcher, useEn);
|
||||||
codedIS.popLimit(old);
|
codedIS.popLimit(old);
|
||||||
}
|
}
|
||||||
return cities;
|
return cities;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void preloadStreets(City c) throws IOException {
|
public void preloadStreets(City c, ResultMatcher<Street> resultMatcher) throws IOException {
|
||||||
checkAddressIndex(c.getFileOffset());
|
checkAddressIndex(c.getFileOffset());
|
||||||
codedIS.seek(c.getFileOffset());
|
codedIS.seek(c.getFileOffset());
|
||||||
int size = codedIS.readRawVarint32();
|
int size = codedIS.readRawVarint32();
|
||||||
int old = codedIS.pushLimit(size);
|
int old = codedIS.pushLimit(size);
|
||||||
addressAdapter.readCity(c, c.getFileOffset(), true, null, false);
|
addressAdapter.readCity(c, c.getFileOffset(), true, resultMatcher, null, false);
|
||||||
codedIS.popLimit(old);
|
codedIS.popLimit(old);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -406,13 +406,13 @@ public class BinaryMapIndexReader {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void preloadStreets(PostCode p) throws IOException {
|
public void preloadStreets(PostCode p, ResultMatcher<Street> resultMatcher) throws IOException {
|
||||||
checkAddressIndex(p.getFileOffset());
|
checkAddressIndex(p.getFileOffset());
|
||||||
|
|
||||||
codedIS.seek(p.getFileOffset());
|
codedIS.seek(p.getFileOffset());
|
||||||
int size = codedIS.readRawVarint32();
|
int size = codedIS.readRawVarint32();
|
||||||
int old = codedIS.pushLimit(size);
|
int old = codedIS.pushLimit(size);
|
||||||
addressAdapter.readPostcode(p, p.getFileOffset(), true, null);
|
addressAdapter.readPostcode(p, p.getFileOffset(), null, true, null);
|
||||||
codedIS.popLimit(old);
|
codedIS.popLimit(old);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -429,12 +429,12 @@ public class BinaryMapIndexReader {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void preloadBuildings(Street s) throws IOException {
|
public void preloadBuildings(Street s, ResultMatcher<Building> resultMatcher) throws IOException {
|
||||||
checkAddressIndex(s.getFileOffset());
|
checkAddressIndex(s.getFileOffset());
|
||||||
codedIS.seek(s.getFileOffset());
|
codedIS.seek(s.getFileOffset());
|
||||||
int size = codedIS.readRawVarint32();
|
int size = codedIS.readRawVarint32();
|
||||||
int old = codedIS.pushLimit(size);
|
int old = codedIS.pushLimit(size);
|
||||||
addressAdapter.readStreet(s, true, 0, 0, null);
|
addressAdapter.readStreet(s, resultMatcher, true, 0, 0, null);
|
||||||
codedIS.popLimit(old);
|
codedIS.popLimit(old);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1138,7 +1138,7 @@ public class BinaryMapIndexReader {
|
||||||
|
|
||||||
// test address index search
|
// test address index search
|
||||||
String reg = reader.getRegionNames().get(0);
|
String reg = reader.getRegionNames().get(0);
|
||||||
List<City> cs = reader.getCities(reg);
|
List<City> cs = reader.getCities(reg, null);
|
||||||
for(City c : cs){
|
for(City c : cs){
|
||||||
int buildings = 0;
|
int buildings = 0;
|
||||||
// reader.preloadStreets(c);
|
// reader.preloadStreets(c);
|
||||||
|
|
|
@ -4,6 +4,7 @@ import java.text.Collator;
|
||||||
import java.util.Comparator;
|
import java.util.Comparator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.data.Building;
|
import net.osmand.data.Building;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
import net.osmand.data.MapObject;
|
import net.osmand.data.MapObject;
|
||||||
|
@ -60,13 +61,13 @@ public interface RegionAddressRepository {
|
||||||
|
|
||||||
public void setUseEnglishNames(boolean useEnglishNames);
|
public void setUseEnglishNames(boolean useEnglishNames);
|
||||||
|
|
||||||
public void fillWithSuggestedBuildings(PostCode postcode, Street street, String name, List<Building> buildingsToFill);
|
public List<Building> fillWithSuggestedBuildings(PostCode postcode, Street street, String name, ResultMatcher<Building> resultMatcher) ;
|
||||||
|
|
||||||
public void fillWithSuggestedStreetsIntersectStreets(City city, Street st, List<Street> streetsToFill);
|
public void fillWithSuggestedStreetsIntersectStreets(City city, Street st, List<Street> streetsToFill);
|
||||||
|
|
||||||
public void fillWithSuggestedStreets(MapObject cityOrPostcode, List<Street> streetsToFill, String... name);
|
public List<Street> fillWithSuggestedStreets(MapObject o, ResultMatcher<Street> resultMatcher, String... names);
|
||||||
|
|
||||||
public void fillWithSuggestedCities(String name, List<MapObject> citiesToFill, LatLon currentLocation);
|
public List<MapObject> fillWithSuggestedCities(String name, ResultMatcher<MapObject> resultMatcher, LatLon currentLocation);
|
||||||
|
|
||||||
public LatLon findStreetIntersection(Street street, Street street2);
|
public LatLon findStreetIntersection(Street street, Street street2);
|
||||||
|
|
||||||
|
@ -80,8 +81,6 @@ public interface RegionAddressRepository {
|
||||||
public LatLon getEstimatedRegionCenter();
|
public LatLon getEstimatedRegionCenter();
|
||||||
|
|
||||||
|
|
||||||
public boolean isMapRepository();
|
|
||||||
|
|
||||||
// is called on low memory
|
// is called on low memory
|
||||||
public void clearCache();
|
public void clearCache();
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,9 @@ import static net.osmand.plus.CollatorStringMatcher.cstartsWith;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.text.Collator;
|
import java.text.Collator;
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
|
import java.util.Iterator;
|
||||||
import java.util.LinkedHashMap;
|
import java.util.LinkedHashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
@ -13,6 +15,7 @@ import java.util.TreeMap;
|
||||||
|
|
||||||
import net.osmand.Algoritms;
|
import net.osmand.Algoritms;
|
||||||
import net.osmand.LogUtil;
|
import net.osmand.LogUtil;
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.binary.BinaryMapIndexReader;
|
import net.osmand.binary.BinaryMapIndexReader;
|
||||||
import net.osmand.data.Building;
|
import net.osmand.data.Building;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
|
@ -47,18 +50,16 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
this.file = null;
|
this.file = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean isMapRepository() {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void fillWithSuggestedBuildings(PostCode postcode, Street street, String name, List<Building> buildingsToFill) {
|
public List<Building> fillWithSuggestedBuildings(PostCode postcode, Street street, String name, ResultMatcher<Building> resultMatcher) {
|
||||||
preloadBuildings(street);
|
List<Building> buildingsToFill = new ArrayList<Building>();
|
||||||
if(name.length() == 0){
|
if (name.length() == 0) {
|
||||||
|
preloadBuildings(street, resultMatcher);
|
||||||
buildingsToFill.addAll(street.getBuildings());
|
buildingsToFill.addAll(street.getBuildings());
|
||||||
return;
|
return buildingsToFill;
|
||||||
}
|
}
|
||||||
|
preloadBuildings(street, null);
|
||||||
name = name.toLowerCase();
|
name = name.toLowerCase();
|
||||||
int ind = 0;
|
int ind = 0;
|
||||||
for (Building building : street.getBuildings()) {
|
for (Building building : street.getBuildings()) {
|
||||||
|
@ -70,13 +71,14 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
buildingsToFill.add(building);
|
buildingsToFill.add(building);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return buildingsToFill;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void preloadBuildings(Street street) {
|
private void preloadBuildings(Street street, ResultMatcher<Building> resultMatcher) {
|
||||||
if(street.getBuildings().isEmpty()){
|
if(street.getBuildings().isEmpty()){
|
||||||
try {
|
try {
|
||||||
file.preloadBuildings(street);
|
file.preloadBuildings(street, resultMatcher);
|
||||||
street.sortBuildings();
|
street.sortBuildings();
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
log.error("Disk operation failed" , e); //$NON-NLS-1$
|
log.error("Disk operation failed" , e); //$NON-NLS-1$
|
||||||
|
@ -86,33 +88,36 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void fillWithSuggestedStreets(MapObject o, List<Street> streetsToFill, String... names) {
|
public List<Street> fillWithSuggestedStreets(MapObject o, ResultMatcher<Street> resultMatcher, String... names) {
|
||||||
assert o instanceof PostCode || o instanceof City;
|
assert o instanceof PostCode || o instanceof City;
|
||||||
City city = (City) (o instanceof City ? o : null);
|
City city = (City) (o instanceof City ? o : null);
|
||||||
PostCode post = (PostCode) (o instanceof PostCode ? o : null);
|
PostCode post = (PostCode) (o instanceof PostCode ? o : null);
|
||||||
preloadStreets(o);
|
List<Street> streetsToFill = new ArrayList<Street>();
|
||||||
Collection<Street> streets = post == null ? city.getStreets() : post.getStreets() ;
|
|
||||||
|
|
||||||
if(names.length == 0){
|
if(names.length == 0){
|
||||||
streetsToFill.addAll(streets);
|
preloadStreets(o, resultMatcher);
|
||||||
return;
|
streetsToFill.addAll(post == null ? city.getStreets() : post.getStreets());
|
||||||
|
return streetsToFill;
|
||||||
}
|
}
|
||||||
|
preloadStreets(o, null);
|
||||||
int ind = 0;
|
int ind = 0;
|
||||||
for (Street s : streets) {
|
Collection<Street> streets = post == null ? city.getStreets() : post.getStreets() ;
|
||||||
String sName = useEnglishNames ? s.getEnName() : s.getName(); //lower case not needed, collator ensures that
|
Iterator<Street> iterator = streets.iterator();
|
||||||
|
while(iterator.hasNext()) {
|
||||||
|
Street s = iterator.next();
|
||||||
|
String sName = useEnglishNames ? s.getEnName() : s.getName(); // lower case not needed, collator ensures that
|
||||||
for (String name : names) {
|
for (String name : names) {
|
||||||
if (cstartsWith(collator,sName,name)) {
|
if (cstartsWith(collator, sName, name)) {
|
||||||
streetsToFill.add(ind, s);
|
streetsToFill.add(ind, s);
|
||||||
ind++;
|
ind++;
|
||||||
} else if (ccontains(collator,name,sName) || ccontains(collator,sName,name)) {
|
} else if (ccontains(collator, name, sName) || ccontains(collator, sName, name)) {
|
||||||
streetsToFill.add(s);
|
streetsToFill.add(s);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return streetsToFill;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void preloadStreets(MapObject o) {
|
private void preloadStreets(MapObject o, ResultMatcher<Street> resultMatcher) {
|
||||||
assert o instanceof PostCode || o instanceof City;
|
assert o instanceof PostCode || o instanceof City;
|
||||||
Collection<Street> streets = o instanceof PostCode ? ((PostCode) o).getStreets() : ((City) o).getStreets();
|
Collection<Street> streets = o instanceof PostCode ? ((PostCode) o).getStreets() : ((City) o).getStreets();
|
||||||
if(!streets.isEmpty()){
|
if(!streets.isEmpty()){
|
||||||
|
@ -120,9 +125,9 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(o instanceof PostCode){
|
if(o instanceof PostCode){
|
||||||
file.preloadStreets((PostCode) o);
|
file.preloadStreets((PostCode) o, resultMatcher);
|
||||||
} else {
|
} else {
|
||||||
file.preloadStreets((City) o);
|
file.preloadStreets((City) o, resultMatcher);
|
||||||
}
|
}
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
log.error("Disk operation failed" , e); //$NON-NLS-1$
|
log.error("Disk operation failed" , e); //$NON-NLS-1$
|
||||||
|
@ -132,18 +137,25 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void fillWithSuggestedCities(String name, List<MapObject> citiesToFill, LatLon currentLocation) {
|
public List<MapObject> fillWithSuggestedCities(String name, ResultMatcher<MapObject> resultMatcher, LatLon currentLocation) {
|
||||||
preloadCities();
|
List<MapObject> citiesToFill = new ArrayList<MapObject>();
|
||||||
|
if (cities.isEmpty()) {
|
||||||
|
preloadCities(resultMatcher);
|
||||||
|
citiesToFill.addAll(cities.values());
|
||||||
|
return citiesToFill;
|
||||||
|
} else {
|
||||||
|
preloadCities(null);
|
||||||
|
}
|
||||||
try {
|
try {
|
||||||
// essentially index is created that cities towns are first in cities map
|
// essentially index is created that cities towns are first in cities map
|
||||||
int ind = 0;
|
int ind = 0;
|
||||||
if (name.length() >= 2 && Algoritms.containsDigit(name)) {
|
if (name.length() >= 2 && Algoritms.containsDigit(name)) {
|
||||||
// also try to identify postcodes
|
// also try to identify postcodes
|
||||||
String uName = name.toUpperCase();
|
String uName = name.toUpperCase();
|
||||||
for (PostCode code : file.getPostcodes(region,new ContainsStringMatcher(uName,collator))) {
|
for (PostCode code : file.getPostcodes(region, resultMatcher, new ContainsStringMatcher(uName, collator))) {
|
||||||
if (cstartsWith(collator,code.getName(),uName)) {
|
if (cstartsWith(collator, code.getName(), uName)) {
|
||||||
citiesToFill.add(ind++, code);
|
citiesToFill.add(ind++, code);
|
||||||
} else if(ccontains(collator,code.getName(),uName)){
|
} else if (ccontains(collator, code.getName(), uName)) {
|
||||||
citiesToFill.add(code);
|
citiesToFill.add(code);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -156,26 +168,32 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
name = name.toLowerCase();
|
name = name.toLowerCase();
|
||||||
for (City c : cities.values()) {
|
for (City c : cities.values()) {
|
||||||
String cName = useEnglishNames ? c.getEnName() : c.getName(); //lower case not needed, collator ensures that
|
String cName = useEnglishNames ? c.getEnName() : c.getName(); //lower case not needed, collator ensures that
|
||||||
if (cstartsWith(collator,cName,name)) {
|
if (cstartsWith(collator, cName, name)) {
|
||||||
|
if (resultMatcher.publish(c)) {
|
||||||
citiesToFill.add(c);
|
citiesToFill.add(c);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
name = name.toLowerCase();
|
name = name.toLowerCase();
|
||||||
Collection<City> src = cities.values();
|
for (City c : cities.values()) {
|
||||||
for (City c : src) {
|
|
||||||
String cName = useEnglishNames ? c.getEnName() : c.getName(); //lower case not needed, collator ensures that
|
String cName = useEnglishNames ? c.getEnName() : c.getName(); //lower case not needed, collator ensures that
|
||||||
if (cstartsWith(collator,cName,name)) {
|
if (cstartsWith(collator,cName,name)) {
|
||||||
|
if (resultMatcher.publish(c)) {
|
||||||
citiesToFill.add(ind, c);
|
citiesToFill.add(ind, c);
|
||||||
ind++;
|
ind++;
|
||||||
|
}
|
||||||
} else if (ccontains(collator,name,cName)) {
|
} else if (ccontains(collator,name,cName)) {
|
||||||
|
if (resultMatcher.publish(c)) {
|
||||||
citiesToFill.add(c);
|
citiesToFill.add(c);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int initialsize = citiesToFill.size();
|
int initialsize = citiesToFill.size();
|
||||||
|
|
||||||
for(City c : file.getVillages(region, new ContainsStringMatcher(name,collator), useEnglishNames )){
|
for(City c : file.getVillages(region, resultMatcher, new ContainsStringMatcher(name,collator), useEnglishNames )){
|
||||||
String cName = c.getName(useEnglishNames); //lower case not needed, collator ensures that
|
String cName = c.getName(useEnglishNames); //lower case not needed, collator ensures that
|
||||||
if (cstartsWith(collator,cName,name)) {
|
if (cstartsWith(collator,cName,name)) {
|
||||||
citiesToFill.add(ind, c);
|
citiesToFill.add(ind, c);
|
||||||
|
@ -189,13 +207,14 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
log.error("Disk operation failed" , e); //$NON-NLS-1$
|
log.error("Disk operation failed" , e); //$NON-NLS-1$
|
||||||
}
|
}
|
||||||
|
return citiesToFill;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void fillWithSuggestedStreetsIntersectStreets(City city, Street st, List<Street> streetsToFill) {
|
public void fillWithSuggestedStreetsIntersectStreets(City city, Street st, List<Street> streetsToFill) {
|
||||||
if(city != null){
|
if(city != null){
|
||||||
preloadStreets(city);
|
preloadStreets(city, null);
|
||||||
try {
|
try {
|
||||||
file.findIntersectedStreets(city, st, streetsToFill);
|
file.findIntersectedStreets(city, st, streetsToFill);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
|
@ -208,7 +227,7 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
public LatLon findStreetIntersection(Street street, Street street2) {
|
public LatLon findStreetIntersection(Street street, Street street2) {
|
||||||
City city = street.getCity();
|
City city = street.getCity();
|
||||||
if(city != null){
|
if(city != null){
|
||||||
preloadStreets(city);
|
preloadStreets(city, null);
|
||||||
try {
|
try {
|
||||||
return file.findStreetIntersection(city, street, street2);
|
return file.findStreetIntersection(city, street, street2);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
|
@ -221,7 +240,7 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Building getBuildingByName(Street street, String name) {
|
public Building getBuildingByName(Street street, String name) {
|
||||||
preloadBuildings(street);
|
preloadBuildings(street, null);
|
||||||
for (Building b : street.getBuildings()) {
|
for (Building b : street.getBuildings()) {
|
||||||
String bName = useEnglishNames ? b.getEnName() : b.getName();
|
String bName = useEnglishNames ? b.getEnName() : b.getName();
|
||||||
if (bName.equals(name)) {
|
if (bName.equals(name)) {
|
||||||
|
@ -249,15 +268,15 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
// do not preload cities for that case
|
// do not preload cities for that case
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
preloadCities();
|
preloadCities(null);
|
||||||
return cities.get(id);
|
return cities.get(id);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void preloadCities() {
|
private void preloadCities(ResultMatcher<MapObject> resultMatcher) {
|
||||||
if (cities.isEmpty()) {
|
if (cities.isEmpty()) {
|
||||||
try {
|
try {
|
||||||
List<City> cs = file.getCities(region);
|
List<City> cs = file.getCities(region, resultMatcher);
|
||||||
for (City c : cs) {
|
for (City c : cs) {
|
||||||
cities.put(c.getId(), c);
|
cities.put(c.getId(), c);
|
||||||
}
|
}
|
||||||
|
@ -290,7 +309,7 @@ public class RegionAddressRepositoryBinary implements RegionAddressRepository {
|
||||||
City city = (City) (o instanceof City ? o : null);
|
City city = (City) (o instanceof City ? o : null);
|
||||||
PostCode post = (PostCode) (o instanceof PostCode ? o : null);
|
PostCode post = (PostCode) (o instanceof PostCode ? o : null);
|
||||||
name = name.toLowerCase();
|
name = name.toLowerCase();
|
||||||
preloadStreets(o);
|
preloadStreets(o, null);
|
||||||
Collection<Street> streets = post == null ? city.getStreets() : post.getStreets();
|
Collection<Street> streets = post == null ? city.getStreets() : post.getStreets();
|
||||||
for (Street s : streets) {
|
for (Street s : streets) {
|
||||||
String sName = useEnglishNames ? s.getEnName() : s.getName(); //lower case not needed, collator ensures that
|
String sName = useEnglishNames ? s.getEnName() : s.getName(); //lower case not needed, collator ensures that
|
||||||
|
|
|
@ -232,7 +232,7 @@ public class GeoIntentActivity extends ListActivity {
|
||||||
for (RegionAddressRepository rar : countriesToSearch) {
|
for (RegionAddressRepository rar : countriesToSearch) {
|
||||||
List<MapObject> citiesFound = new ArrayList<MapObject>();
|
List<MapObject> citiesFound = new ArrayList<MapObject>();
|
||||||
for (String maybeCity : elements) {
|
for (String maybeCity : elements) {
|
||||||
rar.fillWithSuggestedCities(maybeCity, citiesFound, null);
|
citiesFound.addAll(rar.fillWithSuggestedCities(maybeCity, null, null));
|
||||||
}
|
}
|
||||||
if (!citiesFound.isEmpty()) {
|
if (!citiesFound.isEmpty()) {
|
||||||
citiesForRegion.put(rar, citiesFound);
|
citiesForRegion.put(rar, citiesFound);
|
||||||
|
@ -242,8 +242,7 @@ public class GeoIntentActivity extends ListActivity {
|
||||||
Map<MapObject, List<Street>> streetsForCity = new HashMap<MapObject, List<Street>>();
|
Map<MapObject, List<Street>> streetsForCity = new HashMap<MapObject, List<Street>>();
|
||||||
if (citiesForRegion.isEmpty()) {
|
if (citiesForRegion.isEmpty()) {
|
||||||
for (RegionAddressRepository rar : countriesToSearch) {
|
for (RegionAddressRepository rar : countriesToSearch) {
|
||||||
ArrayList<MapObject> allcities = new ArrayList<MapObject>();
|
List<MapObject> allcities = rar.fillWithSuggestedCities("", null, location);
|
||||||
rar.fillWithSuggestedCities("", allcities, location);
|
|
||||||
findStreetsForCities(streetsForCity, rar, allcities);
|
findStreetsForCities(streetsForCity, rar, allcities);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -273,8 +272,7 @@ public class GeoIntentActivity extends ListActivity {
|
||||||
Map<MapObject, List<Street>> streetsForCity,
|
Map<MapObject, List<Street>> streetsForCity,
|
||||||
RegionAddressRepository rar, List<MapObject> allcities) {
|
RegionAddressRepository rar, List<MapObject> allcities) {
|
||||||
for (MapObject city : allcities) {
|
for (MapObject city : allcities) {
|
||||||
List<Street> streets = new ArrayList<Street>();
|
List<Street> streets = rar.fillWithSuggestedStreets(city, null,
|
||||||
rar.fillWithSuggestedStreets(city, streets,
|
|
||||||
elements.toArray(new String[] {}));
|
elements.toArray(new String[] {}));
|
||||||
// we must do this, or we will fill up the whole memory (streets
|
// we must do this, or we will fill up the whole memory (streets
|
||||||
// are preloaded...)
|
// are preloaded...)
|
||||||
|
|
|
@ -7,7 +7,9 @@ import net.osmand.Algoritms;
|
||||||
import net.osmand.osm.LatLon;
|
import net.osmand.osm.LatLon;
|
||||||
import net.osmand.plus.OsmandSettings;
|
import net.osmand.plus.OsmandSettings;
|
||||||
import net.osmand.plus.R;
|
import net.osmand.plus.R;
|
||||||
|
import net.osmand.plus.RegionAddressRepository;
|
||||||
import net.osmand.plus.activities.MapActivity;
|
import net.osmand.plus.activities.MapActivity;
|
||||||
|
import net.osmand.plus.activities.OsmandApplication;
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
|
@ -319,6 +321,10 @@ public class SearchAddressActivity extends Activity {
|
||||||
street = null;
|
street = null;
|
||||||
building = null;
|
building = null;
|
||||||
region = osmandSettings.getLastSearchedRegion();
|
region = osmandSettings.getLastSearchedRegion();
|
||||||
|
RegionAddressRepository reg = ((OsmandApplication)getApplication()).getResourceManager().getRegionRepository(region);
|
||||||
|
if(reg.useEnglishNames() != osmandSettings.USE_ENGLISH_NAMES.get()){
|
||||||
|
reg.setUseEnglishNames(osmandSettings.USE_ENGLISH_NAMES.get());
|
||||||
|
}
|
||||||
loadData();
|
loadData();
|
||||||
updateUI();
|
updateUI();
|
||||||
|
|
||||||
|
|
|
@ -3,11 +3,11 @@ package net.osmand.plus.activities.search;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.data.Building;
|
import net.osmand.data.Building;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
import net.osmand.data.PostCode;
|
import net.osmand.data.PostCode;
|
||||||
import net.osmand.data.Street;
|
import net.osmand.data.Street;
|
||||||
import net.osmand.plus.OsmandSettings;
|
|
||||||
import net.osmand.plus.R;
|
import net.osmand.plus.R;
|
||||||
import net.osmand.plus.RegionAddressRepository;
|
import net.osmand.plus.RegionAddressRepository;
|
||||||
import net.osmand.plus.activities.OsmandApplication;
|
import net.osmand.plus.activities.OsmandApplication;
|
||||||
|
@ -38,7 +38,6 @@ public class SearchBuildingByNameActivity extends SearchByNameAbstractActivity<B
|
||||||
}
|
}
|
||||||
@Override
|
@Override
|
||||||
protected Void doInBackground(Object... params) {
|
protected Void doInBackground(Object... params) {
|
||||||
region = ((OsmandApplication)getApplication()).getResourceManager().getRegionRepository(settings.getLastSearchedRegion());
|
|
||||||
if(region != null){
|
if(region != null){
|
||||||
postcode = region.getPostcode(settings.getLastSearchedPostcode());
|
postcode = region.getPostcode(settings.getLastSearchedPostcode());
|
||||||
city = region.getCityById(settings.getLastSearchedCity());
|
city = region.getCityById(settings.getLastSearchedCity());
|
||||||
|
@ -55,12 +54,17 @@ public class SearchBuildingByNameActivity extends SearchByNameAbstractActivity<B
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Building> getObjects(String filter) {
|
public List<Building> getObjects(String filter, final SearchByNameTask task) {
|
||||||
List<Building> l = new ArrayList<Building>();
|
|
||||||
if(street != null){
|
if(street != null){
|
||||||
region.fillWithSuggestedBuildings(postcode, street, filter, l);
|
return region.fillWithSuggestedBuildings(postcode, street, filter, new ResultMatcher<Building>() {
|
||||||
|
@Override
|
||||||
|
public boolean publish(Building object) {
|
||||||
|
task.progress(object);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
return l;
|
});
|
||||||
|
}
|
||||||
|
return new ArrayList<Building>();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package net.osmand.plus.activities.search;
|
package net.osmand.plus.activities.search;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import net.osmand.osm.LatLon;
|
import net.osmand.osm.LatLon;
|
||||||
|
@ -9,9 +10,6 @@ import android.app.ListActivity;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.os.AsyncTask;
|
import android.os.AsyncTask;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.os.Handler;
|
|
||||||
import android.os.Looper;
|
|
||||||
import android.os.Message;
|
|
||||||
import android.os.AsyncTask.Status;
|
import android.os.AsyncTask.Status;
|
||||||
import android.text.Editable;
|
import android.text.Editable;
|
||||||
import android.text.TextWatcher;
|
import android.text.TextWatcher;
|
||||||
|
@ -30,8 +28,8 @@ import android.widget.TextView;
|
||||||
public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
||||||
|
|
||||||
private EditText searchText;
|
private EditText searchText;
|
||||||
private Handler handlerToLoop;
|
|
||||||
private AsyncTask<Object, ?, ?> initializeTask;
|
private AsyncTask<Object, ?, ?> initializeTask;
|
||||||
|
protected SearchByNameTask searchTask = new SearchByNameTask();
|
||||||
|
|
||||||
protected ProgressBar progress;
|
protected ProgressBar progress;
|
||||||
protected LatLon locationToSearch;
|
protected LatLon locationToSearch;
|
||||||
|
@ -45,7 +43,7 @@ public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
||||||
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
||||||
|
|
||||||
setContentView(R.layout.search_by_name);
|
setContentView(R.layout.search_by_name);
|
||||||
NamesAdapter namesAdapter = new NamesAdapter(getObjects("")); //$NON-NLS-1$
|
NamesAdapter namesAdapter = new NamesAdapter(new ArrayList<T>()); //$NON-NLS-1$
|
||||||
setListAdapter(namesAdapter);
|
setListAdapter(namesAdapter);
|
||||||
progress = (ProgressBar) findViewById(R.id.ProgressBar);
|
progress = (ProgressBar) findViewById(R.id.ProgressBar);
|
||||||
searchText = (EditText) findViewById(R.id.SearchText);
|
searchText = (EditText) findViewById(R.id.SearchText);
|
||||||
|
@ -101,19 +99,6 @@ public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
||||||
setText("");
|
setText("");
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void updateUIList(final List<T> objects){
|
|
||||||
runOnUiThread(new Runnable(){
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
((NamesAdapter)getListAdapter()).setNotifyOnChange(false);
|
|
||||||
for(T o : objects){
|
|
||||||
((NamesAdapter)getListAdapter()).add(o);
|
|
||||||
}
|
|
||||||
((NamesAdapter)getListAdapter()).notifyDataSetChanged();
|
|
||||||
progress.setVisibility(View.INVISIBLE);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setText(final String filter) {
|
public void setText(final String filter) {
|
||||||
if(isFilterableByDefault()){
|
if(isFilterableByDefault()){
|
||||||
|
@ -121,38 +106,19 @@ public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
((NamesAdapter) getListAdapter()).clear();
|
((NamesAdapter) getListAdapter()).clear();
|
||||||
|
Status status = searchTask.getStatus();
|
||||||
if(handlerToLoop == null){
|
if(status == Status.FINISHED){
|
||||||
return;
|
searchTask = new SearchByNameTask();
|
||||||
|
} else if(status == Status.RUNNING){
|
||||||
|
searchTask.cancel(true);
|
||||||
|
// TODO improve
|
||||||
|
searchTask = new SearchByNameTask();
|
||||||
}
|
}
|
||||||
handlerToLoop.removeMessages(1);
|
searchTask.execute(filter);
|
||||||
Message msg = Message.obtain(handlerToLoop, new Runnable() {
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
showProgress(View.VISIBLE);
|
|
||||||
List<T> loadedObjects = getObjects(filter);
|
|
||||||
if(handlerToLoop != null && !handlerToLoop.hasMessages(1)){
|
|
||||||
updateUIList(loadedObjects);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
msg.what = 1;
|
|
||||||
handlerToLoop.sendMessageDelayed(msg, 150);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void showProgress(final int v){
|
|
||||||
runOnUiThread(new Runnable(){
|
|
||||||
|
|
||||||
@Override
|
public abstract List<T> getObjects(String filter, SearchByNameTask searchTask);
|
||||||
public void run() {
|
|
||||||
progress.setVisibility(v);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public abstract List<T> getObjects(String filter);
|
|
||||||
|
|
||||||
public abstract void updateTextView(T obj, TextView txt);
|
public abstract void updateTextView(T obj, TextView txt);
|
||||||
|
|
||||||
|
@ -168,19 +134,6 @@ public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
||||||
@Override
|
@Override
|
||||||
protected void onResume() {
|
protected void onResume() {
|
||||||
super.onResume();
|
super.onResume();
|
||||||
synchronized (this) {
|
|
||||||
if (handlerToLoop == null) {
|
|
||||||
new Thread("Filter data") { //$NON-NLS-1$
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
Looper.prepare();
|
|
||||||
handlerToLoop = new Handler();
|
|
||||||
Looper.loop();
|
|
||||||
}
|
|
||||||
}.start();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
Intent intent = getIntent();
|
Intent intent = getIntent();
|
||||||
if(intent != null){
|
if(intent != null){
|
||||||
if(intent.hasExtra(SearchActivity.SEARCH_LAT) && intent.hasExtra(SearchActivity.SEARCH_LON)){
|
if(intent.hasExtra(SearchActivity.SEARCH_LAT) && intent.hasExtra(SearchActivity.SEARCH_LON)){
|
||||||
|
@ -198,19 +151,53 @@ public abstract class SearchByNameAbstractActivity<T> extends ListActivity {
|
||||||
@Override
|
@Override
|
||||||
protected void onPause() {
|
protected void onPause() {
|
||||||
super.onPause();
|
super.onPause();
|
||||||
synchronized (this) {
|
searchTask.cancel(true);
|
||||||
if(handlerToLoop != null){
|
}
|
||||||
handlerToLoop.post(new Runnable(){
|
|
||||||
|
|
||||||
|
protected class SearchByNameTask extends AsyncTask<String, T, List<T>> {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
protected List<T> doInBackground(String... params) {
|
||||||
Looper.myLooper().quit();
|
if(params == null || params.length == 0){
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
});
|
String filter = params[0];
|
||||||
handlerToLoop = null;
|
return getObjects(filter, this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void progress(T... values){
|
||||||
|
publishProgress(values);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected void onProgressUpdate(T... values) {
|
||||||
|
for(T t :values){
|
||||||
|
((NamesAdapter) getListAdapter()).add(t);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onPreExecute() {
|
||||||
|
super.onPreExecute();
|
||||||
|
progress.setVisibility(View.VISIBLE);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onPostExecute(List<T> result) {
|
||||||
|
if (!isCancelled() && result != null) {
|
||||||
|
((NamesAdapter) getListAdapter()).setNotifyOnChange(false);
|
||||||
|
((NamesAdapter) getListAdapter()).clear();
|
||||||
|
for (T o : result) {
|
||||||
|
((NamesAdapter) getListAdapter()).add(o);
|
||||||
|
}
|
||||||
|
((NamesAdapter) getListAdapter()).notifyDataSetChanged();
|
||||||
|
}
|
||||||
|
if (!isCancelled()) {
|
||||||
|
progress.setVisibility(View.INVISIBLE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
class NamesAdapter extends ArrayAdapter<T> {
|
class NamesAdapter extends ArrayAdapter<T> {
|
||||||
NamesAdapter(List<T> list) {
|
NamesAdapter(List<T> list) {
|
||||||
|
|
|
@ -4,6 +4,7 @@ import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import net.osmand.OsmAndFormatter;
|
import net.osmand.OsmAndFormatter;
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
import net.osmand.data.MapObject;
|
import net.osmand.data.MapObject;
|
||||||
import net.osmand.data.PostCode;
|
import net.osmand.data.PostCode;
|
||||||
|
@ -13,6 +14,7 @@ import net.osmand.plus.OsmandSettings;
|
||||||
import net.osmand.plus.R;
|
import net.osmand.plus.R;
|
||||||
import net.osmand.plus.RegionAddressRepository;
|
import net.osmand.plus.RegionAddressRepository;
|
||||||
import net.osmand.plus.activities.OsmandApplication;
|
import net.osmand.plus.activities.OsmandApplication;
|
||||||
|
import net.osmand.plus.activities.search.SearchByNameAbstractActivity.SearchByNameTask;
|
||||||
import android.os.AsyncTask;
|
import android.os.AsyncTask;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
|
@ -46,12 +48,18 @@ public class SearchCityByNameActivity extends SearchByNameAbstractActivity<MapOb
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<MapObject> getObjects(String filter) {
|
public List<MapObject> getObjects(String filter, final SearchByNameTask task) {
|
||||||
List<MapObject> l = new ArrayList<MapObject>();
|
|
||||||
if(region != null){
|
if(region != null){
|
||||||
region.fillWithSuggestedCities(filter, l, locationToSearch);
|
region.fillWithSuggestedCities(filter, new ResultMatcher<MapObject>() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean publish(MapObject object) {
|
||||||
|
task.progress(object);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
return l;
|
}, locationToSearch);
|
||||||
|
}
|
||||||
|
return new ArrayList<MapObject>();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -24,7 +24,7 @@ public class SearchRegionByNameActivity extends SearchByNameAbstractActivity<Reg
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<RegionAddressRepository> getObjects(String filter) {
|
public List<RegionAddressRepository> getObjects(String filter, SearchByNameTask task) {
|
||||||
return new ArrayList<RegionAddressRepository>(((OsmandApplication)getApplication()).getResourceManager().getAddressRepositories());
|
return new ArrayList<RegionAddressRepository>(((OsmandApplication)getApplication()).getResourceManager().getAddressRepositories());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -6,12 +6,11 @@ import java.util.List;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
import net.osmand.data.PostCode;
|
import net.osmand.data.PostCode;
|
||||||
import net.osmand.data.Street;
|
import net.osmand.data.Street;
|
||||||
import net.osmand.plus.OsmandSettings;
|
|
||||||
import net.osmand.plus.R;
|
import net.osmand.plus.R;
|
||||||
import net.osmand.plus.RegionAddressRepository;
|
import net.osmand.plus.RegionAddressRepository;
|
||||||
import net.osmand.plus.activities.OsmandApplication;
|
import net.osmand.plus.activities.OsmandApplication;
|
||||||
|
import net.osmand.plus.activities.search.SearchByNameAbstractActivity.SearchByNameTask;
|
||||||
import android.os.AsyncTask;
|
import android.os.AsyncTask;
|
||||||
import android.os.Bundle;
|
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
import android.widget.TextView;
|
import android.widget.TextView;
|
||||||
|
|
||||||
|
@ -29,7 +28,6 @@ public class SearchStreet2ByNameActivity extends SearchByNameAbstractActivity<St
|
||||||
@Override
|
@Override
|
||||||
protected void onPostExecute(Void result) {
|
protected void onPostExecute(Void result) {
|
||||||
((TextView)findViewById(R.id.Label)).setText(R.string.incremental_search_street);
|
((TextView)findViewById(R.id.Label)).setText(R.string.incremental_search_street);
|
||||||
((TextView)findViewById(R.id.Label)).setText(R.string.incremental_search_building);
|
|
||||||
progress.setVisibility(View.INVISIBLE);
|
progress.setVisibility(View.INVISIBLE);
|
||||||
resetText();
|
resetText();
|
||||||
}
|
}
|
||||||
|
@ -66,7 +64,7 @@ public class SearchStreet2ByNameActivity extends SearchByNameAbstractActivity<St
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Street> getObjects(String filter) {
|
public List<Street> getObjects(String filter, SearchByNameTask task) {
|
||||||
int ind = 0;
|
int ind = 0;
|
||||||
filter = filter.toLowerCase();
|
filter = filter.toLowerCase();
|
||||||
List<Street> filterList = new ArrayList<Street>();
|
List<Street> filterList = new ArrayList<Street>();
|
||||||
|
|
|
@ -3,6 +3,7 @@ package net.osmand.plus.activities.search;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.osmand.ResultMatcher;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
import net.osmand.data.PostCode;
|
import net.osmand.data.PostCode;
|
||||||
import net.osmand.data.Street;
|
import net.osmand.data.Street;
|
||||||
|
@ -49,12 +50,17 @@ public class SearchStreetByNameActivity extends SearchByNameAbstractActivity<Str
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Street> getObjects(String filter) {
|
public List<Street> getObjects(String filter, final SearchByNameTask task) {
|
||||||
List<Street> l = new ArrayList<Street>();
|
|
||||||
if (city != null || postcode != null) {
|
if (city != null || postcode != null) {
|
||||||
region.fillWithSuggestedStreets(postcode == null ? city : postcode, l, filter);
|
return region.fillWithSuggestedStreets(postcode == null ? city : postcode, new ResultMatcher<Street>() {
|
||||||
|
@Override
|
||||||
|
public boolean publish(Street object) {
|
||||||
|
task.progress(object);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
return l;
|
}, filter);
|
||||||
|
}
|
||||||
|
return new ArrayList<Street>();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
Loading…
Reference in a new issue