JavaScript
jsf
JavaEE

JSFでボタンの活性制御するときの注意…

JSF(Java Server Faces)のイヤンな挙動

JSFを使用しているプロジェクトがどれほどあるか、わたくしには未知数でございますが
自分が経験したJSFのあるクセについて記しておこうと思います。

自分が直面した時のプロジェクトでは、JSFのxhtmlとJavaScript&jQueryで
フロント側を作成していました。

ボタンの活性制御で落とし穴

例えば、必須の入力項目が埋まったのを検知して次画面に遷移させるボタンを
押せるようにする処理を組んだとします。

input.html
<h:commandButton id="nextButton" value="button" 
    action="#{input.nextAction}" disabled="#{!isAllInput}"/>

上記のようにボタンを配置しました。

"isAllInput"はboolean型です。
初期はボタンが押せない状態にしたいためdisabledを"True"でセットしたい。

よって、isAllInputの頭に"!"をつけて「isAllInputがfalseであれば」という条件にしてあげました。
これでページ表示直後は未入力状態なので、disabledが有効になります。
(つまりボタン非活性の状態)

ボタンを押しても無反応

必須入力項目が埋まったら、disabledを無効にしてボタンを活性状態にします。
これでボタンを押して次のページへ……

と、いきたいところですがこれだと反応がありません。
disabledを無効にしてボタン押下可能になってもactionの処理がうまく動作してくれないのです。

<h:commandButton…タグ内のdisabled

上記の書き方ではhtmlを生成する際に、disabledを有効にする初期値の場合、
以降ボタンを押してもAction処理が走らなくなってしまうのです。
これはそういうクセがある模様です。(以下の記事参考にしました)

JSF をめぐる話題

JSFでボタン活性制御をするならタグ内disabledはNG

少し手間ではありますが、前述の理由からボタンの活性制御はjavascript(またはjQuery)で
制御しなければいけません。(入力チェックのロジック表記は省いてます)

input.html
<script type="text/javascript">
function disable_change(){
    if (#{isAllInput}){
        document.getElementById("nextButton").disabled = "";
    } else {
        document.getElementById("nextButton").disabled = "disabled";
    }
}
</script>
・
・
・
<h:commandButton id="nextButton" value="button" action="#{input.nextAction}"/>

jQueryの場合:

input-j.html
<script type="text/javascript">
$(function(){
    if (#{isAllInput}){
        $("#nextButton").attr('disabled', false);
    } else {
        $("#nextButton").attr('disabled', true);
    }
});
</script>
・
・
・
<h:commandButton id="nextButton" value="button" action="#{input.nextAction}"/>

javascriptでdisabledの制御をしてあげれば、ボタン活性状態でクリックした時に
アクション処理がしっかりと動作するようになります。

このクセを知らず当時とっても時間を費やしてしまいました……