Programación y Desarrollo para Android Subforo exclusivo para temas de programación de software para PDAs y desarrollo de aplicaciones, interfaces, etc bajo Android

Respuesta
 
Herramientas
  #1  
Viejo 14/09/13, 18:37:12
Array

[xs_avatar]
rafaxplayer rafaxplayer no está en línea
Miembro del foro
 
Fecha de registro: jun 2013
Localización: en la barcelona media
Mensajes: 224
Modelo de smartphone: LG-E610
Tu operador: Orange
Problema listview con checkboxes

Saludos compañeros , tengo un problema con un listview con custom adapter y checkboxes , el problema básicamente es que al hacer visibles o checkar los checks que están fuera de de la lista al hacer scroll y re-dibujarlos se comportan como quieren , los seleccionados se de-seleccionan y algunos visibles se hace invisibles...
utlizo unos métodos para hacer los check visibles y para checkarlos todos o no , serian estos:

Código:
private void setListChecksVisibles(boolean isVisible) {
		int nVisible = isVisible ? View.VISIBLE : View.GONE;
		header.setVisibility(nVisible);
		footer.setVisibility(nVisible);
		for(int i=0; i<lst.getChildCount(); i++){
			View ll = lst.getChildAt(i);
	        CheckBox cb = (CheckBox) ll.findViewById(R.id.checkItems);
	        cb.setVisibility(nVisible);
	        
		}
		adp.notifyDataSetChanged();
	}
	
	private void checkAll(boolean bCheck) {
		for(int i=0; i<lst.getChildCount(); i++){
			View ll =lst.getChildAt(i);
	        CheckBox cb = (CheckBox)ll.findViewById(R.id.checkItems);
	        cb.setChecked(bCheck);
	        
	       	}
		adp.notifyDataSetChanged();
	}
He probado en el adapter ah crear un array de booleanos para guardar los cambios en los checkboxes y actualizarlos en el getview , pero no me esta dando ningún resultado.

mi adapter es este:

Código:
public class HistoryAdapter extends BaseAdapter  {
		private LayoutInflater mInflater = null;
		private Cursor cur;
		private ArrayList<Boolean> itemSelection;
		
		public HistoryAdapter(){
			db = new DBHelper(getApplicationContext(), DBHelper.TABLE_NAME, null, 1);
			this.cur = db.SelectAll();
			mInflater = (LayoutInflater)getApplicationContext().getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
			itemSelection= new ArrayList<Boolean>();
                        for(int i=0;i<this.getCount();i++) {
				itemSelection.add(i, false);
			}
		}
		@Override
		public int getCount() {
			// TODO Auto-generated method stub
			return cur.getCount();
		}

		@Override
		public Cursor getItem(int position) {
			
			cur.moveToPosition(position);
			return cur;
		}
		
		@Override
		public long getItemId(int position) {
			
			Cursor c = getItem(position);
			long id =(Long)(long)c.getInt(c.getColumnIndex(DBHelper.KEY_ID));
			return id;
		}
		
		
		private class ViewHolder {
	        
	        TextView lng;
	        TextView lat;
	        TextView date;
	        CheckBox ch;
	     	        
	    }
		
		@Override
		public View getView(final int position, View convertView, ViewGroup arg2) {
			  
			
			ViewHolder holder= null;
				holder=	new ViewHolder();
			if (convertView == null) {
		            convertView = mInflater.inflate(R.layout.itemhistory, null);
		 		    holder.lng = (TextView) convertView.findViewById(R.id.textLongitude);
		            holder.lat=(TextView) convertView.findViewById(R.id.textLatitude);
		            holder.date=(TextView) convertView.findViewById(R.id.textDate);
		            holder.ch=(CheckBox)convertView.findViewById(R.id.checkItems);
		            holder.ch.setOnCheckedChangeListener(new OnCheckedChangeListener() {
						
						@Override
						public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
							itemSelection.set(position,isChecked);
							
						}
					});
		            convertView.setTag(holder);
		        }
		        else 
		        {
		            holder = (ViewHolder) convertView.getTag();
		        }
				try
				{
				Cursor rowItem = getItem(position);
				
		        
		        holder.lng.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_LONGITUDE))+" ");
		        holder.lat.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_LATITUDE))+" ");
		        holder.date.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_DATE))+" ");
				holder.ch.setChecked(itemSelection.get(position));
				}catch(Exception ex){
					ex.printStackTrace();
				}
				
				return convertView;
			
		}
		
		
	}
Alguna sugerencia? gracias de antemano ;)

Última edición por rafaxplayer Día 14/09/13 a las 18:49:18.
Responder Con Cita


  #2  
Viejo 14/09/13, 19:19:39
Array

[xs_avatar]
kriogeN kriogeN no está en línea
Colaborador/a
· Votos compra/venta: (1)
 
