2011-11-24 32 views
6

Sử dụng API com.google.android.maps, tôi đã có một MapActivity sử dụng ItemizedOverlay để đặt một số biểu tượng (tối đa 1000) trên MapView. Tôi muốn làm mới (hoặc có thể chỉ cần thêm vào danh sách) các biểu tượng khi LocationListener phát hiện thiết bị đã di chuyển một khoảng cách nhất định (hiện tại là 5 mét, nhưng đó chỉ là để thử nghiệm).bản đồ làm mới ItemizedOverlay cung cấp cho ArrayIndexOutOfBoundsException

Tôi đã thêm setLastFocusedIndex(-1)populate(), nhưng ItemizedOverlay của tôi vẫn bị lỗi. Tôi nghĩ rằng nó bị treo khi tôi thêm nhiều mục vào danh sách, nhưng đôi khi nó có vẻ như sụp đổ ngay cả khi tôi không di chuyển điện thoại của mình. Nó treo trên bản cập nhật đầu tiên. Tôi không thể nói từ LogCat chính xác những gì gây ra lỗi.

MapActivity của tôi là dựa trên các hướng dẫn khác nhau:

EDIT: tinh chỉnh mã để làm một batch update of items nhưng nó vẫn bị treo

public class NearbyActivity extends MapActivity implements VenueCatalogListener { 
    private final String TAG = this.getClass().getSimpleName(); 

    List<Overlay> mapOverlays; 
    HelloItemizedOverlay itemizedOverlay; 

    private MapController mapController; 
    private MapView mapView; 
    private LocationManager locationManager; 

    private int latE6; 
    private int lonE6; 

    private Location current_location; 
    private VenuesFromServer venues_from_server; 

    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     venues_from_server = new VenuesFromServer(this); 
     setupViews(); 
    } 

    private void setupViews() { 
     setContentView(R.layout.nearby_view); 


     RelativeLayout linearLayout = (RelativeLayout) findViewById(R.id.mapMainLayout); 

     mapView = new MapView(this, PreferencesManager.CLUBBERIA_MAPS_API_KEY); 
     initializeMap(); 

     linearLayout.addView(mapView); 
    } 

    private void initializeMap() { 
     mapView.setKeepScreenOn(true); 
     mapView.setClickable(true); 
     mapView.setBuiltInZoomControls(true); 
     mapController = mapView.getController(); 
     mapController.setZoom(mapView.getMaxZoomLevel()-5); // Zoom 1 is world view 

     locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE); 
     locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, new GeoUpdateHandler()); 

     mapOverlays = mapView.getOverlays(); 
     if(itemizedOverlay == null) { 
      Drawable drawable = this.getResources().getDrawable(R.drawable.icon); 
      itemizedOverlay = new HelloItemizedOverlay(drawable); 
      mapOverlays.add(itemizedOverlay); 
     } 
    } 

    @Override 
    protected boolean isRouteDisplayed() { 
     return false; 
    } 

    public class GeoUpdateHandler implements LocationListener { 
     @Override 
     public void onLocationChanged(Location location) { 
      if(current_location == null) { 
       current_location = location; 
      } 

      int lat = (int) (location.getLatitude() * 1E6); 
      int lng = (int) (location.getLongitude() * 1E6); 
      GeoPoint point = new GeoPoint(lat, lng); 
      if(current_location.distanceTo(location) > 5) { 
       // this kicks off an async task that will call back to venueListUpdated() below 
       venues_from_server.getVenueJSONFromServer(location.getLatitude(), location.getLongitude(), 19); 
      } 
      mapController.animateTo(point); // mapController.setCenter(point); 
     } 

     @Override 
     public void onProviderDisabled(String provider) { 
     } 

     @Override 
     public void onProviderEnabled(String provider) { 
     } 

     @Override 
     public void onStatusChanged(String provider, int status, Bundle extras) { 
     } 
    } 

    @Override 
    public void venueListUpdated() { 

     // Base.B.arrayVenuesMap is an ArrayList<Venue> 
     for(int i=0;i<Base.B.arrayVenuesMap.size();i++) { 
      Venue _venue = Base.B.arrayVenuesMap.get(i); 
      latE6 = (int) (_venue.latitude*1e6); 
      lonE6 = (int) (_venue.longitude*1e6); 
      GeoPoint point = new GeoPoint(latE6, lonE6); 
      OverlayItem overlayitem = new OverlayItem(point, _venue.name, ""); 
      Drawable drawable = this.getResources().getDrawable(R.drawable.icon); 

      itemizedOverlay.addOverlay(overlayitem, drawable); 
     } 
     itemizedOverlay.batchPopulate(); 
    } 
} 

