Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 8 years ago.
Improve this question
My main activity collects LatLng data from server and finds some cities distances using google maps. Because of that it extends FragmentActivity. I want also to show the results using a ListView. The problem is that FragmentActivity doesn't support adapter. Any ideas to deal with that given that i'm not an expert...
My code
package com.example.tranfer;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import org.apache.http.NameValuePair;
import org.apache.http.message.BasicNameValuePair;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import com.google.android.gms.maps.model.LatLng;
import android.app.ProgressDialog;
import android.content.SharedPreferences;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.util.Log;
import android.widget.ListAdapter;
import android.widget.ListView;
import android.widget.SimpleAdapter;
public class CheckItineraries extends FragmentActivity {
private ProgressDialog pDialog;
String username , origin_lat ,origin_lng ,destination_lat ,destination_lng ,
waypoint1_lat ,waypoint1_lng ,waypoint2_lat ,waypoint2_lng ,waypoints;
int i, j ,b;
ListView list;
ArrayList<LatLng> markerPoints;
// URL to get contacts JSON
private static String LOGIN_URL = "http://192.168.1.2:80/etruck1/check_itineraries.php";
public static final String PREFS_NAME = "MyPreferencesFile";
// JSON Node names
JSONParser jsonParser = new JSONParser();
// contacts JSONArray
JSONArray contacts = null;
// Hashmap for ListView
ArrayList<HashMap<String, String>> itinList;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.checkitineraries);
itinList = new ArrayList<HashMap<String, String>>();
new GetData().execute();
}
private class GetData extends AsyncTask<Void, Void, Void> {
public void onPreExecute() {
super.onPreExecute();
Log.d("meg", "meg");
pDialog = new ProgressDialog(CheckItineraries.this);
pDialog.setMessage("Καταχωρώ τα στοιχεία...");
pDialog.setIndeterminate(false);
pDialog.setCancelable(true);
pDialog.show();
SharedPreferences settings = getSharedPreferences(PREFS_NAME, 0);
username = settings.getString("username", "nikos");
}
protected Void doInBackground(Void... args) {
// TODO Auto-generated method stub
try {
// Building Parameters
List<NameValuePair> params = new ArrayList<NameValuePair>();
params.add(new BasicNameValuePair("username", username));
JSONObject json = jsonParser.makeHttpRequest(LOGIN_URL, "POST",
params);
// JSONObject jObj = new JSONObject();
JSONArray itin_results = json.getJSONArray("itin_results");
for (int i = 0; i < itin_results.length(); i++) {
JSONObject c = itin_results.getJSONObject(i);
String username = c.getString("username");
String startPoliPro = c.getString("startPoliPro");
String start_lat_pro = c.getString("start_lat_pro");
String start_lng_pro = c.getString("start_lng_pro");
String finalPoliPro = c.getString("finalPoliPro");
String final_lat_pro = c.getString("final_lat_pro");
String final_lng_pro = c.getString("final_lng_pro");
LinkedHashMap<String, String> pinakas = new LinkedHashMap<String, String>();
// adding each child node to HashMap key => value
pinakas.put("username", username);
pinakas.put("startPoliPro", startPoliPro);
pinakas.put("start_lat_pro", start_lat_pro);
pinakas.put("start_lng_pro", start_lng_pro);
pinakas.put("finalPoliPro", finalPoliPro);
pinakas.put("final_lat_pro", final_lat_pro);
pinakas.put("final_lng_pro", final_lng_pro);
// adding contact to contact list
itinList.add(pinakas);
b = itin_results.length();
Log.d("b", String.valueOf(b));
}
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
// Dismiss the progress dialog
if (pDialog.isShowing())
pDialog.dismiss();
list=(ListView)findViewById(R.id.list);
//list.setAdapter(new ArrayAdapter<Object>(CheckItineraries.this, android.R.layout.simple_dropdown_item_1line
origin_lat = itinList.get(0).get("start_lat_pro").toString();
origin_lng = itinList.get(0).get("start_lng_pro").toString();
destination_lat = itinList.get(0).get("final_lat_pro").toString();
destination_lng = itinList.get(0).get("final_lng_pro").toString();
for (i = 0; i <b; i++) {
markerPoints = new ArrayList<LatLng>();
Log.d("panikos", itinList.get(i).get("username").toString());
Log.d("panikos", itinList.get(i).get("startPoliPro").toString());
Log.d("panikos", itinList.get(i).get("start_lat_pro").toString());
Log.d("panikos", itinList.get(i).get("start_lng_pro").toString());
Log.d("panikos", itinList.get(i).get("finalPoliPro").toString());
Log.d("panikos", itinList.get(i).get("final_lat_pro").toString());
Log.d("panikos", itinList.get(i).get("final_lng_pro").toString());
waypoint1_lat = itinList.get(i).get("start_lat_pro").toString();
waypoint1_lng = itinList.get(i).get("start_lng_pro").toString();
waypoint2_lat = itinList.get(i).get("final_lat_pro").toString();
waypoint2_lng = itinList.get(i).get("final_lng_pro").toString();
LatLng origin1 = new LatLng(Double.parseDouble(origin_lat), Double.parseDouble(origin_lng));
LatLng destination = new LatLng(Double.parseDouble(destination_lat), Double.parseDouble(destination_lng));
LatLng waypoint1 = new LatLng(Double.parseDouble(waypoint1_lat), Double.parseDouble(waypoint1_lng));
LatLng waypoint2 = new LatLng(Double.parseDouble(waypoint2_lat), Double.parseDouble(waypoint2_lng));
Log.d("origin1", origin1.toString());
Log.d("destination", destination.toString());
Log.d("waypoint1", waypoint1.toString());
Log.d("waypoint2", waypoint2.toString());
markerPoints.add(origin1);
markerPoints.add(destination);
markerPoints.add(waypoint1);
markerPoints.add(waypoint2);
LatLng or = markerPoints.get(0);
LatLng dest = markerPoints.get(1);
Log.d("ena", markerPoints.get(0).toString());
Log.d("dyo", markerPoints.get(1).toString());
Log.d("tria", markerPoints.get(2).toString());
Log.d("tessera", markerPoints.get(3).toString());
// Getting URL to the Google Directions API
String url = getDirectionsUrl(or, dest);
DownloadTask downloadTask = new DownloadTask();
// Start downloading json data from Google Directions API
downloadTask.execute(url);
}
}
private String getDirectionsUrl(LatLng or, LatLng dest) {
// Origin of route
String str_origin = "origin=" + or.latitude + ","+ or.longitude;
// Destination of route
String str_dest = "destination=" + dest.latitude + "," + dest.longitude;
// Sensor enabled
String sensor = "sensor=false";
// Waypoints
LatLng way1 = markerPoints.get(2);
LatLng way2 = markerPoints.get(3);
Log.d("way1", way1.toString());
Log.d("way2", way2.toString());
// Waypoints
waypoints = "";
for(int i=2;i<markerPoints.size();i++){
LatLng point = (LatLng) markerPoints.get(i);
if(i==2)
waypoints = "waypoints=";
waypoints += point.latitude + "," + point.longitude + "|";
}
// Building the parameters to the web service
String parameters = str_origin + "&" + str_dest + "&" + sensor +"&"+waypoints;
// Output format
String output = "json";
// Building the url to the web service
String url = "https://maps.googleapis.com/maps/api/directions/"
+ output + "?" + parameters;
return url;
}
private String downloadUrl(String strUrl) throws IOException {
String data = "";
InputStream iStream = null;
HttpURLConnection urlConnection = null;
try {
URL url = new URL(strUrl);
// Creating an http connection to communicate with url
urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
iStream = urlConnection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(
iStream));
StringBuffer sb = new StringBuffer();
String line = "";
while ((line = br.readLine()) != null) {
sb.append(line);
}
data = sb.toString();
br.close();
} catch (Exception e) {
Log.d("Exception while downloading url", e.toString());
} finally {
iStream.close();
urlConnection.disconnect();
}
return data;
}
///
// Fetches data from url passed
////
private class DownloadTask extends AsyncTask<String, Void, String> {
// Downloading data in non-ui thread
#Override
protected String doInBackground(String... url) {
// For storing data from web service
String data = "";
try {
// Fetching the data from web service
data = downloadUrl(url[0]);
} catch (Exception e) {
Log.d("Background Task", e.toString());
}
return data;
}
// Executes in UI thread, after the execution of
// doInBackground()
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
ParserTask parserTask = new ParserTask();
// Invokes the thread for parsing the JSON data
parserTask.execute(result);
}
}
//e
public class ParserTask extends
AsyncTask<String, Integer, List<List<HashMap<String, String>>>> {
// Parsing the data in non-ui thread
#Override
protected List<List<HashMap<String, String>>> doInBackground(
String... jsonData) {
JSONObject jObject;
List<List<HashMap<String, String>>> routes = null;
try {
jObject = new JSONObject(jsonData[0]);
DirectionsJSONParser1 parser = new DirectionsJSONParser1();
// Starts parsing data
routes = parser.parse(jObject);
Log.d("json", jObject.toString());
} catch (Exception e) {
e.printStackTrace();
}
return routes;
}
// Executes in UI thread, after the parsing process
#Override
//o
protected void onPostExecute(List<List<HashMap<String, String>>> result) {
ArrayList<LatLng> points = null;
String distance = "";
String duration = "";
Log.d("result", String.valueOf(result.size()));
// Traversing through all the routes
for (int i = 0; i < result.size(); i++) {
points = new ArrayList<LatLng>();
// Fetching i-th route
List<HashMap<String, String>> path = result.get(i);
// Fetching all the points in i-th route
for(int j=0;j<path.size();j++){
HashMap<String,String> point = path.get(j);
if(j==0){ // Get distance from the list
distance = point.get("distance");
continue;
}else if(j==1){ // Get duration from the list
duration = point.get("duration");
continue;
}
Log.d("lat", String.valueOf(point.get("lat")));
Log.d("lng", String.valueOf(point.get("lng")));
double lat = Double.parseDouble(point.get("lat"));
double lng = Double.parseDouble(point.get("lng"));
LatLng position = new LatLng(lat, lng);
points.add(position);
ListAdapter adapter = new SimpleAdapter(
CheckItineraries.this, itinList,
R.layout.list_item, new String[] { "startpoli1", "finalpoli1"},
new int[] { R.id.startpoli, R.id.finalpoli });
**setListAdapter(adapter);**
}
}
if(distance!=null){
Log.d("finito", distance);
}
}
}
}
}
Eclipse says " The method setListAdapter(ListAdapter) is undefined for the type CheckItineraries.GetData.ParserTask"
setListAdapter() ia a method in ListActivity but your activity is not a ListActivity but a FragmentActivity.
You can achieve the same by obtaining a reference to the ListView in your content view layout with findViewById() like you do elsewhere in your code, and then call setAdapter() on the ListView itself.
You can create listview adaptor from context.
listViewAdapter = new ListView_Adapter(getActivity().getBaseContext());
I just have my Activities extend Activity and I use Fragments in my activity which extend ListFragment. From the docs:
ListFragment hosts a ListView object that can be bound to different data sources, typically either an array or a Cursor holding query results.
A FragmentActivity and Adapter is two somethings diferents.
FragmentActivity
Base class for activities that want to use the support-based Fragment and Loader APIs.
Adapter official documentation
An Adapter object acts as a bridge between an AdapterView and the underlying data for that view. The Adapter provides access to the data items. The Adapter is also responsible for making a View for each item in the data set.
You can use one adapter in your ListView.
EDIT POST:
You are creating a ArrayAdapter and you have a String object ArrayAdapter.
list.setAdapter(new ArrayAdapter<String>(CheckItineraries.this, android.R.layout.simple_dropdown_item_1,line);
Related
I am using Algolia's InstantSearch Android library. This is my Query:
searcher.setQuery(new Query().setAroundLatLng(new AbstractQuery.LatLng(lat, lng)).setAroundRadius(5000)).
How can I display the distance between the fetched record and my current location?
Building on top of #Raphi's great answer, here's how you can display the distance with InstantSearch Android: you just have to write a custom Hit View.
Create a Custom hit view: here a specialized TextView implementing AlgoliaHitView
in onUpdateView, get the _rankingInfo.matchedGeoLocation.distance as Raphi recommended
use this value in your View, for example with setText(distance + " meters away.")
Actually you can find the distance in the response for every hit by adding the parameter getRankingInfo=true to your search query.
I'm not familiar with InstantSearch Android but if you have access to the raw response, then look at _rankingInfo.matchedGeoLocation.distance in your records:
{
[...] // your record fields
"_rankingInfo": {
"nbTypos": 0,
"firstMatchedWord": 0,
"proximityDistance": 0,
"userScore": 11,
"geoDistance": 468,
"geoPrecision": 1,
"nbExactWords": 1,
"words": 1,
"filters": 0,
"matchedGeoLocation": {
"lat": 48.86,
"lng": 2.3443,
"distance": 468
}
}
}
See https://www.algolia.com/doc/guides/searching/geo-search/?language=rails#identifying-the-matching-geo-search-with-rankinginfo
Create a new class named as CalculateDistanceTime and paste below code:
import android.content.Context;
import android.os.AsyncTask;
import android.util.Log;
import com.google.android.gms.maps.model.LatLng;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
class CalculateDistanceTime {
private taskCompleteListener mTaskListener;
private Context mContext;
CalculateDistanceTime(Context context) {
mContext = context;
}
void setLoadListener(taskCompleteListener taskListener) {
mTaskListener = taskListener;
}
void getDirectionsUrl(LatLng origin, LatLng dest) {
// Origin of route
String str_origin = "origin=" + origin.latitude + "," + origin.longitude;
// Destination of route
String str_dest = "destination=" + dest.latitude + "," + dest.longitude;
// Sensor enabled
String sensor = "sensor=false";
// Building the parameters to the web service
String parameters = str_origin + "&" + str_dest + "&" + sensor;
// Output format
String output = "json";
// Building the url to the web service
String url = "https://maps.googleapis.com/maps/api/directions/" + output + "?" + parameters;
DownloadTask downloadTask = new DownloadTask();
// Start downloading json data from Google Directions API
downloadTask.execute(url);
}
private String downloadUrl(String strUrl) throws IOException {
String data = "";
HttpURLConnection urlConnection;
URL url = new URL(strUrl);
// Creating an http connection to communicate with url
urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
try (InputStream iStream = urlConnection.getInputStream()) {
BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
StringBuilder sb = new StringBuilder();
String line;
while ((line = br.readLine()) != null) {
sb.append(line);
}
data = sb.toString();
br.close();
} catch (Exception e) {
Log.d("Excp. while downloading", e.toString());
} finally {
urlConnection.disconnect();
}
return data;
}
interface taskCompleteListener {
void taskCompleted(String[] time_distance);
}
private class DownloadTask extends AsyncTask<String, Void, String> {
// Downloading data in non-ui thread
#Override
protected String doInBackground(String... url) {
// For storing data from web service
String data = "";
try {
// Fetching the data from web service
data = downloadUrl(url[0]);
} catch (Exception e) {
Log.d("Background Task", e.toString());
}
return data;
}
// Executes in UI thread, after the execution of
// doInBackground()
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
ParserTask parserTask = new ParserTask();
// Invokes the thread for parsing the JSON data
parserTask.execute(result);
}
}
private class ParserTask extends AsyncTask<String, Integer, List<HashMap<String, String>>> {
// Parsing the data in non-ui thread
#Override
protected List<HashMap<String, String>> doInBackground(String... jsonData) {
JSONObject jObject;
List<HashMap<String, String>> routes = null;
try {
jObject = new JSONObject(jsonData[0]);
DistanceTimeParser parser = new DistanceTimeParser();
// Starts parsing data
routes = parser.parse(jObject);
} catch (Exception e) {
e.printStackTrace();
}
return routes;
}
// Executes in UI thread, after the parsing process
#Override
protected void onPostExecute(List<HashMap<String, String>> result) {
String duration_distance = "";
if (result.size() < 1) {
Log.e("Error : ", "No Points found");
return;
}
String[] date_dist = new String[2];
// Traversing through all the routes
for (int i = 0; i < result.size(); i++) {
// Fetching i-th route
HashMap<String, String> tmpData = result.get(i);
Set<String> key = tmpData.keySet();
Iterator it = key.iterator();
while (it.hasNext()) {
String hmKey = (String) it.next();
duration_distance = tmpData.get(hmKey);
System.out.println("Key: " + hmKey + " & Data: " + duration_distance);
it.remove(); // avoids a ConcurrentModificationException
}
date_dist[i] = duration_distance;
}
mTaskListener.taskCompleted(date_dist);
}
}
}
Then use below code wherever you want to show distance and time.
Create a global variable, CalculateDistanceTime distance_task;
and then, use this code
distance_task.getDirectionsUrl(latLng1, latLng2);
distance_task.setLoadListener(new CalculateDistanceTime.taskCompleteListener() {
#Override
public void taskCompleted(String[] time_distance) {
v1.setVisibility(View.VISIBLE);
text1.setText(time_distance[0]); //Distance
text2.setText(time_distance[1]); //Time
}
});
See, text1 and text2 here are two textviews used to display Distance and Time respectively.Also, the major thing is see the class call here, distance_task.getDirectionsUrl(latLng1, latLng2);, here latLng1 is source and latLng2 is destination and you should provide these two latLngs for it to work.
I am facing a strange problem here.
I want to query the google places webservice from my andorid app.
For that I am always getting the error : "This service requires an API Key".
How ever when I try to query it using my chrome browser and the server key, I get the response properly.
In case of android, which key should I use as the android api key is giving me this error.
Adding a package name is optional :
Edit
This is the request url :
https://maps.googleapis.com/maps/api/place/nearbysearch/json?location=-33.8670522,151.1957362&radius=500&types=food&name=cruise&key=AIzaSyDeFunLJQLF7WInuNnaWfbeyJzfw_1litQ
When i run this in browser I am getting this :
Sending the same request using hurl.it :
The exact error that I am getting #android app.
For the Google Places Web API, you need to use a Server key.
The API is technically not meant for use in a client-side app, it's designed for websites to use.
You can use it in your app, however you will need to use a Server key that is not secured.
If you look at the documentation, it clearly states:
Note: The Google Places API Web Service does not work with an Android
or iOS API key.
Official instructions:
Alternatively, follow these steps to get an API key:
Go to the Google Developers Console.
Create or select a project.
Click Continue to Enable the API.
Go to Credentials to get a Server key (and set the API credentials).
To prevent quota theft, secure your API key following these best practices.
(Optional) Enable billing. See Usage Limits and Billing for more information.
Important: leave the IP address field blank for using this webservice API directly from an app:
Edit: Here is full code for Activity that is working and tested, you can use it as a reference to see if there is a problem in your code:
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.Marker;
import com.google.android.gms.maps.model.MarkerOptions;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
public class MapsActivity2 extends AppCompatActivity implements OnMapReadyCallback
{
private GoogleMap mGoogleMap;
SupportMapFragment mapFrag;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
//Use this one:
setContentView(R.layout.activity_maps2);
mapFrag = (SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map);
mapFrag.getMapAsync(this);
}
#Override
public void onMapReady(GoogleMap googleMap)
{
mGoogleMap=googleMap;
mGoogleMap.setMyLocationEnabled(true);
StringBuilder sbValue = new StringBuilder(sbMethod());
PlacesTask placesTask = new PlacesTask();
placesTask.execute(sbValue.toString());
}
public StringBuilder sbMethod()
{
//use your current location here
double mLatitude = 37.77657;
double mLongitude = -122.417506;
StringBuilder sb = new StringBuilder("https://maps.googleapis.com/maps/api/place/nearbysearch/json?");
sb.append("location=" + mLatitude + "," + mLongitude);
sb.append("&radius=5000");
sb.append("&types=" + "restaurant");
sb.append("&sensor=true");
sb.append("&key=AIza******************************");
Log.d("Map", "url: " + sb.toString());
return sb;
}
private class PlacesTask extends AsyncTask<String, Integer, String>
{
String data = null;
// Invoked by execute() method of this object
#Override
protected String doInBackground(String... url) {
try {
data = downloadUrl(url[0]);
} catch (Exception e) {
Log.d("Background Task", e.toString());
}
return data;
}
// Executed after the complete execution of doInBackground() method
#Override
protected void onPostExecute(String result) {
ParserTask parserTask = new ParserTask();
// Start parsing the Google places in JSON format
// Invokes the "doInBackground()" method of the class ParserTask
parserTask.execute(result);
}
}
private String downloadUrl(String strUrl) throws IOException
{
String data = "";
InputStream iStream = null;
HttpURLConnection urlConnection = null;
try {
URL url = new URL(strUrl);
// Creating an http connection to communicate with url
urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
iStream = urlConnection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
StringBuffer sb = new StringBuffer();
String line = "";
while ((line = br.readLine()) != null) {
sb.append(line);
}
data = sb.toString();
br.close();
} catch (Exception e) {
Log.d("Exception", e.toString());
} finally {
iStream.close();
urlConnection.disconnect();
}
return data;
}
private class ParserTask extends AsyncTask<String, Integer, List<HashMap<String, String>>> {
JSONObject jObject;
// Invoked by execute() method of this object
#Override
protected List<HashMap<String, String>> doInBackground(String... jsonData) {
List<HashMap<String, String>> places = null;
Place_JSON placeJson = new Place_JSON();
try {
jObject = new JSONObject(jsonData[0]);
places = placeJson.parse(jObject);
} catch (Exception e) {
Log.d("Exception", e.toString());
}
return places;
}
// Executed after the complete execution of doInBackground() method
#Override
protected void onPostExecute(List<HashMap<String, String>> list) {
Log.d("Map", "list size: " + list.size());
// Clears all the existing markers;
mGoogleMap.clear();
for (int i = 0; i < list.size(); i++) {
// Creating a marker
MarkerOptions markerOptions = new MarkerOptions();
// Getting a place from the places list
HashMap<String, String> hmPlace = list.get(i);
// Getting latitude of the place
double lat = Double.parseDouble(hmPlace.get("lat"));
// Getting longitude of the place
double lng = Double.parseDouble(hmPlace.get("lng"));
// Getting name
String name = hmPlace.get("place_name");
Log.d("Map", "place: " + name);
// Getting vicinity
String vicinity = hmPlace.get("vicinity");
LatLng latLng = new LatLng(lat, lng);
// Setting the position for the marker
markerOptions.position(latLng);
markerOptions.title(name + " : " + vicinity);
markerOptions.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_MAGENTA));
// Placing a marker on the touched position
Marker m = mGoogleMap.addMarker(markerOptions);
}
}
}
public class Place_JSON {
/**
* Receives a JSONObject and returns a list
*/
public List<HashMap<String, String>> parse(JSONObject jObject) {
JSONArray jPlaces = null;
try {
/** Retrieves all the elements in the 'places' array */
jPlaces = jObject.getJSONArray("results");
} catch (JSONException e) {
e.printStackTrace();
}
/** Invoking getPlaces with the array of json object
* where each json object represent a place
*/
return getPlaces(jPlaces);
}
private List<HashMap<String, String>> getPlaces(JSONArray jPlaces) {
int placesCount = jPlaces.length();
List<HashMap<String, String>> placesList = new ArrayList<HashMap<String, String>>();
HashMap<String, String> place = null;
/** Taking each place, parses and adds to list object */
for (int i = 0; i < placesCount; i++) {
try {
/** Call getPlace with place JSON object to parse the place */
place = getPlace((JSONObject) jPlaces.get(i));
placesList.add(place);
} catch (JSONException e) {
e.printStackTrace();
}
}
return placesList;
}
/**
* Parsing the Place JSON object
*/
private HashMap<String, String> getPlace(JSONObject jPlace)
{
HashMap<String, String> place = new HashMap<String, String>();
String placeName = "-NA-";
String vicinity = "-NA-";
String latitude = "";
String longitude = "";
String reference = "";
try {
// Extracting Place name, if available
if (!jPlace.isNull("name")) {
placeName = jPlace.getString("name");
}
// Extracting Place Vicinity, if available
if (!jPlace.isNull("vicinity")) {
vicinity = jPlace.getString("vicinity");
}
latitude = jPlace.getJSONObject("geometry").getJSONObject("location").getString("lat");
longitude = jPlace.getJSONObject("geometry").getJSONObject("location").getString("lng");
reference = jPlace.getString("reference");
place.put("place_name", placeName);
place.put("vicinity", vicinity);
place.put("lat", latitude);
place.put("lng", longitude);
place.put("reference", reference);
} catch (JSONException e) {
e.printStackTrace();
}
return place;
}
}
}
activity_maps2.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:map="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/map"
tools:context="com.iotaconcepts.aurum.MapsActivity2"
android:name="com.google.android.gms.maps.SupportMapFragment"/>
</LinearLayout>
Result:
under credentials choose api key, than android key
I am facing a strange problem here.
I want to query the google places webservice from my andorid app.
For that I am always getting the error : "This service requires an API Key".
How ever when I try to query it using my chrome browser and the server key, I get the response properly.
In case of android, which key should I use as the android api key is giving me this error.
Adding a package name is optional :
Edit
This is the request url :
https://maps.googleapis.com/maps/api/place/nearbysearch/json?location=-33.8670522,151.1957362&radius=500&types=food&name=cruise&key=AIzaSyDeFunLJQLF7WInuNnaWfbeyJzfw_1litQ
When i run this in browser I am getting this :
Sending the same request using hurl.it :
The exact error that I am getting #android app.
For the Google Places Web API, you need to use a Server key.
The API is technically not meant for use in a client-side app, it's designed for websites to use.
You can use it in your app, however you will need to use a Server key that is not secured.
If you look at the documentation, it clearly states:
Note: The Google Places API Web Service does not work with an Android
or iOS API key.
Official instructions:
Alternatively, follow these steps to get an API key:
Go to the Google Developers Console.
Create or select a project.
Click Continue to Enable the API.
Go to Credentials to get a Server key (and set the API credentials).
To prevent quota theft, secure your API key following these best practices.
(Optional) Enable billing. See Usage Limits and Billing for more information.
Important: leave the IP address field blank for using this webservice API directly from an app:
Edit: Here is full code for Activity that is working and tested, you can use it as a reference to see if there is a problem in your code:
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.Marker;
import com.google.android.gms.maps.model.MarkerOptions;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
public class MapsActivity2 extends AppCompatActivity implements OnMapReadyCallback
{
private GoogleMap mGoogleMap;
SupportMapFragment mapFrag;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
//Use this one:
setContentView(R.layout.activity_maps2);
mapFrag = (SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map);
mapFrag.getMapAsync(this);
}
#Override
public void onMapReady(GoogleMap googleMap)
{
mGoogleMap=googleMap;
mGoogleMap.setMyLocationEnabled(true);
StringBuilder sbValue = new StringBuilder(sbMethod());
PlacesTask placesTask = new PlacesTask();
placesTask.execute(sbValue.toString());
}
public StringBuilder sbMethod()
{
//use your current location here
double mLatitude = 37.77657;
double mLongitude = -122.417506;
StringBuilder sb = new StringBuilder("https://maps.googleapis.com/maps/api/place/nearbysearch/json?");
sb.append("location=" + mLatitude + "," + mLongitude);
sb.append("&radius=5000");
sb.append("&types=" + "restaurant");
sb.append("&sensor=true");
sb.append("&key=AIza******************************");
Log.d("Map", "url: " + sb.toString());
return sb;
}
private class PlacesTask extends AsyncTask<String, Integer, String>
{
String data = null;
// Invoked by execute() method of this object
#Override
protected String doInBackground(String... url) {
try {
data = downloadUrl(url[0]);
} catch (Exception e) {
Log.d("Background Task", e.toString());
}
return data;
}
// Executed after the complete execution of doInBackground() method
#Override
protected void onPostExecute(String result) {
ParserTask parserTask = new ParserTask();
// Start parsing the Google places in JSON format
// Invokes the "doInBackground()" method of the class ParserTask
parserTask.execute(result);
}
}
private String downloadUrl(String strUrl) throws IOException
{
String data = "";
InputStream iStream = null;
HttpURLConnection urlConnection = null;
try {
URL url = new URL(strUrl);
// Creating an http connection to communicate with url
urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
iStream = urlConnection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
StringBuffer sb = new StringBuffer();
String line = "";
while ((line = br.readLine()) != null) {
sb.append(line);
}
data = sb.toString();
br.close();
} catch (Exception e) {
Log.d("Exception", e.toString());
} finally {
iStream.close();
urlConnection.disconnect();
}
return data;
}
private class ParserTask extends AsyncTask<String, Integer, List<HashMap<String, String>>> {
JSONObject jObject;
// Invoked by execute() method of this object
#Override
protected List<HashMap<String, String>> doInBackground(String... jsonData) {
List<HashMap<String, String>> places = null;
Place_JSON placeJson = new Place_JSON();
try {
jObject = new JSONObject(jsonData[0]);
places = placeJson.parse(jObject);
} catch (Exception e) {
Log.d("Exception", e.toString());
}
return places;
}
// Executed after the complete execution of doInBackground() method
#Override
protected void onPostExecute(List<HashMap<String, String>> list) {
Log.d("Map", "list size: " + list.size());
// Clears all the existing markers;
mGoogleMap.clear();
for (int i = 0; i < list.size(); i++) {
// Creating a marker
MarkerOptions markerOptions = new MarkerOptions();
// Getting a place from the places list
HashMap<String, String> hmPlace = list.get(i);
// Getting latitude of the place
double lat = Double.parseDouble(hmPlace.get("lat"));
// Getting longitude of the place
double lng = Double.parseDouble(hmPlace.get("lng"));
// Getting name
String name = hmPlace.get("place_name");
Log.d("Map", "place: " + name);
// Getting vicinity
String vicinity = hmPlace.get("vicinity");
LatLng latLng = new LatLng(lat, lng);
// Setting the position for the marker
markerOptions.position(latLng);
markerOptions.title(name + " : " + vicinity);
markerOptions.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_MAGENTA));
// Placing a marker on the touched position
Marker m = mGoogleMap.addMarker(markerOptions);
}
}
}
public class Place_JSON {
/**
* Receives a JSONObject and returns a list
*/
public List<HashMap<String, String>> parse(JSONObject jObject) {
JSONArray jPlaces = null;
try {
/** Retrieves all the elements in the 'places' array */
jPlaces = jObject.getJSONArray("results");
} catch (JSONException e) {
e.printStackTrace();
}
/** Invoking getPlaces with the array of json object
* where each json object represent a place
*/
return getPlaces(jPlaces);
}
private List<HashMap<String, String>> getPlaces(JSONArray jPlaces) {
int placesCount = jPlaces.length();
List<HashMap<String, String>> placesList = new ArrayList<HashMap<String, String>>();
HashMap<String, String> place = null;
/** Taking each place, parses and adds to list object */
for (int i = 0; i < placesCount; i++) {
try {
/** Call getPlace with place JSON object to parse the place */
place = getPlace((JSONObject) jPlaces.get(i));
placesList.add(place);
} catch (JSONException e) {
e.printStackTrace();
}
}
return placesList;
}
/**
* Parsing the Place JSON object
*/
private HashMap<String, String> getPlace(JSONObject jPlace)
{
HashMap<String, String> place = new HashMap<String, String>();
String placeName = "-NA-";
String vicinity = "-NA-";
String latitude = "";
String longitude = "";
String reference = "";
try {
// Extracting Place name, if available
if (!jPlace.isNull("name")) {
placeName = jPlace.getString("name");
}
// Extracting Place Vicinity, if available
if (!jPlace.isNull("vicinity")) {
vicinity = jPlace.getString("vicinity");
}
latitude = jPlace.getJSONObject("geometry").getJSONObject("location").getString("lat");
longitude = jPlace.getJSONObject("geometry").getJSONObject("location").getString("lng");
reference = jPlace.getString("reference");
place.put("place_name", placeName);
place.put("vicinity", vicinity);
place.put("lat", latitude);
place.put("lng", longitude);
place.put("reference", reference);
} catch (JSONException e) {
e.printStackTrace();
}
return place;
}
}
}
activity_maps2.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:map="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/map"
tools:context="com.iotaconcepts.aurum.MapsActivity2"
android:name="com.google.android.gms.maps.SupportMapFragment"/>
</LinearLayout>
Result:
under credentials choose api key, than android key
I know this seems like a duplicate, but it's not.
I'm following a tutorial on google maps and I just cannot get throught this fail (notice this is my very first time developing in Android).
In function onCreateOptionsMenu I get the error I describe in title.
Here's my MainActivity.java (onCreateOptionsMenu is on bottom):
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import org.json.JSONObject;
import android.graphics.Color;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.util.Log;
import android.view.Menu;
import android.widget.TextView;
import android.widget.Toast;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.GoogleMap.OnMapClickListener;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
import com.google.android.gms.maps.model.PolylineOptions;
public class MainActivity extends FragmentActivity
{
GoogleMap map;
ArrayList<LatLng> markerPoints;
TextView tvDistanceDuration;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
this.setContentView(R.layout.activity_main);
TextView distancia_tiempo = new TextView(this);
this.tvDistanceDuration = distancia_tiempo; //this.findViewById(R.id.tv_distance_time);
// Initializing
this.markerPoints = new ArrayList<LatLng>();
// Getting reference to SupportMapFragment of the activity_main
SupportMapFragment fm = (SupportMapFragment) this.getSupportFragmentManager().findFragmentById(R.id.map);
// Getting Map for the SupportMapFragment
this.map = fm.getMap();
// Enable MyLocation Button in the Map
this.map.setMyLocationEnabled(true);
// Setting onclick event listener for the map
this.map.setOnMapClickListener(new OnMapClickListener()
{
#Override
public void onMapClick(LatLng point)
{
// Already two locations
if (MainActivity.this.markerPoints.size() > 1)
{
MainActivity.this.markerPoints.clear();
MainActivity.this.map.clear();
}
// Adding new item to the ArrayList
MainActivity.this.markerPoints.add(point);
// Creating MarkerOptions
MarkerOptions options = new MarkerOptions();
// Setting the position of the marker
options.position(point);
/**
* For the start location, the color of marker is GREEN and
* for the end location, the color of marker is RED.
*/
if (MainActivity.this.markerPoints.size() == 1)
{
options.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_GREEN));
} else if (MainActivity.this.markerPoints.size() == 2)
{
options.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_RED));
}
// Add new marker to the Google Map Android API V2
MainActivity.this.map.addMarker(options);
// Checks, whether start and end locations are captured
if (MainActivity.this.markerPoints.size() >= 2)
{
LatLng origin = MainActivity.this.markerPoints.get(0);
LatLng dest = MainActivity.this.markerPoints.get(1);
// Getting URL to the Google Directions API
String url = MainActivity.this.getDirectionsUrl(origin, dest);
DownloadTask downloadTask = new DownloadTask();
// Start downloading json data from Google Directions API
downloadTask.execute(url);
}
}
});
}
private String getDirectionsUrl(LatLng origin, LatLng dest)
{
// Origin of route
String str_origin = "origin=" + origin.latitude + "," + origin.longitude;
// Destination of route
String str_dest = "destination=" + dest.latitude + "," + dest.longitude;
// Sensor enabled
String sensor = "sensor=false";
// Building the parameters to the web service
String parameters = str_origin + "&" + str_dest + "&" + sensor;
// Output format
String output = "json";
// Building the url to the web service
String url = "https://maps.googleapis.com/maps/api/directions/" + output + "?" + parameters;
return url;
}
/** A method to download json data from url */
private String downloadUrl(String strUrl) throws IOException
{
String data = "";
InputStream iStream = null;
HttpURLConnection urlConnection = null;
try
{
URL url = new URL(strUrl);
// Creating an http connection to communicate with url
urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
iStream = urlConnection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
StringBuffer sb = new StringBuffer();
String line = "";
while ((line = br.readLine()) != null)
{
sb.append(line);
}
data = sb.toString();
br.close();
} catch (Exception e)
{
Log.d("Exception while downloading url", e.toString());
} finally
{
iStream.close();
urlConnection.disconnect();
}
return data;
}
// Fetches data from url passed
private class DownloadTask extends AsyncTask<String, Void, String>
{
// Downloading data in non-ui thread
#Override
protected String doInBackground(String... url)
{
// For storing data from web service
String data = "";
try
{
// Fetching the data from web service
data = MainActivity.this.downloadUrl(url[0]);
} catch (Exception e)
{
Log.d("Background Task", e.toString());
}
return data;
}
// Executes in UI thread, after the execution of
// doInBackground()
#Override
protected void onPostExecute(String result)
{
super.onPostExecute(result);
ParserTask parserTask = new ParserTask();
// Invokes the thread for parsing the JSON data
parserTask.execute(result);
}
}
/** A class to parse the Google Places in JSON format */
private class ParserTask extends AsyncTask<String, Integer, List<List<HashMap<String, String>>>>
{
// Parsing the data in non-ui thread
#Override
protected List<List<HashMap<String, String>>> doInBackground(String... jsonData)
{
JSONObject jObject;
List<List<HashMap<String, String>>> routes = null;
try
{
jObject = new JSONObject(jsonData[0]);
DirectionsJSONParser parser = new DirectionsJSONParser();
// Starts parsing data
routes = parser.parse(jObject);
} catch (Exception e)
{
e.printStackTrace();
}
return routes;
}
// Executes in UI thread, after the parsing process
#Override
protected void onPostExecute(List<List<HashMap<String, String>>> result)
{
ArrayList<LatLng> points = null;
PolylineOptions lineOptions = null;
MarkerOptions markerOptions = new MarkerOptions();
String distance = "";
String duration = "";
if (result.size() < 1)
{
Toast.makeText(MainActivity.this.getBaseContext(), "No Points", Toast.LENGTH_SHORT).show();
return;
}
// Traversing through all the routes
for (int i = 0; i < result.size(); i++)
{
points = new ArrayList<LatLng>();
lineOptions = new PolylineOptions();
// Fetching i-th route
List<HashMap<String, String>> path = result.get(i);
// Fetching all the points in i-th route
for (int j = 0; j < path.size(); j++)
{
HashMap<String, String> point = path.get(j);
if (j == 0)
{ // Get distance from the list
distance = point.get("distance");
continue;
} else if (j == 1)
{ // Get duration from the list
duration = point.get("duration");
continue;
}
double lat = Double.parseDouble(point.get("lat"));
double lng = Double.parseDouble(point.get("lng"));
LatLng position = new LatLng(lat, lng);
points.add(position);
}
// Adding all the points in the route to LineOptions
lineOptions.addAll(points);
lineOptions.width(2);
lineOptions.color(Color.RED);
}
MainActivity.this.tvDistanceDuration.setText("Distance:" + distance + ", Duration:" + duration);
// Drawing polyline in the Google Map for the i-th route
MainActivity.this.map.addPolyline(lineOptions);
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu)
{
// Inflate the menu; this adds items to the action bar if it is present.
this.getMenuInflater().inflate(R.menu.main, menu);
return true;
}
}
And here's activity_main.xml:
<MapFragment xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<fragment
android:id="#+id/map"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:name="com.google.android.gms.maps.MapFragment"/>
</MapFragment>
Any ideas??
Hi I'm having an issue trying to retrieve information from an async task.
What I'm trying to achieve is get the lng/lat from a postcode and then display them on a map. Getting the lng/lat works fine, its just I cant work out how to get that information from the onPostExecute back to the onCreate in an array.
I can perform a loop to add the map markers there.
Anyone know how I go about this?
Updated code
This is the working code that also updates the zoom to fit all entries in. Might help some people out
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import org.json.JSONObject;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.util.Log;
import android.widget.Button;
import android.widget.EditText;
import com.example.coreoffice.library.GeocodeJSONParser;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.LatLngBounds;
import com.google.android.gms.maps.model.LatLngBounds.Builder;
import com.google.android.gms.maps.model.MarkerOptions;
public class MapsActivity extends FragmentActivity
{
Button mBtnFind;
static GoogleMap mMap;
EditText etPlace;
private static final String TAG = "MainActivity";
static ArrayList<Double> lat = new ArrayList<Double>();
static ArrayList<Double> lng = new ArrayList<Double>();
static Builder bounds = new LatLngBounds.Builder();
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.fragment_maps);
Log.v(TAG + "onCreate", "onCreate call");
SupportMapFragment mapFragment = (SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map);
mMap = mapFragment.getMap();
String[] location =
{ "WA32ED", "M30oft", "W21AA" }; // address
String url;
for (int i = 0; i < location.length; i++)
{
DownloadTask downloadTask = new DownloadTask();
url = "";
url = "https://maps.googleapis.com/maps/api/geocode/json?address=" + location[i] + "&sensor=false";
Log.v("URL", url);
downloadTask.execute(url);
}
}
public static void processMap()
{
for (int i = 0; i < lat.size(); i++)
{
MarkerOptions markerOptions = new MarkerOptions();
LatLng latLng = new LatLng(lat.get(i), lng.get(i));
markerOptions.position(latLng);
markerOptions.title("title");
mMap.addMarker(markerOptions);
bounds.include(new LatLng(lat.get(i), lng.get(i)));
}
mMap.moveCamera(CameraUpdateFactory.newLatLngBounds(bounds.build(), 100));
}
private String downloadUrl(String strUrl) throws IOException
{
String data = "";
InputStream iStream = null;
HttpURLConnection urlConnection = null;
try
{
URL url = new URL(strUrl);
urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.connect();
iStream = urlConnection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
StringBuffer sb = new StringBuffer();
String line = "";
while ((line = br.readLine()) != null)
{
sb.append(line);
}
data = sb.toString();
br.close();
}
catch (Exception e)
{
Log.d("Exception while downloading url", e.toString());
}
finally
{
iStream.close();
urlConnection.disconnect();
}
return data;
}
private class DownloadTask extends AsyncTask<String, Integer, String>
{
String data = null;
#Override
protected String doInBackground(String... url)
{
try
{
data = downloadUrl(url[0]);
}
catch (Exception e)
{
Log.d("Background Task", e.toString());
}
return data;
}
#Override
protected void onPostExecute(String result)
{
ParserTask parserTask = new ParserTask();
parserTask.execute(result);
}
}
class ParserTask extends AsyncTask<String, Integer, List<HashMap<String, String>>>
{
JSONObject jObject;
#Override
protected List<HashMap<String, String>> doInBackground(String... jsonData)
{
List<HashMap<String, String>> places = null;
GeocodeJSONParser parser = new GeocodeJSONParser();
try
{
jObject = new JSONObject(jsonData[0]);
places = parser.parse(jObject);
}
catch (Exception e)
{
Log.d("Exception", e.toString());
}
return places;
}
#Override
protected void onPostExecute(List<HashMap<String, String>> list)
{
for (int i = 0; i < list.size(); i++)
{
HashMap<String, String> hmPlace = list.get(i);
double lat = Double.parseDouble(hmPlace.get("lat"));
double lng = Double.parseDouble(hmPlace.get("lng"));
MapsActivity.this.lat.add(lat);
MapsActivity.this.lng.add(lng);
MapsActivity.processMap();
Log.v("lat", Double.toString(lat));
Log.v("lng", Double.toString(lng));
}
}
}
}
As your AsyncTasks are, by definition, asynchronous, you cannot guarantee that they will be done before onCreate() finishes. You merely need to call a method in onPostExecute() of ParserTask to handle the "loop" you describe after the tasks have completed.
Your ArrayLists lat and lng are accessible to the inner classes that are your AsyncTasks, so you just need to add a few lines to onPostExecute():
protected void onPostExecute(List<HashMap<String, String>> list)
{
for (int i = 0; i < list.size(); i++)
{
HashMap<String, String> hmPlace = list.get(i);
double lat = Double.parseDouble(hmPlace.get("lat"));
double lng = Double.parseDouble(hmPlace.get("lng"));
MapsActivity.this.lat.add(lat);
MapsActivity.this.lng.add(lng);
Log.v("lat", Double.toString(lat));
Log.v("lng", Double.toString(lng));
}
processData();
}
Then create a method in MapsActivity:
private void processData()
{
// Do your loop here.
}
You can define an interface as callback for your ParserTask class, and call it in onPostExecute method.
First declare an interface:
public interface OnParseFinishedListener {
public void onFinished(/* required params */);
}
Then add these methods to your ParserTask:
public void setOnParseFinishedListener(OnParseFinishedListener listener){
this.listener = listener;
}
and in your onPostExecute add this line:
if(listener != null) {
listener.onFinished(/* pass params here! */);
}
Use a global variable to hold your HashMap, and then pass it from your Activity into your AsyncTask.
you Should do the donwloading and parsing in a single asynctask.
I would propose using loader instead of asynctask (as you will have a problem once your asynctask returns and your activity has been recreated (eg due to turning the screen or any other configuration change)
In onPostExecute you just call a method in your activity. There you can access your map object /fragment (which you store in an instance variable in onCreate).
Again use an asyncloader which behaves very similar to asynctask but will save you a lot of grief down the line even if it's slightly more complex in the beginning.