1

ui:binderコンポーネント内のいくつかのオブジェクトにアクセスしようとしていますが、夜に目を覚まし続ける厄介なコードを記述せずにeventBus、requestFactoryなどにアクセスする方法がわかりません(また、私は完全に新しいことに注意してくださいJAVA、背景はPerl / Python / PHPにあります)。

私のui.xmlファイル:

<ui:UiBinder xmlns:ui='urn:ui:com.google.gwt.uibinder'
    xmlns:g='urn:import:com.google.gwt.user.client.ui'
    xmlns:ig='urn:import:com.ig.client.scaffold.ui.widget'>
    <ui:style>
        ...
    </ui:style>
    <g:HorizontalPanel>
        ...
    </g:HorizontalPanel>
</ui:UiBinder>

この方法でeventBusを挿入すると、com.ig.client.scaffold.ui.widget.Rで失敗します。デフォルト(引数ゼロ)のコンストラクターはありません。

public class R extends Composite {

    interface MyUiBinder extends UiBinder<Widget, R> {}
    private static MyUiBinder uiBinder = GWT.create(MyUiBinder.class);

    private final EventBus eventBus;

    @UiField SimplePanel fieldA, ...;

    @Inject
    public R(EventBus eventBus){
        this.eventBus = eventBus;
        initWidget(uiBinder.createAndBindUi(this));
    }
}

したがって、エラーメッセージに従って、UIFactoryを作成すると、エラーが発生します...'{style.entityComponent}'>必要な属性がありません:eventBus Element ...( ui:binderスタイルシートのeventBus。

public class R extends Composite {

    interface MyUiBinder extends UiBinder<Widget, R> {}
    private static MyUiBinder uiBinder = GWT.create(MyUiBinder.class);

    private final EventBus eventBus;

    @UiField SimplePanel fieldA, ...;

    public @UiConstructor R(EventBus eventBus){
        this.eventBus = eventBus;
        initWidget(uiBinder.createAndBindUi(this));
    }

    @Inject
    @UiFactory R makeR(){
        return new R(eventBus);
    }
}

過去数日間の読書と読書、さらに読書から、ui:binderウィジェットにバインドするビューでeventBus、requestFactory、historyControllerに直接アクセスする人を見たことがないため、おそらくベストプラクティスではないという結論に至りました。とりあえず。

オブジェクトがあるとしましょう。それをプロキシと呼びましょう。プロキシにはhandleButtonClickが含まれており、これがeventBus.doSomething()を呼び出します。このプロキシオブジェクトをインスタンス化することなく、またはすべてのウィジェットに渡すことなく、ui:binderウィジェットにリンクするにはどうすればよいですか?

インターフェイスでGINインジェクションを実行し、クラスRを介してそのインターフェイスを実装することは可能ですか?クラスRには、探しているオブジェクトが含まれていますか?

基本的にフロントエンドをROOによって作成された残りのサービスに接続できるサンプル(Java n00bが理解できる)を探すだけで、機能するソリューションはどれでも歓迎されます。

ありがとうJ

4

1 に答える 1

2

モデル、ビュー、プレゼンターのパターンを確認してください- この問題を解決します。通常、すべての非表示ロジックはビューから除外する必要があります。これにより、1) 非表示ロジックを (インスタンス化に時間がかかる) ブラウザー内で実行せずに単体テストを実行でき、2) 異なるディスプレイを複製せずに同じアプリケーションにプラグインできます。非表示ロジック。

探している動作を示す MVP の例を次に示します (スタイルは、Activities & Places の実装とは少し異なることに注意してください)。

MyPresenter.java:

public class MyPresenter {
  public interface Display extends IsWidget {
    void setButtonClickHandler(ClickHandler buttonClickHandler);
  }

  private final Display display;
  private final EventBus eventBus;

  @Inject
  public MyPresenter(EventBus eventBus,
                     Display display)
  {
    this.display = display;
    this.eventBus = eventBus;

    bind();
  }

  private void bind() {
    display.setButtonClickHandler(new ClickHandler() {
      @Override
      public void onClick(ClickEvent event) {
        eventBus.fireEvent(new MyButtonClickedEvent());
      }
    });
  }

  public void go(HasWidgets container) {
    container.add(display.asWidget());
  }
}

MyView.ui.xml:

<ui:UiBinder xmlns:ui='urn:ui:com.google.gwt.uibinder'
  xmlns:g='urn:import:com.google.gwt.user.client.ui'
  xmlns:ig='urn:import:com.ig.client.scaffold.ui.widget'>

  <g:Button ui:field="myButton"/>
</ui:UiBinder>

MyView.java

public class MyView extends Composite implements MyPresenter.Display {
  interface MyViewUiBinder extends UiBinder<Widget, MyView> {}
  private static MyViewUiBinder uiBinder = GWT.Create(MyViewUiBinder.class);

  private ClickHandler buttonClickHandler = null;

  public MyView() {
    initWidget(uiBinder.createAndBindUi(this));
  }

  @UiHandler("myButton")
  void onButtonClick(ClickEvent event) {
    if (buttonClickHandler != null) {
      buttonClickHandler.onClick(event);
    }
  }

  @Override
  public void setButtonClickHandler(ClickHandler buttonClickHandler) {
    this.buttonClickHandler = buttonClickHandler;
  }
}

そしてあなたのGINモジュールで:bind(MyPresenter.Display.class).to(MyView.class);

于 2011-01-09T19:38:16.533 に答える