2015-09-04 12 views
14

カスタムビューでイベントを新しいAndroidデータバインディングライブラリにバインドしようとしていますが、問題が発生しています。ここでカスタムビューでのカスタムリスナーによるデータバインド

は私のカスタムビューの関連部分です:

public class SuperCustomView extends FrameLayout { 
    private OnToggleListener mToggleListener; 

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

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

私は、このカスタムビューを使用して、次のとonToggleイベントをバインドしようとしている:

toggleStrokeLimitationがメソッドである
<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"/> 

コントローラの

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

このエラーが発生しましたまたはコンパイルする場合:

> 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 **** 

私の代わりにapp:onToggleandroid:onToggleを使用しますが、同じエラーを取得しようとしました。

binding events section of the docを読むと、コントローラーからどの方法でもonToggleイベントに接続できるようになりました。

フレームワークでcontroller.toggleStrokeLimitationメソッドをSuperCustomView.OnToggleListenerにラップしますか?フレームワークによって提供されている既存のonClickの後ろにある種類の魔法に関するヒント?テストコードに

+0

onToggle属性http://developer.android.com/tools/data-binding/guide.html#custom_settersのカスタムセッターを実装して、controller.toggleStrokeLimitationがOnToggleListenerタイプのものであることを確認してください。 –

+0

'コントローラーのタイプは何ですか。 toggleStrokeLimitation'?それが 'Object'のようで、あなたのセッターが' OnToggleListener'を期待しています – yigit

+0

あなたはそうですが、私はそれを行うことができますが、イベントをカスタムメソッドにマップしたいと思います。 https://developer.android.com/tools/data-binding/guide.html#binding_eventsで説明されているように、私は推論で質問を編集します。 – fstephany

答えて

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; 
    } 
    .../... 
} 

マイハックされました:

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

そして、私のコントローラオブジェクト上:

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(); 
    } 
} 

うん!

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

@BindingMethods注釈を追加する必要が:それはまたあなたのようなXMLを使用することはできません

を働きました。

ドキュメントは言う: "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

まさに私が探していたもの:) – Shirane85

0

あなたは、あなたがメソッド名が正しくJavaの豆の形式に従って定義する場合は、カスタムビューのリスナーを聞くためBindingMethodsを必要としない場合があります。ここ は一例で

の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}" 
    /> 

ビューモデル

public class ViewModel extends BaseObservable{ 

    public void viewModelListenerMethod(int aNumber){ 
     // handle listener here 
    } 
} 
関連する問題