0

Could anybody explain me, how i can fix my problem:

I have custom ListViewenter image description here

Images changes by click on image, all works fine, but - when image (for example item10) was changed and then scroll down and again scroll up - image for item10 loses state (green image changes to red). The same problem with bottom images, which not in visible position on screen.

How i can save image state when works scroll?

Thx!

2

2 Answers 2

2

Ok, i don't know your code so i can't help you with a "more specific solution" but you can create an array of boolean

boolean[] status;

Every item have an id in the array.

In the getView() method check if status == true put green image, red if false.

It's how you can do it, if you post your code i can help you with a more efficent solution if possible. But it's the basic idea.

Ah, if you use a class to put items in the ListView you can save his state as a field in the class.

And this video helped me a lot to understand how Android works with ListView

Wow, ok your code is a bit messy around and i don't understand why you do somethings.. Anyway save the "yes|no" in the imagetag is not a great idea for me..

You can edit your "Product" class and add a field called "selected" something like:

class Product
{
    public boolean userSelectedIt;
}

Then edit your getView to something like this:

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    // используем созданные, но не используемые view
    View view = convertView;
    if (view == null) {
        view = lInflater.inflate(R.layout.item, parent, false);
    }

    Product p = getProduct(position);
    final int pos = position;
    final String name = p.name;
    final boolean selected = p.userSelectedIt;

    // заполняем View в пункте списка данными из класса продукт: наименование, картинка и тег(используется для детекта картинки)
    // и картинка
    ((TextView) view.findViewById(R.id.tvDescr)).setText(p.name);
    ((ImageView) view.findViewById(R.id.ivImage)).setImageResource(p.image);
    ((ImageView) view.findViewById(R.id.ivImage)).setTag(p.tag);

    iv = ((ImageView) view.findViewById(R.id.ivImage));

    String temp = (String)iv.getTag();      //Получаю инфу, какая картинка у текущего элемента

    //Блок для определения какую картинку добавить в массив
    if (selected)
        iarr.add(new ImgArray(iv,pos,name,"yes"));
    else
        iarr.add(new ImgArray(iv,pos,name,"no"));

    //Обработчик нажатия на картинку

    iv.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {

            // Здесь можно писать в базу, в name содержится имя продукта по которому кликнули
            //
            // Log.d(LOG_TAG,"PRODUCT --- " + name);
            Log.d(LOG_TAG, "NAME ACTIVITY --- " + title);

            //Получаю картинку, которая была нажата
            LinearLayout ll = (LinearLayout) view.getParent();
            ImageView iv = (ImageView) ll.getChildAt(0);

            //String bufferTag = (String) iv.getTag();        //Получаю данные, какая картинка была перед нажатием

            //Блок для определения, какая картинка пришла и на какую ее изменить
            selected = !selected;
            if (selected) {
                iv.setImageResource(R.drawable.no);
                iarr.set(pos,new ImgArray(iv,pos,name,"no"));       //Заменяется картинка в массиве картинок. Замена происходит по позиции

            }
            else {
                iv.setImageResource(R.drawable.yes);
                iarr.set(pos,new ImgArray(iv,pos,name,"yes"));
            }
        }
    });

    return view;
}

Or, if you don't want to add a field to Product class you can edit your Adapter to look like this:

