2 Recycler Views Within a Linear Layout - android

I'm having issues with the UI not being properly bound with the recycler view or at least not what I intend to happen. The following image is the two recycler views beside one another. Everything looks fine, but when I run the app, the children within the recycler views extend off-screen. The second image shows that.

If you are using one adapter, you can basically use GridLayoutManager for that. So, you can have 2 columns on your recycler view.
To do that with Kotlin code, just add below functionality to your recycler view reference in your fragment or activity.
recyclerView.apply {
layoutManager = GridLayoutManager(this, 2)
}
Also, there is another way to do that in XML. You can use, app:layoutManager and app:spanCount in your recycler view.
<androidx.recyclerview.widget.RecyclerView
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layoutManager="androidx.recyclerview.widget.GridLayoutManager"
app:spanCount="2" />

Related

Recyclerview inside NestedScrollView - Scroll to bottom

I have a RecyclerView inside a NestedScrollView:
<android.support.v4.widget.NestedScrollView
android:layout_width="match_parent"
android:layout_height="#dimen/_100sdp">
<android.support.v7.widget.RecyclerView
android:id="#+id/recycler_view_chat"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:minHeight="#dimen/_100sdp"
android:layout_marginLeft="#dimen/_30sdp"
android:layout_marginRight="#dimen/_30sdp"
android:background="#color/bright_grey"
></android.support.v7.widget.RecyclerView>
</android.support.v4.widget.NestedScrollView>
My RecyclerView is being filled with items in onCreate()
On a device you would see the first item of the RecyclerView on the very top und would have to scroll down the NestedScrollView in order to see the last item.
Since my items are chat message sorted by the time sent I need the NestedScrollView to be scrolled all the way down so users would see the latest chat message first without having to scroll in the first place.
Any ideas on this?
Given that your RecyclerView is the only child of your NestedScrollView, you would be better off removing the NestedScrollView altogether, and instead applying the fixed height to the RecyclerView. Something like this:
<android.support.v7.widget.RecyclerView
android:id="#+id/recycler_view_chat"
android:layout_width="match_parent"
android:layout_height="#dimen/_100sdp"
android:layout_marginLeft="#dimen/_30sdp"
android:layout_marginRight="#dimen/_30sdp"
android:background="#color/bright_grey" />
Doing this allows you to have the RecyclerView itself manage scrolling, rather than the parent scroll view. And that allows you to leverage a property of LinearLayoutManager to achieve what you want.
Reverse layout -- setting this will "invert" your list; the first item in your adapter will appear at the bottom of the list, and the default scroll position of the RecyclerView will be to scroll all the way to the bottom.
https://developer.android.com/reference/android/support/v7/widget/LinearLayoutManager.html#setReverseLayout(boolean)
LinearLayoutManager lm = new LinearLayoutManager(this);
lm.setReverseLayout(true);
If you have the same issue and want to keep the NestedScrollView.
It will work like this.
Handler(Looper.getMainLooper()).postDelayed({
binding.nestedScrollView.smoothScrollTo(
0,
binding.recyclerview.measuredHeight,
500
)
// binding.nestedScrollView.scrollTo(0, binding.recyclerview.measuredHeight)
// binding.nestedScrollView.smoothScrollTo(0, binding.recyclerview.measuredHeight)
}, 50L)
For me, it didn't work without delay.

Two List View inside scrollview

I want to create multiple list view inside ScrollView in Android. I have created the two list view inside ScrollView. In first List View each row contains a single text upto 5 rows will be presented. Whereas, in second list view each row will contains multiple paragraph text, ie, text very long . In my case I am unable to scroll the second list to view fully.
Is any other way available to handle this scenario ?
Its Work in My RecyclerView try this:
<android.support.v4.widget.NestedScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fillViewport="true"
app:layout_behavior="#string/appbar_scrolling_view_behavior">
<android.support.v7.widget.RecyclerView
android:id="#+id/rv_recycler_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_behavior="#string/appbar_scrolling_view_behavior"/>
</android.support.v4.widget.NestedScrollView>
You need to disable nested scrolling programatically. It doesn't seem to work correctly if done in xml.
recyclerView.setNestedScrollingEnabled(false);
Don't use the listview inside the scroll view, the listview is already scrollable . Using a ListView to make it not scroll is extremely expensive and goes against the whole purpose of ListView. You should NOT do this. Just use a LinearLayout instead.

