Остановить getView() от автоматического вызова

Я реализую расширяемый ListView. Каждый дочерний элемент имеет текстовое представление и текст редактирования.

Проблема в том, что в группе 10 элементов / строк. Я ввел данные в строки 1 и 2. Когда я прокручиваю вниз до строки 6 и 7. У них уже есть текст (строка 6 содержит данные строки 1, а строка 7 - данные строки 2).

Я понимаю, почему это радует. Это потому, что, когда я печатаю в строке 1, я могу видеть строку 1 - строку 5. Когда я прокручиваю вниз, чтобы просмотреть оставшиеся строки. getChildView () вызывается автоматически, чтобы показать мне оставшиеся строки и их данные, так как все editTexts имеют одинаковый идентификатор. Итак, Next View имеет те же данные, что и в предыдущем представлении.Подобная проблема здесь: метод getView() ArrayAdapter вызывается автоматически при загрузке, и при прокрутке просмотра спиская пытался:

  1. его решение, оно не работает.
  2. установка getChildCount() вручную: безуспешно

Вот мой ExpandableListAdapter.java:

package com.syapaa;


import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import android.content.Context;
import android.content.SharedPreferences;
import android.graphics.Typeface;
import android.text.Editable;
import android.text.TextUtils;
import android.text.TextWatcher;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

import static android.content.Context.MODE_PRIVATE;

public class ExpandableListAdapter extends BaseExpandableListAdapter {



    int j=1;
    int neww=0;
    EditText edt;
    private Context _context;
    private List<String> _listDataHeader; // header titles
    // child data in format of header title, child title
    private HashMap<String, List<String>> _listDataChild;






    public ExpandableListAdapter(Context context, List<String> listDataHeader,
                                 HashMap<String, List<String>> listChildData) {
        this._context = context;
        this._listDataHeader = listDataHeader;
        this._listDataChild = listChildData;

    }



    @Override
    public Object getChild(int groupPosition, int childPosititon) {
        return this._listDataChild.get(this._listDataHeader.get(groupPosition))
                .get(childPosititon);
    }

    @Override
    public long getChildId(int groupPosition, int childPosition) {
        return childPosition;
    }



    @Override
    public View getChildView(int groupPosition, final int childPosition,
                             boolean isLastChild, View convertView, ViewGroup parent) {



        //Don't change://///////////////////////////////-/////////////////////
        final String childText = (String) getChild(groupPosition, childPosition);

        if (convertView == null) {
            LayoutInflater infalInflater = (LayoutInflater) this._context
                    .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = infalInflater.inflate(R.layout.list_item, null);
        }
        TextView txtListChild = (TextView) convertView.findViewById(R.id.lblListItem);
        //////////////------------------------------------------------------------/////

        //For Sharing my ID(I am Group PG):
        SharedPreferences prefb = convertView.getContext().getSharedPreferences("my_prefb", MODE_PRIVATE);
        SharedPreferences.Editor editb = prefb.edit();
        editb.putInt("GR", groupPosition );
        editb.commit();




        if(childPosition==0){
            //Receiving 1857 of OnClick
            SharedPreferences phobjc = convertView.getContext().getSharedPreferences("my_prefd", 0);
            neww = phobjc.getInt("BRNDM", 0);
            phobjc.edit().clear().commit();
        }


        if(neww==1857){
            edt=convertView.findViewById(R.id.marks);
            String abc=edt.getText().toString();


            j=childPosition+1;
            //For Sharing data entered in list:
            SharedPreferences prefa = convertView.getContext().getSharedPreferences("my_prefa", MODE_PRIVATE);
            SharedPreferences.Editor edita = prefa.edit();
            edita.putString("PH"+j, abc );
            edita.commit();
            Toast.makeText(convertView.getContext(),"Sharing "+ abc+"with "+"PH"+j,Toast.LENGTH_SHORT).show();

            if(isLastChild==true){
                int tellmaxitems=childPosition+1;

                //Sharing No of Items in Group
                SharedPreferences prefd = convertView.getContext().getSharedPreferences("noofitems", MODE_PRIVATE);
                SharedPreferences.Editor editd = prefd.edit();
                editd.putInt("NoItems", tellmaxitems );
                editd.commit();
            }
        }

        txtListChild.setText(childText);
        return convertView;

    }





