Generated binding classes (產生綁定類別)

前言


Data Binding 會產生綁定類別(binding class),用來存取佈局變數(layout's variable)和視圖(View)。

以下描述了如何建立及客製化綁定類別。

綁定類別將佈局變量與佈局中的視圖連結起來,綁定類別的名稱和 package 可以自行定義。所有的綁定類別都繼承自 ViewDataBinding 類別。

每個 layout file 都會有一個對應的綁定類別。預設,類別的名稱會根據佈局文件的名稱,將其轉換為 Pascal 大小寫並添加 Binding。

若 layout 的名稱為 activity_main.xml,則對應的綁定類別為 ActivityMainBinding。

此類別包含佈局屬性(如user variable)到佈局視圖的所有綁定內容,並知道如何為綁定表達式指定值。

 

Create a binding object


在對佈局進行填充之後,應該快速的創建綁定對象(binding object),以確保在綁定到佈局中具有表達式的視圖之前不會修改視圖層次結構。

將對象綁定到佈局的最常用方法是使用綁定類別上的靜態方法。

可以透過使用綁定類別的 inflate 方法來擴展視圖層次結構並將對象綁定到該層次結構。如下
@Override  
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    MyLayoutBinding binding = MyLayoutBinding.inflate(getLayoutInflater());
}

 

除了 LayoutInflater 對象之外,還有一個替換的 inflate 方法,它接受 ViewGroup對象,如下
MyLayoutBinding binding = MyLayoutBinding.inflate(getLayoutInflater(), viewGroup, false);

如果使用不同的機制對佈局進行填充,則可以單獨綁定,如下
MyLayoutBinding binding = MyLayoutBinding.bind(viewRoot);

有時候沒辦法事先知道綁定類型。在這種情況下,可以使用 DataBindingUtil 類創建綁定,如下
View rootView = LayoutInflater.from(this).inflate(layoutId, parent, attachToParent);  
ViewDataBinding binding = DataBindingUtil.bind(viewRoot);

若開發者是在 Fragment, ListView, RecyclerView adapter 中使用 data binding item

則可以使用綁定類別或 DataBindingUtil 的 inflate方法。如下
ListItemBinding binding = ListItemBinding.inflate(layoutInflater, viewGroup, false);  
// or
ListItemBinding binding = DataBindingUtil.inflate(layoutInflater, R.layout.list_item, viewGroup, false);

 

具有 ID 的視圖


Data Binding 會在綁定類別中建立一個不可變的欄位,該欄位會對應於 layout 檔案中每個具有 id 的 View。如下 Data Binding 會建立 firstName 和 lastName 欄位
<layout xmlns:android="http://schemas.android.com/apk/res/android">  
<data>
<variable name="user" type="com.example.User"/>
</data>
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{user.firstName}"
android:id="@+id/firstName"/>
<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{user.lastName}"
android:id="@+id/lastName"/>
</LinearLayout>
</layout>


Data Binding 會在單次傳遞中從視圖層次結構中提取具有 ID 的視圖。這個機制比為佈局中的每個視圖調用 findViewById 方法都要快。ID 對於 Data Binding 並不是必要的,但仍有些實體需要從 code 存取視圖。

 

Variables


Data Binding 會為每個宣告在 layout 中的變數建立存取方法(setter and getter)。如下,將會為 user, image, note 變數建立存取方法。
<data>  
<import type="android.graphics.drawable.Drawable"/>
<variable name="user" type="com.example.User"/>
<variable name="image" type="Drawable"/>
<variable name="note" type="String"/>
</data>


ViewStubs


與普通視圖不同,ViewStub 物件從一個不可見的視圖開始。

當它們被顯示或被明確告知要填充時,它們會通過填充另一個佈局來替換自己的佈局。

由於 ViewStub 基本上會從視圖層次結構中消失,因此綁定對像的視圖也必須消失以允許垃圾回收聲明。

因為視圖是不可變的,所以 ViewStubProxy 對象取代了生成綁定類中的 ViewStub,使您可以在 ViewStub 存在時訪問它,並在 ViewStub 填充時訪問視圖層次結構

當填充另一個佈局時,必須為該佈局建立綁定。因此 ViewStubProxy 必須監聽  ViewStub,並在需要時建立綁定。在同一時間內只能有一個監聽器存在,ViewStubProxy 予許開發者設定 OnInflateListener,該監聽器將在建立綁定之後被呼叫。

 

Immediate Binding


當變量或可觀察對象發生變化時,綁定將會被排程更改在下一幀之前。但是,有時必須立即執行綁定。要強制執行,可以使用 executePendingBindings 方法。

 

 

進階綁定


動態變數


動態變數適用於無法得知特定的綁定類別的時候。如當一個 RecyclerView.Adapter 對非特定的佈局進行操作時並不知道特定的綁定類別,但它還是必須在呼叫 onBindViewHolder 方法時指定綁定値。

在下面的範例中,RecyclerView 綁定的所有佈局都有個 item 變數。而 BindingHolder 物件具有 getBinding 方法,該方法可以回傳 ViewDataBinding 基本類別。
public void onBindViewHolder(BindingHolder holder, int position) {  
final T item = mItems.get(position);
holder.getBinding().setVariable(BR.item, item);
holder.getBinding().executePendingBindings();
}

Data Binding 在 module package 會產生一個名為 BR 的類別,該類別包含用於數據綁定的資源的 ID。在上一個範例中 BR.item 是自動產生的。

 

背景執行緒


開發者可以在背景執行緒中更改數據模型(data model),只要它不是集合即可。Data Binding 會判斷每個變數/屬性以避免任何並發問題。

 

客製化綁定類別名稱


在預設情況下綁定類別的名稱是根據其相關佈局名稱而來,主要規則是將佈局名稱的底線去除並讓首字改為大寫,最後再加上 Binding,而綁定類別的位置會放置於 module package 的 databinding 資料夾下。 如佈局名稱為 contact_item.xml,其綁定類別為 ContactItemBinding。若 module package 為 com.example.my.app 則綁定類別的位置為 com.example.my.app.databinding。

可以透過 data 元素的 class 屬性來改變綁定類別的名稱或位置。

如下面的內容將會產生名為 ContactItem 綁定類別。
<data class="ContactItem">  

</data>

也可以使用完整名稱來指定綁定類別的位置。如下

將產生 ContactItem 綁定類別,其位置為 com.example
<data class="com.example.ContactItem">  

</data>

 

Orignal From: Generated binding classes (產生綁定類別)

0 意見:

張貼留言

Twitter Delicious Facebook Digg Stumbleupon Favorites More

 
Design by Free WordPress Themes | Bloggerized by Lasantha - Premium Blogger Themes | Affiliate Network Reviews