Recyclerview binds all views at the same time

I have a vertical recyclerview (with a GridLayoutManager) inside another recyclerview (with LinearLayoutManager). The problem I am facing right now is that, the inner recyclerview (with GridLayoutManager) binds all of it's items at the same time, even the views that are not on the screen at the moment (onBindViewHolder() gets called for all of its items).
To give you more information, in my layout file, I put height of my recycler view as wrap_content.
I think the problem is, since there are 2 nested vertically recyclerviews, when the parent RV wants to measure its children and the children is another RV, in onMeasure() it computes the size needed for the entire RV, not just the portion that it wants to bind on the screen.
Any idea how to solve this?
Here is the layout file for my outer recyclerview:
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.v7.widget.RecyclerView
android:id="#+id/component_list"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</FrameLayout>
And here is the code for my inner recyclerview:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/container"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingTop="#dimen/gutter"
android:paddingBottom="#dimen/gutter">
<TextView
android:id="#+id/title_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginBottom="#dimen/gutter"
android:textSize="30sp"
android:textColor="#android:color/white"
android:fontFamily="sans-serif-thin"/>
<android.support.v7.widget.RecyclerView
android:id="#+id/my_slider"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
</LinearLayout>
P.S.: I'm using this adapter delegate for my outer recyclerview:
https://github.com/sockeqwe/AdapterDelegates
I think nested recyclerviews are a very bad idea. When i try to scroll, which recyclerview has to respond the the scolling, the parrent or child.
That is why I think you are looking for the ExpandableListView? That's limited to only two levels of listings, but that sounds like it would work for your needs). It also solves the soling issue.
It would look something like this:
EDIT: even nested ExpandableListViews are possible:
EDIT: check this lib for horizontal scroling
This is a known bug.
You should not put a RecyclerView inside another RecyclerView because RecyclerView gives its children infinite space. Hence the inner RecyclerView keeps measuring till the dataset is exhausted. Try setting setAutoMeasureEnabled(false) to false on layout manager or you can solve this problem by using a wrapper adapter instead of inner recycler view.
The first thing you need to know is that, when you nest scrolling layouts, the inner ones will get infinity allowed height, effectively making them wrap_content. There is in fact a relatively easy way to fix this problem.
Say I had two nested RecyclerViews such as these, in this case vertically oriented.
<RecyclerView
android:layout_height="match_parent"
android:layout_width="match_parent"
android:orientation="vertical>
<View .../>
<!-- other stuff -->
<RecyclerView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"/>
</RecyclerView>
The inner recyclerView here will bind all of it's children immediately every time because, from it's position, your screen will have infinite height.
The solution is to set the height of your inner recyclerview to some static value, not wrap_content or match parent, as either of those will simply fill up the outer recyclerview with one view that will all be bound at once due to it's large height. If you make the height of the inner recyclerview the same as the display's height, you should see your problem go away.
Here is an implementation that will not bind all children at once:
<RecyclerView
android:layout_height="match_parent"
android:layout_width="match_parent"
android:orientation="vertical>
<View .../>
<!-- other stuff -->
<RecyclerView
android:layout_width="match_parent"
android:layout_height="#dimen/screen_height"
android:orientation="vertical"/>
</RecyclerView>
Note the layout_height of the inner RecyclerView is now a fixed value pulled from the dimensions file. You yourself will have to come up with a reasonable value to put there.
Side Note: In order to make all of this work and for scrolling to work properly, you may have to play around with the parameter: NestedScrollingEnabled in your RecyclerViews - there are several known bugs relating to this that you may need to work around.
i.e.: innerRecyclerView.setHasFixedSize(true); and innerRecyclerView.setNestedScrollingEnabled(false).
so what happens here when you place a scrollview(no fixed size because of wrap content) inside another scrollview(again no fixed size because of wrap content),both nested scroll view fails to render.
So there is two solutions--
1- Either you will have to think of alternative solution for nested scrollviews
2- You can give outside recyclerview cell fixed height so that inside recycler view can get some fixed layout to render itself.
I could solve my issue by using only one Recyclerview, where it has a grid layout, and based on the component items i'm adding into it, i change the spancount for that. Basically instead of adding the inner recyclerview, i add the items that were supposed to go to the inner recyclerview, to the outer recyclerview.