Fecha de registro: oct 2010
Localización: Murcia
Mensajes: 4,637
Modelo de smartphone: Samsung Galaxy S7 Edge SM-G935F
Tu operador: Vodafone
Para el setListChecksVisibles debería funcionar, porque no veo en el getView ningún código que modifique la visibilidad de los elementos. Y el reciclado de vista no debería influir, porque estás haciéndolo sobre todos los elementos (aunque realmente sea sobre los elementos visibles todo el tiempo).

Para el checkAll es lógico que no funcione, porque al scrollear y ejecutarse el getView el estado del check depende de itemSelection.get(position), y por tanto se marca según lo que dice ese ArrayList.

La solución para el checkAll es poner todos los elementos de itemSelection al estado que pasas por parámetro.

Para el otro caso, prueba añadiendo en el getView que la visibilidad dependa de una variable booleana en el HistoryAdapter. Y en el método setListChecksVisibles establece esa variable al valor que pasas por parámetro.
Responder Con Cita
  #3  
Viejo 14/09/13, 21:01:23
Array

[xs_avatar]
rafaxplayer rafaxplayer no está en línea
Miembro del foro
 
Fecha de registro: jun 2013
Localización: en la barcelona media
Mensajes: 224
Modelo de smartphone: LG-E610
Tu operador: Orange
Gracias kriogen , he logrado solucionar lo de mostrar y checkar o no todos los checks , lo conseguido usando unos métodos dentro del adapter(setCheckedall(boolean check) , setVisibleChecks(int vis) ) .
Mi problema es ahora la persistencia cuando hago selección aleatoria de los checks , cuando los oculta el scroll y vuelven cambian de estado como le da la gana ;(

he puesto un checkedchangedlistener para editar el array donde guardo el estado para aplicarlo al redibujar pero no funciona, ademas como veras en el listener hay un log.d que me da estado y posicion y por lo que veo la posición no cuadra cuando los items salen de ocultos en el scroll, no se que hago mal en este sentido;(

El adapter:

Código:
public class HistoryAdapter extends BaseAdapter  {
		private LayoutInflater mInflater = null;
		private Cursor cur;
		private ArrayList<Boolean> itemSelection;
		private ArrayList<Integer> itemVisible;
		public HistoryAdapter(){
			db = new DBHelper(getApplicationContext(), DBHelper.TABLE_NAME, null, 1);
			this.cur = db.SelectAll();
			
			mInflater = (LayoutInflater)getApplicationContext().getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
			itemSelection=new ArrayList<Boolean>();
			for(int i=0 ;i<this.getCount();i++ ) {
				itemSelection.add(i, false);
			}
			itemVisible=new ArrayList<Integer>();
			for(int i=0 ;i<this.getCount();i++ ) {
				itemVisible.add(i, View.GONE);
			}
		}
		@Override
		public int getCount() {
			// TODO Auto-generated method stub
			return cur.getCount();
		}

		@Override
		public Cursor getItem(int position) {
			
			cur.moveToPosition(position);
			return cur;
		}
		
		@Override
		public long getItemId(int position) {
			
			Cursor c = getItem(position);
			long id =(Long)(long)c.getInt(c.getColumnIndex(DBHelper.KEY_ID));
			return id;
		}
		
		public void setCheckedall(boolean check) {
			for(int i=0 ;i<itemSelection.size();i++ ) {
				itemSelection.set(i,check);
			}
			this.notifyDataSetChanged();
		}
		
		public void setVisibleChecks(int vis) {
			for(int i=0 ;i<itemVisible.size();i++ ) {
				itemVisible.set(i, vis);
			}
			this.notifyDataSetChanged();
		}
		
		private class ViewHolder {
	        
	        TextView lng;
	        TextView lat;
	        TextView date;
	        CheckBox ch;
	     	        
	    }
		
		@Override
		public View getView(final int position, View convertView, ViewGroup arg2) {
			  
			
			ViewHolder holder= null;
				
			if (convertView == null) {
					holder=	new ViewHolder();
		            convertView = mInflater.inflate(R.layout.itemhistory, null);
		 		    holder.lng = (TextView) convertView.findViewById(R.id.textLongitude);
		            holder.lat=(TextView) convertView.findViewById(R.id.textLatitude);
		            holder.date=(TextView) convertView.findViewById(R.id.textDate);
		            holder.ch=(CheckBox)convertView.findViewById(R.id.checkItems);
		            holder.ch.setOnCheckedChangeListener(new OnCheckedChangeListener() {
						
						@Override
						public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
							// TODO Auto-generated method stub
							itemSelection.set(position,isChecked);
							Log.d("Position",String.valueOf(position)+" "+String.valueOf(isChecked));
							
						}
					});
		            convertView.setTag(holder);
		        }
		        else 
		        {
		            holder = (ViewHolder) convertView.getTag();
		        }
				try
				{
				Cursor rowItem = getItem(position);
				
		        
		        holder.lng.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_LONGITUDE))+" ");
		        holder.lat.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_LATITUDE))+" ");
		        holder.date.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_DATE))+" ");
				holder.ch.setChecked(itemSelection.get(position));
				holder.ch.setVisibility(itemVisible.get(position));
				}catch(Exception ex){
					ex.printStackTrace();
				}
				
				return convertView;
			
		}
		
		
	}
