Add search neighborhood cities
This commit is contained in:
parent
7de85b7cf6
commit
33f7399149
5 changed files with 234 additions and 55 deletions
|
@ -8,10 +8,10 @@
|
|||
<string name="ga_debug">true</string>
|
||||
<string name="versionFeatures">+play_market +gps_status -parking_plugin -blackberry -free_version -amazon</string>
|
||||
<string name="next_tips_and_tricks_not_translate">
|
||||
* Order waypoints in optimal way to visit all (Travelling salesman, door-to-door)
|
||||
* New downlad screen
|
||||
* Planning mode
|
||||
* Delete SRTM files
|
||||
* GPX subfolders structure
|
||||
* Order waypoints in optimal way (Travel salesman)
|
||||
</string>
|
||||
</resources>
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
3. All your modified/created strings are in the top of the file (to make easier find what\'s translated).
|
||||
PLEASE: Have a look at http://code.google.com/p/osmand/wiki/UIConsistency, it may really improve your and our work :-) Thx - Hardy
|
||||
-->
|
||||
<string name="search_street_in_neighborhood_cities">Search street in neighborhood cities</string>
|
||||
<string name="intermediate_items_sort_return">Positions ordered to form optimal way from map position to the target location</string>
|
||||
<string name="intermediate_items_sort_by_distance">Sort (door-to-door)</string>
|
||||
<string name="local_osm_changes_backup_successful">OSM change file succesfully generated %1$s</string>
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
package net.osmand.plus.activities;
|
||||
|
||||
import gnu.trove.list.array.TIntArrayList;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
|
@ -12,26 +14,25 @@ import net.osmand.plus.R;
|
|||
import net.osmand.plus.TargetPointsHelper;
|
||||
import net.osmand.util.MapUtils;
|
||||
import android.app.Activity;
|
||||
import android.app.AlertDialog;
|
||||
import android.app.AlertDialog.Builder;
|
||||
import android.app.Dialog;
|
||||
import android.content.DialogInterface;
|
||||
import android.content.DialogInterface.OnShowListener;
|
||||
import android.graphics.Color;
|
||||
import android.os.AsyncTask;
|
||||
import android.view.View;
|
||||
import android.view.View.OnClickListener;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.AdapterView;
|
||||
import android.widget.AdapterView.OnItemClickListener;
|
||||
import android.widget.ArrayAdapter;
|
||||
import android.widget.Button;
|
||||
import android.widget.CheckBox;
|
||||
import android.widget.CompoundButton;
|
||||
import android.widget.CompoundButton.OnCheckedChangeListener;
|
||||
import android.widget.ImageButton;
|
||||
import android.widget.LinearLayout;
|
||||
import android.widget.LinearLayout.LayoutParams;
|
||||
import android.widget.ListView;
|
||||
import android.widget.ProgressBar;
|
||||
import android.widget.ScrollView;
|
||||
import android.widget.TextView;
|
||||
|
||||
public class IntermediatePointsDialog {
|
||||
|
@ -45,57 +46,31 @@ public class IntermediatePointsDialog {
|
|||
final OsmandApplication app, final boolean changeOrder){
|
||||
TargetPointsHelper targets = app.getTargetPointsHelper();
|
||||
final List<LatLon> intermediates = targets.getIntermediatePointsWithTarget();
|
||||
final TIntArrayList originalPositions = new TIntArrayList(intermediates.size());
|
||||
for(int j = 1; j <= intermediates.size(); j++) {
|
||||
originalPositions.add(j);
|
||||
}
|
||||
final List<String> names = targets.getIntermediatePointNamesWithTarget();
|
||||
final boolean[] checkedIntermediates = new boolean[intermediates.size()];
|
||||
final ArrayAdapter<LatLon> listadapter = getListAdapter(app, activity, changeOrder, intermediates, names, checkedIntermediates);
|
||||
final ArrayAdapter<LatLon> listadapter = getListAdapter(app, activity, changeOrder, intermediates, originalPositions, names, checkedIntermediates);
|
||||
ListView lv = new ListView(activity);
|
||||
View contentView = lv;
|
||||
final ProgressBar pb = new ProgressBar(activity);
|
||||
pb.setVisibility(View.GONE);
|
||||
final TextView textInfo = new TextView(activity);
|
||||
textInfo.setText(R.string.intermediate_items_sort_return);
|
||||
textInfo.setVisibility(View.GONE);
|
||||
|
||||
if (changeOrder) {
|
||||
Button btn = new Button(activity);
|
||||
btn.setText(R.string.intermediate_items_sort_by_distance);
|
||||
btn.setOnClickListener(new OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
new AsyncTask<Void, Void, int[]>() {
|
||||
LinearLayout ll = new LinearLayout(activity);
|
||||
ll.setOrientation(LinearLayout.VERTICAL);
|
||||
ll.addView(lv);
|
||||
ll.addView(pb);
|
||||
ll.addView(textInfo);
|
||||
contentView = ll;
|
||||
|
||||
protected void onPreExecute() {
|
||||
pb.setVisibility(View.VISIBLE);
|
||||
textInfo.setVisibility(View.VISIBLE);
|
||||
};
|
||||
|
||||
protected int[] doInBackground(Void[] params) {
|
||||
ArrayList<LatLon> lt = new ArrayList<LatLon>(intermediates);
|
||||
LatLon start = new LatLon(activity.getMapView().getLatitude(), activity.getMapView().getLongitude());
|
||||
LatLon end = lt.remove(lt.size() - 1);
|
||||
return new TspAnt().readGraph(lt, start, end).solve();
|
||||
};
|
||||
|
||||
protected void onPostExecute(int[] result) {
|
||||
pb.setVisibility(View.GONE);
|
||||
List<LatLon> alocs = new ArrayList<LatLon>();
|
||||
List<String> anames = new ArrayList<String>();
|
||||
for (int i = 0; i < result.length; i++) {
|
||||
if(result[i] > 0) {
|
||||
alocs.add(intermediates.get(result[i] - 1));
|
||||
anames.add(names.get(result[i] - 1));
|
||||
}
|
||||
}
|
||||
intermediates.clear();
|
||||
intermediates.addAll(alocs);
|
||||
names.clear();
|
||||
names.addAll(anames);
|
||||
listadapter.notifyDataSetChanged();
|
||||
};
|
||||
}.execute(new Void[0]);
|
||||
}
|
||||
});
|
||||
lv.addFooterView(pb);
|
||||
lv.addFooterView(textInfo);
|
||||
lv.addFooterView(btn);
|
||||
// lv.addFooterView(pb);
|
||||
// lv.addFooterView(textInfo);
|
||||
}
|
||||
lv.setAdapter(listadapter);
|
||||
lv.setOnItemClickListener(new OnItemClickListener() {
|
||||
|
@ -114,7 +89,7 @@ public class IntermediatePointsDialog {
|
|||
});
|
||||
|
||||
Builder builder = new AccessibleAlertBuilder(activity);
|
||||
builder.setView(lv);
|
||||
builder.setView(contentView);
|
||||
builder.setInverseBackgroundForced(true);
|
||||
lv.setBackgroundColor(Color.WHITE);
|
||||
builder.setPositiveButton(R.string.default_buttons_ok, new DialogInterface.OnClickListener() {
|
||||
|
@ -135,13 +110,79 @@ public class IntermediatePointsDialog {
|
|||
openIntermediatePointsDialog(activity, app, true);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
builder.setNeutralButton(R.string.intermediate_items_sort_by_distance, new Dialog.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(DialogInterface d, int which) {
|
||||
//Do nothing here. We override the onclick
|
||||
}
|
||||
builder.show();
|
||||
});
|
||||
}
|
||||
AlertDialog dlg = builder.create();
|
||||
if (changeOrder) {
|
||||
applySortTargets(dlg, activity, intermediates, originalPositions, names, listadapter, pb, textInfo);
|
||||
}
|
||||
dlg.show();
|
||||
}
|
||||
|
||||
private static void applySortTargets(AlertDialog dlg, final MapActivity activity, final List<LatLon> intermediates,
|
||||
final TIntArrayList originalPositions,
|
||||
final List<String> names, final ArrayAdapter<LatLon> listadapter, final ProgressBar pb, final TextView textInfo) {
|
||||
dlg.setOnShowListener(new OnShowListener() {
|
||||
@Override
|
||||
public void onShow(DialogInterface dialog) {
|
||||
((AlertDialog) dialog).getButton(AlertDialog.BUTTON_NEUTRAL).setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
|
||||
new AsyncTask<Void, Void, int[]>() {
|
||||
|
||||
protected void onPreExecute() {
|
||||
pb.setVisibility(View.VISIBLE);
|
||||
textInfo.setVisibility(View.VISIBLE);
|
||||
};
|
||||
|
||||
protected int[] doInBackground(Void[] params) {
|
||||
ArrayList<LatLon> lt = new ArrayList<LatLon>(intermediates);
|
||||
LatLon start = new LatLon(activity.getMapView().getLatitude(), activity.getMapView().getLongitude());
|
||||
LatLon end = lt.remove(lt.size() - 1);
|
||||
return new TspAnt().readGraph(lt, start, end).solve();
|
||||
};
|
||||
|
||||
protected void onPostExecute(int[] result) {
|
||||
pb.setVisibility(View.GONE);
|
||||
List<LatLon> alocs = new ArrayList<LatLon>();
|
||||
List<String> anames = new ArrayList<String>();
|
||||
TIntArrayList newOriginalPositions = new TIntArrayList();
|
||||
for (int i = 0; i < result.length; i++) {
|
||||
if (result[i] > 0) {
|
||||
LatLon loc = intermediates.get(result[i] - 1);
|
||||
alocs.add(loc);
|
||||
newOriginalPositions.add(originalPositions.get(intermediates.indexOf(loc)));
|
||||
anames.add(names.get(result[i] - 1));
|
||||
}
|
||||
}
|
||||
intermediates.clear();
|
||||
intermediates.addAll(alocs);
|
||||
names.clear();
|
||||
names.addAll(anames);
|
||||
originalPositions.clear();
|
||||
originalPositions.addAll(newOriginalPositions);
|
||||
listadapter.notifyDataSetChanged();
|
||||
};
|
||||
}.execute(new Void[0]);
|
||||
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
|
||||
private static ArrayAdapter<LatLon> getListAdapter(final OsmandApplication app, final Activity activity, final boolean changeOrder,
|
||||
final List<LatLon> intermediates, final List<String> names, final boolean[] checkedIntermediates) {
|
||||
final List<LatLon> intermediates, final TIntArrayList originalPositions, final List<String> names, final boolean[] checkedIntermediates) {
|
||||
final int padding = (int) (12 * activity.getResources().getDisplayMetrics().density + 0.5f);
|
||||
final ArrayAdapter<LatLon> listadapter = new ArrayAdapter<LatLon>(app,
|
||||
changeOrder? R.layout.change_order_item : R.layout.list_menu_item, R.id.title,
|
||||
|
@ -152,7 +193,7 @@ public class IntermediatePointsDialog {
|
|||
// User super class to create the View
|
||||
View v = super.getView(position, convertView, parent);
|
||||
TextView tv = (TextView) v.findViewById(R.id.title);
|
||||
String nm = (position + 1) + ". ";
|
||||
String nm = originalPositions.get(position) + ". ";
|
||||
String distString = "";
|
||||
if(activity instanceof MapActivity) {
|
||||
double lat = ((MapActivity) activity).getMapView().getLatitude();
|
||||
|
@ -175,8 +216,10 @@ public class IntermediatePointsDialog {
|
|||
if(position > 0) {
|
||||
LatLon old = intermediates.remove(position - 1);
|
||||
String oldN = names.remove(position - 1);
|
||||
int oldI = originalPositions.removeAt(position -1 );
|
||||
names.add(position, oldN);
|
||||
intermediates.add(position, old);
|
||||
originalPositions.insert(position, oldI);
|
||||
notifyDataSetInvalidated();
|
||||
}
|
||||
}
|
||||
|
@ -187,8 +230,10 @@ public class IntermediatePointsDialog {
|
|||
if(position < intermediates.size() - 1) {
|
||||
LatLon old = intermediates.remove(position + 1);
|
||||
String oldN = names.remove(position + 1);
|
||||
int oldI = originalPositions.removeAt(position + 1 );
|
||||
names.add(position, oldN);
|
||||
intermediates.add(position, old);
|
||||
originalPositions.insert(position, oldI);
|
||||
notifyDataSetInvalidated();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -32,6 +32,7 @@ import android.os.Message;
|
|||
import android.text.Editable;
|
||||
import android.text.Spannable;
|
||||
import android.text.TextWatcher;
|
||||
import android.text.style.ForegroundColorSpan;
|
||||
import android.text.style.StyleSpan;
|
||||
import android.view.KeyEvent;
|
||||
import android.view.LayoutInflater;
|
||||
|
@ -45,6 +46,7 @@ import android.widget.Filter;
|
|||
import android.widget.ListView;
|
||||
import android.widget.ProgressBar;
|
||||
import android.widget.TextView;
|
||||
import android.widget.TextView.BufferType;
|
||||
import android.widget.TextView.OnEditorActionListener;
|
||||
|
||||
|
||||
|
@ -137,8 +139,9 @@ public abstract class SearchByNameAbstractActivity<T> extends OsmandListActivity
|
|||
findViewById(R.id.ResetButton).setOnClickListener(new View.OnClickListener(){
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
searchText.setText("");
|
||||
reset();
|
||||
}
|
||||
|
||||
});
|
||||
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE);
|
||||
if(initializeTask != null){
|
||||
|
@ -146,6 +149,10 @@ public abstract class SearchByNameAbstractActivity<T> extends OsmandListActivity
|
|||
}
|
||||
}
|
||||
|
||||
protected void reset() {
|
||||
searchText.setText("");
|
||||
}
|
||||
|
||||
protected void addFooterViews() {
|
||||
}
|
||||
|
||||
|
@ -189,6 +196,10 @@ public abstract class SearchByNameAbstractActivity<T> extends OsmandListActivity
|
|||
querySearch(currentFilter);
|
||||
}
|
||||
|
||||
protected View getFooterView() {
|
||||
return null;
|
||||
}
|
||||
|
||||
private void querySearch(final String filter) {
|
||||
if (!currentFilter.equals(filter) || !initFilter) {
|
||||
currentFilter = filter;
|
||||
|
@ -242,6 +253,10 @@ public abstract class SearchByNameAbstractActivity<T> extends OsmandListActivity
|
|||
|
||||
protected abstract Comparator<? super T> createComparator();
|
||||
|
||||
public String getDistanceText(T obj) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public abstract String getText(T obj);
|
||||
|
||||
public String getShortText(T obj) {
|
||||
|
@ -413,7 +428,15 @@ public abstract class SearchByNameAbstractActivity<T> extends OsmandListActivity
|
|||
row = inflater.inflate(R.layout.searchbyname_list, parent, false);
|
||||
}
|
||||
TextView label = (TextView) row.findViewById(R.id.NameLabel);
|
||||
label.setText(getText(getItem(position)));
|
||||
String distanceText = getDistanceText(getItem(position));
|
||||
String text = getText(getItem(position));
|
||||
if(distanceText == null) {
|
||||
label.setText(text);
|
||||
} else {
|
||||
label.setText(distanceText + " " + text, BufferType.SPANNABLE);
|
||||
((Spannable) label.getText()).setSpan(new ForegroundColorSpan(getResources().getColor(R.color.color_distance)), 0,
|
||||
distanceText.length(), 0);
|
||||
}
|
||||
return row;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,22 +10,69 @@ import net.osmand.CollatorStringMatcher;
|
|||
import net.osmand.CollatorStringMatcher.StringMatcherMode;
|
||||
import net.osmand.ResultMatcher;
|
||||
import net.osmand.data.City;
|
||||
import net.osmand.data.MapObject;
|
||||
import net.osmand.data.MapObject.MapObjectComparator;
|
||||
import net.osmand.data.Street;
|
||||
import net.osmand.plus.OsmAndFormatter;
|
||||
import net.osmand.plus.OsmandApplication;
|
||||
import net.osmand.plus.R;
|
||||
import net.osmand.plus.resources.RegionAddressRepository;
|
||||
import net.osmand.util.Algorithms;
|
||||
import net.osmand.util.MapUtils;
|
||||
import android.os.AsyncTask;
|
||||
import android.os.Message;
|
||||
import android.view.Gravity;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup.LayoutParams;
|
||||
import android.widget.Button;
|
||||
import android.widget.FrameLayout;
|
||||
|
||||
public class SearchStreetByNameActivity extends SearchByNameAbstractActivity<Street> {
|
||||
private RegionAddressRepository region;
|
||||
private City city;
|
||||
private Button searchAllStrets;
|
||||
private int searchWithCity = -1; // -1 - default, 0 - filter city, 1 - deep search
|
||||
|
||||
@Override
|
||||
protected Comparator<? super Street> createComparator() {
|
||||
return new MapObjectComparator(getMyApplication().getSettings().usingEnglishNames());
|
||||
return new MapObjectComparator(getMyApplication().getSettings().usingEnglishNames()) {
|
||||
@Override
|
||||
public int compare(MapObject o1, MapObject o2) {
|
||||
if(searchWithCity >= 0 && city != null) {
|
||||
double d1 = MapUtils.getDistance(city.getLocation(), o1.getLocation());
|
||||
double d2 = MapUtils.getDistance(city.getLocation(), o2.getLocation());
|
||||
return Double.compare(d1, d2);
|
||||
}
|
||||
return super.compare(o1, o2);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void reset() {
|
||||
searchWithCity = -1;
|
||||
super.reset();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected void addFooterViews() {
|
||||
final FrameLayout ll = new FrameLayout(this);
|
||||
searchAllStrets = new Button(this);
|
||||
android.widget.FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
|
||||
lp.gravity = Gravity.CENTER_HORIZONTAL;
|
||||
searchAllStrets.setLayoutParams(lp);
|
||||
searchAllStrets.setText(R.string.search_street_in_neighborhood_cities);
|
||||
ll.addView(searchAllStrets);
|
||||
searchAllStrets.setOnClickListener(new View.OnClickListener() {
|
||||
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
searchWithCity = 1;
|
||||
research();
|
||||
}
|
||||
});
|
||||
getListView().addFooterView(ll);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -50,7 +97,7 @@ public class SearchStreetByNameActivity extends SearchByNameAbstractActivity<Str
|
|||
if (region != null) {
|
||||
city = region.getCityById(settings.getLastSearchedCity(), settings.getLastSearchedCityName());
|
||||
if (city == null) {
|
||||
return null;
|
||||
return new ArrayList<Street>();
|
||||
}
|
||||
region.preloadStreets(city, new ResultMatcher<Street>() {
|
||||
@Override
|
||||
|
@ -73,6 +120,53 @@ public class SearchStreetByNameActivity extends SearchByNameAbstractActivity<Str
|
|||
|
||||
@Override
|
||||
protected void filterLoop(String query, Collection<Street> list) {
|
||||
if(searchWithCity == -1){
|
||||
filter(query, list);
|
||||
} else if(searchWithCity == 0){
|
||||
for (Street obj : list) {
|
||||
if(namesFilter.isCancelled){
|
||||
break;
|
||||
}
|
||||
if(filterObject(obj, query)){
|
||||
Message msg = uiHandler.obtainMessage(MESSAGE_ADD_ENTITY, obj);
|
||||
msg.sendToTarget();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
searchWithCity = 0;
|
||||
final List res = region.searchMapObjectsByName(query, new ResultMatcher<MapObject>() {
|
||||
@Override
|
||||
public boolean publish(MapObject object) {
|
||||
if (object instanceof Street) {
|
||||
if(city == null ||
|
||||
MapUtils.getDistance(city.getLocation(), object.getLocation()) < 100*1000) {
|
||||
Message msg = uiHandler.obtainMessage(MESSAGE_ADD_ENTITY, object);
|
||||
msg.sendToTarget();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCancelled() {
|
||||
return namesFilter.isCancelled;
|
||||
}
|
||||
});
|
||||
runOnUiThread(new Runnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
finishInitializing(res);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
private void filter(String query, Collection<Street> list) {
|
||||
boolean emptyQuery = query == null || query.length() == 0;
|
||||
for (Street obj : list) {
|
||||
if (namesFilter.isCancelled) {
|
||||
|
@ -99,12 +193,28 @@ public class SearchStreetByNameActivity extends SearchByNameAbstractActivity<Str
|
|||
|
||||
@Override
|
||||
public String getText(Street obj) {
|
||||
if(searchWithCity >= 0 || city == null) {
|
||||
String nameWithCity = obj.getName(region.useEnglishNames()) + " - " + obj.getCity().getName(region.useEnglishNames());
|
||||
return nameWithCity ;
|
||||
}
|
||||
return obj.getName(region.useEnglishNames());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDistanceText(Street obj) {
|
||||
if(searchWithCity >= 0 && city != null) {
|
||||
return OsmAndFormatter.getFormattedDistance((float) MapUtils.getDistance(obj.getLocation(), city.getLocation()),
|
||||
getMyApplication());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void itemSelected(Street obj) {
|
||||
if(!Algorithms.objectEquals(settings.getLastSearchedCity(), obj.getCity().getId())) {
|
||||
settings.setLastSearchedCity(obj.getCity().getId(), obj.getCity().getName(), obj.getLocation());
|
||||
}
|
||||
settings.setLastSearchedStreet(obj.getName(region.useEnglishNames()), obj.getLocation());
|
||||
finish();
|
||||
|
||||
|
|
Loading…
Reference in a new issue