2013-02-16 6 views
6
zeigt

Das letzte, was ich tue, ist: Ich habe die Google Map in meiner Anwendung mit Som Buttons und Extras. aber ich muss auch den aktualisierten Standort einer Markierung die ganze Zeit innerhalb meiner Karte zeigen (ich werde die Daten vom externen Gerät nicht gps-Sensor des androiden Telefons erhalten). Also dachte ich, zuerst thread zu verwenden, dann aber zu AsyncTask, wie du es in meinem Code siehst, und habe versucht, die addMarker-Methode dort zu verwenden, aber jedes Mal, wenn ich es starte, läuft die Map einfach nicht mehr. Ich möchte jetzt nur einen Marker auf der Karte zeigen, aber jetzt erfolgreich! Die GoogleMap-Karte kann nicht über den UI-Thread und innerhalb von AsyncTask erreicht werden. Warum? Ist das jemand begegnet? was soll ich tun, diese zu lösen ... plz helpwie man Markierungen ständig durch AsyncTask oder Handler in Google Karte Version 2

package com.example.mapsversion2; 

    //All imports 

    public class MainActivity extends Activity { 
    static final LatLng exmpoint = new LatLng(59.331438,18.064957); 

    public static GoogleMap map; 

    Button button; 
    Button waypointButton; 
    Button destinationButton; 
    Marker wayPoint; 
    TextView positiontext; 
    int countclick= 3; 
    public static DataModel autoboxdata= new DataModel(); 
    public static Bitmap arrowBitmap; 
    Marker currentPlace; 
    MapFragment mapF; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 
    mapF = ((MapFragment) getFragmentManager().findFragmentById(R.id.map)); 
    map= mapF.getMap(); 
    map.setMapType(GoogleMap.MAP_TYPE_HYBRID); 

    // positiontext = (TextView) findViewById(R.id.position); 

    // Move the camera instantly to hamburg with a zoom of 15. 
    map.moveCamera(CameraUpdateFactory.newLatLngZoom(exmpoint,15)); 

    // Zoom in, animating the camera. 
    map.animateCamera(CameraUpdateFactory.zoomTo(6), 2000, null); 

    addListenerOnButton(); 
    map.setOnMarkerDragListener(this); 

    new PositionUpdate1().execute(); 
    } 
    @Override 
    public boolean onCreateOptionsMenu(Menu menu) { 
    getMenuInflater().inflate(R.menu.activity_main, menu); 
    return true; 
    } 

    public void addListenerOnButton() { 

     destinationButton= (Button) findViewById(R.id.destinationB); 

     destinationButton.setOnClickListener(new OnClickListener() { 

      @Override 
      public void onClick(View arg0) { 
       //do something 
      } 
     });  
    } 

    } 

    public class PositionUpdate1 extends AsyncTask<Void, Void, Void>{ 


    @Override 
    protected Void doInBackground(Void...arg0) { 
     // TODO Auto-generated method stub 


     map.addMarker(new MarkerOptions() 
      .position(hereIam)); 

     System.out.println("hej"); 
     return null; 
    } 
    } 
    } 

Hier ist die LogCat:

02-17 18:57:17.805: E/AndroidRuntime(9905): FATAL EXCEPTION: main 
02-17 18:57:17.805: E/AndroidRuntime(9905): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.mapsv2/com.example.mapsv2.MainActivity}: java.lang.NullPointerException 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2100) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2125) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.ActivityThread.access$600(ActivityThread.java:140) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1227) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.os.Handler.dispatchMessage(Handler.java:99) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.os.Looper.loop(Looper.java:137) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.ActivityThread.main(ActivityThread.java:4898) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at java.lang.reflect.Method.invokeNative(Native Method) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at java.lang.reflect.Method.invoke(Method.java:511) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1006) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:773) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at dalvik.system.NativeStart.main(Native Method) 
02-17 18:57:17.805: E/AndroidRuntime(9905): Caused by: java.lang.NullPointerException 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at com.example.mapsv2.MainActivity.onCreate(MainActivity.java:140) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.Activity.performCreate(Activity.java:5206) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1083) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2064) 
02-17 18:57:17.805: E/AndroidRuntime(9905):  ... 11 more 
02-17 18:57:17.935: E/android.os.Debug(2287): [email protected] > dumpstate -k -t -z -d -o /data/log/dumpstate_app_error 

Antwort

17

Sie versuchen, eine Markierung auf der Karte in der Hintergrund-Thread hinzufügen, aber Sie Die Benutzeroberfläche in Android kann nicht über einen anderen Thread als den UI-Thread aktualisiert werden. So bewegen Sie Ihren map.addMarker Aufruf der onPostExecute Methode, die in UI-Thread nach Hintergrundbetrieb genannt wird, ist komplett:

public class PositionUpdate1 extends AsyncTask<Void, Void, Location> { 

