Update search example
This commit is contained in:
parent
5c7562604a
commit
f5a22970b0
9 changed files with 386 additions and 102 deletions
|
@ -1,5 +1,6 @@
|
||||||
package net.osmand;
|
package net.osmand;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Easy matcher to be able to filter streets,buildings, etc.. using custom
|
* Easy matcher to be able to filter streets,buildings, etc.. using custom
|
||||||
* rules
|
* rules
|
||||||
|
@ -14,4 +15,5 @@ public interface StringMatcher {
|
||||||
*/
|
*/
|
||||||
boolean matches(String name);
|
boolean matches(String name);
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -92,6 +92,18 @@ public abstract class MapObject implements Comparable<MapObject> {
|
||||||
}
|
}
|
||||||
return l;
|
return l;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public List<String> getAllNames(boolean transliterate) {
|
||||||
|
List<String> l = new ArrayList<String>();
|
||||||
|
String enName = getEnName(transliterate);
|
||||||
|
if (!Algorithms.isEmpty(enName)) {
|
||||||
|
l.add(enName);
|
||||||
|
}
|
||||||
|
if (names != null) {
|
||||||
|
l.addAll(names.values());
|
||||||
|
}
|
||||||
|
return l;
|
||||||
|
}
|
||||||
|
|
||||||
public void copyNames(String otherName, String otherEnName, Map<String, String> otherNames, boolean overwrite) {
|
public void copyNames(String otherName, String otherEnName, Map<String, String> otherNames, boolean overwrite) {
|
||||||
if (!Algorithms.isEmpty(otherName) && (overwrite || Algorithms.isEmpty(name))) {
|
if (!Algorithms.isEmpty(otherName) && (overwrite || Algorithms.isEmpty(name))) {
|
||||||
|
|
|
@ -19,10 +19,12 @@ import net.osmand.ResultMatcher;
|
||||||
import net.osmand.StringMatcher;
|
import net.osmand.StringMatcher;
|
||||||
import net.osmand.binary.BinaryMapIndexReader;
|
import net.osmand.binary.BinaryMapIndexReader;
|
||||||
import net.osmand.data.LatLon;
|
import net.osmand.data.LatLon;
|
||||||
|
import net.osmand.osm.MapPoiTypes;
|
||||||
import net.osmand.search.example.core.ObjectType;
|
import net.osmand.search.example.core.ObjectType;
|
||||||
import net.osmand.search.example.core.SearchCoreAPI;
|
import net.osmand.search.example.core.SearchCoreAPI;
|
||||||
import net.osmand.search.example.core.SearchCoreFactory;
|
import net.osmand.search.example.core.SearchCoreFactory;
|
||||||
import net.osmand.search.example.core.SearchPhrase;
|
import net.osmand.search.example.core.SearchPhrase;
|
||||||
|
import net.osmand.search.example.core.SearchPhrase.NameStringMatcher;
|
||||||
import net.osmand.search.example.core.SearchResult;
|
import net.osmand.search.example.core.SearchResult;
|
||||||
import net.osmand.search.example.core.SearchSettings;
|
import net.osmand.search.example.core.SearchSettings;
|
||||||
import net.osmand.search.example.core.SearchWord;
|
import net.osmand.search.example.core.SearchWord;
|
||||||
|
@ -38,16 +40,19 @@ public class SearchUICore {
|
||||||
private LinkedBlockingQueue<Runnable> taskQueue;
|
private LinkedBlockingQueue<Runnable> taskQueue;
|
||||||
private Runnable onResultsComplete = null;
|
private Runnable onResultsComplete = null;
|
||||||
private AtomicInteger requestNumber = new AtomicInteger();
|
private AtomicInteger requestNumber = new AtomicInteger();
|
||||||
private int totalLimit = 20; // -1 unlimited
|
private int totalLimit = -1; // -1 unlimited - not used
|
||||||
|
|
||||||
List<SearchCoreAPI> apis = new ArrayList<>();
|
List<SearchCoreAPI> apis = new ArrayList<>();
|
||||||
private SearchSettings searchSettings;
|
private SearchSettings searchSettings;
|
||||||
|
private MapPoiTypes poiTypes;
|
||||||
|
|
||||||
|
|
||||||
public SearchUICore(BinaryMapIndexReader[] searchIndexes) {
|
public SearchUICore(MapPoiTypes poiTypes, String locale, BinaryMapIndexReader[] searchIndexes) {
|
||||||
|
this.poiTypes = poiTypes;
|
||||||
List<BinaryMapIndexReader> searchIndexesList = Arrays.asList(searchIndexes);
|
List<BinaryMapIndexReader> searchIndexesList = Arrays.asList(searchIndexes);
|
||||||
taskQueue = new LinkedBlockingQueue<Runnable>();
|
taskQueue = new LinkedBlockingQueue<Runnable>();
|
||||||
searchSettings = new SearchSettings(searchIndexesList);
|
searchSettings = new SearchSettings(searchIndexesList);
|
||||||
|
searchSettings = searchSettings.setLang(locale);
|
||||||
phrase = new SearchPhrase(searchSettings);
|
phrase = new SearchPhrase(searchSettings);
|
||||||
singleThreadedExecutor = new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, taskQueue);
|
singleThreadedExecutor = new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, taskQueue);
|
||||||
init();
|
init();
|
||||||
|
@ -62,11 +67,11 @@ public class SearchUICore {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void init() {
|
public void init() {
|
||||||
// apis.add(new SearchAmenityByNameAPI());
|
apis.add(new SearchCoreFactory.SearchAmenityTypesAPI(poiTypes));
|
||||||
// apis.add(new SearchAmenityByTypeAPI());
|
apis.add(new SearchCoreFactory.SearchAmenityByNameAPI());
|
||||||
// apis.add(new SearchAddressByNameAPI());
|
apis.add(new SearchCoreFactory.SearchAmenityByTypeAPI());
|
||||||
// apis.add(new SearchStreetByCityAPI());
|
apis.add(new SearchCoreFactory.SearchStreetByCityAPI());
|
||||||
// apis.add(new SearchBuildingAndIntersectionsByStreetAPI());
|
apis.add(new SearchCoreFactory.SearchBuildingAndIntersectionsByStreetAPI());
|
||||||
apis.add(new SearchCoreFactory.SearchRegionByNameAPI());
|
apis.add(new SearchCoreFactory.SearchRegionByNameAPI());
|
||||||
apis.add(new SearchCoreFactory.SearchAddressByNameAPI());
|
apis.add(new SearchCoreFactory.SearchAddressByNameAPI());
|
||||||
}
|
}
|
||||||
|
@ -84,11 +89,10 @@ public class SearchUICore {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void setSearchLocation(LatLon l) {
|
public void updateSettings(SearchSettings settings) {
|
||||||
searchSettings = searchSettings.setOriginalLocation(l);
|
searchSettings = settings;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private List<SearchResult> filterCurrentResults(SearchPhrase phrase) {
|
private List<SearchResult> filterCurrentResults(SearchPhrase phrase) {
|
||||||
List<SearchResult> rr = new ArrayList<>();
|
List<SearchResult> rr = new ArrayList<>();
|
||||||
List<SearchResult> l = currentSearchResults;
|
List<SearchResult> l = currentSearchResults;
|
||||||
|
@ -101,9 +105,8 @@ public class SearchUICore {
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean filterOneResult(SearchResult object, SearchPhrase phrase) {
|
private boolean filterOneResult(SearchResult object, SearchPhrase phrase) {
|
||||||
StringMatcher nameStringMatcher = phrase.getNameStringMatcher();
|
NameStringMatcher nameStringMatcher = phrase.getNameStringMatcher();
|
||||||
|
return nameStringMatcher.matches(object.localeName) || nameStringMatcher.matches(object.otherNames);
|
||||||
return nameStringMatcher.matches(object.mainName);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean selectSearchResult(SearchResult r) {
|
public boolean selectSearchResult(SearchResult r) {
|
||||||
|
@ -127,7 +130,7 @@ public class SearchUICore {
|
||||||
if(rm.isCancelled()) {
|
if(rm.isCancelled()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Thread.sleep(200); // FIXME
|
Thread.sleep(200); // FIXME remove timeout
|
||||||
searchInBackground(phrase, rm);
|
searchInBackground(phrase, rm);
|
||||||
if (!rm.isCancelled()) {
|
if (!rm.isCancelled()) {
|
||||||
sortSearchResults(phrase, rm.getRequestResults());
|
sortSearchResults(phrase, rm.getRequestResults());
|
||||||
|
@ -154,6 +157,7 @@ public class SearchUICore {
|
||||||
phrase.selectFile((BinaryMapIndexReader) sw.getResult().object);
|
phrase.selectFile((BinaryMapIndexReader) sw.getResult().object);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
phrase.sortFiles();
|
||||||
ArrayList<SearchCoreAPI> lst = new ArrayList<>(apis);
|
ArrayList<SearchCoreAPI> lst = new ArrayList<>(apis);
|
||||||
Collections.sort(lst, new Comparator<SearchCoreAPI>() {
|
Collections.sort(lst, new Comparator<SearchCoreAPI>() {
|
||||||
|
|
||||||
|
@ -167,6 +171,9 @@ public class SearchUICore {
|
||||||
if(matcher.isCancelled()) {
|
if(matcher.isCancelled()) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
if(api.getSearchPriority(phrase) == -1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
try {
|
try {
|
||||||
api.search(phrase, matcher);
|
api.search(phrase, matcher);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
|
@ -194,7 +201,7 @@ public class SearchUICore {
|
||||||
if(cmp != 0) {
|
if(cmp != 0) {
|
||||||
return cmp;
|
return cmp;
|
||||||
}
|
}
|
||||||
return clt.compare(o1.mainName, o2.mainName);
|
return clt.compare(o1.localeName, o2.localeName);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,7 +2,7 @@ package net.osmand.search.example.core;
|
||||||
|
|
||||||
public enum ObjectType {
|
public enum ObjectType {
|
||||||
CITY(true), VILLAGE(true), POSTCODE(true), STREET(true), HOUSE(true),
|
CITY(true), VILLAGE(true), POSTCODE(true), STREET(true), HOUSE(true),
|
||||||
POI_TYPE(false), POI(true), LOCATION(true), FAVORITE(true),
|
STREET_INTERSECTION(true), POI_TYPE(false), POI(true), LOCATION(true), FAVORITE(true),
|
||||||
REGION(true), RECENT_OBJ(true), WPT(true), UNKNOWN_NAME_FILTER(false);
|
REGION(true), RECENT_OBJ(true), WPT(true), UNKNOWN_NAME_FILTER(false);
|
||||||
private boolean hasLocation;
|
private boolean hasLocation;
|
||||||
private ObjectType(boolean location) {
|
private ObjectType(boolean location) {
|
||||||
|
|
|
@ -6,6 +6,10 @@ import net.osmand.search.example.SearchUICore.SearchResultMatcher;
|
||||||
|
|
||||||
public interface SearchCoreAPI {
|
public interface SearchCoreAPI {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param p
|
||||||
|
* @return order in which search core apis should be called, -1 means do not call
|
||||||
|
*/
|
||||||
public int getSearchPriority(SearchPhrase p);
|
public int getSearchPriority(SearchPhrase p);
|
||||||
|
|
||||||
public boolean search(SearchPhrase phrase, SearchResultMatcher resultMatcher) throws IOException;
|
public boolean search(SearchPhrase phrase, SearchResultMatcher resultMatcher) throws IOException;
|
||||||
|
|
|
@ -1,33 +1,61 @@
|
||||||
package net.osmand.search.example.core;
|
package net.osmand.search.example.core;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.Comparator;
|
||||||
|
import java.util.Iterator;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Map.Entry;
|
||||||
|
import java.util.TreeSet;
|
||||||
|
|
||||||
import net.osmand.CollatorStringMatcher.StringMatcherMode;
|
import net.osmand.CollatorStringMatcher.StringMatcherMode;
|
||||||
|
import net.osmand.OsmAndCollator;
|
||||||
import net.osmand.ResultMatcher;
|
import net.osmand.ResultMatcher;
|
||||||
|
import net.osmand.StringMatcher;
|
||||||
import net.osmand.binary.BinaryMapIndexReader;
|
import net.osmand.binary.BinaryMapIndexReader;
|
||||||
import net.osmand.binary.BinaryMapIndexReader.SearchRequest;
|
import net.osmand.binary.BinaryMapIndexReader.SearchRequest;
|
||||||
|
import net.osmand.data.Building;
|
||||||
import net.osmand.data.City;
|
import net.osmand.data.City;
|
||||||
import net.osmand.data.City.CityType;
|
import net.osmand.data.City.CityType;
|
||||||
import net.osmand.data.LatLon;
|
import net.osmand.data.LatLon;
|
||||||
import net.osmand.data.MapObject;
|
import net.osmand.data.MapObject;
|
||||||
import net.osmand.data.QuadRect;
|
import net.osmand.data.QuadRect;
|
||||||
import net.osmand.data.Street;
|
import net.osmand.data.Street;
|
||||||
|
import net.osmand.osm.AbstractPoiType;
|
||||||
|
import net.osmand.osm.MapPoiTypes;
|
||||||
|
import net.osmand.osm.PoiFilter;
|
||||||
|
import net.osmand.osm.PoiType;
|
||||||
import net.osmand.search.example.SearchUICore.SearchResultMatcher;
|
import net.osmand.search.example.SearchUICore.SearchResultMatcher;
|
||||||
|
import net.osmand.search.example.core.SearchPhrase.NameStringMatcher;
|
||||||
|
import net.osmand.util.Algorithms;
|
||||||
import net.osmand.util.MapUtils;
|
import net.osmand.util.MapUtils;
|
||||||
|
|
||||||
|
|
||||||
public class SearchCoreFactory {
|
public class SearchCoreFactory {
|
||||||
// TODO sort offline indexes by location
|
|
||||||
// TODO test add and delete characters
|
// TODO display more (+)
|
||||||
|
|
||||||
|
// TODO streets by city
|
||||||
|
// TODO search only closest file
|
||||||
|
// TODO limit to one file if city/street/village/poi selected
|
||||||
|
|
||||||
// TODO add location parse
|
// TODO add location parse
|
||||||
// TODO add url parse (geo)
|
// TODO add url parse (geo)
|
||||||
// TODO ? boolean hasSameConstantWords = p.hasSameConstantWords(this.phrase);
|
// TODO amenity by name
|
||||||
// TODO amenity types
|
|
||||||
// TODO amenity by type
|
// TODO amenity by type
|
||||||
// TODO streets by city
|
|
||||||
// TODO buildings by street
|
// TODO display closest city to villages (and city to street)
|
||||||
// TODO display closest city to villages
|
|
||||||
// TODO automatically increase radius if nothing found
|
// TODO automatically increase radius if nothing found
|
||||||
|
// TODO buildings interpolation
|
||||||
|
// TODO show buildings if street is one or default ( <CITY>, CITY (den ilp), 1186RM)
|
||||||
|
// TODO exclude duplicate streets/cities...
|
||||||
|
|
||||||
|
// TODO map creator (setting for locale)
|
||||||
|
|
||||||
|
// TODO add full text search with comma
|
||||||
|
// TODO add full text search without comma
|
||||||
|
|
||||||
|
|
||||||
public static abstract class SearchBaseAPI implements SearchCoreAPI {
|
public static abstract class SearchBaseAPI implements SearchCoreAPI {
|
||||||
@Override
|
@Override
|
||||||
|
@ -52,7 +80,7 @@ public class SearchCoreFactory {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getSearchPriority(SearchPhrase p) {
|
public int getSearchPriority(SearchPhrase p) {
|
||||||
return 10;
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -66,14 +94,16 @@ public class SearchCoreFactory {
|
||||||
for (BinaryMapIndexReader bmir : phrase.getOfflineIndexes()) {
|
for (BinaryMapIndexReader bmir : phrase.getOfflineIndexes()) {
|
||||||
if (bmir.getRegionCenter() != null) {
|
if (bmir.getRegionCenter() != null) {
|
||||||
SearchResult sr = new SearchResult(phrase);
|
SearchResult sr = new SearchResult(phrase);
|
||||||
sr.mainName = bmir.getRegionName();
|
sr.localeName = bmir.getRegionName();
|
||||||
sr.object = bmir;
|
sr.object = bmir;
|
||||||
|
sr.file = bmir;
|
||||||
|
sr.priority = 3;
|
||||||
sr.objectType = ObjectType.REGION;
|
sr.objectType = ObjectType.REGION;
|
||||||
sr.location = bmir.getRegionCenter();
|
sr.location = bmir.getRegionCenter();
|
||||||
sr.preferredZoom = 6;
|
sr.preferredZoom = 6;
|
||||||
if (phrase.getLastWord().length() <= 2 && phrase.isNoSelectedType()) {
|
if (phrase.getLastWord().length() <= 1 && phrase.isNoSelectedType()) {
|
||||||
resultMatcher.publish(sr);
|
resultMatcher.publish(sr);
|
||||||
} else if (phrase.getNameStringMatcher().matches(sr.mainName)) {
|
} else if (phrase.getNameStringMatcher().matches(sr.localeName)) {
|
||||||
resultMatcher.publish(sr);
|
resultMatcher.publish(sr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -83,13 +113,16 @@ public class SearchCoreFactory {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getSearchPriority(SearchPhrase p) {
|
public int getSearchPriority(SearchPhrase p) {
|
||||||
|
if(p.getWordLocation() != null) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class SearchAddressByNameAPI extends SearchBaseAPI {
|
public static class SearchAddressByNameAPI extends SearchBaseAPI {
|
||||||
|
|
||||||
private static final int DEFAULT_BBOX_RADIUS = 1000*10000;
|
private static final int DEFAULT_BBOX_RADIUS = 1000*1000;
|
||||||
private static final int LIMIT = 100;
|
private static final int LIMIT = 100;
|
||||||
|
|
||||||
public boolean isLastWordPoi(SearchPhrase p) {
|
public boolean isLastWordPoi(SearchPhrase p) {
|
||||||
|
@ -103,28 +136,29 @@ public class SearchCoreFactory {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean search(final SearchPhrase phrase, final SearchResultMatcher resultMatcher) throws IOException {
|
public boolean search(final SearchPhrase phrase, final SearchResultMatcher resultMatcher) throws IOException {
|
||||||
if (!phrase.hasObjectType(ObjectType.REGION)) {
|
// if (!phrase.hasObjectType(ObjectType.REGION)) {
|
||||||
return false;
|
// return false;
|
||||||
}
|
// }
|
||||||
if (phrase.getLastWord().isEmpty()) {
|
if (phrase.getLastWord().isEmpty()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// (search streets in neighboor cities for radiusLevel > 2)
|
// (search streets in neighbor cities for radiusLevel > 2)
|
||||||
if (isLastWordPoi(phrase) || isNoSelectedType(phrase) ||
|
if (phrase.isNoSelectedType() ||
|
||||||
phrase.isLastWord(ObjectType.CITY, ObjectType.VILLAGE, ObjectType.POSTCODE) ||
|
phrase.isLastWord(ObjectType.CITY, ObjectType.VILLAGE, ObjectType.POSTCODE) || // ?
|
||||||
phrase.isLastWord(ObjectType.REGION) || phrase.getRadiusLevel() >= 2) {
|
phrase.isLastWord(ObjectType.REGION) || phrase.getRadiusLevel() >= 2) {
|
||||||
int letters = phrase.getLastWord().length() / 3 + 1;
|
int letters = phrase.getLastWord().length() / 3 + 1;
|
||||||
final boolean locSpecified = false; // phrase.getLastTokenLocation() != null;
|
final boolean locSpecified = false; // phrase.getLastTokenLocation() != null;
|
||||||
LatLon loc = phrase.getLastTokenLocation();
|
LatLon loc = phrase.getLastTokenLocation();
|
||||||
final QuadRect streetBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * letters, phrase.getRadiusLevel(),
|
final QuadRect streetBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS, phrase.getRadiusLevel(),
|
||||||
phrase.getLastTokenLocation());
|
phrase.getLastTokenLocation());
|
||||||
final QuadRect postcodeBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * 2 * letters, phrase.getRadiusLevel(),
|
final QuadRect postcodeBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * 5, phrase.getRadiusLevel(),
|
||||||
phrase.getLastTokenLocation());
|
phrase.getLastTokenLocation());
|
||||||
final QuadRect villagesBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * letters, phrase.getRadiusLevel(),
|
final QuadRect villagesBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * 5, phrase.getRadiusLevel(),
|
||||||
phrase.getLastTokenLocation());
|
phrase.getLastTokenLocation());
|
||||||
final QuadRect cityBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * 4 * letters, phrase.getRadiusLevel(),
|
final QuadRect cityBbox = getBBoxToSearch(DEFAULT_BBOX_RADIUS * 10, phrase.getRadiusLevel(),
|
||||||
phrase.getLastTokenLocation());
|
phrase.getLastTokenLocation());
|
||||||
final int priority = isNoSelectedType(phrase) ? 1 : 3;
|
final int priority = isNoSelectedType(phrase) ? 1 : 3;
|
||||||
|
final BinaryMapIndexReader[] currentFile = new BinaryMapIndexReader[1];
|
||||||
ResultMatcher<MapObject> rm = new ResultMatcher<MapObject>() {
|
ResultMatcher<MapObject> rm = new ResultMatcher<MapObject>() {
|
||||||
int limit = 0;
|
int limit = 0;
|
||||||
@Override
|
@Override
|
||||||
|
@ -134,7 +168,9 @@ public class SearchCoreFactory {
|
||||||
}
|
}
|
||||||
SearchResult sr = new SearchResult(phrase);
|
SearchResult sr = new SearchResult(phrase);
|
||||||
sr.object = object;
|
sr.object = object;
|
||||||
sr.mainName = object.getName();
|
sr.file = currentFile[0];
|
||||||
|
sr.localeName = object.getName(phrase.getSettings().getLang());
|
||||||
|
sr.otherNames = object.getAllNames(true);
|
||||||
sr.location = object.getLocation();
|
sr.location = object.getLocation();
|
||||||
sr.priorityDistance = 1;
|
sr.priorityDistance = 1;
|
||||||
sr.priority = priority;
|
sr.priority = priority;
|
||||||
|
@ -179,10 +215,11 @@ public class SearchCoreFactory {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
for(BinaryMapIndexReader r : phrase.getOfflineIndexes()) {
|
for(BinaryMapIndexReader r : phrase.getOfflineIndexes()) {
|
||||||
|
currentFile[0] = r;
|
||||||
SearchRequest<MapObject> req = BinaryMapIndexReader.buildAddressByNameRequest(rm,
|
SearchRequest<MapObject> req = BinaryMapIndexReader.buildAddressByNameRequest(rm,
|
||||||
phrase.getLastWord().toLowerCase(), StringMatcherMode.CHECK_ONLY_STARTS_WITH);
|
phrase.getLastWord().toLowerCase(), StringMatcherMode.CHECK_STARTS_FROM_SPACE);
|
||||||
if(locSpecified) {
|
if(locSpecified) {
|
||||||
req.setBBoxRadius(loc.getLatitude(), loc.getLongitude(), DEFAULT_BBOX_RADIUS * 4 * letters);
|
req.setBBoxRadius(loc.getLatitude(), loc.getLongitude(), DEFAULT_BBOX_RADIUS * 20);
|
||||||
}
|
}
|
||||||
r.searchAddressDataByName(req);
|
r.searchAddressDataByName(req);
|
||||||
}
|
}
|
||||||
|
@ -192,12 +229,9 @@ public class SearchCoreFactory {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getSearchPriority(SearchPhrase p) {
|
public int getSearchPriority(SearchPhrase p) {
|
||||||
if (isNoSelectedType(p)) {
|
if (p.isNoSelectedType()) {
|
||||||
return 5;
|
return 5;
|
||||||
}
|
}
|
||||||
if (isLastWordPoi(p)) {
|
|
||||||
return 8;
|
|
||||||
}
|
|
||||||
return 10;
|
return 10;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -216,7 +250,63 @@ public class SearchCoreFactory {
|
||||||
// }
|
// }
|
||||||
@Override
|
@Override
|
||||||
public int getSearchPriority(SearchPhrase p) {
|
public int getSearchPriority(SearchPhrase p) {
|
||||||
return 10;
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public static class SearchAmenityTypesAPI extends SearchBaseAPI {
|
||||||
|
|
||||||
|
|
||||||
|
private Map<String, PoiType> translatedNames;
|
||||||
|
private List<PoiFilter> topVisibleFilters;
|
||||||
|
private TreeSet<AbstractPoiType> results;
|
||||||
|
|
||||||
|
public SearchAmenityTypesAPI(MapPoiTypes types) {
|
||||||
|
translatedNames = types.getAllTranslatedNames(false);
|
||||||
|
topVisibleFilters = types.getTopVisibleFilters();
|
||||||
|
final net.osmand.Collator clt = OsmAndCollator.primaryCollator();
|
||||||
|
results = new TreeSet<>(new Comparator<AbstractPoiType>() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int compare(AbstractPoiType o1, AbstractPoiType o2) {
|
||||||
|
return clt.compare(o1.getTranslation(), o2.getTranslation());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean search(SearchPhrase phrase, SearchResultMatcher resultMatcher) throws IOException {
|
||||||
|
results.clear();
|
||||||
|
if(Algorithms.isEmpty(phrase.getLastWord())) {
|
||||||
|
results.addAll(topVisibleFilters);
|
||||||
|
} else {
|
||||||
|
Iterator<Entry<String, PoiType>> it = translatedNames.entrySet().iterator();
|
||||||
|
StringMatcher nm = phrase.getNameStringMatcher();
|
||||||
|
while (it.hasNext()) {
|
||||||
|
Entry<String, PoiType> e = it.next();
|
||||||
|
if (nm.matches(e.getKey())) {
|
||||||
|
results.add(e.getValue());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for(AbstractPoiType p : results) {
|
||||||
|
SearchResult res = new SearchResult(phrase);
|
||||||
|
res.localeName = p.getTranslation();
|
||||||
|
res.object = p;
|
||||||
|
res.priority = 2;
|
||||||
|
res.objectType = ObjectType.POI_TYPE;
|
||||||
|
resultMatcher.publish(res);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getSearchPriority(SearchPhrase p) {
|
||||||
|
if(p.hasObjectType(ObjectType.POI) ||p.hasObjectType(ObjectType.POI_TYPE)) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -250,7 +340,7 @@ public class SearchCoreFactory {
|
||||||
public boolean search(SearchPhrase phrase, SearchResultMatcher resultMatcher) {
|
public boolean search(SearchPhrase phrase, SearchResultMatcher resultMatcher) {
|
||||||
if(isLastWordCityGroup(phrase)) {
|
if(isLastWordCityGroup(phrase)) {
|
||||||
// search all streets
|
// search all streets
|
||||||
// TODO LIMIT 100 * radiusLevel - priority 1, distPriority 0 (alphabetic)
|
// LIMIT 100 * radiusLevel - priority 1, distPriority 0 (alphabetic)
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -270,22 +360,87 @@ public class SearchCoreFactory {
|
||||||
|
|
||||||
|
|
||||||
public static class SearchBuildingAndIntersectionsByStreetAPI extends SearchBaseAPI {
|
public static class SearchBuildingAndIntersectionsByStreetAPI extends SearchBaseAPI {
|
||||||
|
Street cacheBuilding;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean search(SearchPhrase phrase, SearchResultMatcher resultMatcher) {
|
public boolean search(SearchPhrase phrase, final SearchResultMatcher resultMatcher) throws IOException {
|
||||||
if(isLastWordStreet(phrase)) {
|
if(phrase.isLastWord(ObjectType.STREET)) {
|
||||||
// search all buildings
|
Street s = (Street) phrase.getLastSelectedWord().getResult().object;
|
||||||
// TODO NO LIMIT - priority 1, distPriority 0 (alphabetic)
|
BinaryMapIndexReader file = phrase.getLastSelectedWord().getResult().file;
|
||||||
|
String lw = phrase.getLastWord();
|
||||||
|
NameStringMatcher sm = phrase.getNameStringMatcher();
|
||||||
|
if (cacheBuilding != s) {
|
||||||
|
cacheBuilding = s;
|
||||||
|
SearchRequest<Building> sr = BinaryMapIndexReader
|
||||||
|
.buildAddressRequest(new ResultMatcher<Building>() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean publish(Building object) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isCancelled() {
|
||||||
|
return resultMatcher.isCancelled();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
file.preloadBuildings(s, sr);
|
||||||
|
Collections.sort(s.getBuildings(), new Comparator<Building>() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int compare(Building o1, Building o2) {
|
||||||
|
int i1 = Algorithms.extractFirstIntegerNumber(o1.getName());
|
||||||
|
int i2 = Algorithms.extractFirstIntegerNumber(o2.getName());
|
||||||
|
if (i1 == i2) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return Algorithms.compare(i1, i2);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
for(Building b : s.getBuildings()) {
|
||||||
|
SearchResult res = new SearchResult(phrase);
|
||||||
|
if(!sm.matches(b.getName())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
res.localeName = b.getName(phrase.getSettings().getLang());
|
||||||
|
res.otherNames = b.getAllNames(true);
|
||||||
|
res.object = b;
|
||||||
|
res.file = file;
|
||||||
|
res.objectType = ObjectType.HOUSE;
|
||||||
|
res.location = b.getLocation();
|
||||||
|
res.preferredZoom = 16;
|
||||||
|
resultMatcher.publish(res);
|
||||||
|
}
|
||||||
|
if(!Algorithms.isEmpty(lw) && !Character.isDigit(lw.charAt(0))) {
|
||||||
|
for(Street street : s.getIntersectedStreets()) {
|
||||||
|
SearchResult res = new SearchResult(phrase);
|
||||||
|
if(!sm.matches(street.getName()) && !sm.matches(street.getAllNames(true))) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
res.otherNames = street.getAllNames(true);
|
||||||
|
res.localeName = street.getName(phrase.getSettings().getLang());
|
||||||
|
res.object = street;
|
||||||
|
res.file = file;
|
||||||
|
res.objectType = ObjectType.STREET_INTERSECTION;
|
||||||
|
res.location = street.getLocation();
|
||||||
|
res.preferredZoom = 16;
|
||||||
|
resultMatcher.publish(res);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isLastWordStreet(SearchPhrase p ) {
|
|
||||||
return p.isLastWord(ObjectType.STREET);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getSearchPriority(SearchPhrase p) {
|
public int getSearchPriority(SearchPhrase p) {
|
||||||
|
if(!p.isLastWord(ObjectType.STREET)) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,26 +1,72 @@
|
||||||
package net.osmand.search.example.core;
|
package net.osmand.search.example.core;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.Comparator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
import net.osmand.CollatorStringMatcher;
|
import net.osmand.CollatorStringMatcher;
|
||||||
import net.osmand.StringMatcher;
|
import net.osmand.StringMatcher;
|
||||||
import net.osmand.CollatorStringMatcher.StringMatcherMode;
|
import net.osmand.CollatorStringMatcher.StringMatcherMode;
|
||||||
import net.osmand.binary.BinaryMapIndexReader;
|
import net.osmand.binary.BinaryMapIndexReader;
|
||||||
import net.osmand.data.LatLon;
|
import net.osmand.data.LatLon;
|
||||||
|
import net.osmand.util.MapUtils;
|
||||||
|
|
||||||
//immutable object
|
//immutable object
|
||||||
public class SearchPhrase {
|
public class SearchPhrase {
|
||||||
|
|
||||||
private List<SearchWord> words = new ArrayList<>();
|
private List<SearchWord> words = new ArrayList<>();
|
||||||
private String lastWord = "";
|
private String lastWord = "";
|
||||||
private CollatorStringMatcher sm;
|
private NameStringMatcher sm;
|
||||||
private SearchSettings settings;
|
private SearchSettings settings;
|
||||||
private List<BinaryMapIndexReader> indexes;
|
private List<BinaryMapIndexReader> indexes;
|
||||||
|
private String lastWordTrim;
|
||||||
|
|
||||||
public SearchPhrase(SearchSettings settings) {
|
public SearchPhrase(SearchSettings settings) {
|
||||||
this.settings = settings;
|
this.settings = settings;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public SearchPhrase generateNewPhrase(String text, SearchSettings settings) {
|
||||||
|
SearchPhrase sp = new SearchPhrase(settings);
|
||||||
|
String atext = text;
|
||||||
|
List<SearchWord> leftWords = this.words;
|
||||||
|
String thisTxt = getText(true);
|
||||||
|
if (text.startsWith(thisTxt)) {
|
||||||
|
// string is longer
|
||||||
|
atext = text.substring(getText(false).length());
|
||||||
|
sp.words = new ArrayList<>(this.words);
|
||||||
|
leftWords = leftWords.subList(leftWords.size(), leftWords.size());
|
||||||
|
}
|
||||||
|
if (!atext.contains(",")) {
|
||||||
|
sp.lastWord = atext;
|
||||||
|
|
||||||
|
} else {
|
||||||
|
String[] ws = atext.split(",");
|
||||||
|
for (int i = 0; i < ws.length - 1; i++) {
|
||||||
|
boolean unknown = true;
|
||||||
|
if (ws[i].trim().length() > 0) {
|
||||||
|
if (leftWords.size() > 0) {
|
||||||
|
if (leftWords.get(0).getWord().equalsIgnoreCase(ws[i].trim())) {
|
||||||
|
sp.words.add(leftWords.get(0));
|
||||||
|
leftWords = leftWords.subList(1, leftWords.size());
|
||||||
|
unknown = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(unknown) {
|
||||||
|
sp.words.add(new SearchWord(ws[i].trim()));
|
||||||
|
}
|
||||||
|
// sp.text += ws[i] + ", ";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
sp.lastWord = ws[ws.length - 1];
|
||||||
|
}
|
||||||
|
sp.lastWordTrim = sp.lastWord.trim();
|
||||||
|
//sp.text = sp.text.trim();
|
||||||
|
return sp;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
public List<SearchWord> getWords() {
|
public List<SearchWord> getWords() {
|
||||||
return words;
|
return words;
|
||||||
|
@ -45,11 +91,8 @@ public class SearchPhrase {
|
||||||
public SearchPhrase selectWord(SearchResult res) {
|
public SearchPhrase selectWord(SearchResult res) {
|
||||||
SearchPhrase sp = new SearchPhrase(this.settings);
|
SearchPhrase sp = new SearchPhrase(this.settings);
|
||||||
sp.words.addAll(this.words);
|
sp.words.addAll(this.words);
|
||||||
SearchWord sw = new SearchWord(res.mainName.trim(), res);
|
SearchWord sw = new SearchWord(res.localeName.trim(), res);
|
||||||
sp.words.add(sw);
|
sp.words.add(sw);
|
||||||
// sp.text = this.text + sw.getWord() + ", ";
|
|
||||||
// TODO FIX
|
|
||||||
// sp.text = this.text + " " + sw.getWord() + ", ";
|
|
||||||
return sp;
|
return sp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -84,11 +127,14 @@ public class SearchPhrase {
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public StringMatcher getNameStringMatcher() {
|
|
||||||
|
|
||||||
|
|
||||||
|
public NameStringMatcher getNameStringMatcher() {
|
||||||
if(sm != null) {
|
if(sm != null) {
|
||||||
return sm;
|
return sm;
|
||||||
}
|
}
|
||||||
sm = new CollatorStringMatcher(lastWord, StringMatcherMode.CHECK_STARTS_FROM_SPACE);
|
sm = new NameStringMatcher(lastWordTrim, StringMatcherMode.CHECK_STARTS_FROM_SPACE);
|
||||||
return sm;
|
return sm;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -140,9 +186,28 @@ public class SearchPhrase {
|
||||||
|
|
||||||
|
|
||||||
public String getLastWord() {
|
public String getLastWord() {
|
||||||
return lastWord;
|
return lastWordTrim;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public SearchWord getLastSelectedWord() {
|
||||||
|
if(words.isEmpty()) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return words.get(words.size() - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public LatLon getWordLocation() {
|
||||||
|
for(int i = words.size() - 1; i >= 0; i--) {
|
||||||
|
SearchWord sw = words.get(i);
|
||||||
|
if(sw.getLocation() != null) {
|
||||||
|
return sw.getLocation();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
public LatLon getLastTokenLocation() {
|
public LatLon getLastTokenLocation() {
|
||||||
for(int i = words.size() - 1; i >= 0; i--) {
|
for(int i = words.size() - 1; i >= 0; i--) {
|
||||||
SearchWord sw = words.get(i);
|
SearchWord sw = words.get(i);
|
||||||
|
@ -154,45 +219,6 @@ public class SearchPhrase {
|
||||||
return settings.getOriginalLocation();
|
return settings.getOriginalLocation();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public SearchPhrase generateNewPhrase(String text, SearchSettings settings) {
|
|
||||||
SearchPhrase sp = new SearchPhrase(settings);
|
|
||||||
String atext = text;
|
|
||||||
List<SearchWord> leftWords = this.words;
|
|
||||||
String thisTxt = getText(true);
|
|
||||||
if (text.startsWith(thisTxt)) {
|
|
||||||
// string is longer
|
|
||||||
atext = text.substring(getText(false).length());
|
|
||||||
sp.words = new ArrayList<>(this.words);
|
|
||||||
leftWords = leftWords.subList(leftWords.size(), leftWords.size());
|
|
||||||
}
|
|
||||||
if (!atext.contains(",")) {
|
|
||||||
sp.lastWord = atext;
|
|
||||||
} else {
|
|
||||||
String[] ws = atext.split(",");
|
|
||||||
for (int i = 0; i < ws.length - 1; i++) {
|
|
||||||
boolean unknown = true;
|
|
||||||
if (ws[i].trim().length() > 0) {
|
|
||||||
if (leftWords.size() > 0) {
|
|
||||||
if (leftWords.get(0).getWord().equalsIgnoreCase(ws[i].trim())) {
|
|
||||||
sp.words.add(leftWords.get(0));
|
|
||||||
leftWords = leftWords.subList(1, leftWords.size());
|
|
||||||
unknown = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if(unknown) {
|
|
||||||
sp.words.add(new SearchWord(ws[i].trim()));
|
|
||||||
}
|
|
||||||
// sp.text += ws[i] + ", ";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
sp.lastWord = ws[ws.length - 1];
|
|
||||||
}
|
|
||||||
//sp.text = sp.text.trim();
|
|
||||||
return sp;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public void selectFile(BinaryMapIndexReader object) {
|
public void selectFile(BinaryMapIndexReader object) {
|
||||||
if(indexes == null) {
|
if(indexes == null) {
|
||||||
|
@ -200,4 +226,51 @@ public class SearchPhrase {
|
||||||
}
|
}
|
||||||
this.indexes.add(object);
|
this.indexes.add(object);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void sortFiles() {
|
||||||
|
if(indexes == null) {
|
||||||
|
indexes = new ArrayList<>(getOfflineIndexes());
|
||||||
|
}
|
||||||
|
final LatLon ll = getLastTokenLocation();
|
||||||
|
if(ll != null) {
|
||||||
|
Collections.sort(indexes, new Comparator<BinaryMapIndexReader>() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int compare(BinaryMapIndexReader o1, BinaryMapIndexReader o2) {
|
||||||
|
LatLon rc1 = o1.getRegionCenter();
|
||||||
|
LatLon rc2 = o2.getRegionCenter();
|
||||||
|
double d1 = rc1 == null ? 10000000d : MapUtils.getDistance(rc1, ll);
|
||||||
|
double d2 = rc2 == null ? 10000000d : MapUtils.getDistance(rc2, ll);
|
||||||
|
return Double.compare(d1, d2);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class NameStringMatcher implements StringMatcher {
|
||||||
|
|
||||||
|
private CollatorStringMatcher sm;
|
||||||
|
|
||||||
|
public NameStringMatcher(String lastWordTrim, StringMatcherMode checkStartsFromSpace) {
|
||||||
|
sm = new CollatorStringMatcher(lastWordTrim, StringMatcherMode.CHECK_STARTS_FROM_SPACE);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean matches(Collection<String> map) {
|
||||||
|
if(map == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
for(String v : map) {
|
||||||
|
if(sm.matches(v)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean matches(String name) {
|
||||||
|
return sm.matches(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,8 @@
|
||||||
package net.osmand.search.example.core;
|
package net.osmand.search.example.core;
|
||||||
|
|
||||||
|
import java.util.Collection;
|
||||||
|
|
||||||
|
import net.osmand.binary.BinaryMapIndexReader;
|
||||||
import net.osmand.data.LatLon;
|
import net.osmand.data.LatLon;
|
||||||
import net.osmand.util.MapUtils;
|
import net.osmand.util.MapUtils;
|
||||||
|
|
||||||
|
@ -9,6 +12,7 @@ public class SearchResult {
|
||||||
|
|
||||||
public Object object;
|
public Object object;
|
||||||
public ObjectType objectType;
|
public ObjectType objectType;
|
||||||
|
public BinaryMapIndexReader file;
|
||||||
|
|
||||||
public double priority;
|
public double priority;
|
||||||
public double priorityDistance;
|
public double priorityDistance;
|
||||||
|
@ -26,6 +30,8 @@ public class SearchResult {
|
||||||
|
|
||||||
public LatLon location;
|
public LatLon location;
|
||||||
public int preferredZoom = 15;
|
public int preferredZoom = 15;
|
||||||
public String mainName;
|
public String localeName;
|
||||||
|
public Collection<String> otherNames;
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,10 +14,12 @@ public class SearchSettings {
|
||||||
private List<BinaryMapIndexReader> offlineIndexes = new ArrayList<>();
|
private List<BinaryMapIndexReader> offlineIndexes = new ArrayList<>();
|
||||||
private int radiusLevel = 1;
|
private int radiusLevel = 1;
|
||||||
private int totalLimit = -1;
|
private int totalLimit = -1;
|
||||||
|
private String lang;
|
||||||
|
|
||||||
public SearchSettings(SearchSettings s) {
|
public SearchSettings(SearchSettings s) {
|
||||||
if(s != null) {
|
if(s != null) {
|
||||||
this.radiusLevel = s.radiusLevel;
|
this.radiusLevel = s.radiusLevel;
|
||||||
|
this.lang = s.lang;
|
||||||
this.totalLimit = s.totalLimit;
|
this.totalLimit = s.totalLimit;
|
||||||
this.offlineIndexes = s.offlineIndexes;
|
this.offlineIndexes = s.offlineIndexes;
|
||||||
this.originalLocation = s.originalLocation;
|
this.originalLocation = s.originalLocation;
|
||||||
|
@ -37,10 +39,32 @@ public class SearchSettings {
|
||||||
return radiusLevel;
|
return radiusLevel;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String getLang() {
|
||||||
|
return lang;
|
||||||
|
}
|
||||||
|
|
||||||
|
public SearchSettings setLang(String lang) {
|
||||||
|
SearchSettings s = new SearchSettings(this);
|
||||||
|
s.lang = lang;
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
|
public SearchSettings setRadiusLevel(int radiusLevel) {
|
||||||
|
SearchSettings s = new SearchSettings(this);
|
||||||
|
s.radiusLevel = radiusLevel;
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
public int getTotalLimit() {
|
public int getTotalLimit() {
|
||||||
return totalLimit;
|
return totalLimit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public SearchSettings setTotalLimit(int totalLimit) {
|
||||||
|
SearchSettings s = new SearchSettings(this);
|
||||||
|
s.totalLimit = totalLimit;
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
public LatLon getOriginalLocation() {
|
public LatLon getOriginalLocation() {
|
||||||
return originalLocation;
|
return originalLocation;
|
||||||
}
|
}
|
||||||
|
@ -51,4 +75,5 @@ public class SearchSettings {
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue