i'm using for firts time Retrofit on my Android app.
This is the structure of json object that i have to retrive:
{
"placemarks":[
{
"address":"Via di Santa Maria a Marignolle, 15, 50124 Firenze",
"coordinates":[
11.23348,
43.75855,
0
],
"engineType":"CE",
"exterior":"GOOD",
"fuel":100,
"interior":"GOOD",
"name":"049/EV284TP",
"smartPhoneRequired":false,
"vin":"WME4513341K774636"
}
]
}
i have write this Pojo model for object "placemarks" and all otehr items.
And i have write this code to retrive the json data and put it into map:
private void getPlacemark(){
Retrofit retrofit = new Retrofit.Builder()
.baseUrl("https://www.car2go.com/api/v2.1/vehicles?loc=roma&oauth_consumer_key=roadzapp&format=json")
.addConverterFactory(GsonConverterFactory.create())
.build();
APIService service = retrofit.create(APIService.class);
Call<ResponsePlacemarks> call = service.getPlacemark();
call.enqueue(new Callback<ResponsePlacemarks>() {
#Override
public void onResponse(Response<ResponsePlacemarks> response, Retrofit retrofit) {
Log.d("response: ", String.valueOf(response.body()));
try {
mMap.clear();
// This loop will go through all the results and add marker on each location.
for (int i = 0; i < response.body().getPlacemarks().size(); i++) {
Double lat = response.body().getPlacemarks().get(i).getCoordinates().get(1);
Double lng = response.body().getPlacemarks().get(i).getCoordinates().get(0);
String placeName = response.body().getPlacemarks().get(i).getAddress();
MarkerOptions markerOptions = new MarkerOptions();
LatLng latLng = new LatLng(lat, lng);
// Position of Marker on Map
markerOptions.position(latLng);
// Adding Title to the Marker
markerOptions.title(placeName);
// Adding Marker to the Camera.
Marker m = mMap.addMarker(markerOptions);
// Adding colour to the marker
markerOptions.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_RED));
// move map camera
mMap.moveCamera(CameraUpdateFactory.newLatLng(latLng));
mMap.animateCamera(CameraUpdateFactory.zoomTo(11));
}
} catch (Exception e) {
Log.d("onResponse", "There is an error");
e.printStackTrace();
}
}
#Override
public void onFailure(Throwable t) {
}
});
}
but now when i run app the json are note load and i have error in the first line of for loop:
java.lang.NullPointerException: Attempt to invoke virtual method 'java.util.List android.mobility.com.mobiity.model.ResponsePlacemarks.getPlacemarks()' on a null object reference
Hi have found the error.
On APIService i have set #GET method in this way: #GET(".") because i use as URL the URL into BaseURL. So if i set all url into #GET the method works fine.
How i can use only the url into BaseULRalso into #GET?
First, you can only call response.body() exactly once.
So, comment this.
// Log.d("response: ", String.valueOf(response.body()));
And extract that list variable
final ResponsePlacemarks _response = response.body();
final List<Placemark> placemarks = _response.getPlacemarks();
for (int i = 0; i < placemarks.size(); i++) {
final Placemark p = placemarks.get(i);
Coordinates c = p.getCoordinates();
Double lat = c.get(1);
Double lng = c.get(0);
String placeName = p.getAddress();
And if that doesn't work, then you need for the Java object to exactly match the JSON response, otherwise it is null
How i can use only the url into BaseULRalso into #GET?
Your base URL should look like something this
https://www.car2go.com/api/v2.1
Then you should be able to have something like
#GET("/vehicles")
public ResponsePlacemarks getVehicles(
#Query("oauth_consumer_key") String key,
#Query("format") String format
#Query("loc") String loc
);
public ResponsePlacemarks getVehicles(String loc) {
return getVehicles("roadzapp", "json", loc);
}
Or maybe just
#GET("/vehicles?format=json")
public ResponsePlacemarks getVehicles(
#Query("oauth_consumer_key") String key,
#Query("loc") String loc
);
The reason for putting the key into the method call is that you shouldn't store the key as a string on your device for security reasons.
Most likely your POJO does not match the JSON structure.
Can you post your POJO class and how are you deserializing the JSON?
Related
I'm writing a lambda expression to convert the given latitude and longitude into an address. The expression is supposed to take co-ordinates as arguments and returns their corresponding address. However, the value returned is null. Following is my class:
public class LambdaDeclarations {
String loc;
private static final String TAG = "LambdaDeclarations";
public CoordinatesToAddressInterface convert = (latitude, longitude, context) -> {
RequestQueue queue = Volley.newRequestQueue(context);
Log.d(TAG, "onCreate: Requesting: Lat: "+latitude+" Lon: "+longitude);
String url ="https://maps.googleapis.com/maps/api/distancematrix/json?units=metric&origins="+latitude+","+longitude+"&destinations="+latitude+","+longitude+"&key=AIzaSyCdKSW0glin4h9sGYa_3hj0L83zI0NsNRo";
// Request a string response from the provided URL.
StringRequest stringRequest = new StringRequest(Request.Method.GET, url,
(String response) -> {
try {
JSONObject jsonObject = new JSONObject(response);
JSONArray destinations = jsonObject.getJSONArray("destination_addresses");
Log.d(TAG, "GETRequest: JSON Object: "+destinations.toString());
String location = destinations.toString();
Log.d(TAG, "Location: "+location);
setLocation(location);
} catch (JSONException e) {
e.printStackTrace();
}
}, error -> Log.d(TAG, "onErrorResponse: That didn't work!"));
queue.add(stringRequest);
return getLocation();
};
public String getLocation() {
return loc;
}
public void setLocation(String location) {
this.loc = location;
}
}
Following is the output from logcat:
09-16 10:31:09.160 26525-26525/com.rmit.tejas.mad_foodtruck_2 D/LambdaDeclarations: GETRequest: JSON Object: ["77 State Route 32, West Melbourne VIC 3003, Australia"]
Location: ["77 State Route 32, West Melbourne VIC 3003, Australia"]
09-16 10:31:09.176 26525-26525/com.rmit.tejas.mad_foodtruck_2 D/LambdaDeclarations: GETRequest: JSON Object: ["111 Adderley St, West Melbourne VIC 3003, Australia"]
Location: ["111 Adderley St, West Melbourne VIC 3003, Australia"]
09-16 10:31:09.177 26525-26525/com.rmit.tejas.mad_foodtruck_2 D/LambdaDeclarations: GETRequest: JSON Object: ["4\/326 William St, Melbourne VIC 3000, Australia"]
Location: ["4\/326 William St, Melbourne VIC 3000, Australia"]
Following is my usage:
myViewHolder.textView3.setText("Location: i->"+i+" add: "+l.convert.toAddress(trackingInfos.get(i).getLatitude(),trackingInfos.get(i).getLongitude(),context));
l is an object of the class LambdaDeclarations and following is the relevant interface:
public interface CoordinatesToAddressInterface {
String toAddress(double latitude, double longitude, Context context);
}
When I try to print the coordinates from the relevant adapter they are getting printed correctly. So the location is getting set properly but when I try to access it from another class it shows me a null value for the string. Can you please advise an alternate method to extract the location from the expression?
First of all, Lambda Expression is just a anonymous class implementation, it was design to be used as a method or class argument and solve shadowing issues of anonymous class.
So in your case, you don't need it at all, just simply implement CoordinatesToAddressInterface interface as named class as usual.
Second, you used Volley wrong, the first lambda you provided to StringRequest, hereafter will be call response callback, is going to be called when HTTP request finish but the return statement
return getLocation();
will return null immediately before your setLocation(location) or even your response callback ever get executed, that why you got null every time you call convert(), though you can still see log that you print because the response callback will be executed anyway (assume that request is success).
To use response callback correctly, you have to update your UI inside callback, pretty much like this
public class MyAdapter extends RecyclerView.Adapter<MyAdapter.MyViewHolder> {
public static final String TAG = "MyAdapter";
private RequestQueue mQueue;
public MyAdapter(Context context) {
this.mQueue = Volley.newRequestQueue(context);
}
public RequestQueue getMyAdapterRequestQueue() {
return this.mQueue;
}
...
#Override
public void onBindViewHolder(#NonNull final MyViewHolder holder, int position) {
String url ="some url";
StringRequest stringRequest = new StringRequest(Request.Method.GET, url,
(String response) -> {
try {
JSONObject jsonObject = new JSONObject(response);
JSONArray destinations = jsonObject.getJSONArray("destination_addresses");
Log.d(TAG, "GETRequest: JSON Object: "+destinations.toString());
String location = destinations.toString();
Log.d(TAG, "Location: "+location);
// update UI
holder.mTextView.setText(location);
} catch (JSONException e) {
e.printStackTrace();
}
}, error -> Log.d(TAG, "onErrorResponse: That didn't work!"));
stringRequest.setTag(TAG);
mQueue.add(stringRequest);
}
Of course, you can edit your interface's method signature and make your adapter implement that interface (I would rather do it this way though) but the point is that you have to process asynchronous results in callback method, never expect asynchronous operation's callback to finish before your next lines of code.
RequestQueue shouldn't be created per-request since it manages internal state that help you make request faster (caching), you can also cancel requests too in an event like phone rotation and your will get destroy, in this case, just call cancel method in Activity/Fragment's onStop()
#Override
protected void onStop () {
super.onStop();
if (myAdapter.getMyAdapterRequestQueue() != null) {
myAdapter.getMyAdapterRequestQueue().cancelAll(MyAdapter.TAG);
}
}
Response callback won't be called after you cancel request.
I have an activity implementing OnMapReadyCallback to display some markers.
Before opening the map i provide a target city which i'd like to look at closer on the map basically by calling :
LatLng currentCity = new LatLng(cityLat,cityLng)
CameraUpdate location = CameraUpdateFactory.newLatLngZoom(currentCity,13);
googleMap.animateCamera(location);
The main problem here is that the zoom level is just an arbitrary number which works fine for some city and bad for others (Too zoomed in, Not enough zoomed in).
What i would like to achieve is to determine the zoom level dynamically depending on the city in the same way Google Maps does.
I know that the bigger the ViewPort of the city is, the smaller the zoom needs to be but i can't find a method to get the ViewPort for a given city and then changing the zoom level accordingly
EDIT : I was thinking about using a Geocoder to get a list of adress using the latitude and longitude of the city using
List<Address> addresses = mGeocoder.getFromLocation(Lat,Lon,maxLimit);
and then iterating over this list to find out the outermost adresses avaible for that city, in order to build a LatLngBounds to pass at setLatLngBoundsForCameraTarget() method.
The main problem with this approach is that, once again, the "maxLimit" is arbitrary and needs to be quite big for a big city, eventually returning a really big List
You can retrieve a view port for the city from the Geocoding API reverse geocoding response.
You should execute HTTP request to retrieve city view port from your activity. Once you receive the response you can construct the LatLngBounds instance and move camera accordingly.
Sample reverse geocoding request that gets city from coordinates is the following
https://maps.googleapis.com/maps/api/geocode/json?latlng=47.376887%2C8.541694&result_type=locality&key=YOUR_API_KEY
I wrote a small example for Map activity that receives lat and lng from the intent, executes the reverse geocoding HTTP request using the Volley library and moves camera to show the city view port.
public class MapsActivity extends FragmentActivity implements OnMapReadyCallback {
private GoogleMap mMap;
private float lat;
private float lng;
private String name;
private RequestQueue mRequestQueue;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Intent i = getIntent();
this.lat = i.getFloatExtra("lat", 0);
this.lng = i.getFloatExtra("lng", 0);
this.name = i.getStringExtra("name");
mRequestQueue = Volley.newRequestQueue(this);
setContentView(R.layout.activity_maps);
// Obtain the SupportMapFragment and get notified when the map is ready to be used.
SupportMapFragment mapFragment = (SupportMapFragment) getSupportFragmentManager()
.findFragmentById(R.id.map);
mapFragment.getMapAsync(this);
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
// Add a marker in Sydney and move the camera
LatLng pos = new LatLng(this.lat, this.lng);
mMap.addMarker(new MarkerOptions().position(pos).title(this.name));
mMap.moveCamera(CameraUpdateFactory.newLatLng(pos));
this.fetchReverseGeocodeJson();
}
private void fetchReverseGeocodeJson() {
// Pass second argument as "null" for GET requests
JsonObjectRequest req = new JsonObjectRequest(Request.Method.GET,
"https://maps.googleapis.com/maps/api/geocode/json?latlng=" + this.lat + "%2C" + this.lng + "&result_type=locality&key=AIzaSyBrPt88vvoPDDn_imh-RzCXl5Ha2F2LYig",
null,
new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
try {
String status = response.getString("status");
if (status.equals("OK")) {
JSONArray results = response.getJSONArray("results");
JSONObject item = results.getJSONObject(0);
JSONObject geom = item.getJSONObject("geometry");
JSONObject bounds = geom.getJSONObject("viewport");
JSONObject ne = bounds.getJSONObject("northeast");
JSONObject sw = bounds.getJSONObject("southwest");
LatLngBounds mapbounds = new LatLngBounds(new LatLng(sw.getDouble("lat"),sw.getDouble("lng")),
new LatLng(ne.getDouble("lat"), ne.getDouble("lng")));
mMap.moveCamera(CameraUpdateFactory.newLatLngBounds(mapbounds, 0));
}
} catch (JSONException e) {
e.printStackTrace();
}
}
},
new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
VolleyLog.e("Error: ", error.getMessage());
}
}
);
/* Add your Requests to the RequestQueue to execute */
mRequestQueue.add(req);
}
}
You can find a complete sample project at github:
https://github.com/xomena-so/so44735477
Hope this helps!
I am looking for an example how could I send file and other params together to server.
I have to send server JSON which
{
"title": "title",
"file": "uploaded file instance",
"location": {
"lat": 48.8583,
"lng": 2.29232,
"place": "Eiffel Tower"
}
}
How could I create Retrofit to handle this case?
If file is a string I know how to handle this. If file is File object I have no idea how to do this.
Use gson and create a model class for the location.
Add the following dependencies to your build.gradle.
compile 'com.squareup.retrofit2:converter-gson:2.0.0'
compile 'com.google.code.gson:gson:2.5'
Create a model to represent the location.
public class Location {
double lat;
double lng;
String location;
public Location(double lat, double lon, String place) {
this.lat = lat;
this.lon = long;
this.place = place;
}
}
If the variable names for the payload fields don't match the actual required name for the endpoint you will need to add the annotation #SerializedName([expected name])
ex:
import com.google.gson.annotations.SerializedName;
public class Location {
#SerializedName("lat")
double latitude;
#SerializedName("lng")
double longitude;
#SerializedName("place")
String location;
public Location(double lat, double lon, String place) {
latitude = lat;
longitude = long;
location = place;
}
}
Define the api interface.
public interface Api {
#POST("upload/")
#Multipart
Call<ResponseBody> uploadFile(#Part("title") RequestBody title,
#Part MultipartBody.Part imageFile,
#Part("location") Location location
);
}
Create a Retrofit instance and call the api.
File file;
// create retrofit instance
Retrofit retrofit = new Retrofit.Builder()
.baseUrl("https://baseurl.com/api/")
.addConverterFactory(GsonConverterFactory.create())
.build();
// create api instance
Api api = retrofit.create(Api.class);
// create call object
Call<ResponseBody> uploadFileCall = api.uploadFile(
RequestBody.create(MediaType.parse("text/plain"), "title"),
MultipartBody.Part.createFormData(
"file",
file.getName(),
RequestBody.create(MediaType.parse("image"), file)),
new Location(48.8583, 2.29232, "Eiffel Tower"));
// sync call
try {
ResponseBody responseBody = uploadFileCall.execute().body();
} catch (IOException e) {
e.printStackTrace();
}
// async call
uploadFileCall.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
if (response.isSuccessful()) {
// TODO
}
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
// TODO
}
});
You will need to change the MediaType.parse() call if you are not using an image file.
You can similarly create a custom response type object and replace ResponseBody with it to receive a deserialized result object.
Let me know if this works. I didn't have a chance to test in your exact scenario obviously but I'm fairly confident this should work. The only part I'm not 100% on is whether #Part("location") Location location should be #Body("location") Location location
As of 02.2020 #Abtin Gramian's answer is great, except RequestBody.create() and MediaType.parse() are deprecated in Kotlin, so you have to use:
file.asRequestBody("image".toMediaTypeOrNull())
instead of:
RequestBody.create(MediaType.parse("image"), file)
Also, I had to write the following manually:
import okhttp3.MediaType.Companion.toMediaTypeOrNull
import okhttp3.RequestBody.Companion.asRequestBody
I have implemented Google Place API autocomplete functionality for my application like this: https://developers.google.com/places/training/autocomplete-android
No it just makes a Toast with that address.
How can I get the latitude and longitude from the selected address?
Use the method
public List<Address> getFromLocationName (String locationName, int maxResults) from Android Geocoder API, pass in the location name and the maximum number of results you would like and you should be good to go.
Eg.
Geocoder coder = new Geocoder(this);
try {
ArrayList<Address> adresses = (ArrayList<Address>) coder.getFromLocationName("Some Address", 10);
for(Address add : adresses){
double longitude = add.getLongitude();
double latitude = add.getLatitude();
}
} catch (IOException e) {
e.printStackTrace();
} catch(IllegalArgumentException e){
e.printStackTrace();
}
If it helps, I've recently created a library in Java for Google Places API.
Autocompletion is as simple as:
GooglePlaces client = new GooglePlace("apiKey");
List<Prediction> predictions = client.getPlacePredictions("Empire");
for (Prediction prediction : predictions) {
String description = prediction.getDescription();
// etc etc
}
And getting a latitude-longitude from an address is as simple as.
List<Place> places = client.getPlacesByQuery(address, GooglePlaces.MAXIMUM_RESULTS);
for (Place place : places) {
if (place.getAddress().equals(address)) {
double lat = place.getLatitude();
double lng = place.getLongitude();
}
}
https://github.com/windy1/google-places-api-java
You can simply use google maps api to get the lat and long
http://maps.google.com/maps/api/geocode/json?address=&sensor=false
In the above link u have to add the address next to "address=" and u can get the json data with lat and long and some other infos.
Try GeoDataClient. Refer GeoDataClient and Place IDs and details.
geoDataClient.getPlaceById(autoCompletePredictionItem.getPlaceId())
.addOnCompleteListener(new OnCompleteListener<PlaceBufferResponse>() {
#Override
public void onComplete(#NonNull Task<PlaceBufferResponse> task) {
if (task.isSuccessful()) {
PlaceBufferResponse places = task.getResult();
Place myPlace = places.get(0);
Log.e(TAG, "Place found: " + myPlace.getLatLng().toString());
places.release();
} else {
Log.e(TAG, "Place not found.");
}
}
});
According to updated documents, GeoDAtaClient is deprecated. New way is to use this:
// Define a Place ID. val placeId = "INSERT_PLACE_ID_HERE"
// Specify the fields to return. val placeFields = listOf(Place.Field.ID, Place.Field.NAME)
// Construct a request object, passing the place ID and fields array. val request = FetchPlaceRequest.newInstance(placeId, placeFields)
placesClient.fetchPlace(request)
.addOnSuccessListener { response: FetchPlaceResponse ->
val place = response.place
Log.i(PlaceDetailsActivity.TAG, "Place found: ${place.name}")
}.addOnFailureListener { exception: Exception ->
if (exception is ApiException) {
Log.e(TAG, "Place not found: ${exception.message}")
val statusCode = exception.statusCode
TODO("Handle error with given status code")
}
}
https://developers.google.com/maps/documentation/places/android-sdk/place-details#maps_places_get_place_by_id-kotlin
Is it possible to use it as library project for my application,i want to use Android Google Maps real app search-ability functionality. How can i do it,is it possible?
Thanks in advance..
EDIT:
I have shown Google Map in my app successfully, I want to include Google Map search functionality means that I can able to search any location in the world in auto suggested field and by selecting a particular location and move marker to that location. so how can I?
I tried this and this but not getting auto suggested text why I don't know..
I want like:
step1: show map with search box
step2: while entering text it should auto suggest.
step3: when click on particular name move map to that location
You can easily provide that kind of search functionality by using Places API and Geocode API (Both will help you according to your usecase).
Read the below Documentation for your assistance.
GeoCode API
Places API
I would recommend to use Places API for your need ( As per my observation on your usecase). But you could also use geocode, If you needed.
Many working reference and examples are there.
For startup, below are my reference :
PlacesAPI AutoComplete feature, Hotel Finder with Autocomplete
GeocodeAPI Simple GeoCoding
NOTE :
I have suggested javascript API. But not sure whether it will help you in Android environment (I dont know anything about android environment).
No single Api can help you have to use multiple google api's
Step1. Implement Google Place autocomplete Read this
Step2. You have to geocode means you have to convert address to latitude and longitude check this
Step3. Now You can plot these lat-long on the map.
This works for me.
I think you should take a look at the Google Maps API for Android at https://developers.google.com/maps/documentation/android/
The Google Search Appliance doesn't have any mapping or geo search features right now.
This is how I did it ---
Android Manifest file should contain the following lines:
<uses-library
android:name="com.google.android.maps"
android:required="true" >
</uses-library>
<!-- You must insert your own Google Maps for Android API v2 key in here. -->
<meta-data
android:name="com.google.android.maps.v2.API_KEY"
android:value="<put your api key value here>" />
Location XML file should have the following apart from anything extra:
<fragment
android:name="com.google.android.gms.maps.SupportMapFragment"
android:id="#+id/map"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
Location java file should have something like this:
View mapView = null;
private GoogleMap mMap;
mMap = supportMapFragment.getMap();
mapView = (View) view.findViewById(R.id.map);
SupportMapFragment supportMapFragment = (SupportMapFragment) fragmentManager
.findFragmentById(R.id.map);
if(mMap != null){
mMap.setMyLocationEnabled(true);
}
if(mMap != null)
mMap.setOnMapLongClickListener(new GoogleMap.OnMapLongClickListener() {
#Override
public void onMapLongClick(LatLng latLng) {
new EditMap().execute("", String.valueOf(latLng.latitude), String.valueOf(latLng.longitude));
}
});
class EditMap extends AsyncTask<String, String, String> {
/**
* Before starting background thread Show Progress Dialog
* */
#Override
protected void onPreExecute() {
super.onPreExecute();
}
/**
* getting Albums JSON
* */
protected String doInBackground(String... args) {
String address = args[0];
double latitude = Double.parseDouble(args[1]);
double longitude = Double.parseDouble(args[2]);
return editMap(address, latitude, longitude);
}
/**
* After completing background task Dismiss the progress dialog
* **/
protected void onPostExecute(String result) {
if(!result.equals(""))
ToastUtil.ToastShort(getActivity(), result);
else {
mMap.clear();
mMap.addMarker(new MarkerOptions().position(new LatLng(lat, lng)).title(attvalue));
mMap.moveCamera(CameraUpdateFactory.newLatLngZoom(new LatLng(lat, lng), 11));
}
}
}
NOTE:
These are the minimal requirements for the setting of location as you choose from Map that fills the location in your text.
There is a background thread that runs as you long press the location in a map.
The listener defined for that is setOnMapLongClickListener as you see above.
The execution will place the marker to the exact location you chose to mark as set.
There will be a done button after you have chosen the location by a marker. This done button will confirm what you have chosen and will set that on a textfield for you.
The above code uses the method editMap to edit the map location.
The implementation is as done here:
private String editMap(String address, double latitude, double longitude ) {
String keyword = null;
try {
Geocoder geocoder = new Geocoder(getActivity(), Locale.getDefault());
if(!address.equals("")){
keyword = address;
java.util.List<android.location.Address> result = geocoder
.getFromLocationName(keyword, 1);
if (result.size() > 0) {
lat = (double) result.get(0).getLatitude();
lng = (double) result.get(0).getLongitude();
attvalue = address;
} else {
return "Record not found";
}
} else {
String sUrl = "http://google.com/maps/api/geocode/json?latlng="+latitude+","+longitude+"&sensor=true";
DefaultHttpClient client = new DefaultHttpClient();
HttpGet get = new HttpGet(sUrl);
HttpResponse r = client.execute(get);
int status = r.getStatusLine().getStatusCode();
if(status == 200){
HttpEntity e = r.getEntity();
String data = EntityUtils.toString(e);
try{
JSONObject jsonObject = new JSONObject(data);
JSONArray results = jsonObject.getJSONArray("results");
JSONObject addressObject = results.getJSONObject(0);
JSONArray addressComp = addressObject.getJSONArray("address_components");
String city = "", state = "";
for(int i=0; i < addressComp.length(); i++){
JSONArray types = addressComp.getJSONObject(i).getJSONArray("types");
if(city.equals("") && types.getString(0).equals("locality"))
city = addressComp.getJSONObject(i).getString("long_name");
if(state.equals("") && types.getString(0).equals("administrative_area_level_1"))
state = addressComp.getJSONObject(i).getString("long_name");
if(!city.equals("") && !state.equals(""))
break;
}
attvalue = city + ", " + state;
} catch (JSONException e1) {
e1.printStackTrace();
}
lat = latitude;
lng = longitude;
}else{
return "Location Not Found";
}
}
} catch (IOException io) {
return "Connection Error";
}
return "";
}
I hope this is enough to help you out.