2016-08-10 3 views
4

홈페이지보기 모델은 다음과 같습니다내부 통제 내부 ObservableField 전달하는 방법을

class MainVM{ 
    public ObservableField<String> title; 
    public ObservableField<Boolean> isFlexible; 
} 

메인 레이아웃은 다음과 같습니다

<layout> 
    <date><variable name="item" type="MainVM"></data> 
    <LinearLayout> 
    <TextView text="@{item.title}"/> 
    <CustomCtrl1 vm="@{item.isFlexible}"> 
    </LinearLayout> 
</layout> 

CustomCtrl의 레이아웃이 다소 같은

<layout> 
     <date><variable name="item" type="boolean"></data> 
     <LinearLayout> 
      ... 
     <Switch checked="@{item}"/> 
      ... 
     </LinearLayout> 
    </layout> 
를 찾습니다

문제는 ObservableField ~ MainVM에서 부울 값으로 변환하는 것입니다. 암탉이 CustomCtrl에 전달 된 후 CustomCtrl 안에 부울 값이 변경되면 MainVM 님의 영향을받지 않습니다. 첫 번째 아이디어는 Boolean에서 ObservableField<Boolean>까지 CustomCtrl's viewmodel 변경 이었지만 어떤 이유로 허용되지 않았습니다.

그래서 내부 제어 내부에 ObservableField을 전달하는 적절한 방법은 무엇입니까?

+0

양방향 바인딩 대신 ObservableBoolean을 사용하려고합니까? –

+0

예, 그 것처럼 보입니다. –

답변

1

가장 좋은 방법은 양방향 바인딩을 직접 사용하는 것입니다. Android Studio 2.1 이상이 필요합니다. Android Studio 2.2는 맞춤 컨트롤로 인해 발생할 수있는 인플레이션 버그를 수정합니다.

<layout> 
    <date><variable name="item" type="MainVM"></data> 
    <LinearLayout> 
    <TextView android:text="@{item.title}"/> 
    <include layout="@layout/other" app:vm="@={item.isFlexible}"> 
    </LinearLayout> 
</layout> 

을 그리고의 다른 레이아웃 : 당신이 대신 사용자 지정 컨트롤의 포함 사용했다면, 오히려 사소한 것이 사용자 지정 컨트롤로

<layout> 
    <date><variable name="item" type="boolean"></data> 
    <LinearLayout> 
     ... 
    <switch android:checked="@={item}"/> 
     ... 
    </LinearLayout> 
</layout> 

, 당신은 청취자를 직접 구현해야합니다. 즉, 속성에 대한 리스너가 있어야합니다. 나는이 일을해야한다고 생각 (지금은 태블릿에 오전, 그래서 나는 확인할 수 없습니다) :

@InverseBindingMethods({ 
    InverseBindingMethod(type = CustomControl.class, attribute="vm")}) 
public class CustomCtrl extends View { 
    private CustomCtrlBinding binding; 
    private InverseBindingAdapter listener; 

    public CustomCtrl(...) { 
     binding = ... 
     binding.addOnPropertyChangedCallback(new OnPropertyChangedCallback() { 
      @Overriide 
      public void OnPropertyChanged(Observable sender, int propertyId) { 
       if (listener != null) { 
        listener.onChange(); 
       } 
      } 
     }); 
    } 

    @Bindable 
    public boolean getVm() { return binding.getItem(); } 

    public void setVm(boolean vm) { 
     binding.setItem(vm); 
    } 

    @BindingAdapter("vmAttrChanged") 
    public static void setListener(CustomCtrl view, 
      InverseBindingListener listener) { 
     view.listener = listener; 
    } 
} 

그런 다음 2 웨이 바인딩 한 :

<layout> 
    <date><variable name="item" type="MainVM"></data> 
    <LinearLayout> 
    <TextView android:text="@{item.title}"/> 
    <CustomCtrl app:vm="@={item.isFlexible}"> 
    </LinearLayout> 
</layout> 

그리고 사용자 지정 컨트롤 레이아웃 :

<layout> 
    <date><variable name="item" type="boolean"></data> 
    <LinearLayout> 
     ... 
    <switch android:checked="@={item}"/> 
     ... 
    </LinearLayout> 
</layout> 

보통 속성에 대한 자체 수신기가있는 사용자 지정 컨트롤을 작성하지만 InverseBindingListener는 핀치로 작동합니다.