- - PR -
JSF selectOneMenuの連動
投稿者 | 投稿内容 | ||||||||
---|---|---|---|---|---|---|---|---|---|
|
投稿日時: 2006-02-09 22:48
selectOneMenuで
あるリスト(A1)を変更したら、リスト(B1)が作成され、 あるリスト(A2)を変更したら、リスト(B2)が作成され、 ということを行いたく、valueChangeListener等を用い 以下のような実装を行っているのですが、(上記リストは全て1画面内にいます) ------------------- <!-- リストボックスA1 --> <h:selectOneMenu immediate="true" id="cdA1" value="#{bean.codeA1}" onchange="submit()" valueChangeListener="#{bean.codeListenerA1}"> <f:selectItems value="#{bean.codeListA1}"/> </h:selectOneMenu> <!-- リストボックスB1 --> <h:selectOneMenu id="cdB1" value="#{bean.codeB1}"> <f:selectItems value="#{bean.codeListB1}"/> </h:selectOneMenu> <!-- リストボックスA2 --> <h:selectOneMenu immediate="true" id="cdA2" value="#{bean.codeA2}" onchange="submit()" valueChangeListener="#{bean.codeListenerA2}"> <f:selectItems value="#{bean.codeListA2}"/> </h:selectOneMenu> <!-- リストボックスB2 --> <h:selectOneMenu id="cdB2" value="#{bean.codeB2}"> <f:selectItems value="#{bean.codeListB2}" /> </h:selectOneMenu> ------------------- このとき、 A1を変更し、B1を作成し、B1から要素を選択したのち A2を変更した際にB1での選択値を以前の状態に保ちたいのですが 初期化されてしまいます。 何か手段・参考になるURLなど御座いましたらよろしくお願いします。 ValueChangeListenerでは、そのリストの値しか取得出来ませんでした。 submit()されていると思ったのですが、プロパティにセットされた値はnullでした。 | ||||||||
|
投稿日時: 2006-02-09 22:53
すみません。valueChangeListenerに関するスレッドを見ていませんでした。
一度確認・検証後、それでもダメな場合はよろしくお願いします。 | ||||||||
|
投稿日時: 2006-02-10 10:39
「B1から要素を選択したのちA2を変更した」というのは,B1にはonchangeを指定して いないですから,A2の変更でsubmitされ,そのときにB1の新しい値も送信されている ということですよね. ここで「初期化されてしまいます」というのは,どのタイミングでどこから何をみたら 初期化されていたのですか? 「beanのcodeListenerA2の中でcodeB1を見たら初期化されていた」? 初期化とは?nullになっていた?以前の入力値になっていた? 例えば,beanをrequestスコープにしておくと,リクエスト毎にインスタンシエートしま すから,当然,初期値になっています.
「そのリストの値」とは? ValueChangeListenerはデフォルトではProcess Validationsフェーズで実行しますから beanへの値の反映はまだ行われていません. | ||||||||
|
投稿日時: 2006-02-10 11:28
説明不足ですみません。
引用: ------------------------------------------------------------------------ 「B1から要素を選択したのちA2を変更した」というのは,B1にはonchangeを指定して いないですから,A2の変更でsubmitされ,そのときにB1の新しい値も送信されている ということですよね. ------------------------------------------------------------------------------ はい。そうです。 以前のスレッドを参考にし、 フェーズをUPDATE_MODEL_VALUESへ変更するという箇所を見ながら 直接Beanのプロパティの値を参照してみましたが、 他の項目(画面上にはtextbox、連動しない別のselectOneMenu等)の値は submitされた値を参照出来たのですが、 ----- A1:valueChangeListener実装---->動的に変更されるリスト:B1 A2:valueChangeListener実装---->動的に変更されるリスト:B2 ----- A1を変更しvalueChangeListenerを発生させ、 生成されたリストB1の選択値が、A2のvalueChangeListenerの際に B1の選択値がnull値となってしまい"selected"状態を保てないのです。 (逆の場合も同じ事象でした) | ||||||||
|
投稿日時: 2006-02-10 11:52
度々すみません。今気づいたのですが、
下記のように実装しているのですが、初回は問題ないのですが、 2回目以降、valueChangeListenerが両方とも起動してしまう (A1を変更させても、A1のvalueChangeListenerの起動後に A2のvalueChangeListenerが起動します) 個別に動くものとばかり思っておりましたので、今まで気づきませんでした。 原因として何が考えられるでしょうか。 [JSP]------------------- <!-- リストボックスA1 --> <h:selectOneMenu immediate="true" id="cdA1" value="#{bean.codeA1}" onchange="submit()" valueChangeListener="#{bean.codeListenerA1}"> <f:selectItems value="#{bean.codeListA1}"/> </h:selectOneMenu> <!-- リストボックスB1 --> <h:selectOneMenu id="cdB1" value="#{bean.codeB1}"> <f:selectItems value="#{bean.codeListB1}"/> </h:selectOneMenu> <!-- リストボックスA2 --> <h:selectOneMenu immediate="true" id="cdA2" value="#{bean.codeA2}" onchange="submit()" valueChangeListener="#{bean.codeListenerA2}"> <f:selectItems value="#{bean.codeListA2}"/> </h:selectOneMenu> <!-- リストボックスB2 --> <h:selectOneMenu id="cdB2" value="#{bean.codeB2}"> <f:selectItems value="#{bean.codeListB2}" /> </h:selectOneMenu> ------------------- [managedBaen]------------------- /** * リストA1 * @param event */ public void codeListenerA1(ValueChangeEvent event) throws AbortProcessingException { codeListB1 = changeCodeListB1((String) event.getNewValue()); } /** * リストA2 * @param event */ public void codeListenerA2(ValueChangeEvent event) throws AbortProcessingException { codeListB2 = changeCodeListB2((String) event.getNewValue()); } ------------------- | ||||||||
|
投稿日時: 2006-02-14 11:53
以前のスレッドにも書きましたが,Update Model Valuesフェーズの後で, 一部のビーンの値は更新され,一部は更新されないということはありえません. 考えられるのは, ・B1の値としてnullが入力されたものとして処理された ・ビーンの値がnullに初期化されていて,かつB1の入力値がリクエストパラメタとして 送られていないか,更新されていない リクエストパラメタとして何か来ているか確認して下さい. それと,ビーンのスコープがrequestになっていませんか?
「フェーズをUPDATE_MODEL_VALUESへ変更」はやった上での話でしょうか? immediate="true"のままでそうする意味はないと思いますが. | ||||||||
|
投稿日時: 2006-02-14 13:52
なんだかEvent/Listenerの機構にひっぱられてトリッキーな方向に向かっているような気がします。
他のスレッドでも記しましたが、当該リストボックスを生成するgetterでハンドリングしてあげるとすっきりすると思います。
これの肝は、当該画面の再描画を行なう際に「#{bean.codeListB1}」で毎回「getCodeListB1()」が呼ばれるということです。 ValueChangeListenerの機構を使わなくてもgetterで状況に応じた値を返すことができますし、必要であればキャッシュを使ってある程度の効率化を図ることもできます。 何より構造がシンプルになりますし、モデルとの同期も簡単に取れます。 http://www.atmarkit.co.jp/bbs/phpBB/viewtopic.php?mode=viewtopic&topic=27658&forum=12&start=8 | ||||||||
|
投稿日時: 2006-02-15 22:06
賛成です. A1,A2のsetterの方で処理する手もありますね. いずれにしてもValueChangeListenerにはうかつに手を出さない方がやっぱり良さそうです. |