My ItemizedOverlay trông như thế này:

public class HelloItemizedOverlay extends ItemizedOverlay<OverlayItem> { 

    private ArrayList<OverlayItem> mOverlays = null; 

    public HelloItemizedOverlay(Drawable defaultMarker) { 
     super(boundCenterBottom(defaultMarker)); 
     mOverlays = new ArrayList<OverlayItem>(); 
     setLastFocusedIndex(-1); 
     populate(); 
    } 

    public void addOverlay(OverlayItem overlay, Drawable defaultMarker) { 
     if(!mOverlays.contains(overlay)) { 
      setLastFocusedIndex(-1); 
      overlay.setMarker(boundCenterBottom(defaultMarker)); 
      mOverlays.add(overlay); 
     } 
    } 

    public void batchPopulate() { 
     setLastFocusedIndex(-1); 
     populate(); 
    } 

    @Override 
    protected OverlayItem createItem(int i) { 
     return mOverlays.get(i); 
    } 

    @Override 
    public int size() { 
     return mOverlays.size(); 
    } 
} 

Logcat có các dòng sau:

11-24 18:28:02.245: D/AsyncJSONClient(18382): starting connect with this many pairs: 0; thread 17 
11-24 18:28:02.255: E/AndroidRuntime(18382): FATAL EXCEPTION: main 
11-24 18:28:02.255: E/AndroidRuntime(18382): java.lang.ArrayIndexOutOfBoundsException 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.google.android.maps.ItemizedOverlay.getIndexToDraw(ItemizedOverlay.java:211) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.google.android.maps.ItemizedOverlay.draw(ItemizedOverlay.java:240) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.google.android.maps.Overlay.draw(Overlay.java:179) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.google.android.maps.OverlayBundle.draw(OverlayBundle.java:42) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.google.android.maps.MapView.onDraw(MapView.java:530) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.View.draw(View.java:6918) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1646) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1644) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.View.draw(View.java:6921) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.widget.FrameLayout.draw(FrameLayout.java:357) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1646) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1644) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1644) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1644) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1644) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.View.draw(View.java:6921) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.widget.FrameLayout.draw(FrameLayout.java:357) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.drawChild(ViewGroup.java:1646) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1373) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.View.draw(View.java:6921) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.widget.FrameLayout.draw(FrameLayout.java:357) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.android.internal.policy.impl.PhoneWindow$DecorView.draw(PhoneWindow.java:1947) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewRoot.draw(ViewRoot.java:1539) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewRoot.performTraversals(ViewRoot.java:1275) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.view.ViewRoot.handleMessage(ViewRoot.java:1876) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.os.Handler.dispatchMessage(Handler.java:99) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.os.Looper.loop(Looper.java:123) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at android.app.ActivityThread.main(ActivityThread.java:3728) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at java.lang.reflect.Method.invokeNative(Native Method) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at java.lang.reflect.Method.invoke(Method.java:507) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:864) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:622) 
11-24 18:28:02.255: E/AndroidRuntime(18382): at dalvik.system.NativeStart.main(Native Method) 
11-24 18:28:02.255: W/ActivityManager(308): Force finishing activity com.clubberia.android/.ClubberiaMain 

Đôi khi tôi có thể thêm các mục vào ItemizedOverlay mà không gặp sự cố?

Trả lời

3

ni biết nó một chút cũ, nhưng @cgwylie là gần như ngay ..

bạn nên gọi populate() sau khi cập nhật lớp phủ giá trị ... và sau đó bạn có thể gọi hmm postInvalidate()

0

Khi bạn thay đổi các mục trong ItemizedOverlay, bạn cần gọi postInvalidate() trên MapView để thông báo cho bạn biết rằng bạn đã điều chỉnh lớp phủ sao cho không thử và vẽ các mục không có trong danh sách nữa.

Trong số venueListUpdated() bạn có thể thử thêm mapView.postInvalidate() sau khi gọi itemizedOverlay.addOverlay(overlayitem, drawable) để giải quyết sự cố của mình.

+0

. Tôi vừa thử đề xuất của bạn, nhưng nó không hoạt động. Dù sao cũng cảm ơn bạn! –

+0

Thật tuyệt, xin lỗi nó đã không hoạt động, nó đã giải quyết được vấn đề trong quá khứ đối với tôi. – cgwyllie

Các vấn đề liên quan