2016-05-17 8 views
1

Я реализовал ExpandableListAdapter, и он отлично работает. За исключением того, что при возобновлении действия дочерние узлы повторяются. Я не знаю, как это исправить, я искал в Интернете для этого и не нашел ничего полезного.ExpandableListView, повторяющий дочерние узлы

Я смягчил проблему, добавив некоторые ошибки != null. Таким образом, избегайте вставки и создания новых данных, если они не нужны. Но это не устранило проблему.

Вот CustomAdapter

public class ContatoAdapter extends BaseExpandableListAdapter { 

private final Activity context; 
private final Map<String, List<Contato>> contatosCollection; 
private final List<String> area; 

public ContatoAdapter(Activity context, List<String> area, Map<String, List<Contato>> contatosCollection) { 
    this.context = context; 
    this.contatosCollection = contatosCollection; 
    this.area = area; 
} 

@Override 
public int getGroupCount() { 
    return area.size() ; 
} 

@Override 
public int getChildrenCount(int groupPosition) { 
    return this.contatosCollection.get(area.get(groupPosition)).size(); 
} 


@Override 
public Object getGroup(int groupPosition) { 
    return this.area.get(groupPosition); 
} 

@Override 
public Object getChild(int groupPosition, int childPosition) { 
    return this.contatosCollection.get(this.area.get(groupPosition)).get(childPosition); 
} 

@Override 
public long getGroupId(int groupPosition) { 
    return this.area.get(groupPosition).hashCode(); 
} 

@Override 
public long getChildId(int groupPosition, int childPosition) { 
    return this.contatosCollection.get(this.area.get(groupPosition)).get(childPosition).hashCode(); 
} 

@Override 
public boolean hasStableIds() { 
    return false; 
} 

@Override 
public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { 
    String s = (String) getGroup(groupPosition); 
    final LayoutInflater gInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
    if (convertView == null){ 
     convertView = gInflater.inflate(R.layout.group_item, parent, false); 
    } 

    final TextView item = (TextView) convertView.findViewById(R.id.list_header); 

    item.setText(s); 
    item.setTypeface(null, Typeface.BOLD); 

    return convertView; 
} 

@Override 
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) { 
    final Contato contato = (Contato) getChild(groupPosition, childPosition); 
    final LayoutInflater cInflater = this.context.getLayoutInflater(); 

    if (convertView == null){ 
     convertView = cInflater.inflate(R.layout.list_item, parent, false); 
    } 

    TextView item = (TextView) convertView.findViewById(R.id.list_item_nome); 
    ImageView ver = (ImageView) convertView.findViewById(R.id.list_item_ver); 

    ver.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      Intent intent = new Intent(context.getApplicationContext(), DetalheActivity.class); 
      intent.putExtra("contato", contato); 
      context.startActivity(intent); 
     } 
    }); 

    item.setText(contato.getNome()); 

    return convertView; 
} 

@Override 
public boolean isChildSelectable(int groupPosition, int childPosition) { 
    return true; 
} 
} 

Вот деятельность, которая имеет listView с адаптером:

public class MedicosActivity extends AppCompatActivity { 
private ExpandableListView listView; 
private ArrayList<Contato> contatos; 
private ArrayList<String> areas; 
private HashMap<String, List<Contato>> contatosCollection; 
private ContatoAdapter adapter; 

String jsonString = ""; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_medicos); 

    setTitle("Médicos | Etc"); 

    init(); 

    if (listView == null) 
     listView = (ExpandableListView) findViewById(android.R.id.list); 
    adapter = new ContatoAdapter(this,areas,contatosCollection); 
    listView.setAdapter(adapter); 

    listView.setOnChildClickListener(new ExpandableListView.OnChildClickListener() { 
     @Override 
     public boolean onChildClick(ExpandableListView parent, View v, int groupPosition, int childPosition, long id) { 
      Contato selected = (Contato) adapter.getChild(groupPosition,childPosition); 
      Toast.makeText(MedicosActivity.this, selected.getNome() , Toast.LENGTH_SHORT).show(); 

      return true; 
     } 
    }); 
} 

private void init() { 
    if (jsonString.isEmpty()) 
     jsonString = JsonUtil.loadJSON(MedicosActivity.this, "data.json"); 
    if (contatosCollection == null) 
     contatos = JsonUtil.parseJSON(jsonString); 
    if (areas == null){ 
     areas = new ArrayList<>(); 
     createGroupList(); 
    } 
    if (contatosCollection == null){ 
     contatosCollection = new HashMap<>(); 
     createCollection(); 
    } 
} 