    @Override
    public int getChildrenCount(int groupPosition) {
        return this._listDataChild.get(this._listDataHeader.get(groupPosition)).size();

    }

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

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

    @Override
    public long getGroupId(int groupPosition) {
        return groupPosition;
    }

    @Override
    public View getGroupView(int groupPosition, boolean isExpanded,
                             View convertView, ViewGroup parent) {
        String headerTitle = (String) getGroup(groupPosition);
        if (convertView == null) {
            LayoutInflater infalInflater = (LayoutInflater) this._context
                    .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = infalInflater.inflate(R.layout.list_group, null);
        }

        TextView lblListHeader = (TextView) convertView
                .findViewById(R.id.lblListHeader);
        lblListHeader.setText(headerTitle);

        return convertView;
    }

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

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

}

Вот Tab1.Java, где я добавляю элементы в списки / строки:

package com.syapaa;

import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.CountDownTimer;
import android.support.v4.app.Fragment;
import android.os.Bundle;
import android.support.v4.widget.SwipeRefreshLayout;
import android.telephony.SmsManager;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import android.widget.ExpandableListView;


import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import static android.content.Context.MODE_PRIVATE;


public class Tab1 extends Fragment {
    int grtoShow=0;
    int prGroup=-1;

    String last="ls.txt";
    SwipeRefreshLayout rfrsh;
    ExpandableListAdapter listAdapter;
    ExpandableListView expListView;
    List<String> listDataHeader;
    HashMap<String, List<String>> listDataChild;
    Button btn;


