我一直試圖在Spinner上設置一個雙向綁定。使用@InverseBindingAdapter/AttrChanged進行Android Spinner雙向綁定不起作用
有很多這樣的例子,在網絡上和堆棧溢出,但沒有一個適合我。
這只是一個國家的微調,我已經爲它定義一個國家適配器此方法:
@InverseBindingAdapter(attribute = "selectedCountry", event = "selectedCountryAttrChanged")
public static String bindCountryInverseAdapter(AppCompatSpinner pAppCompatSpinner) {
Object selectedItem = pAppCompatSpinner.getSelectedItem();
SpinnerAdapter adapter = pAppCompatSpinner.getAdapter();
if (adapter instanceof CountrySpinnerAdapter) {
return (String) selectedItem;
}
throw new UnsupportedOperationException("The adapter must be a CountrySpinnerAdapter");
}
@BindingAdapter(value = "selectedCountryAttrChanged", requireAll = false)
public static void bindCountryChanged(AppCompatSpinner pAppCompatSpinner, final InverseBindingListener newTextAttrChanged) {
AdapterView.OnItemSelectedListener listener = new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
newTextAttrChanged.onChange();
}
@Override
public void onNothingSelected(AdapterView<?> parent) {
newTextAttrChanged.onChange();
}
};
pAppCompatSpinner.setOnItemSelectedListener(listener);
}
@BindingAdapter("selectedCountry")
public static void bindCountryValue(AppCompatSpinner pAppCompatSpinner, String newSelectedValue) {
SpinnerAdapter adapter = pAppCompatSpinner.getAdapter();
if (adapter instanceof CountrySpinnerAdapter) {
((CountrySpinnerAdapter) adapter).bindSelectedValue(pAppCompatSpinner, newSelectedValue);
return;
}
throw new UnsupportedOperationException("The adapter must be a CountrySpinnerAdapter");
}
的bindCountryChanged
方法不會被調用。
我也試過這個變體(以下其他例子):
@BindingAdapter(value = {"selectedCountry", "selectedCountryAttrChanged"}, requireAll = false)
public static void bindCountryValueChanged(AppCompatSpinner pAppCompatSpinner, String newSelectedValue, final InverseBindingListener newTextAttrChanged) {
AdapterView.OnItemSelectedListener listener = new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
newTextAttrChanged.onChange();
}
@Override
public void onNothingSelected(AdapterView<?> parent) {
newTextAttrChanged.onChange();
}
};
pAppCompatSpinner.setOnItemSelectedListener(listener);
}
這就是所謂的,但newTextAttrChanged
總是空。
佈局,結合部分:
<data>
<variable
name="customer"
type="my.package.CustomerBinding" />
</data>
而且小部件:
<android.support.v7.widget.AppCompatSpinner
android:id="@+id/editCountry"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:spinnerMode="dropdown"
app:adapter="@{customer.countrySpinnerAdapter}"
app:selectedCountry="@{customer.country}" />
country
ID只是一個ObservableField<String>
和countrySpinnerAdapter
是國家的列表中BaseAdapter
。
的Android gradle這個插件:
classpath 'com.android.tools.build:gradle:2.2.1'
工具版本:
buildToolsVersion "24.0.2"
當然,數據綁定啓用:
dataBinding {
enabled = true
}
爲什麼newTextAttrChanged
總是空/對BindingAdapter從來都不是calld?我究竟做錯了什麼?
'應用:= SELECTEDCOUNTRY 「@ {} customer.country」'你不缺少'='的雙向綁定,所以它應該是'應用:= SELECTEDCOUNTRY 「@ = {} customer.country」'...? – yennsarah
耶穌你是對的!我總是忽視它...你能告訴我'@ = {'和'@ {'?我一直使用後者,當我應該使用'='形式? –
我會發佈一個答案。 ;) – yennsarah