17

I added a "pull to refresh" to my listView, i also wanted to add an empty view when the list is empty - Now i got this error. How can i make this work? if im positioning a view outside of the swipeRefresh and then add it as the emptyView it will work. So how do i so it with an outer xml file .. ?

The xml code:

        <android.support.v4.widget.SwipeRefreshLayout
        android:id="@+id/swipeRefreshLayout"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_alignParentLeft="true"
        android:layout_alignParentTop="true" >


        <ListView
            android:id="@android:id/list"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_alignParentLeft="true"
            android:layout_alignParentTop="true"
            android:clipToPadding="false"
            android:paddingBottom="@dimen/inbox_vertical_margin" ></ListView>


</android.support.v4.widget.SwipeRefreshLayout>

onCreateView:

View rootView = inflater.inflate(R.layout.fragment_inbox, container,
        false);

View empty = inflater.inflate(R.layout.empty_message_list, container,
        false);
ListView mListView = (ListView) rootView
        .findViewById(android.R.id.list);
((ViewGroup) mListView.getParent()).addView(empty);
TextView textViewToChange = (TextView) empty
        .findViewById(R.id.welcomeMessage);

textViewToChange.setText("YO "
        + ParseUser.getCurrentUser().getString(
                ParseConstants.KEY_PRESENTING_USERNAME)
        + "!  bad news.. :(");
mListView.setEmptyView(empty);

mSwipeRefreshLayout = (SwipeRefreshLayout) rootView
        .findViewById(R.id.swipeRefreshLayout);
mSwipeRefreshLayout.setOnRefreshListener(mOnRefreshListener);
mSwipeRefreshLayout.setColorScheme(R.color.swipeRefresh1,
        R.color.swipeRefresh2, R.color.swipeRefresh3,
        R.color.swipeRefresh4);

return rootView;
Yevgeni
  • 1,533
  • 17
  • 32
  • i was facing the same issue and found that though you are using only one listview which is one child only and that is fine but you might be hiding it's visibility, that is what i was making mistake at my end – Syed Raza Mehdi Apr 30 '15 at 07:54

2 Answers2

29

SwipeRefreshLayout should be the parent in the XML file.

You can use a FrameLayout as the child of SwipeRefreshLayout. The ListView and TextView (or any other empty state view) can be child views of the FrameLayout.

LordRaydenMK
  • 13,074
  • 5
  • 50
  • 56
  • Is there anyway to set SwipeRefreshLayout inside another layout as child? – Vinil Chandran Jan 07 '16 at 11:10
  • 2
    @VinilChandran sure. You can use it eg. inside `CoordinatorLayout`. The only limitation is `SwipeRefreshLayout` can have only one child, the view that is being refreshed. – LordRaydenMK Jan 07 '16 at 11:28
  • 2
    Don't you end up with the bug when the ListView can't scroll up if you do it like this? I have experienced it and read about it. http://innodroid.com/blog/post/recycler-empty-swipe-refresh – Varvara Kalinina Apr 25 '17 at 15:21
  • ok, but if we also have a list that is in a framelayout: scrolling will interfere with swipe to refresh - what to do in that case? – Kamen Dobrev Jun 09 '23 at 13:22
0

I needed to implement the same "pull to refresh" feature in my Apps. An alternative (and quite simple) way to implement the 'empty view' is to use the ListView's header or footer views.

First you create an "empty_view.xml" containing the empty view layout. Then within the onCreate() method of your hosting activity, do something like:

View headerView = LayoutInflater.from(this).inflate(R.layout.empty_view, myListView, false);
myListView.addHeaderView(headerView);
myListView.setAdapter(adapter);

// populate your ListView here
// ......

// now check the number of items and remove the empty view if needed
if (number_of_items > 1) {
  myListView.removeHeaderView(headerView);
}
adapter.notifyDataSetChanged();

In the above code myListView is the ListView object and adapter is its adapter.

This is useful in other situations too. For example, assume the list data is read from a web service and is slow to load, then one can put a ProgressBar is a view and set it as the ListView's header view so that user has some visual indication.

macelee
  • 321
  • 2
  • 7