    @Override
    public View onCreateView(LayoutInflater inflater,ViewGroup container,Bundle savedInstanceState) {
         final View v = inflater.inflate(R.layout.tab1, container, false);


        // get the listview
        expListView =  v.findViewById(R.id.lvExp);


        //Pull Down to Refresh ListView///////////////////////////////////////////////////////
        rfrsh=v.findViewById(R.id.refresh);
        rfrsh.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
            @Override
            public void onRefresh() {
                Intent intent = getActivity().getIntent();
                intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK
                        | Intent.FLAG_ACTIVITY_NO_ANIMATION);
                getActivity().overridePendingTransition(0, 0);
                getActivity().finish();
                getActivity().overridePendingTransition(0, 0);
                startActivity(intent);
                rfrsh.setRefreshing(false);
            }
        });
        ////-------Refresh Logic Ends here----------------------------------------/////////////



        ////////Expand Only One Group at a Time (collapse previously Expanded Gruop)///////////////
        expListView.setOnGroupExpandListener(new ExpandableListView.OnGroupExpandListener() {
            @Override
            public void onGroupExpand(int i) {
                new CountDownTimer(120, 1) {
                    public void onFinish() {
                        // When timer is finished
                        // Execute your code here
                        //Taking Group ID (which group was expanded last)
                        SharedPreferences phobjb = getContext().getSharedPreferences("my_prefb", 0);
                        final int i= phobjb.getInt("GR", 0);
                    }
                    public void onTick(long millisUntilFinished) {}
                }.start();
                if ((prGroup != -1) && (i != prGroup)) {
                    expListView.collapseGroup(prGroup);
                    InputMethodManager imm = (InputMethodManager)getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
                    try{imm.hideSoftInputFromWindow(v.getWindowToken(), 0);}
                    catch (Exception e){}
                }
                prGroup = i;
            }
        });
        /////////////-----------Only One Expand at a time Ends here-------------------------/////////////////////

        // preparing list data
        prepareListData();

        listAdapter = new ExpandableListAdapter(getContext(), listDataHeader, listDataChild);
        // setting list adapter
        expListView.setAdapter(listAdapter);


        //Send Button OnClick Starts /////////////////////////////////////////////////////////////////
        btn=v.findViewById(R.id.button);
        btn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {

                //Sharing Rndom to OnChildView
                SharedPreferences prefd = getContext().getSharedPreferences("my_prefd", MODE_PRIVATE);
                SharedPreferences.Editor editd = prefd.edit();
                editd.putInt("BRNDM", 1857 );
                editd.commit();

                //Taking Group ID (which group was expanded last)
                SharedPreferences phobjb = getContext().getSharedPreferences("my_prefb", 0);
                int grID = phobjb.getInt("GR", 0);

                expListView.collapseGroup(grID);
                expListView.expandGroup(grID);


                new CountDownTimer(1000, 1000) {
                    public void onFinish() {
                        // When timer is finished
                        // Execute your code here
                        //Receiving 1857 of OnClick
                        SharedPreferences phobjc = getContext().getSharedPreferences("noofitems", 0);
                        int j = phobjc.getInt("NoItems", 0);
                        phobjc.edit().clear().commit();

                        for(int i=1;i<=j;i++){
                            //Taking data entered in  ETs
                            SharedPreferences phobja = getContext().getSharedPreferences("my_prefa", 0);
                            String data = phobja.getString("PH"+i, "");
                            Toast.makeText(getContext(),"Recving "+data+"from PH"+i,Toast.LENGTH_SHORT).show();
                        }
                    }

                    public void onTick(long millisUntilFinished) {
                        // millisUntilFinished    The amount of time until finished.
                    }
                }.start();



            }
        });
        //-------On Click of button ends here----------------------////////////
        return v;
    }
    //////----------------OnCreate ends here-----------------------------////////////////





    private void prepareListData() {
        listDataHeader = new ArrayList<String>();
        listDataChild = new HashMap<String, List<String>>();


        if(readFile("filePG1.txt").equals(null)||readFile("filePG1.txt").equals("")){
            //pg.add("No Contacts Present");
        }
        else {
            listDataHeader.add("PG");
            List<String> pg = new ArrayList<String>();

            int j=1;
            int i = Integer.parseInt(readFile(last));

            //Start reading from 1 to "How many files are saved"/////////////////
            while (j <= i) {
                try {
                    FileInputStream fis = getContext().openFileInput("filePG"+ j + ".txt");

                    pg.add(readFile("filePG"+ j + ".txt"));
                    //Add items to listView by reading all saved files/Contacts/////////////

                    int size = fis.available();
                    byte[] buffer = new byte[size];
                    fis.read(buffer);
                    fis.close();
                } catch (Exception e) {
                    //If limit is reached , Break the Loop///////////////////////////
                    break;
                }
                j++;

            }

            listDataChild.put(listDataHeader.get(grtoShow), pg); // Header, Child data
            grtoShow++;


        }


        if(readFile("fileNur1.txt").equals(null)||readFile("fileNur1.txt").equals("")){
            //nur.add("No Contacts Present");
        }
        else {
            listDataHeader.add("Nursery");
            List<String> nur = new ArrayList<String>();

            int j=1;
            int i = Integer.parseInt(readFile(last));

            //Start reading from 1 to "How many files are saved"/////////////////
            while (j <= i) {
                try {
                    FileInputStream fis = getContext().openFileInput("fileNur"+ j + ".txt");
                    nur.add(readFile("fileNur"+ j + ".txt"));
                    //Add items to listView by reading all saved files/Contacts/////////////

                    int size = fis.available();
                    byte[] buffer = new byte[size];
                    fis.read(buffer);
                    fis.close();
                } catch (Exception e) {
                    //If limit is reached , Break the Loop///////////////////////////
                    break;
                }
                j++;

            }
            listDataChild.put(listDataHeader.get(grtoShow), nur);
            grtoShow++;






        }




        if(readFile("filePrep1.txt").equals(null)||readFile("filePrep1.txt").equals("")){
            //prep.add("No Contacts Present");
        }
        else {
            listDataHeader.add("Prep");
            List<String> prep = new ArrayList<String>();
            int j=1;
            int i = Integer.parseInt(readFile(last));

            //Start reading from 1 to "How many files are saved"/////////////////
            while (j <= i) {
                try {
                    FileInputStream fis = getContext().openFileInput("filePrep"+ j + ".txt");
                    prep.add(readFile("filePrep"+ j + ".txt"));
                    //Add items to listView by reading all saved files/Contacts/////////////

                    int size = fis.available();
                    byte[] buffer = new byte[size];
                    fis.read(buffer);
                    fis.close();
                } catch (Exception e) {
                    //If limit is reached , Break the Loop///////////////////////////
                    break;
                }
                j++;

            }
            listDataChild.put(listDataHeader.get(grtoShow), prep);
            grtoShow++;


        }


        if(readFile("fileOne1.txt").equals(null)||readFile("fileOne1.txt").equals("")){
            //one.add("No Contacts Present");
        }
        else {
            listDataHeader.add("One");
            List<String> one = new ArrayList<String>();


            int j=1;
            int i = Integer.parseInt(readFile(last));

            //Start reading from 1 to "How many files are saved"/////////////////
            while (j <= i) {
                try {
                    FileInputStream fis = getContext().openFileInput("fileOne"+ j + ".txt");
                    one.add(readFile("fileOne"+ j + ".txt"));
                    //Add items to listView by reading all saved files/Contacts/////////////

                    int size = fis.available();
                    byte[] buffer = new byte[size];
                    fis.read(buffer);
                    fis.close();
                } catch (Exception e) {
                    //If limit is reached , Break the Loop///////////////////////////
                    break;
                }
                j++;
            }

            listDataChild.put(listDataHeader.get(grtoShow), one);
            grtoShow++;

        }
        if(readFile("fileTwo1.txt").equals(null)||readFile("fileTwo1.txt").equals("")){
            //two.add("No Contacts Present");
        }
        else {
            listDataHeader.add("Two");
            List<String> two = new ArrayList<String>();

            int j=1;
            int i = Integer.parseInt(readFile(last));

            //Start reading from 1 to "How many files are saved"/////////////////
            while (j <= i) {
                try {
                    FileInputStream fis = getContext().openFileInput("fileTwo"+ j + ".txt");
                    two.add(readFile("fileTwo"+ j + ".txt"));
                    //Add items to listView by reading all saved files/Contacts/////////////

                    int size = fis.available();
                    byte[] buffer = new byte[size];
                    fis.read(buffer);
                    fis.close();
                } catch (Exception e) {
                    //If limit is reached , Break the Loop///////////////////////////
                    break;
                }
                j++;
            }
            listDataChild.put(listDataHeader.get(grtoShow), two);
            grtoShow++;

        }
        if(readFile("fileThree1.txt").equals(null)||readFile("fileThree1.txt").equals("")){
            //three.add("No Contacts Present");
        }
        else {

            listDataHeader.add("Three");
            List<String> three = new ArrayList<String>();

            int j=1;
            int i = Integer.parseInt(readFile(last));

            //Start reading from 1 to "How many files are saved"/////////////////
            while (j <= i) {
                try {
                    FileInputStream fis = getContext().openFileInput("fileThree"+ j + ".txt");
                    three.add(readFile("fileThree"+ j + ".txt"));
                    //Add items to listView by reading all saved files/Contacts/////////////

                    int size = fis.available();
                    byte[] buffer = new byte[size];
                    fis.read(buffer);
                    fis.close();
                } catch (Exception e) {
                    //If limit is reached , Break the Loop///////////////////////////
                    break;
                }
                j++;
            }
            listDataChild.put(listDataHeader.get(grtoShow), three);
            grtoShow++;

        }


    }



    public String readFile(String file){
        String text="";
        try {
            FileInputStream fis=getContext().openFileInput(file);
            int size=fis.available();
            byte[] buffer=new byte[size];
            fis.read(buffer);
            fis.close();
            text=new String(buffer);
        }
        catch (Exception e){
            e.printStackTrace();
        }
        return text;
    }

}