Add RecyclerView body

Can I use RecyclerView as a parent element for other views declared in XML?
<android.support.v7.widget.RecyclerView ... >
<TextView ... />
<ImageView ... />
</android.support.v7.widget.RecyclerView>
Something like this. I need this in order to get my collapsing toolbar working with main content on my activity.
You have to use a RecyclerView.Adapter with RecyclerView.
But items in RecyclerView.Adapter can have different viewType just like ListView.
With this feature you can achieve something like HeaderView in RecyclerView and FooterView in RecyclerView, and make these views scroll with your items.
No, You can't add any child view inside Recycler View. See the example https://github.com/javatechig/Android-RecyclerView-Example.
Create separate .xml file (e.g. single_recycler_view_row.xml)
and use it to build layout for single RecyclerView item.
Then you need to create an adapter and pass single_recycler_view_row.xml as a parameter.
To make sure that your RecyclerView works well with CollapsingToolbarLayout add
app:layout_behavior="#string/appbar_scrolling_view_behavior" />
attribute to RecyclerView.

Two recycler view in same layout as in flipboard app

I want to use a RecyclerView(list like) below another RecyclerView(Grid like) as in flipboard
I tried two RecyclerView inside ScrollView with wrap content but nothing is showing.
I can able to see two views if it is placed in linear layout and equal weight is added to it. But that does not look like this app View.
This is my layout
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fillViewport="true"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<android.support.v7.widget.RecyclerView
android:id="#+id/parent_category_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:minWidth="#dimen/default_small_padding"
android:gravity="center"
android:visibility="visible"/>
<android.support.v7.widget.RecyclerView
android:id="#+id/category_grid"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:columnWidth="150dp"
android:gravity="center"
android:visibility="visible"/>
</LinearLayout>
There's actually a really simple way to achieve the desired layout with just one RecyclerView!
The key is using a GridLayoutManager and its SpanSizeLookup.
First of all define your GridLayoutManager like this:
GridLayoutManager layoutManager = new GridLayoutManager(context, spanCount);
where spanCount is the maximum amount of spans/columns you want to have. In your case, spanCount should be 2;
Now you need a way to tell this layoutManager how many spans an item should span.
A simple way would be to use a viewtype/ViewHolder for items that should span just one column and another one for items that span the whole width.
Let's assume you define the viewtype for grid-items as VIEWTYPE_GRID_ITEM and the viewtype for standard listitems as VIEWTYPE_LIST_ITEM.
You can then use these viewtypes to tell the layoutManager when to use just one span:
layoutManager.setSpanSizeLookup(new SpanSizeLookup() {
#Override
public int getSpanSize(int position){
return adapter.getItemViewType(position) == VIEWTYPE_GRID_ITEM ? 1 : spanCount;
}
});
Finally, set the layoutManager to your RecyclerView:
recyclerView.setLayoutManager(layoutManager);
And that's it!
I don't think that they use two ListViews (or ListView + GridView).
I think they use a ListView ( the one in the bottom) and they add a custom Header to this list (the one in the top), which look like a GridView.
Or if they use a Recyclerview, they can achieve this by using a different layout in the adapter for the first item.
PS: it's not recommended to use two scrollable view inside each other (like Recyclerview inside ScrollView).
In android we are advise to use only one scrollable view at time , if you want to use one scrollable view inside other one refer below links.
1)Android list view inside a scroll view
2) https://stackoverflow.com/questions/6210895/listview-inside-scrollview-is-not-scrolling-on-android

Categories

Resources