2015-09-04 9 views
14

Próbuję powiązać zdarzenie w niestandardowym widoku z nową biblioteką wiążącą dane Androida, ale pojawia się problem.Powiązania danych z niestandardowymi odbiornikami w widoku niestandardowym

Tutaj jest odpowiednia część mojego widoku niestandardowego:

public class SuperCustomView extends FrameLayout { 
    private OnToggleListener mToggleListener; 

    public interface OnToggleListener { 
     void onToggle(boolean switchPosition); 
    } 

    public void setOnToggleListener(OnToggleListener listener) { 
     mToggleListener = listener; 
    } 
    .../... 
} 

Próbuję użyć tego widok niestandardowy i powiązać zdarzenie onToggle z następujących czynności:

<data> 
    <variable 
     name="controller" 
     type="com.xxx.BlopController"/> 
</data> 

<com.company.views.SuperCustomView 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" 
     app:onToggle="@{controller.toggleStrokeLimitation}" 
     app:custom_title="Blah" 
     app:custom_summary="Bloh" 
     app:custom_widget="toggle"/> 

Gdzie toggleStrokeLimitation jest metoda na kontrolerze:

public void toggleStrokeLimitation(boolean switchPosition) { 
    maxStrokeEnabled.set(switchPosition); 
} 

Dostaję ten błąd lub podczas kompilacji:

> java.lang.RuntimeException: Found data binding errors. 
****/ data binding error ****msg:Cannot find the setter for attribute 'app:onToggle' with parameter type java.lang.Object. file:/path/to/androidapp/app/src/main/res/layout/fragment_stroke.xml loc:36:35 - 36:67 ****\ data binding error **** 

Próbowałem użyć android:onToggle zamiast app:onToggle ale uzyskać ten sam błąd.

Podczas czytania binding events section of the doc, czuję, że mogę podłączyć dowolną metodę ze sterownika do zdarzenia onToggle.

Czy ramy obejmują metody controller.toggleStrokeLimitation w postaci ? Jakaś wskazówka na temat rodzaju magii, która jest za istniejącym onClick dostarczonym przez framework?

+0

Spróbuj zaimplementować niestandardowy ustawnik dla atrybutu onToggle http://developer.android.com/tools/data-binding/guide.html#custom_setters i upewnij się, że kontroler.toggleStrokeLimitation jest typu OnToggleListener –

+0

Jaki jest typ 'kontrolera. toggleStrokeLimitation'.. Wydaje się, że jest to 'Obiekt' i twój programista oczekuje' OnToggleListener' – yigit

+0

Masz rację, mógłbym to zrobić, ale chcę zmapować zdarzenie do niestandardowej metody. Jak wyjaśniono w https://developer.android.com/tools/data-binding/guide.html#binding_events, edytuję pytanie za pomocą mojego rozumowania. – fstephany

Odpowiedz

17
@BindingMethods(@BindingMethod(type = SuperCustomView.class, attribute = "app:onToggle", method = "setOnToggleListener")) 
public class SuperCustomView extends FrameLayout { 
    private OnToggleListener mToggleListener; 

    public interface OnToggleListener { 
     void onToggle(boolean switchPosition); 
    } 

    public void setOnToggleListener(OnToggleListener listener) { 
     mToggleListener = listener; 
    } 
    .../... 
} 

My Hack przetestować kod był:

public void setOnToggleListener(final OnToggleListener listener) { 
    this.setOnClickListener(new OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      toggle = !toggle; 
      listener.onToggle(toggle); 
     } 
    }); 
} 

I na moim kontrolera obiektu:

public class MyController { 

    private Context context; 

    public MyController(Context context) { 
     this.context = context; 
    } 

    public void toggleStrokeLimitation(boolean switchPosition) { 
     Toast.makeText(context, "Toggle" + switchPosition, Toast.LENGTH_SHORT).show(); 
    } 
} 

Tak !! pracował

Alternatywnie można użyć xml jak:

<com.androidbolts.databindingsample.model.SuperCustomView 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    app:onToggleListener="@{controller.toggleStrokeLimitation}" /> 

Teraz nie trzeba dodawać @BindingMethods adnotacji.

Dokumentacja mówi: "Some attributes have setters that don't match by name. For these methods, an attribute may be associated with the setter through BindingMethods annotation. This must be associated with a class and contains BindingMethod annotations, one for each renamed method. "

+0

Dokładnie to, czego szukałem :) – Shirane85

0

Ty może nie trzeba słuchaćBindingMethods dla słuchaczy na widoku niestandardowego jeśli nazwa metody definiowania formatu śledzić fasoli Java poprawnie. Oto przykład

klasa CustomView

public class CustomView extends LinearLayout { 
    ... 
    private OnCustomViewListener onCustomViewListener; 

    ... 
    public void setOnCustomViewListener(OnCustomViewListener onCustomViewListener) { 
     this.onCustomViewListener = onCustomViewListener; 
    } 


    .... 
    public interface OnCustomViewListener { 
     void onCustomViewListenerMethod(int aNumber); 
    } 
} 

XML

<...CustomView 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    app:onCustomViewListener="@{viewModel.viewModelListenerMethod}" // or use can use app:onCustomViewListener="@{viewModel::viewModelListenerMethod}" 
    /> 

ViewModel

public class ViewModel extends BaseObservable{ 

    public void viewModelListenerMethod(int aNumber){ 
     // handle listener here 
    } 
} 
Powiązane problemy