public class BoxAdapter extends BaseAdapter {
Context ctx;
LayoutInflater lInflater;
ArrayList<Product> objects;
ArrayList<boolean> userSelected; // Here i added a ArrayList of booleans to remember the user chooise
String title;
public ImageView iv;
public int counter;
public ArrayList<ImgArray> iarr = new ArrayList<ImgArray>();
public ArrayList<ImgArray> startIarr = new ArrayList<ImgArray>();
final String LOG_TAG = "myLogs";


BoxAdapter(Context context, ArrayList<Product> products, String curTitle) {
    ctx = context;
    objects = products;
    lInflater = (LayoutInflater) ctx
            .getSystemService(Context.LAYOUT_INFLATER_SERVICE);

    //Получаю название Activity
    title = curTitle;
}

// кол-во элементов
@Override
public int getCount() {
    return objects.size();
}

// элемент по позиции
@Override
public Object getItem(int position) {
    return objects.get(position);
}

// id по позиции
@Override
public long getItemId(int position) {
    return position;
}

// пункт списка
@Override
public View getView(int position, View convertView, ViewGroup parent) {
    // используем созданные, но не используемые view
    View view = convertView;
    if (view == null) {
        view = lInflater.inflate(R.layout.item, parent, false);
    }

    Product p = getProduct(position);
    final int pos = position;
    final String name = p.name;
    final boolean selected = userSelected.get(position);

    // заполняем View в пункте списка данными из класса продукт: наименование, картинка и тег(используется для детекта картинки)
    // и картинка
    ((TextView) view.findViewById(R.id.tvDescr)).setText(p.name);
    ((ImageView) view.findViewById(R.id.ivImage)).setImageResource(p.image);
    ((ImageView) view.findViewById(R.id.ivImage)).setTag(p.tag);

    iv = ((ImageView) view.findViewById(R.id.ivImage));

    //Блок для определения какую картинку добавить в массив
    if (selected)
        iarr.add(new ImgArray(iv,pos,name,"yes"));
    else
        iarr.add(new ImgArray(iv,pos,name,"no"));

    //Обработчик нажатия на картинку

    iv.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {

            // Здесь можно писать в базу, в name содержится имя продукта по которому кликнули
            //
            // Log.d(LOG_TAG,"PRODUCT --- " + name);
            Log.d(LOG_TAG, "NAME ACTIVITY --- " + title);

            //Получаю картинку, которая была нажата
            LinearLayout ll = (LinearLayout) view.getParent();
            ImageView iv = (ImageView) ll.getChildAt(0);

            //String bufferTag = (String) iv.getTag();        //Получаю данные, какая картинка была перед нажатием

            //Блок для определения, какая картинка пришла и на какую ее изменить
            userSelected.set(position, !selected);
            if (!selected) {
                iv.setImageResource(R.drawable.no);
                iarr.set(pos,new ImgArray(iv,pos,name,"no"));       //Заменяется картинка в массиве картинок. Замена происходит по позиции

            }
            else {
                iv.setImageResource(R.drawable.yes);
                iarr.set(pos,new ImgArray(iv,pos,name,"yes"));
            }

        }
    });

    return view;
}


// товар по позиции
Product getProduct(int position) {
    return ((Product) getItem(position));
}


//Функция для возврата информации о количестве элементов в массиве картинок(не используется)
public Object getV (View v,int position) {
    ListView lv = (ListView) v.findViewById(R.id.lvView);

    //Object o = lv.getItemAtPosition(position);
    Object o = iarr.size();

    return o;
}


//Функция для возврата элемента картинок
public ArrayList iFunc(){
    return iarr;
}

//не используется
public ArrayList sIarr(){
    return startIarr;
}

//не используется
public int C (View v) {
    ListView lv = (ListView) v.findViewById(R.id.lvView);
    return lv.getCount();
}



}

(Yeah i know, the code looks horrible here due to indentation sorry.) This code should work, if not say and i try to fix it.

Sign up to request clarification or add additional context in comments.

3 Comments

This image check should be in ListView class?
Thx for example. Your code doesn't work properly, but i understood idea and i will work. Thank you!
I missed Varname = new ArrayList <Boolean>(); and change boolean to Boolean. Anyway i tried to let you understand the idea not the complete code at all (because you can do the same thing in different ways)
0

Fix for my problem

lvMain.setOnScrollListener(new AbsListView.OnScrollListener() {
            @Override
            public void onScrollStateChanged(AbsListView absListView, int i) {
                Log.d(LOG_TAG, "STATE CHANGED");

                saveImagesState();

            }

            @Override
            public void onScroll(AbsListView absListView, int i, int i2, int i3) {
                Log.d(LOG_TAG,"ONSCROLL");
            }
        });

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.