Search code examples
androidlistviewandroid-listviewandroid-custom-view

How to change color of listView item depending on position


How to change color of listView item depending on position? I can't solve this problem about 4 days. Maybe someone could help me.

I have customView class:

public class CustomView extends View  {

    private String[] hoursList = getResources().getStringArray(R.array.hours); ;
    private String[] minutesList = getResources().getStringArray(R.array.minutes);;
    private String[] dayOfTimeList = getResources().getStringArray(R.array.timeOfDay);
    private ListView listView;
    private HourAdapter hourAdapter;
    private MinuteAdapter minuteAdapter;
    private DayOfTimeAdapter dayOfTimeAdapter;
    public static int middlePosition;



     public CustomView(Context context) {
            super(context);
        }
    
        public CustomView(Context context, ViewGroup viewGroup) {
            super(context);
            inflate(context, R.layout.custom_test, viewGroup);
    
   
            listView = viewGroup.findViewById(R.id.hours_list);
            hourAdapter = new HourAdapter(context, hoursList);
            listView.setAdapter(hourAdapter);
    
            listView.setOnScrollListener(new AbsListView.OnScrollListener() {
    
                                             @Override
                                             public void onScrollStateChanged(AbsListView view, int scrollState) {
                                             }
    
                                             @Override
                                             public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {
                                              middlePosition = firstVisibleItem+1;
    
                                             }
                                         }
            );

    
        }
    }

and adapter class:

 public class HourAdapter extends BaseAdapter {
        private LayoutInflater lInflater;
        private String[] hoursValueList;
    
        public HourAdapter(Context context, String[] hoursValueList{
            lInflater = LayoutInflater.from(context);
            this.hoursValueList = hoursValueList;
        }

        @Override
        public View getView(int position, View convertView,ViewGroup parent) {
            View view = convertView;
          if (view == null) {
                view = lInflater.inflate(R.layout.row, parent, false);
            }
    
            TextView textHours = view.findViewById(R.id.textRow);
            textHours.setText(hoursValueList[position]);
            
            if (position == CustomView.middlePosition) {
              view.setBackgroundResource(R.drawable.selected_color);
            }
    
            return view;
        }
    }

What I need: when any element is in the middle position it has another color. 

But with code which I have now, it doesn't work. Every 2nd element is colored, but I need that any element which is in the middle position to be colored

enter image description here


Solution

  • Try the code below:

    CustomAdapter.java:

    public class CustomAdapter extends BaseAdapter {
    private LayoutInflater lInflater;
    private String[] valueList;
    
    public CustomAdapter(Context context, String[] valueList) {
        lInflater = LayoutInflater.from(context);
        this.valueList = valueList;
    }
    
    @Override
    public int getCount() {
        return valueList.length;
    }
    
    @Override
    public Object getItem(int position) {
        return valueList[position];
    }
    
    @Override
    public long getItemId(int position) {
        return position;
    }
    
    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        View view = convertView;
        if (view == null) {
            view = lInflater.inflate(R.layout.row, parent, false);
        }
        TextView text = view.findViewById(R.id.textRow);
        text.setText(valueList[position]);
        return view;
    }
    }
    

    CustomView.java:

    public class CustomView extends View {
    
    private String[] hoursList;
    private String[] minutesList;
    private String[] dayOfTimeList;
    private ListView hoursListView;
    private ListView minutesListView;
    private ListView dayOfTimeListView;
    private CustomAdapter hoursAdapter;
    private CustomAdapter minutesAdapter;
    private CustomAdapter dayOfTimeAdapter;
    
    AbsListView.OnScrollListener scrollListener = new AbsListView.OnScrollListener() {
        @Override
        public void onScrollStateChanged(AbsListView view, int scrollState) {
            if (scrollState == SCROLL_STATE_IDLE) {
                View firstView = view.getChildAt(0);
                int offset = view.getTop() - firstView.getTop();
                if (offset > (firstView.getHeight() / 2)) {
                    view.smoothScrollToPosition(view.getLastVisiblePosition());
                } else {
                    view.smoothScrollToPosition(view.getFirstVisiblePosition());
                }
            }
        }
    
        @Override
        public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {
            for (int i = 0; i < view.getChildCount(); i++) {
                View childView = view.getChildAt(i);
                if (i == 1) childView.setBackgroundColor(Color.BLUE); else childView.setBackgroundColor(Color.WHITE);
            }
        }
    };
    
    public CustomView(Context context) {
        super(context);
    }
    
    public CustomView(Context context, ViewGroup viewGroup) {
        super(context);
        inflate(context, R.layout.custom_test, viewGroup);
    
        hoursList = new String[26];
        hoursList[0] = " ";
        hoursList[25] = " ";
        for (int i = 1; i < hoursList.length - 1; i++) hoursList[i] = String.valueOf(i);
        minutesList = new String[62];
        minutesList[0] = " ";
        minutesList[61] = " ";
        for (int i = 1; i < minutesList.length - 1; i++) minutesList[i] = String.valueOf(i);
        dayOfTimeList = new String[4];
        dayOfTimeList[0] = " ";
        dayOfTimeList[1] = "AM";
        dayOfTimeList[2] = "PM";
        dayOfTimeList[3] = " ";
    
        hoursListView = viewGroup.findViewById(R.id.hours_list);
        hoursAdapter = new CustomAdapter(context, hoursList);
        hoursListView.setAdapter(hoursAdapter);
        minutesListView = viewGroup.findViewById(R.id.minutes_list);
        minutesAdapter = new CustomAdapter(context, minutesList);
        minutesListView.setAdapter(minutesAdapter);
        dayOfTimeListView = viewGroup.findViewById(R.id.dayOfTime_list);
        dayOfTimeAdapter = new CustomAdapter(context, dayOfTimeList);
        dayOfTimeListView.setAdapter(dayOfTimeAdapter);
    
        hoursListView.setOnScrollListener(scrollListener);
        minutesListView.setOnScrollListener(scrollListener);
        dayOfTimeListView.setOnScrollListener(scrollListener);
    }
    }
    

    To color the 2nd element, the color of other elements need reset. Please note that, if 3 rows is displayed initially, then there may be 4 rows (2 partial displayed and 2 completely displayed) during/after scroll. The 2nd element may be off from the middle position.