在我的应用程序中,我正在显示地图和项目列表。我正在使用 google place api 来获取最近的地方并在地图上显示为具有名称和附近以及列表的标记。这是我的代码
GooglePlacesActivity.java
import android.app.ActionBar;
import android.location.Location;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.util.Log;
import android.view.KeyEvent;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.TextView;
import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.api.GoogleApiClient;
import com.google.android.gms.location.LocationListener;
import com.google.android.gms.location.LocationRequest;
import com.google.android.gms.location.LocationServices;
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.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.CameraPosition;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
import java.io.IOException;
import java.util.List;
public class GooglePlacesActivity extends FragmentActivity implements LocationListener, GoogleApiClient.ConnectionCallbacks,
GoogleApiClient.OnConnectionFailedListener{
GoogleMap mMap;
private GoogleApiClient mGoogleApiClient;
private LocationRequest mLocationRequest;
private double latitude;
private double longitude;
List<Place> placeList;
ListView listView;
PlaceAdapter mPlaceAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_google_places);
ActionBar actionBar = getActionBar();
actionBar.show();
mGoogleApiClient = new GoogleApiClient.Builder(this).
addApi(LocationServices.API).
addConnectionCallbacks(this).
addOnConnectionFailedListener(this).
build();
actionBar.setCustomView(R.layout.search_actionbar);
final EditText search = (EditText) actionBar.getCustomView().findViewById(R.id.searchField);
listView = (ListView) findViewById(R.id.list_item);
search.setOnEditorActionListener(new TextView.OnEditorActionListener() {
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
String value = search.getText().toString();
StringBuilder googlePlacesUrl = new StringBuilder("https://maps.googleapis.com/maps/api/place/search/json?");
googlePlacesUrl.append("location=" + latitude + "," + longitude);
googlePlacesUrl.append("&radius=" + 1000);
googlePlacesUrl.append("&types=" + value);
googlePlacesUrl.append("&key=" + API_KEY);
GooglePlacesTask googlePlacesTask = new GooglePlacesTask();
googlePlacesTask.execute(googlePlacesUrl.toString());
return false;
}
});
actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM | ActionBar.DISPLAY_SHOW_HOME);
if (mMap == null){
mMap = ((SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.googleMap)).getMap();
mMap.setMyLocationEnabled(true);
}
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.menu_google_places, menu);
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
@Override
protected void onStart() {
super.onStart();
mGoogleApiClient.connect();
}
@Override
protected void onStop() {
mGoogleApiClient.disconnect();
super.onStop();
}
@Override
public void onConnected(Bundle bundle) {
mLocationRequest = LocationRequest.create();
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
mLocationRequest.setInterval(1000*60);
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this);
}
@Override
public void onConnectionSuspended(int i) {
}
@Override
public void onConnectionFailed(ConnectionResult connectionResult) {
}
@Override
public void onLocationChanged(Location location) {
latitude = location.getLatitude();
longitude = location.getLongitude();
LatLng latLng = new LatLng(latitude, longitude);
mMap.moveCamera(CameraUpdateFactory.newLatLng(latLng));
mMap.animateCamera(CameraUpdateFactory.zoomTo(12));
}
private class GooglePlacesTask extends AsyncTask<String, Void, String>{
String data;
@Override
protected String doInBackground(String... params) {
try{
data = Http.read(params[0]);
Log.d("DATA", data);
}catch (IOException e){
e.printStackTrace();
}
return data;
}
@Override
protected void onPostExecute(String result) {
placeList = ParseJson.parsedata(result);
for (Place place : placeList){
Log.d("Latitude", String.valueOf(place.getLatitude()));
Log.d("Longitude", String.valueOf(place.getLongitude()));
Log.d("Name", place.getName());
Log.d("Vicinity", place.getVicinity());
}
for (int i = 0; i < placeList.size(); i++) {
mMap.addMarker(new MarkerOptions()
.title(placeList.get(i).getName())
.position(
new LatLng(placeList.get(i).getLatitude(), placeList
.get(i).getLongitude()))
.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_GREEN))
.snippet(placeList.get(i).getVicinity()));
}
CameraPosition cameraPosition = new CameraPosition.Builder()
.target(new LatLng(placeList.get(0).getLatitude(), placeList
.get(0).getLongitude())) // Sets the center of the map to
// Mountain View
.zoom(14) // Sets the zoom
.tilt(30) // Sets the tilt of the camera to 30 degrees
.build(); // Creates a CameraPosition from the builder
mMap.animateCamera(CameraUpdateFactory
.newCameraPosition(cameraPosition));
mPlaceAdapter = new PlaceAdapter(GooglePlacesActivity.this, placeList);
mPlaceAdapter.notifyDataSetChanged();
listView.setAdapter(mPlaceAdapter);
}
}
}
PlaceAdapter.java
package com.aquib.android.placefinder;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.TextView;
import java.util.List;
/**
* Created by dell on 2/19/2015.
*/
public class PlaceAdapter extends ArrayAdapter<Place>{
private final List<Place> list;
private final Context context;
public PlaceAdapter(Context context, List<Place> list){
super(context, R.layout.place_list, list);
this.context = context;
this.list = list;
}
static class ViewHolder{
protected TextView text;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
View view = null;
ViewHolder viewHolder;
if (convertView == null){
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.place_list, parent, false);
viewHolder = new ViewHolder();
viewHolder.text = (TextView) view.findViewById(R.id.placeName);
view.setTag(viewHolder);
}
else {
viewHolder = (ViewHolder) view.getTag();
}
viewHolder.text.setText(list.get(position).getName());
return view;
}
}
当我滚动列表时,应用程序崩溃并生成 NullPointerException。
这个错误正在生成
java.lang.NullPointerException
at com.aquib.android.placefinder.PlaceAdapter.getView(PlaceAdapter.java:46)
at android.widget.AbsListView.obtainView(AbsListView.java:2255)
at android.widget.ListView.makeAndAddView(ListView.java:1790)
at android.widget.ListView.fillDown(ListView.java:691)
at android.widget.ListView.fillGap(ListView.java:655)
at android.widget.AbsListView.trackMotionScroll(AbsListView.java:5143)
at android.widget.AbsListView.scrollIfNeeded(AbsListView.java:3243)
at android.widget.AbsListView.onTouchMove(AbsListView.java:3587)
at android.widget.AbsListView.onTouchEvent(AbsListView.java:3431)
at android.view.View.dispatchTouchEvent(View.java:7706)
at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2210)
at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1945)
at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2216)
at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1959)
at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2216)
at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1959)
at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2216)
at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1959)
at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2216)
at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1959)
at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2216)
at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1959)
at com.android.internal.policy.impl.PhoneWindow$DecorView.superDispatchTouchEvent(PhoneWindow.java:2068)
at com.android.internal.policy.impl.PhoneWindow.superDispatchTouchEvent(PhoneWindow.java:1515)
at android.app.Activity.dispatchTouchEvent(Activity.java:2458)
at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchTouchEvent(PhoneWindow.java:2016)
at android.view.View.dispatchPointerEvent(View.java:7886)
at android.view.ViewRootImpl$ViewPostImeInputStage.processPointerEvent(ViewRootImpl.java:3947)
at android.view.ViewRootImpl$ViewPostImeInputStage.onProcess(ViewRootImpl.java:3826)
at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:3392)
at android.view.ViewRootImpl$InputStage.onDeliverToNext(ViewRootImpl.java:3442)
at android.view.ViewRootImpl$InputStage.forward(ViewRootImpl.java:3411)
at android.view.ViewRootImpl$AsyncInputStage.forward(ViewRootImpl.java:3518)
at android.view.ViewRootImpl$InputStage.apply(ViewRootImpl.java:3419)
at android.view.ViewRootImpl$AsyncInputStage.apply(ViewRootImpl.java:3575)
at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:3392)
at android.view.ViewRootImpl$InputStage.onDeliverToNext(ViewRootImpl.java:3442)
at android.view.ViewRootImpl$InputStage.forward(ViewRootImpl.java:3411)
at android.view.ViewRootImpl$InputStage.apply(ViewRootImpl.java:3419)
at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:3392)
at android.view.ViewRootImpl.deliverInputEvent(ViewRootImpl.java:5532)
at android.view.ViewRootImpl.doProcessInputEvents(ViewRootImpl.java:5512)
at android.view.ViewRootImpl.enqueueInputEvent(ViewRootImpl.java:5483)
at android.view.ViewRootImpl$WindowInputEventReceiver.onInputEvent(ViewRootImpl.java:5612)
at android.view.InputEventReceiver.dispatchInputEvent(InputEventReceiver.java:185)
at android.view.InputEventReceiver.nativeConsumeBatchedInputEvents(Native Method)
at android.view.InputEventReceiver.consumeBatchedInputEvents(InputEventReceiver.java:176)
at android.view.ViewRootImpl.doConsumeBatchedInput(ViewRootImpl.java:5585)
at android.view.ViewRootImpl$ConsumeBatchedInputRunnable.run(ViewRootImpl.java:5631)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:761)
at android.view.Choreographer.doCallbacks(Choreographer.java:574)
at android.view.Choreographer.doFrame(Choreographer.java:542)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographe.