I am trying to get city in TextView using latitude and longitude. I am getting IndexOutOfBoundsException.
AndroidGPSTrackingActivity.java
import android.app.Activity;
import android.location.Address;
import android.location.Geocoder;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import java.io.IOException;
import java.util.List;
import java.util.Locale;
import static com.example.khaledsb.location.R.id.lng;
import static java.util.Locale.*;
public class AndroidGPSTrackingActivity extends Activity {
public static float distFrom(float lat1, float lng1, float lat2, float lng2) {
double earthRadius = 6371000; //meters
double dLat = Math.toRadians(lat2-lat1);
double dLng = Math.toRadians(lng2-lng1);
double a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(Math.toRadians(lat1)) * Math.cos(Math.toRadians(lat2)) *
Math.sin(dLng/2) * Math.sin(dLng/2);
double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
float dist = (float) (earthRadius * c);
return dist;
}
Button btnShowLocation;
// GPSTracker class
GPSTracker gps;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
btnShowLocation = (Button) findViewById(R.id.btnShowLocation);
final TextView lat =(TextView) findViewById(R.id.lat);
final TextView lon = (TextView) findViewById(R.id.longt);
final TextView addr = (TextView) findViewById(R.id.address);
// show location button click event
btnShowLocation.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View arg0) {
// create class object
gps = new GPSTracker(AndroidGPSTrackingActivity.this);
// check if GPS enabled
if(gps.canGetLocation()){
double latitude = gps.getLatitude();
double longitude = gps.getLongitude();
double Distance;
Distance = distFrom((float) 36.5925907, 2.9051544f, 36.5805505f, 2.914749f);
lat.setText(String.valueOf(latitude));
lon.setText(String.valueOf(longitude));
Geocoder geocoder = new Geocoder(AndroidGPSTrackingActivity.this, Locale.ENGLISH);
try {
List<Address> addresses = geocoder.getFromLocation(latitude, longitude, 1);
if(addresses != null) {
Address returnedAddress = addresses.get(0);
StringBuilder strReturnedAddress = new StringBuilder("Address:\n");
for(int i=0; i<returnedAddress.getMaxAddressLineIndex(); i++) {
strReturnedAddress.append(returnedAddress.getAddressLine(i)).append("\n");
}
addr.setText(strReturnedAddress.toString());
}
else{
addr.setText("No Address returned!");
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
addr.setText("Can not get Address!");
}
// \n is for new line
//Toast.makeText(getApplicationContext(), "Your Location is - \nLat: " + latitude + "\nLong: " + longitude+" " +
//" diastance "+Distance, Toast.LENGTH_LONG).show();
}else{
// can't get location
// GPS or Network is not enabled
// Ask user to enable GPS/network in settings
gps.showSettingsAlert();
}
}
});
}
}
I am getting the following error in logcat :
5-09 11:17:21.858 4501-4501/com.example.khaledsb.location E/AndroidRuntime: FATAL EXCEPTION: main
java.lang.IndexOutOfBoundsException: Invalid index 0, size is 0
at java.util.ArrayList.throwIndexOutOfBoundsException(ArrayList.java:251)
at java.util.ArrayList.get(ArrayList.java:304)
at com.example.khaledsb.location.AndroidGPSTrackingActivity$1.onClick(AndroidGPSTrackingActivity.java:79)
at android.view.View.performClick(View.java:4204)
at android.view.View$PerformClick.run(View.java:17355)
at android.os.Handler.handleCallback(Handler.java:725)
at android.os.Handler.dispatchMessage(Handler.java:92)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:5041)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:511)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560)
at dalvik.system.NativeStart.main(Native Method)
Try
Geocoder gcd = new Geocoder(this, Locale.getDefault());
List<Address> addresses = null;
try {
addresses = gcd.getFromLocation(lat, lng, 1);
} catch (IOException e) {
e.printStackTrace();
}
if (addresses != null && addresses.size() > 0) {
String locality = addresses.get(0).getLocality();
}
Use below code to get city name
Geocoder geocoder = new Geocoder(this);
try {
List<Address>addresses = geocoder.getFromLocation(latitude,longitue,1);
if (geocoder.isPresent()) {
StringBuilder stringBuilder = new StringBuilder();
if (addresses.size()>0) {
Address returnAddress = addresses.get(0);
String localityString = returnAddress.getLocality();
String name = returnAddress.getFeatureName();
String subLocality = returnAddress.getSubLocality();
String country = returnAddress.getCountryName();
String region_code = returnAddress.getCountryCode();
String zipcode = returnAddress.getPostalCode();
String state = returnAddress.getAdminArea();
}
} else {
}
} catch (IOException e) {
e.printStackTrace();
}
Try this code, Hope it helps..
private static String getRegionName(double lati, double longi) {
String regioName = "";
Geocoder gcd = new Geocoder(AppInstance, Locale.getDefault());
try {
List<Address> addresses = gcd.getFromLocation(lati, longi, 1);
if (addresses.size() > 0) {
regioName = addresses.get(0).getLocality();
}
} catch (Exception e) {
e.printStackTrace();
}
return regioName;
}
Try to use following code to get complete address,
//Get address from Google api
//Log.e("Else","else");
try {
JSONObject jsonObj = getJSONfromURL("http://maps.googleapis.com/maps/api/geocode/json?latlng=" + latitude + ","
+ longitude + "&sensor=true");
String Status = jsonObj.getString("status");
if (Status.equalsIgnoreCase("OK")) {
JSONArray Results = jsonObj.getJSONArray("results");
JSONObject location = Results.getJSONObject(0);
finalAddress = location.getString("formatted_address");
}
} catch (Exception e) {
e.printStackTrace();
}
instead of,
geocoder.getFromLocation(latitude, longitude, 1);
For Avoid ArrayIndexOutOfBound you could add if condition like below:
if (addresses != null && addresses.size() > 0) {
String locality = addresses.get(0).getLocality();
}
but, as I saw your code you are trying to get address using GeoCoder inside button click, So avoid this because it is a network call. You should not perform network call in main thread, it could block UI Or Cause ANR. You should use AsyncTask/Thread for network operation to avoid blocking Of UI.
Also make sure you have added
INTERNET_PERMISSION
in your manifest file.
Hope It help you !
Error states that the Array list is empty so make sure you initialize the list and check if it contains any data.
try this code:
List<Address> addresses = new List<Address>;
addresses = geocoder.getFromLocation(latitude, longitude, 1);
if(addresses != null) {
String address = addresses.get(0).getAddressLine(0);
String city = addresses.get(0).getLocality();
String state = addresses.get(0).getAdminArea();
String country = addresses.get(0).getCountryName();
String postalCode = addresses.get(0).getPostalCode();
String knownName = addresses.get(0).getFeatureName();
}
This should give you required info.
Fetching location address from latlong co-ordinates fetched from Location object.
#Override
public void onLocationChanged(Location location) {
String longitude = "Longitude: " + location.getLongitude();
Log.v(TAG, longitude);
String latitude = "Latitude: " + location.getLatitude();
Log.v(TAG, latitude);
String address = null;
String knownName = null;
String city = null;
String state = null;
String country = null;
String postalCode = null;
Geocoder gcd = new Geocoder(MainActivity.this.getBaseContext(), Locale.getDefault());
List<Address> addresses;
try {
addresses = gcd.getFromLocation(location.getLatitude(), location.getLongitude(), 1);
address = addresses.get(0).getAddressLine(0);
if (addresses.get(0).getFeatureName() != address) {
knownName = addresses.get(0).getFeatureName();
}
city = addresses.get(0).getLocality();
state = addresses.get(0).getAdminArea();
country = addresses.get(0).getCountryName();
postalCode = addresses.get(0).getPostalCode();
} catch (IOException e) {
e.printStackTrace();
}
String foundAddress = knownName + ", " + address + ", " + city + ", " + state + ", " + country + "- " + postalCode + "\n";
myLocation.setText(foundAddress);
storeLocation();
}
My findViewById is throwing error saying it has not been defined and it asks me to create a function. What should I do?
public void geoLocate(View v) throws IOException {
hideSoftKeyboard(v);
EditText et = (EditText) findViewById(R.id.editText1);
String location = et.getText().toString();
Geocoder gc = new Geocoder(context);
List<Address> list = gc.getFromLocationName(location, 1);
Address add = list.get(0);
String locality = add.getLocality();
Toast.makeText(context, locality, Toast.LENGTH_LONG).show();
double lat = add.getLatitude();
double lng = add.getLatitude();
gotoLocation(lat, lng, DEFAULTZOOM);
MarkerOptions markerOptions = new MarkerOptions().title(locality).position(new LatLng(lat,lng));
mMap.addMarker(markerOptions);
}
In your function find id like this
EditText et = (EditText) v.findViewById(R.id.editText1);
You havve to use the View variable passed in the method to find id
My full code
https://gist.github.com/anonymous/6dd0f33270cc4f46149e
In line 110~131 I want to change the location, it does work, the mapview will change
private class MapClickedListener implements OnClickListener {
#Override
public void onClick (View v) {
String lng = "121.558561";
lng = edt_lng.getText().toString().trim();
String lat = "25.031005";
lat = edt_lat.getText().toString().trim();
if(lng.equals("")||lat.equals("")){
Toast.makeText(getApplicationContext(), "input again!", Toast.LENGTH_LONG).show();
location = locManager.getLastKnownLocation(bestProvider);
updateToNewLocation(location);
}else{
Location location = new Location(LocationManager.NETWORK_PROVIDER);
location.setLongitude(Double.parseDouble(lng));
location.setLatitude(Double.parseDouble(lat));
updateToNewLocation(location);
}
}
}
On line 133~148, I want to know distance between location and a point I set
private Button.OnClickListener EQ = new Button.OnClickListener(){
#Override
public void onClick (View v) {
eqlocation.setLongitude(120.82);
eqlocation.setLatitude(23.85);
location = locManager.getLastKnownLocation(bestProvider);
float[] result = new float[5];
Location.distanceBetween(location.getLatitude(), location.getLongitude(), eqlocation.getLatitude(), eqlocation.getLongitude(), result);
BigDecimal bd = new BigDecimal(result[0]);
BigDecimal rounded = bd.setScale(2, RoundingMode.HALF_UP);
double dis = rounded.doubleValue();
String dist = String.valueOf(dis/1000);
Toast.makeText(getApplicationContext(), "distance: " + dist + "km", Toast.LENGTH_LONG).show();
}
};
But the result is wrong when I change the location by line 110~131's code.
What should I do to get the right result?
have you tried distanceTo() and checked if you get any better results?, I ususally use distanceTo() with good results.
In my app I am using osm map. I have latitude and longitude.
using this method
proj = mapView.getProjection();
loc = (GeoPoint) proj.fromPixels((int) e.getX(), (int) e.getY());
String longitude = Double
.toString(((double) loc.getLongitudeE6()) / 1000000);
String latitude = Double
.toString(((double) loc.getLatitudeE6()) / 1000000);
Toast toast = Toast.makeText(getApplicationContext(), "Longitude: "
+ longitude + " Latitude: " + latitude, Toast.LENGTH_SHORT);
toast.show();
So from here how I will query to get the city name from osm database. Please help me.
How can I convert this into human understandable form. Here is my code which I am using.link
Try this code for getting address.
Geocoder geocoder;
List<Address> addresses;
geocoder = new Geocoder(this, Locale.getDefault());
addresses = geocoder.getFromLocation(latitude, longitude, 1);
String address = addresses.get(0).getAddressLine(0);
String city = addresses.get(0).getAddressLine(1);
String country = addresses.get(0).getAddressLine(2);
for openstreammap
final String requestString = "http://nominatim.openstreetmap.org/reverse?format=json&lat=" +
Double.toString(lat) + "&lon=" + Double.toString(lon) + "&zoom=18&addressdetails=1";
RequestBuilder builder = new RequestBuilder(RequestBuilder.GET, URL.encode(requestString));
try {
#SuppressWarnings("unused")
Request request = builder.sendRequest(null, new RequestCallback() {
#Override
public void onResponseReceived(Request request, Response response) {
if (response.getStatusCode() == 200) {
String city = "";
try {
JSONValue json = JSONParser.parseStrict(response);
JSONObject address = json.isObject().get("address").isObject();
final String quotes = "^\"|\"$";
if (address.get("city") != null) {
city = address.get("city").toString().replaceAll(quotes, "");
} else if (address.get("village") != null) {
city = address.get("village").toString().replaceAll(quotes, "");
}
} catch (Exception e) {
}
}
}
});
} catch (Exception e) {
}
here is my solution. i think it works for you also.
public String ConvertPointToLocation(GeoPoint point) {
String address = "";
Geocoder geoCoder = new Geocoder( getBaseContext(), Locale.getDefault());
try {
List<Address> addresses = geoCoder.getFromLocation(
point.getLatitudeE6() / 1E6,
point.getLongitudeE6() / 1E6, 1);
if (addresses.size() > 0) {
for (int index = 0; index < addresses.get(0).getMaxAddressLineIndex(); index++)
address += addresses.get(0).getAddressLine(index) + " ";
}
Toast.makeText(getBaseContext(), address, Toast.LENGTH_SHORT).show();
}
catch (IOException e) {
e.printStackTrace();
}
return address;
}
Im trying to display the address from an EditText using geoCoder and also it would be able editable to click on the finder button and update the googlemap display on the top of the screen, this is my code:
Geocoder geocoder = null;
MapView mapView = null;
int lat, lng;
EditText loc;
#Override
protected boolean isRouteDisplayed() {
return false;
}
#Override
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
setContentView(R.layout.main);
mapView = (MapView) findViewById(R.id.geoMap);
try
{
loc = (EditText)findViewById(R.id.location);
String locationName = loc.getText().toString();
List<Address> addressList = geocoder.getFromLocationName(locationName, 5);
if (addressList != null && addressList.size() > 0) {
lat = (int) addressList.get(0).getLatitude() * 1000000;
lng = (int) addressList.get(0).getLongitude() * 1000000;
GeoPoint pt = new GeoPoint(lat, lng);
mapView.getController().setZoom(10);
mapView.getController().setCenter(pt);
mapView.getController().animateTo(pt);
}
}
catch
(IOException e)
{
e.printStackTrace();
}
//
Button geoBtn = (Button) findViewById(R.id.geocodeBtn);
geocoder = new Geocoder(this);
//
geoBtn.setOnClickListener(new OnClickListener() {
public void onClick(View arg0) {
try {
EditText loc = (EditText) findViewById(R.id.location);
String locationName = loc.getText().toString();
List<Address> addressList = geocoder.getFromLocationName(locationName, 5);
if (addressList != null && addressList.size() > 0) {
int lat = (int) addressList.get(0).getLatitude() * 1000000;
int lng = (int) addressList.get(0).getLongitude() * 1000000;
GeoPoint pt = new GeoPoint(lat, lng);
mapView.getController().setZoom(10);
mapView.getController().setCenter(pt);
mapView.getController().animateTo(pt);
}
} catch (IOException e) {
e.printStackTrace();
}
}
});
}
But it crashes at this point: List addressList = geocoder.getFromLocationName(locationName, 5);
Im using googles APi 2.3.3.