11

ArrayAdapter를 사용하여 사용자 정의 ListView에 항목을 추가하고 Android 앱에 결과를 표시합니다. 내가 겪고있는 문제는 ArrayAdapter가 뷰를 표시하기 전에 모든 항목이 포함될 때까지 기다리는 것 같습니다. 즉, ArrayAdapter에 항목을 추가 할 때 notifyDataSetChanged를 호출하면 추가 된 항목을 표시하도록 ListView가 업데이트되지 않습니다. 항목을 표시하기 전에 모든 항목이 추가되고 GetView가 호출 될 때까지 대기합니다.Android - ArrayAdapter를 사용하여 한 번에 하나씩 ListView에 항목을 추가하고 표시합니다.

내가하고 싶은 것은 항목을 ListView에 추가 한 직후에 항목을 표시하는 것입니다. 이것이 가능한가? 당신이 볼 수 있듯이, 나는 추가 방법 후 notifyDataSetChanged를 호출하고있다하더라도, 실제로보기를 업데이트하지 않습니다

r_adapter = new ReminderAdapater(Activity_ContentSearch.this, R.layout.search_listitem, myList); 
listView.setAdapter(r_adapter); 
... 
r_adapter.notifyDataSetChanged(); 
r_adapter.clear(); 
for(int i = 0; i < myList.size(); i++) 
{ 
    r_adapter.add(myList.get(i)); 
    r_adapter.notifyDataSetChanged(); 
} 

:

나는 관련 코드는 다음 믿습니다. 위 루프가 끝나면보기가 마침내 업데이트됩니다 (코드 섹션이 완료 될 때까지 GetView가 호출되지 않기 때문에 아는 바를 기반으로합니다).

행운을 빌어 내 맞춤 ArrayAdapter의 add 메소드를 오버라이드하려고했는데, 그 방법의 뷰에 액세스 할 수 없기 때문에.

어떤 도움을 환영합니다 :)에게 것

바라

답변

23

안드로이드의 UI가 단일 스레드입니다. 어댑터에 항목을 추가 할 때마다 기본 응용 프로그램 스레드에서 안드로이드 제어권을 돌려주지 않습니다. 따라서 안드로이드는 컨트롤을 반환 할 때까지 엔트리를 표시 할 수있는 기회를 얻지 못합니다. 어댑터를 완전히 채울 때까지는 안됩니다.

Here is an example은 배경 스레드를 통해 ArrayAdapter을 점진적으로 채우기 위해 AsyncTask을 사용하는 것을 보여줍니다.

/*** 
    Copyright (c) 2008-2012 CommonsWare, LLC 
    Licensed under the Apache License, Version 2.0 (the "License"); you may not 
    use this file except in compliance with the License. You may obtain a copy 
    of the License at http://www.apache.org/licenses/LICENSE-2.0. Unless required 
    by applicable law or agreed to in writing, software distributed under the 
    License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS 
    OF ANY KIND, either express or implied. See the License for the specific 
    language governing permissions and limitations under the License. 

    From _The Busy Coder's Guide to Android Development_ 
    http://commonsware.com/Android 
*/ 

package com.commonsware.android.async; 

import android.app.ListActivity; 
import android.os.AsyncTask; 
import android.os.Bundle; 
import android.os.SystemClock; 
import android.widget.ArrayAdapter; 
import android.widget.Toast; 
import java.util.ArrayList; 

public class AsyncDemo extends ListActivity { 
    private static final String[] items={"lorem", "ipsum", "dolor", 
             "sit", "amet", "consectetuer", 
             "adipiscing", "elit", "morbi", 
             "vel", "ligula", "vitae", 
             "arcu", "aliquet", "mollis", 
             "etiam", "vel", "erat", 
             "placerat", "ante", 
             "porttitor", "sodales", 
             "pellentesque", "augue", 
             "purus"}; 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.main); 

    setListAdapter(new ArrayAdapter<String>(this, 
         android.R.layout.simple_list_item_1, 
         new ArrayList<String>())); 

    new AddStringTask().execute(); 
    } 

    class AddStringTask extends AsyncTask<Void, String, Void> { 
    @Override 
    protected Void doInBackground(Void... unused) { 
     for (String item : items) { 
     publishProgress(item); 
     SystemClock.sleep(200); 
     } 

     return(null); 
    } 

    @SuppressWarnings("unchecked") 
    @Override 
    protected void onProgressUpdate(String... item) { 
     ((ArrayAdapter<String>)getListAdapter()).add(item[0]); 
    } 

    @Override 
    protected void onPostExecute(Void unused) { 
     Toast 
     .makeText(AsyncDemo.this, "Done!", Toast.LENGTH_SHORT) 
     .show(); 
    } 
    } 
}