Responder Con Cita
  #4  
Viejo 15/09/13, 12:34:05
Array

[xs_avatar]
rafaxplayer rafaxplayer no está en línea
Miembro del foro
 
Fecha de registro: jun 2013
Localización: en la barcelona media
Mensajes: 224
Modelo de smartphone: LG-E610
Tu operador: Orange
Bueno arreglado , al final el evento checkedchangued no estaba funcionando bien guardando los cambios , lo ha cambiado por clicklistener y declarado despues:

asi ha quedado el adapter:

Código:
public class HistoryAdapter extends BaseAdapter  {
		private LayoutInflater mInflater = null;
		private Cursor cur;
		private ArrayList<Boolean> itemSelection;
		private ArrayList<Integer> itemVisible;
		public HistoryAdapter(){
			db = new DBHelper(getApplicationContext(), DBHelper.TABLE_NAME, null, 1);
			this.cur = db.SelectAll();
			
			mInflater = (LayoutInflater)getApplicationContext().getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
			itemSelection=new ArrayList<Boolean>();
			for(int i=0 ;i<this.getCount();i++ ) {
				itemSelection.add(i, false);
			}
			itemVisible=new ArrayList<Integer>();
			for(int i=0 ;i<this.getCount();i++ ) {
				itemVisible.add(i, View.GONE);
			}
		}
		@Override
		public int getCount() {
			// TODO Auto-generated method stub
			return cur.getCount();
		}

		@Override
		public Cursor getItem(int position) {
			
			cur.moveToPosition(position);
			return cur;
		}
		
		@Override
		public long getItemId(int position) {
			
			Cursor c = getItem(position);
			long id =(Long)(long)c.getInt(c.getColumnIndex(DBHelper.KEY_ID));
			return id;
		}
		
		public void setCheckedall(boolean check) {
			for(int i=0 ;i<itemSelection.size();i++ ) {
				itemSelection.set(i,check);
			}
			this.notifyDataSetChanged();
		}
		
		public void setVisibleChecks(int vis) {
			for(int i=0 ;i<itemVisible.size();i++ ) {
				itemVisible.set(i, vis);
			}
			this.notifyDataSetChanged();
		}
		
		private class ViewHolder {
	        
	        TextView lng;
	        TextView lat;
	        TextView date;
	        CheckBox ch;
	     	        
	    }
		
		@Override
		public View getView(final int position, View convertView, ViewGroup arg2) {
			  
			
			ViewHolder holder= null;
				
			if (convertView == null) {
					holder=	new ViewHolder();
		            convertView = mInflater.inflate(R.layout.itemhistory, null);
		 		    holder.lng = (TextView) convertView.findViewById(R.id.textLongitude);
		            holder.lat=(TextView) convertView.findViewById(R.id.textLatitude);
		            holder.date=(TextView) convertView.findViewById(R.id.textDate);
		            holder.ch=(CheckBox)convertView.findViewById(R.id.checkItems);
		            
		            convertView.setTag(holder);
		        }
		        else 
		        {
		            holder = (ViewHolder) convertView.getTag();
		        }
				
				try
				{
				Cursor rowItem = getItem(position);
				
		        
		        holder.lng.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_LONGITUDE))+" ");
		        holder.lat.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_LATITUDE))+" ");
		        holder.date.setText(rowItem.getString(rowItem.getColumnIndex(DBHelper.KEY_DATE))+" ");
				holder.ch.setChecked(itemSelection.get(position));
				holder.ch.setOnClickListener(new OnClickListener() {

					@Override
					public void onClick(View v) {

						itemSelection.set(position, ((CheckBox) v).isChecked());

					}
				});
				holder.ch.setVisibility(itemVisible.get(position));
				//holder.ch.setTag(position);
				}catch(Exception ex){
					ex.printStackTrace();
				}
				
				return convertView;
			
		}
Responder Con Cita
Respuesta

Estás aquí
Regresar   Portal | Indice > Todo sobre Android > Programación y Desarrollo para Android



Hora actual: 07:41:39 (GMT +1)



User Alert System provided by Advanced User Tagging (Lite) - vBulletin Mods & Addons Copyright © 2026 DragonByte Technologies Ltd.

Contactar por correo / Contact by mail / 邮件联系 /