2011-03-03 15 views
8

Tengo algunos problemas con notifyDataSetChanged() de un BaseAdapter. Este método se llama en refreshItems() y actualizará BaseAdapter de mi ListActivity. Al invocar notifyDataSetChanged() no ocurre nada hasta que me desplazo hacia abajo en ListView, por ejemplo, con las teclas de flecha. De alguna manera, el método getView() modificado tampoco se llama. Quizás puedas darme una pista, ¡gracias! :)[done] notifyDataSetChanged() no actualiza ListActivity automáticamente

public class WinampControlClientPlaylist extends ListActivity { 

static WinampControlClientPlaylist activity = null; 

static EfficientAdapter adapter = null; 


static class EfficientAdapter extends BaseAdapter { 


    public EfficientAdapter(Context context) { 
     mInflater = LayoutInflater.from(context); 
    } 

    private LayoutInflater mInflater; 

    @Override 
    public int getCount() { 
     return Settings.playlistlength; 
    } 

    @Override 
    public long getItemId(int position) { 
     return position; 
    } 

    @Override 
    public View getView(final int position, View convertView, ViewGroup parent) { 
     ViewHolder holder; 


     if (convertView == null) 
     { 
      holder = new ViewHolder(); 

      convertView = mInflater.inflate(R.layout.listview, null); 

      holder.text = (TextView) convertView.findViewById(R.string.playlist_title); 
      holder.image = (ImageView) convertView.findViewById(R.string.playlist_play); 

      convertView.setTag(holder); 
     } else { 
      holder = (ViewHolder) convertView.getTag(); 
     } 


     holder.text.setText(Settings.playlist[position]); 

     if (position == Settings.playlistPosition) 
     { 
      holder.text.setTypeface(null, Typeface.ITALIC); 
      holder.image.setVisibility(0); 
     } 
     else 
     { 
      holder.text.setTypeface(null, Typeface.NORMAL); 
      holder.image.setVisibility(4); 
     } 


     return convertView; 
    } 


    static class ViewHolder { 
     TextView text; 
     ImageView image; 
    } 

    @Override 
    public Object getItem(int position) { 
     return Settings.playlist[position]; 
    } 
} 




void initialize() 
{ 
    adapter = new EfficientAdapter(this); 
    setListAdapter(adapter); 

    //registerForContextMenu(getListView()); 
} 


@Override 
public void onResume() 
{ 
    super.onResume(); 

    // REFRESH PLAYLIST 
    if (getListAdapter() == null && Settings.playlist != null) 
     initialize(); 
} 

@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.playlist); 

    activity = this; 
} 

static void refreshItems() 
{ 
    try { 
     adapter.notifyDataSetChanged(); 
    } catch (Exception e) {} 

} 

}

+0

Bueno, tal vez no entiendo su pregunta, pero un ListView se actualizará si su conjunto de datos ha cambiado, y la forma de notificar que llama a notifyDataSetChanged() al ListView. Pero aquí no veo dónde cambias el conjunto de datos, los ajustes están cambiando en otro hilo o lugar? – Franco

+0

sí, otra actividad llama al Settings.playlistPosition = newNumber y WinampControlClientPlaylist.refreshItems(); Pero cuando esto sucede, ListView no se actualiza. Solo veo cambios cuando pulso flecha arriba/abajo en el emulador luego. – martin

Respuesta

4

Como se señaló Franco, notifyDataSetChanged() se usa para decirle al ListView que el contenido de su adaptador han cambiado, no es que se necesita para volver a dibujar en sí. Solo está cambiando una configuración que afecta cómo se representa algo. Intente llamar al refreshDrawableState para decirle a la lista que vuelva a dibujar.

+0

Gran ayuda. ¡Gracias! –

4

Intente llamar al invalidate() en su ListView.

+0

sí, trabajando para mí –

0

Creo que puede haber algunos problemas con el adaptador; tal vez no está configurado.

En mi experiencia, siempre hubo algún tipo de razón que impidió la vista de lista (y el adaptador) para actualizar.

+0

No realmente, ahora mismo tengo ListActivity que no quiero actualizar. Lo interesante es que se actualiza si se ejecuta en depurador y NO se ejecuta de forma nativa ... – AlexeyVMP

0

Tuve el mismo problema, y ​​la solución para mí fue llamar al requestLayout() en el ListView.

9

Tuve el mismo problema (las actualizaciones de ListView solo cuando lo desplazo, incluso notifyDataSetChanged no me ayudó). puedo solucionar esta manera: simplemente tratar de hacer su "visión" modificaciones en el hilo que crea la interfaz de usuario, es decir

activity.runOnUiThread(new Runnable() {   
     public void run() { 
       //do your modifications here 

       // for example  
       adapter.add(new Object()); 
       adapter.notifyDataSetChanged() 
     } 
}); 
+0

obtuvo esta solución después de 2 días .. gracias Sr. @ almaz_from_kazan –

0

me encontré con el mismo problema e intenté llamar al notifyDataSetChanged() en el adaptador. Además, también traté de llamar al refreshDrawableState(), invalidateViews() en la vista y ninguno funcionó. Todos estos métodos se llaman en el hilo de UI. Entonces encontré esto How to clear the views which are held in the ListView's RecycleBin?. Finalmente, setAdapter() funcionó, solo si creo un nuevo adaptador.

0

La razón principal detrás de esto es la referencia incorrecta del adaptador al que está llamando notifyDataSetChanged();

Creo que debe asegurarse de crear un objeto adaptador una vez y llamar a notifyDataSetChanged() en el mismo objeto.

Puede depurar el valor de referencia del objeto al crear la hora del objeto adaptador y cuando llama al método notifyDataSetChanged().

0
Why it works in first code ? 

--- Debido a que está configurando los valores a la Lista temporal y pasándole el adaptador y lo muestra en la vista de lista.

Why not work in second code ? 

--- Debido a que se está configurando temp al adaptador mucho antes de establecer el valor de temperatura en segundo, su clase de adaptador podría no obtener el valor actualizado cuando se establece un nuevo valor a temp temp ..que porque no es público o no a nivel de clase o no estático. Pon la declaración de temperatura en el nivel de raíz y prueba.

Y muestre su código completo tanto como sea necesario y Logcat si recibe alguna advertencia que también.

Cuestiones relacionadas