[解決済み] valueChangeListenerとf:ajaxリスナーのどちらを使うべきか?
質問
次の二つのコードの違いは何でしょうか?
listener
の配置に関して、どのような違いがあるのでしょうか?
<h:selectOneMenu ...>
<f:selectItems ... />
<f:ajax listener="#{bean.listener}" />
</h:selectOneMenu>
と
<h:selectOneMenu ... valueChangeListener="#{bean.listener}">
<f:selectItems ... />
</h:selectOneMenu>
どのように解決するのですか?
この
valueChangeListener
は、フォームが送信されたときにのみ呼び出されます。
と
の場合、送信された値は初期値とは異なります。したがって
のみ
の場合、HTML DOM
change
イベントが発生します。フォームを送信したい場合は、HTML DOMの
change
イベントの間にフォームを送信したい場合は、別の
<f:ajax/>
を追加する必要があります。これは、現在のコンポーネントのみを処理するフォーム送信を引き起こします (たとえば
execute="@this"
).
<h:selectOneMenu value="#{bean.value}" valueChangeListener="#{bean.changeListener}">
<f:selectItems ... />
<f:ajax />
</h:selectOneMenu>
を使用する場合
<f:ajax listener>
の代わりに
valueChangeListener
の代わりに、HTML DOM の中でデフォルトで実行されます。
change
イベント中に実行されます。内部では
UICommand
コンポーネントや、チェックボックスやラジオボタンを表す入力コンポーネントの内部では、デフォルトで HTML DOM の
click
イベント時にのみ実行されます。
<h:selectOneMenu value="#{bean.value}">
<f:selectItems ... />
<f:ajax listener="#{bean.ajaxListener}" />
</h:selectOneMenu>
もう一つの大きな違いは
valueChangeListener
メソッドの終了時に呼び出されることです。
PROCESS_VALIDATIONS
フェーズの終了時に呼び出されます。その時点では、投稿された値はまだモデル内で更新されていません。従って、入力コンポーネントにバインドされたビーンプロパティにアクセスするだけでは、その値を取得することはできません。
value
. によって取得する必要があります。
ValueChangeEvent#getNewValue()
. ちなみに、古い値も
ValueChangeEvent#getOldValue()
.
public void changeListener(ValueChangeEvent event) {
Object oldValue = event.getOldValue();
Object newValue = event.getNewValue();
// ...
}
は
<f:ajax listener>
メソッドが呼び出されるのは
INVOKE_APPLICATION
フェーズで呼び出されます。このとき、投稿された値はすでにモデル内で更新されています。入力コンポーネントにバインドされたビーンプロパティに直接アクセスすることで、それを取得することができます。
value
.
private Object value; // +getter+setter.
public void ajaxListener(AjaxBehaviorEvent event) {
System.out.println(value); // Look, (new) value is already set.
}
また、もし更新が必要なら
別の
プロパティを更新する必要がある場合、それは
valueChangeListener
を更新されたプロパティとして
ができます。
の間に提出された値によって上書きされます。
UPDATE_MODEL_VALUES
フェーズで送信された値によって上書きされます。これはまさに、古い JSF 1.x のアプリケーション/チュートリアル/リソースで
valueChangeListener
がこのような構成で
immediate="true"
と
FacesContext#renderResponse()
を使って、それを防いでいます。結局のところ
valueChangeListener
を使用してビジネスアクションを実行することは、実際には常にハック/回避策なのです。
要約すると このような場合
valueChangeListener
を使うのは、実際の値の変化そのものを傍受する必要がある場合だけです。つまり、あなたが実際に興味を持っているのは
と
に興味がある場合です(例えば、ログを取るため)。
public void changeListener(ValueChangeEvent event) {
changeLogger.log(event.getOldValue(), event.getNewValue());
}
を使用します。
<f:ajax listener>
を使うのは、新しく変更された値に対してビジネスアクションを実行する必要がある場合だけです。つまり、あなたが実際に興味を持っているのは
だけです。
にしか興味がない場合です (たとえば、2 番目のドロップダウンにデータを入力する場合など)。
public void ajaxListener(AjaxBehaviorEvent event) {
selectItemsOfSecondDropdown = populateItBasedOn(selectedValueOfFirstDropdown);
}
ビジネス・アクションの実行中に、実は古い値にも興味があるのなら、フォールバックして
valueChangeListener
に戻りますが、キューに入れるのは
INVOKE_APPLICATION
フェーズに待ちます。
public void changeListener(ValueChangeEvent event) {
if (event.getPhaseId() != PhaseId.INVOKE_APPLICATION) {
event.setPhaseId(PhaseId.INVOKE_APPLICATION);
event.queue();
return;
}
Object oldValue = event.getOldValue();
Object newValue = event.getNewValue();
System.out.println(newValue.equals(value)); // true
// ...
}
関連
-
これだけ読めばOK! -Ajaxの説明
-
Jquery EasyUI +Ajax +Json +汎用ハンドラで、データのフロントエンドとバックエンドのインタラクションを実現 --- Goodness Commune Project
-
[解決済み] なぜGoogleはJSONレスポンスにwhile(1);を前置するのでしょうか?
-
[解決済み] グリッドレイアウトにおけるフリングジェスチャーの検出
-
[解決済み] 同じサーバーの異なるポートはクロスドメインとみなされますか?(Ajax的な意味で)
-
[解決済み] IEでjQueryのajaxを呼び出すと「No Transport」エラーが発生する。
-
[解決済み] Django に最適な AJAX ライブラリは?[クローズド]
-
[解決済み] jQuery が POST パラメータとして文字列を送信する
-
[解決済み] Symfony 2.0 AJAX アプリケーションで Doctrine のエンティティを JSON にエンコードするには?
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
これだけ読めばOK! -Ajaxの説明
-
Jquery EasyUI +Ajax +Json +汎用ハンドラで、データのフロントエンドとバックエンドのインタラクションを実現 --- Goodness Commune Project
-
[解決済み] 同じサーバーの異なるポートはクロスドメインとみなされますか?(Ajax的な意味で)
-
[解決済み] IEでjQueryのajaxを呼び出すと「No Transport」エラーが発生する。
-
[解決済み] Django に最適な AJAX ライブラリは?[クローズド]
-
[解決済み] jQuery が POST パラメータとして文字列を送信する
-
[解決済み] Symfony 2.0 AJAX アプリケーションで Doctrine のエンティティを JSON にエンコードするには?