42

I want to use one of my layouts multiple times in the same view using include. Let's say I have a custom.xml including some TextViews.

custom.xml:

 <LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:padding="10dp"
    android:orientation="vertical" >

    <TextView
        android:id="@+id/text1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />

    <TextView
        android:id="@+id/text2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />
</LinearLayout>

I have included this layout multiple times in parent.xml:

 <LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <include layout="@layout/custom"
        android:id="@+id/layout1"/>

    <include layout="@layout/custom"
        android:id="@+id/layout2"/>
</LinearLayout>

Now I want to bind my data models to this layout, but the problem is that I don't know how to bind two different data models to layout1 and layout2 since both of them are refrenced from one layout which is custom.xml. As far as I know I can add this tag in my xml layout:

    <data>
       <variable name="user" type="com.myproject.model.User"/>
   </data>

But I need to bind two different data models to custom.xml.

My question is how to have an included layout multiple times in one view and passing different data to them using Data Binding? something like passing data to the layout but not statically binding a model to an xml.

I also found this question which is exactly had the same problem But since Data Binding is released in newer versions of android I am seeking a way to solve the same issue using Data Binding. Here is the part of that question that I have quoted for clarification:

For instance, I have a carefully crafted layout that I want to display three times in my view. Every of those instances would need different values. Since the include is basically a take that XML and paste it here, I'd need something more powerful.

Community
  • 1
  • 1
Milad Faridnia
  • 9,113
  • 13
  • 65
  • 78
  • If the layouts are same, and only the data is changing, why dont you consider to using a custom recycleView ? – Alex Chengalan Oct 05 '16 at 06:51
  • because I want to pass two different data models for example one is User and another is Address but both models are using the same layout to show their data – Milad Faridnia Oct 05 '16 at 06:54
  • @MiladFaridnia hey Gentleman can u help me with given link question comment? https://stackoverflow.com/questions/35554796/rotate-marker-and-move-animation-on-map-like-uber-android/39569076 – Kevan Aghera Apr 06 '18 at 07:14

4 Answers4

63

You can pass that from parent.xml

<include layout="@layout/custom"
    android:id="@+id/layout1"
    app:user="@{object of user1`}"/>

<include layout="@layout/custom"
    android:id="@+id/layout2"
    app:user="@{object of user2`}"/>

Here you need to pass User object from parent.xml

Make sure you have <data> in custom.xml

<data>
   <variable name="user" type="com.myproject.model.User"/>
</data>

Here is detailed answer related to this, refer it

Community
  • 1
  • 1
Ravi
  • 34,851
  • 21
  • 122
  • 183
18

We know how to use the POJO name and its type on the XML which we are using in setContentView() as a parent view. We should focus on the include tag if we are including any layouts from resource as follows:

<?xml version="1.0" encoding="utf-8"?>

<layout xmlns:bind="http://schemas.android.com/apk/res-auto">

    <data>

        <variable
            name="user"
            type="exapmpe.model.User" />
    </data>

    <android.support.design.widget.CoordinatorLayout
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <android.support.design.widget.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/AppTheme.AppBarOverlay">

            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:popupTheme="@style/AppTheme.PopupOverlay" />

        </android.support.design.widget.AppBarLayout>

        <include
            layout="@layout/content_main"
            bind:user="@{user}" />

    </android.support.design.widget.CoordinatorLayout>

</layout>

Here we've use the bind attribute to pass the object to show the detailed info on the content screen. Please make sure the object name should be same in both places like bind:user="@{user}. The content_main.xml should look as follows:

<?xml version="1.0" encoding="utf-8"?>

<layout>

    <data>

        <variable
            name="user"
            type="exapmpe.model.User" />
    </data>

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:id="@+id/content_main" >

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="@{user.firstName + user.lastName}" />

    </RelativeLayout>

</layout>
fawaad
  • 341
  • 6
  • 12
Deva
  • 2,386
  • 1
  • 16
  • 16
2

The problem is that the included layout isn't being thought of as a data-bound layout, take a look here to undertstand how to solve it

Community
  • 1
  • 1
Lior
  • 832
  • 6
  • 6
0

1> In the Main layout screen where you use include tag added xmlns:bind="http://schemas.android.com/apk/res-auto" This code is under the layout tag. For your reference check the screenshot.

point 1

reference screenshort

2> Now under your include tag add bind:includeLayoutViewModel="@{viewModel}" (In this case add your ViewModel name which you declare)For more check out the screenshot

For point 2

reference screenshot

3> Now in your included layout screen call ViewModel here for reference check the below screenshot (In screenshots there is TestViewModel behalf of this you mention your view model which is you declare in your main layout screen)

For point 3 screenshot

Milad Faridnia
  • 9,113
  • 13
  • 65
  • 78