private void createGroupList() { 
    for(Contato c : contatos){ 
     if (!areas.contains(c.getArea())){ 
      areas.add(c.getArea()); 
     } 
    } 
} 

private void createCollection() { 
    for (Contato c : contatos){ 
     List<Contato> ctg = contatosCollection.get(c.getArea()); 
     if (ctg == null){ 
      ctg = new ArrayList<>(); 
      contatosCollection.put(c.getArea(), ctg); 
     } 
     ctg.add(c); 
    } 
} 
} 

Добавление JSON Parser класс, который вызвал ошибку:

private static ArrayList<Contato> contatoList = new ArrayList<>(); 
public static ArrayList<Contato> parseJSON(String jsonString){ 
    try { 
     JSONObject jsonObject = new JSONObject(jsonString); 
     JSONArray jsonArray = jsonObject.optJSONArray("medicos"); 

     for (int i = 0; i < jsonArray.length(); i++){ 
      JSONObject medicoObj = jsonArray.getJSONObject(i); 
      JSONObject end = medicoObj.getJSONObject("endereco"); 
       JSONArray coord = end.getJSONArray("coord"); 
       LatLng latLng = new LatLng(coord.getDouble(0), coord.getDouble(1)); 
       JSONArray telefones = medicoObj.getJSONArray("telefone"); 
       String[] tels = new String[telefones.length()]; 
       for (int j = 0; i < telefones.length(); i++) { 
        tels[i] = telefones.get(i).toString(); 
       } 
       Contato c = new Contato(
         medicoObj.getString("area") 
         , medicoObj.getString("nome") 
         , end.getString("rua") 
         , Integer.parseInt(end.getString("numero")) 
         , end.getString("complemento") 
         , tels 
         , latLng 
       ); 
       contatoList.add(c); 
     } 

     return contatoList; 
    } catch (JSONException e) { 
     e.printStackTrace(); 
    } 
    return null; 
} 
+0

Вы уверены, что данные передаются в адаптер не имеет дублированные значения? –

+0

ДА .. спасибо, ты заставил меня отлаживать именно это. Я хочу сходить с ума, думая, что проблема была в моем адаптере и не смотрела на значения массива. На самом деле проблема заключалась в том, что ArrayList , который получал дублирование при получении данных от JSON. Изменен мой код парсера, чтобы проверить дубликаты, и он работает нормально. Выведет ответ. –

ответ

1

Спасибо до Жидкий пингвин комментарий я смог обнаружить проблему. Поскольку я изучал класс Adapter для проблем, я не замечал повторяющихся данных, исходящих из класса JSON parser.

Он не проверял дубликаты данных при получении данных из JSON в массив. Здесь приходит неподвижная анализатор code с необходимыми проверками:

private static ArrayList<Contato> contatoList = new ArrayList<>(); 
public static ArrayList<Contato> parseJSON(String jsonString){ 
    try { 
     JSONObject jsonObject = new JSONObject(jsonString); 

     JSONArray jsonArray = jsonObject.optJSONArray("medicos"); 

      for (int i = 0; i < jsonArray.length(); i++) { 
       JSONObject medicoObj = jsonArray.getJSONObject(i); 
       if (medicoObj.length() != contatoList.size()) { 
        JSONObject end = medicoObj.getJSONObject("endereco"); 
        JSONArray coord = end.getJSONArray("coord"); 
        LatLng latLng = new LatLng(coord.getDouble(0), coord.getDouble(1)); 
        JSONArray telefones = medicoObj.getJSONArray("telefone"); 
        String[] tels = new String[telefones.length()]; 
        for (int j = 0; i < telefones.length(); i++) { 
         tels[i] = telefones.get(i).toString(); 
        } 
        Contato c = new Contato(
          medicoObj.getString("area") 
          , medicoObj.getString("nome") 
          , end.getString("rua") 
          , Integer.parseInt(end.getString("numero")) 
          , end.getString("complemento") 
          , tels 
          , latLng 
        ); 
        if (!contatoList.contains(c)) 
         contatoList.add(c); 
       } 
      } 

     return contatoList; 
    } catch (JSONException e) { 
     e.printStackTrace(); 
    } 
    return null; 
} 
Смежные вопросы