1

I am trying to use PulltoRefresh and EndlessAdapter, the first time that the app run, the list loads very well, but when it gets in the end to load more data, it crash.

Library EndLessAdapter: https://github.com/commonsguy/cwac-endless

Library PulltoRefresh: https://github.com/chrisbanes/Android-PullToRefresh

It was working without PullToRefresh.

First time that app run, it calls:

  1. getPendingView
  2. MyAsyncTask
  3. return hasmoredata
  4. Call postOnExecute - listener
  5. Call OnItemsReady
  6. Set DemoAdapter.notydatasetchanged

When it get the end of list, then it calls:

  1. getPendingView
  2. MyAsyncTask
  3. return hasmoredata
  4. Gives IndexOutofBoundException

StackTrace:

01-28 11:12:15.273: E/AndroidRuntime(12735): FATAL EXCEPTION: main
01-28 11:12:15.273: E/AndroidRuntime(12735): java.lang.IndexOutOfBoundsException: Invalid index 1, size is 1
01-28 11:12:15.273: E/AndroidRuntime(12735):    at java.util.ArrayList.throwIndexOutOfBoundsException(ArrayList.java:257)
01-28 11:12:15.273: E/AndroidRuntime(12735):    at java.util.ArrayList.get(ArrayList.java:311)
01-28 11:12:15.273: E/AndroidRuntime(12735):    at android.widget.HeaderViewListAdapter.getView(HeaderViewListAdapter.java:225)
01-28 11:12:15.273: E/AndroidRuntime(12735):    at android.widget.AbsListView.obtainView(AbsListView.java:1592)
01-28 11:12:15.273: E/AndroidRuntime(12735):    at android.widget.ListView.makeAndAddView(ListView.java:1782)
01-28 11:12:15.273: E/AndroidRuntime(12735):    at android.widget.ListView.fillDown(ListView.java:705)

Inside PullToRefreshListinViewPager sample:

public View instantiateItem(ViewGroup container, int position) {
    PullToRefreshListView plv = null;
    Context context = container.getContext();

    plv = (PullToRefreshListView) LayoutInflater.from(context).inflate(
                        R.layout.layout_listview_in_viewpager, container, false);
    endlessList = new ArrayList<HashMap<String, String>>(); 
    demoAdapter = new DemoAdapter(context, endlessList); 
    demoAdapter.setRunInBackground(false);
    plv.setAdapter(demoAdapter);

    plv.setOnRefreshListener(BaseSampleActivity.this);

    // Now just add ListView to ViewPager and return it
    container.addView(plv, LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
    return plv;
}

EndLessAdapter:

private class DemoAdapter extends EndlessAdapter implements IItemsReadyListener{

      private RotateAnimation rotate=null;
      private View pendingView=null;
      private ArrayList<HashMap<String, String>> data;
      private List<HashMap<String, String>> mOriginalNames;
      private boolean hasMoreData=true;
      private Context mContext;

      DemoAdapter(Context context, ArrayList<HashMap<String, String>> d) {

        super(new LazyAdapter(context, d));
        this.data = d;
        this.mContext = context;
        rotate=new RotateAnimation(0f, 360f, Animation.RELATIVE_TO_SELF,
                  0.5f, Animation.RELATIVE_TO_SELF,
                  0.5f);

        rotate.setRepeatMode(Animation.RESTART);
        rotate.setRepeatCount(Animation.INFINITE);
      }

      @Override
      protected View getPendingView(ViewGroup parent) {
          View row = LayoutInflater.from(mContext).inflate(R.layout.row, null);

              View child=row.findViewById(android.R.id.text1);

              child.setVisibility(View.GONE);

              child=row.findViewById(R.id.throbber);
              child.setVisibility(View.VISIBLE);
              child.startAnimation(rotate);
            return(row);
      }



      @Override
      protected boolean cacheInBackground() {
        if(isNetworkOnline() == true){
          new MyAsyncTask(this, data.size()).execute();
        }
        return hasMoreData;
      }

      public void onItemsReady(ArrayList<HashMap<String, String>> data) {
          endlessList.addAll(data);
          demoAdapter.onDataReady();  // Tell the EndlessAdapter to remove it's pending
                                  // view and call notifyDataSetChanged()
          hasMoreData = endlessList.isEmpty();
        }

      @Override
      protected void appendCachedData() {
        if (getWrappedAdapter().getCount()<75) {
          @SuppressWarnings("unchecked")
          LazyAdapter a=(LazyAdapter)getWrappedAdapter();
          for (int i = 0; i < data.size(); i++) {
              a.add(data.get(i));
          }
        }
      }
    }

AsyncTask:

private static class MyAsyncTask extends AsyncTask<Void,Void,ArrayList<HashMap<String, String>>>{
        IItemsReadyListener listener;

        int startPoint;

        public MyAsyncTask(IItemsReadyListener listener, int startPoint) {
            // TODO Auto-generated constructor stub
            this.listener = listener;
            this.startPoint = startPoint;
        }

        @Override
        protected ArrayList<HashMap<String, String>> doInBackground(Void... params) {

            XMLParser parser = new XMLParser();
            String xml = parser.getXmlFromUrl(URL); // getting XML from URL
            Document doc = parser.getDomElement(xml); // getting DOM element

            NodeList nl = doc.getElementsByTagName(KEY_SONG);
            // looping through all song nodes <song>
            for (int i = 0; i < 10; i++) {
                // creating new HashMap
                HashMap<String, String> map = new HashMap<String, String>();
                Element e = (Element) nl.item(i);
                // adding each child node to HashMap key => value
                map.put(KEY_ID, parser.getValue(e, KEY_ID));
                map.put(KEY_TITLE, parser.getValue(e, KEY_TITLE));
                map.put(KEY_ARTIST, parser.getValue(e, KEY_ARTIST));
                map.put(KEY_DURATION, parser.getValue(e, KEY_DURATION));
                map.put(KEY_THUMB_URL, parser.getValue(e, KEY_THUMB_URL));
                // adding HashList to ArrayList
                endlessList.add(map);
            }
            return (endlessList);
        }




        @Override
        protected void onPostExecute(ArrayList<HashMap<String, String>> result)
        {
            listener.onItemsReady(endlessList);
             // Getting adapter by passing xml data ArrayList
            if (demoAdapter != null) 
            {
                demoAdapter.notifyDataSetChanged();
            }

        }
}

UPDATE:

I just change:

      @Override
      protected boolean cacheInBackground() throws Exception {
        if(isNetworkOnline() == true){
          new MyAsyncTask(this).execute();
        }
        if (getWrappedAdapter().getCount()<75) {
            return(true);
          }
        throw new Exception("Gadzooks!");

        }

Now it loads more content, but after it loads 3 times and get into final, it throws the Exception Gadzooks and after it shows me the same IndexOutofBoundException.

I just know that every time that cacheinBackground return false, then it crash.

Michael Celey
  • 12,645
  • 6
  • 57
  • 62
Marckaraujo
  • 7,422
  • 11
  • 59
  • 97
  • Temporarily remove the `EndlessAdapter`, using just the PullToRefresh stuff. Based on your exception, I suspect that your problem will remain. – CommonsWare Jan 28 '13 at 14:02
  • It works well without EndlessAdapter, in debug mode I dont see listener.onItemsReady(endlessList); got called when need to load more data – Marckaraujo Jan 28 '13 at 14:09
  • I just added the step by step when programs execute. – Marckaraujo Jan 28 '13 at 14:20
  • 1
    Then perhaps `EndlessAdapter` is not compatible with the pull-to-refresh code. I am not a fan of pull-to-refresh (in general -- I haven't looked at this specific implementation), so this is not an itch that I wish to invest much time in scratching. You are welcome to submit a pull request or an issue on the project to point out changes that I can make to have `EndlessAdapter` work better with this pull-to-refresh code, but off the top of my head I have no idea how `EndlessAdapter` itself can be causing your specific crash. – CommonsWare Jan 28 '13 at 14:25
  • Ok, I just submited an Issue on the project, I hope you can make it works with PulltoRefresh. Thanks – Marckaraujo Jan 28 '13 at 14:37
  • As I noted in my comment, if ***you*** find a solution and wish to have me integrate it into the baseline code, submit a pull request or open an issue with the changes. – CommonsWare Jan 28 '13 at 14:40
  • Oh, sorry, I am not too expert yet in Android to make this thing done, but I could try and then I edit the issue opened. – Marckaraujo Jan 28 '13 at 14:48
  • @CommonsWare, Could you see my Update, maybe you can understand better. – Marckaraujo Jan 28 '13 at 19:26
  • That simply means that your list has 75 or more entries in it. – CommonsWare Jan 28 '13 at 19:29
  • I want to integrate both, please let me know if the issue is resolved or I have to look into something :-( – AZ_ Feb 20 '14 at 11:35

0 Answers0