android studio 30天学习笔记-day 15-databinding 双向绑定

昨天了解如何使用databinding的单向绑定,把data放到view里,那反过来当view发生变化,data也能跟着改变呢?
这时就会用到了databinding的双向绑定。

example

当EditText在进行输入时TextView也会跟着显示EditText正在输入的内容

<TextView
     android:layout_width="wrap_content"
     android:layout_height="wrap_content"
     android:text="@{dataItem.name}"
     android:textSize="20sp"/>
<EditText
     android:layout_width="200dp"
     android:layout_height="wrap_content"
     android:text="@={dataItem.name}"
     android:textSize="20sp"/>

跟之前databinding的赋值一样,只是EditText的text赋值会变成@={dataItem.name}(在@{}中间加个等号),当EditText的text一改变,那麽TextView的text也会及时改变,这是一个简单的双向绑定。

使用InverseBindingAdapter

实作:将seekbar随意调动,TextView会显示其数字。

@BindingAdapter(value = {"progressNow"})
    public static void setProgressNow(SeekBar seekBar,String progressNum){
        int value = 0;
        try {
            value = Integer.parseInt(progressNum);
        } catch (NumberFormatException e) {

        }
        seekBar.setProgress(value);
    }

自定义属性app:progressNow,将SeekBar与viewModel做双向绑定,当app:progressNow发生改变时要如何get app:progressNow的值,这时可以用InverseBindingAdapter去达成。

//@InverseBindingAdapter(attribute = "attribute_name",event="")event属性:双向绑定时对view的变化发出通知。

 @InverseBindingAdapter(attribute = "progressNow")
    public static String getProgressNow(SeekBar seekBar){
        return ""+seekBar.getProgress();
    }

1.@InverseBindingAdapter的属性必须跟BindingAdapter自定义的属性一样
2.可以看到@InverseBindingAdapter只配置了一个(attribute = "progressNow"),而event没有配置,那麽会使用Default:将event的属性值为"{属姓名}+AttrChanged" (EX:progressNowAttrChanged)。

@BindingAdapter(value = {"onProgressChanged","progressNowAttrChanged"},requireAll = false)
    public static void setProgressNowAttrChanged(SeekBar seekBar,final SeekBar.OnSeekBarChangeListener listener,final InverseBindingListener attrChange){//注解中属性的顺序与方法中的参数顺序要保持一致,也就是说属性的`onProgressChanged`会对应到`SeekBar.OnSeekBarChangeListener listener`,而`progressNowAttrChanged`对应`InverseBindingListener attrChange`,
        
        if (attrChange ==null){
            seekBar.setOnSeekBarChangeListener(listener);
        }else{
            seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
                //当seekbar的值改变时,InverseBindingListener会进行 attrChange.onChange()。

                    attrChange.onChange();
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {

                }
            });
        }
    }

设置MODEL

public class DataItem2 {
    public final ObservableField<String> progressNum= new ObservableField<>();
}

设置UI

<SeekBar
      android:layout_width="match_parent"
      android:layout_height="50dp"
      app:progressNow="@={observableData2.progressNum}"/>
<TextView
      android:layout_width="match_parent"
      android:layout_height="wrap_content"
      android:text="@{observableData2.progressNum}"
      android:gravity="center"
      android:textSize="50sp"/>

在seekbar加上@={}

MainActivity2

public class MainActivity2 extends AppCompatActivity {
   ActivityMain2Binding main2Binding;
    DataItem2 dataItem2;
   
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        init();

    }
    private void init() {
        main2Binding=DataBindingUtil.setContentView(this,R.layout.activity_main2);
        
        dataItem2=new DataItem2();
        main2Binding.setObservableData2(dataItem2);
    }
}

tip: BindingAdapter当成是setter,InverseBindingAdapter是getter
这样就完成罗


<<:  【Day 16】 介绍 AWS 中资讯安全 - 流量相关日志

>>:  D3JsDay15 了解WEB地图学,先懂一点地理学—web地图的科学

Google Maps JavaScript API 工具|专案实作

串接地图 JavaScript API 中虽然相较起来难度较高,不过官方文件写的也很简单易懂。 使用...

网页盒子-30天学会HTML+CSS,制作精美网站

Box Model定义 每个html的元素都是一个Box Model,由外而内为外边距(Margin...

【PHP Telegram Bot】Day11 - Webhook 与 Web Hosting

网站服务器 网路上有很多的免费服务器(Free Hosting) 几乎每个都有支援 PHP 我就拿 ...

[分享] verilog设计经验总结

先记下来: 1、不使用初始化语句; 2、不使用延时语句; 3、不使用循环次数不确定的语句,如:for...

第五天:在 macOS 上安装 Gradle

同为 Unix 系列的 macOS 可以完全相容上一篇使用 SDKMAN 安装 JDK 及 Grad...