Итак, как я могу ограничить onChildView() для вызова только при расширении группы, а не при прокрутке / изменении View.

2 ответа

Решение

GetView() - это собственный метод Android, его нельзя переопределить. Единственный способ, которым вы пытаетесь достичь:

То, что вы пытаетесь сделать, конечно, возможно, но сложно:

  1. Добавить кнопку в каждый дочерний элемент
  2. Когда пользователь вводит дочерний элемент 0, он должен нажать кнопку этого дочернего элемента (при нажатии кнопки сохранить значение в массиве по индексу [childPosition]). Таким образом, Array[0] будет иметь текст Child 1, аналогичный для Next Children.

(Шаг 3 и далее являются необязательными)

  1. Если вам не нравится этот дизайн (поскольку пользователю нужно нажимать кнопку каждый раз, когда он вводит значение, см. Шаг 4)
  2. Установите видимость кнопки (которая была добавлена ​​в шаге 1) в невидимый
  3. Добавьте TextWatcher (TextChangedListener) для EditText в ChildItem (будет введено значение TextText> Сохранить его в массиве [] > Нажмите кнопку "Само по себе", как только пользователь покинет текущий EditText). Как:

    edt.addTextChangedListener(new TextWatcher() {
        @Override
        public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {}
    
        @Override
        public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {}
    @Override
    public void afterTextChanged(Editable editable) {
    
    if(edt.getText().toString()==""&&edt.getText().toString().equals(null)){
    }
    else {
        edt.setOnFocusChangeListener(new View.OnFocusChangeListener() {
            @Override
            public void onFocusChange(View v, boolean hasFocus) {
                if (!hasFocus)//Perform Click when edt loses Focus {
                    btn.callOnClick();
                }
            }
        });
    }
    }});
    

    Теперь нажатие кнопки будет выглядеть так:

    btn.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
            if(edt.getText().toString().equals("")){
    
            }
            else {
            Toast.makeText(view.getContext(),"Entered: "+edt.getText().toString(),Toast.LENGTH_SHORT).show();
            myStringArray[childPosition]=edt.getText().toString();
            edt.setText("");
            }
        }
    });
    