    @Override 
    protected Location doInBackground(Void...arg0) { 
     // get your location... 
     return hereIam; 
    } 

    @Override 
    protected void onPostExecute(Location loc) { 
     map.addMarker(new MarkerOptions().position(loc)); 
    } 
} 

Wenn Sie kontinuierlich den Marker zu aktualisieren, ist der einfachste Weg ist, ein Handler zu verwenden:

public class MainActivity extends Activity { 

    final int MARKER_UPDATE_INTERVAL = 2000; /* milliseconds */ 
    Handler handler = new Handler(); 

    GoogleMap map; 
    Marker marker; 
    Location location; 

    Runnable updateMarker = new Runnable() { 
     @Override 
     public void run() { 
      marker.remove(); 
      marker = map.addMarker(new MarkerOptions().position(location)); 

      handler.postDelayed(this, MARKER_UPDATE_INTERVAL); 
     } 
    }; 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     map = ...; // get map 
     location = ...; // get location 
     marker = map.addMarker(new MarkerOptions().position(location)); 

     handler.postDelayed(updateMarker, MARKER_UPDATE_INTERVAL); 
    } 

    @Override 
    protected void onDestroy() { 
     handler.removeCallbacks(updateMarker); 

     super.onDestroy(); 
    } 
} 
+0

Ich habe dies getan. Die App funktioniert immer noch nicht. mit den gleichen Logcat-Fehlern –

+0

Ok, Sie haben auch eine 'NullPointerException' in Zeile 140 in' MainActivity'. Sind Sie sicher, dass Ihre Karte nicht null ist? ('mapF.getMap()' Aufruf wird 'null' zurückgeben, wenn Google Play-Dienste nicht auf dem Gerät installiert sind, also sollten Sie mit einem solchen Fall umgehen) – whyleee

+0

wenn ich die Markierung im Haupt-Thread hinzufüge inkrementiere alles funktioniert. und ich sehe den Marker .. und ja, ich habe Google Play Services installiert –

1

Wenn Ihr async Aufgabe mehr als eine Markierung wird geladen können Sie wie folgt vorgehen:

private class AddMarker implements Runnable { 

    private GoogleMap map; 
    private MarkerOptions options; 

    public AddMarker(GoogleMap map, MarkerOptions options) { 
     this.map = map; 
     this.options = options; 
    } 

    @Override 
    public void run() 
    { 
     map.addMarker(options); 
    } 
} 
Runnable addMarker = new AddMarker(map, markerOptions); 
activity.runOnUiThread(addMarker); 

Und, cours e, Sie sollten die asynchrone Aufgabe mit dem Aktivitätsobjekt erstellen.

+0

Wie aktualisiert man 6 Marker alle 1 Sekunde? –

3

Sie können so etwas tun. Laden Sie die benötigten Daten in doInBackground und zeichnen Sie die Markierungen in onProgressUpdate. Um onProgressUpdate aufzurufen, führen Sie einfach publishProgress() von doInBackground aus. Auf diese Weise können Sie die Benutzeroberfläche innerhalb der ASyncTask aktualisieren. Funktioniert für mich.

public class CDrawHotspotsAsync extends AsyncTask<Void, CHotspot, Boolean> 
{ 
private final Context mCntxt; 
private final GoogleMap mGMap; 

// --------------------------------------------------------- 

public CDrawHotspotsAsync(Context cntxt, GoogleMap gmap) 
{ 
    this.mCntxt = cntxt; 
    this.mGMap = gmap; 
} 

// --------------------------------------------------------- 

private void drawMarker(GoogleMap gmap, CHotspot hotspot) 
{ 
    // Set marker options 
    MarkerOptions mo = new MarkerOptions(); 
    mo.position(hotspot.getPosition()); 
    mo.title(hotspot.getName()); 
    String descr = hotspot.getAddress() + ", " + hotspot.getPostal() + ", " + hotspot.getCity(); 
    mo.snippet(descr); 
    mo.icon(BitmapDescriptorFactory.fromResource(R.drawable.hotspot_marker)); 

    // Add marker to map 
    gmap.addMarker(mo); 
} 

// --------------------------------------------------------- 

@Override 
protected Boolean doInBackground(Void... params) 
{ 
    // Get hotspots from database 
    CHotspotList hotspots = new CHotspotList(this.mCntxt); 
    ArrayList<CHotspot> arrHotspots = hotspots.getHotspotList(); 

    for (CHotspot hotspot : arrHotspots) 
    { 
     // Publish progress 
     publishProgress(hotspot); 
    } 

    // Always return true 
    return true; 
} 

// --------------------------------------------------------- 

@Override 
protected void onProgressUpdate(CHotspot... hotspot) 
{ 
    // Draw the marker 
    drawMarker(this.mGMap, hotspot[0]); 
} 
} 
Verwandte Themen