vlc for android中的数据绑定(Data Binding)

数据绑定(Data Binding)在布局文件中实现数据绑定申明,使数据的变化引起视图的自动更新,减少逻辑代码,从而在Android中方便地实现MVVM的开发模式。

vlc for android中用到了数据绑定(databinding),下面看一个例子:

一、布局文件

list_item.xml中布局是这样的:

<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android">
    <data>
        <import type="org.videolan.vlc.media.MediaWrapper"/>
        <import type="android.view.View"/>
        <variable
            name="holder"
            type="org.videolan.vlc.gui.HistoryAdapter.ViewHolder"/>
        <variable
            name="media"
            type="MediaWrapper"/>
        <variable
            name="position"
            type="int"/>
    </data>
    <LinearLayout
        android:id="@+id/layout_item"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_gravity="center_vertical"
        android:orientation="horizontal"
        android:clickable="true"
        android:onClick="@{holder.onClick}">

        <ImageView
            android:id="@+id/icon"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:src="@{media.type == MediaWrapper.TYPE_VIDEO ? @drawable/ic_browser_video_normal : @drawable/ic_browser_audio_normal}" />

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical" >

            <TextView
                android:id="@+id/title"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginLeft="5dip"
                android:layout_marginRight="5dip"
                android:layout_marginTop="5dip"
                android:text="@{media.title}"
                android:layout_gravity="center_vertical"
                android:fontFamily="sans-serif-light"
                android:textColor="?attr/list_title"
                android:textSize="16sp"
                android:singleLine="true"
                android:scrollHorizontally="true"/>

            <TextView
                android:id="@+id/subtitle"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginBottom="5dip"
                android:layout_marginLeft="5dip"
                android:layout_marginRight="5dip"
                android:text="@{media.artist}"
                android:fontFamily="sans-serif-light"
                android:textColor="?attr/list_subtitle"
                android:singleLine="true"
                android:ellipsize="start"
                android:visibility="@{media.artist == null ? View.GONE : View.VISIBLE}"/>
        </LinearLayout>

    </LinearLayout>
</layout>

我们可以看到支持 Data Binding的布局文件和以前的布局文件不一样,它的跟节点不再是一个ViewGroup,而是layout,并且多了一个data节点。在上面这个例子中定义了3个变量:holder,media,position。


二、POJO文件:
构建工具gradle会自动构建一个中间文件ListItemBinding.java,该文件存在于vlc-android/build/intermediates/classes/vanillaARMv7/debug/org/videolan/vlc/databinding这个目录下,具体代码如下:

package org.videolan.vlc.databinding;
import org.videolan.vlc.R;
import org.videolan.vlc.BR;
import android.view.View;
public class ListItemBinding extends android.databinding.ViewDataBinding  {

    private static final android.databinding.ViewDataBinding.IncludedLayouts sIncludes;
    private static final android.util.SparseIntArray sViewsWithIds;
    static {
        sIncludes = null;
        sViewsWithIds = null;
    }
    // views
    public final android.widget.ImageView icon;
    public final android.widget.LinearLayout layoutItem;
    public final android.widget.TextView subtitle;
    public final android.widget.TextView title;
    // variables
    private org.videolan.vlc.gui.HistoryAdapter.ViewHolder mHolder;
    private org.videolan.vlc.media.MediaWrapper mMedia;
    // values
    // listeners
    private OnClickListenerImpl mAndroidViewViewOnCl;
    // Inverse Binding Event Handlers

    public ListItemBinding(android.databinding.DataBindingComponent bindingComponent, View root) {
        super(bindingComponent, root, 0);
        final Object[] bindings = mapBindings(bindingComponent, root, 4, sIncludes, sViewsWithIds);
        this.icon = (android.widget.ImageView) bindings[1];
        this.icon.setTag(null);
        this.layoutItem = (android.widget.LinearLayout) bindings[0];
        this.subtitle = (android.widget.TextView) bindings[3];
        this.subtitle.setTag(null);
        this.title = (android.widget.TextView) bindings[2];
        this.title.setTag(null);
        setRootTag(root);
        // listeners
        invalidateAll();
    }

    @Override
    public void invalidateAll() {
        synchronized(this) {
                mDirtyFlags = 0x8L;
        }
        requestRebind();
    }

    @Override
    public boolean hasPendingBindings() {
        synchronized(this) {
            if (mDirtyFlags != 0) {
                return true;
            }
        }
        return false;
    }

    public boolean setVariable(int variableId, Object variable) {
        switch(variableId) {
            case BR.holder :
                setHolder((org.videolan.vlc.gui.HistoryAdapter.ViewHolder) variable);
                return true;
            case BR.media :
                setMedia((org.videolan.vlc.media.MediaWrapper) variable);
                return true;
            case BR.position :
                return true;
        }
        return false;
    }

    public void setPosition(int position) {
        // not used, ignore
    }
    public int getPosition() {
        return 0;
    }
    public void setHolder(org.videolan.vlc.gui.HistoryAdapter.ViewHolder holder) {
        this.mHolder = holder;
        synchronized(this) {
            mDirtyFlags |= 0x1L;
        }
        super.requestRebind();
    }
    public org.videolan.vlc.gui.HistoryAdapter.ViewHolder getHolder() {
        return mHolder;
    }
    public void setMedia(org.videolan.vlc.media.MediaWrapper media) {
        this.mMedia = media;
        synchronized(this) {
            mDirtyFlags |= 0x2L;
        }
        super.requestRebind();
    }
    public org.videolan.vlc.media.MediaWrapper getMedia() {
        return mMedia;
    }

    @Override
    protected boolean onFieldChange(int localFieldId, Object object, int fieldId) {
        switch (localFieldId) {
        }
        return false;
    }

    ......   
}

这个java文件有点像java bean文件,3个变量的getter和setter方法。

三、绑定数据

怎么使用的呢?可以看vlc-android\src\org\videolan\vlc\gui\HistoryAdapter.java,有如下代码:

ListItemBinding binding;

public ViewHolder(View itemView) {
    super(itemView);
    binding = DataBindingUtil.bind(itemView);
}

@Override
public void onBindViewHolder(ViewHolder holder, int position) {
    final MediaWrapper media = mMediaList.get(position);
    holder.binding.setMedia(media);
    holder.binding.setHolder(holder);
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值