Проблема в том, что ваше представление перерабатывается, это означает, что Android использует то же представление, что прокручивается за пределы экрана, и повторно использует его, чтобы нарисовать следующее, на которое вы прокручиваете, так как на этом вы написали какой-то текст, используя тот же самый представление будет иметь тот же текст.

Решение очень простое.

Ваши модели должны отражать данные, которые пользователь вводит в представление. И в любое время вы должны знать, какой текст есть у каждого ребенка, возможно, используйте TextWatcher,

И для каждого ребенка вы просто делаете следующее.

String text = getTextForThisChild();
if (!TextUtils.isEmpty(text) {
    yourEditText.setText(text); // Sets correct text for view
} else {
    yourEditText.setText(null); // Clears text of recycled view
}

Вы должны отслеживать изменения текста

edt.addTextChangedListener(new TextWatcher() {
        @Override
        public void beforeTextChanged(final CharSequence charSequence, final int i, final int i1, final int i2) {}

        @Override
        public void onTextChanged(final CharSequence charSequence, final int i, final int i1, final int i2) {
          yourModelList.get(childPosition).setText(charSequence);  // This is dummy, you should get the correct model for this child
        }

        @Override
        public void afterTextChanged(final Editable editable) {}
    });

Тогда в той же модели получил yourModelList.get(childPosition) это где вы получаете text тот, который вы проверяете, если он пуст или нет.

Пожалуйста, дайте мне знать, если это все еще не ясно

Другие вопросы по тегам