Android ListView with arrows using ScrollListener

  Recently I got a task to make a gallery with three vertical rows with each row containing four images layed horizontally one to each other.

  On the top and at the bottom of that listview i would have arrows, which should be greyed out if you have reached the top or the bottom of the list view. So you can either press the arrows or scroll using the view.

  Initially to make that I was thinking for the GridView element for android. It didn’t work out because the OnScrollListener was not firing with the correct values. For example I had 3 rows and when you scroll to the bottom of the gridview you could still see the 3 rows (a very little part of the top one) so it was always saying that there are 3 visible rows.

  As a workaround I used a ListView with an adapter of four images. So basically using the ScrollListener I posted below i could detect if the top or bottom of the ListView are reached.

  Check the code:

package com.example.test



import android.content.Context;

import android.util.AttributeSet;

import android.widget.AbsListView;

import android.widget.ListView;



/**

 * Created by georgi_mirchev on 14-9-8.

 */

public class ScrollListView extends ListView implements AbsListView.OnScrollListener {

    private OnScrollListener mListener;

    /**

     * Scroll position offset value to trigger earlier bottom reached events.

     */

    private int mOffset = 3;



    public ScrollListView(Context context, AttributeSet attrs, int defStyle) {

        super(context, attrs, defStyle);

        defineScrolling();

    }


    public ScrollListView(Context context, AttributeSet attrs) {

        super(context, attrs);

        defineScrolling();

    }


    public ScrollListView(Context context) {

        super(context);

        defineScrolling();

    }


    /**

     * Defines scrolling behaviour by subscribing a scroll listener.

     */

    private void defineScrolling() {

        this.setOnScrollListener(this);

    }


    /**

     * Removes internal scroll listener.

     */

    public void reset() {

        this.setScrollingListener(null);

    }

    // Listeners

    @Override

    public void onScrollStateChanged(AbsListView view, int scrollState) {

    }



    @Override

    public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount,
        int totalItemCount) {

        if(getAdapter() == null || mListener == null) {

            return;

        }

        if (getLastVisiblePosition() == getAdapter().getCount() - 1

            && getChildAt(getChildCount() - 1).getBottom() == getHeight()) {

                mListener.onBottomReached();

        } else if(getChildAt(0).getTop() == 0) {

            mListener.onTopReached();

        } else {

            mListener.onScrollMoving();

        }

    }





    // Getters & Setters



    public OnScrollListener getOnBottomReachedListener() {

        return mListener;

    }



    public void setScrollingListener(OnScrollListener scrollListener) {

        this.mListener = scrollListener;

    }



    public int getOffset() {

        return mOffset;

    }



    public void setOffset(int offset) {

        mOffset = offset;

    }





    /**

     * Event listener.

     */

    public interface OnScrollListener {

        public void onBottomReached();

        public void onTopReached();

        public void onScrollMoving();

    }

}

You may also like...