Auffüllen listview in einem separaten thread
In eine Aktivität, mit der ich geladen Zeilen eines listview-was nimmt sich viel Zeit, deshalb lege ich diese Aufgabe in einem separaten thread damit die Anzeige einen progressDialog.
Ich den folgenden
private void doMyStuff() {
listItems.clear();
progressDialog.show();
new Thread(new Runnable() {
@Override
public void run() {
for () {
listItems.add(something to add);
}
handler.sendEmptyMessage(0);
progressDialog.dismiss();
}
}).start();
}
private Handler handler = new Handler() {
public void handleMessage(android.os.Message msg) {
if (msg.what == 0) {
adapter.notifyDataSetChanged();
}
};
};
Ich habe manchmal einen bug, der wirft eine IllegalStateException. Zunächst war ich überrascht, weil die Programmierung thread wie das ist, was ich in der Regel nicht in standard-Java-Programme.
Der Fehler erscheint nur "manchmal" und es wird nicht angezeigt, wenn Schritt für Schritt Debuggen.
Dies führte mich zu suchen, um die web, und ich fand einige Fragen, die in SO im Zusammenhang, und ich muss zugeben, dass die Dinge nicht klar sind meine Gedanken.
Wie rufe ich die notifyDataSetChanged() nur, wenn der thread fertig ist, warum es manchmal wirft eine exception.
Kann jemand bestätigen mir, dass diese Art von tun, ist falsch, und das MUSS ich nutzen async task und vielleicht erklären Sie mir, warum ???
Benötige ich einen progressDialog angezeigt, kann mir jemand ein einfaches Beispiel von AsyncTask füllen eines listview UND anzeigen ein progressDialog das Auffüllen Fortschritt.
Dank
UPDATE
jtanveer gab mir die Antwort auf die asynctask Frage. Jetzt die anderen darauf hin, dass die Entlassung nicht in der Prozedur, die ich korrigieren.
Laut dem Artikel gegeben durch jtanveer auf "Painless Threading" Sie sagen, dass
Android bietet mehrere Optionen für den Zugriff auf UI-thread aus anderen threads in denen einer von Ihnen ist-HANDLER.
Weiss einer warum setzen die entlassenen in der hf nicht mein problem lösen ? für mich listItem.hinzufügen nichts zu tun hat mit UI ? Bin ich falsch in diesem Punkt ?
Für mich, in meinem code nur die UI-adapter und progressdialog ? Jeder Kommentar oder Erklärung ist willkommen.
LETZTE ANTWORT
stjom gab eine funktionierende Antwort auf meine spezifischen code. Läuft die runOnUiThread in der Prozedur. Es funktioniert, aber ich bin überrascht, weil ich dachte der handler ausgeführt wurde, in den Ui-Thread ...
Vielen Dank an alle für all Eure Antworten.
- Ich glaube, es gibt eine Menge Beispiele gibt. Suchen Sie im web nach so etwas wie "android progressdialog asynctask-Beispiel".
- Beide Antworten haben Sie jetzt richtig sind. Sie brauchen nicht zu verwenden
AsyncTask
, obwohl es nicht machen Operationen wie diese zu reinigen. Was Sie tun MÜSSEN, ist alle UI-Operationen im UI - /Haupt-thread, und dazu gehört auch die Entlassung der Fortschritts-dialog. Entweder Sie verwenden dieAsyncTask
Beispiel unten oder fügen Sie einfachprogressDialog.dismiss()
in IhreHandler
Rückruf. - +1 an Euch beide für den Hinweis auf diesen Fehler. Leider hat es nicht mein problem beheben, aber ich verstehe nicht, warum besause der handler im UI-thread !
- Ich habe das update auf meine Frage. warum sind deine Antworten nicht funktioniert ?
Du musst angemeldet sein, um einen Kommentar abzugeben.
Wann immer Sie nennen
adapter.notifyDataSetChanged();
es identifiziert alle änderungen IhrerlistItems
Objekt. falls eine Veränderung gefunden wird, wird es die Aktualisierung der Benutzeroberfläche entsprechend an die ich denke, die Ursachen Ihres Problems. Sie können rufen Siein Ihrem handler.
definieren eine innere Klasse wie unten:
wenn Sie brauchen, können Sie sich an dieser Artikel.
listItems
verknüpft mit adapter in einen hintergrund-thread. Manchmal kann es raise exception. Damit ich in der Regel erstellen Sie eine weitere Liste (Sammlung), Elemente hinzufügen, die es gibt. Dann im UI-thread füge ich eine Sammlung der adapter (adapter.addAll(newList); adapter.notifyDataSetChanged();).Brauchen Sie nicht zu verwenden, AsyncTask, es ist nur eine Bequemlichkeit.
Soweit, warum Ihre aktuelle Implementierung funktioniert nicht, manchmal -
Sollten Sie entlassen Ihre Fortschritts-dialog, aus dem UI-thread, also das muss gehen in Ihren handler, nicht den hintergrund-thread.