2011-04-18 45 views
1

這個例子是一種極致的,什麼我嘗試做的是不是正是這一點,但它更簡單的演示我的問題與此JSF2 AJAX更新部分參數

我有一個頁面,用簡單的index.xhtml:

<html 
    xmlns:h="http://java.sun.com/jsf/html" 
    xmlns:mc="http://java.sun.com/jsf/composite/mc"> 
    ... 
    <h:panelGroup id="u1" styleClass="unique_container"> 
     <mc:component1></mc:component1> 
    </h:panelGroup> 
    <h:panelGroup id="u2" styleClass="unique_container"> 
     <mc:component2></mc:component2> 
    </h:panelGroup> 
    <h:panelGroup id="u3" styleClass="unique_container"> 
     <mc:component3></mc:component3> 
    </h:panelGroup> 
    <form action="/faces/async.xhtml"> 
     <input type="checkbox" name="renderu1" /> 
     <input type="checkbox" name="renderu2" /> 
     <input type="checkbox" name="renderu1" /> 
     <input type="submit" value="render" /> 
    </form> 
    ... 
</html> 

當我按下了 「GO」 按鈕,我想如果是renderu2到cheked呈現COMPONENT1如果renderu1被選中,COMPONENT2和component3如果renderu3檢查

我目前這個解決方案是一個使用jQuery表單插件的js函數:

$(document).ready(function(){ 
    registerForms($(document)); 
}); 

function registerForms(rootElement) 
{ 
    rootElement.find("form").submit(function() { 
    // submit the form 
    $(this).ajaxSubmit(function(data, textStatus) { 
     if(textStatus == "notmodified") 
      return; 


     var tempDiv = $('<div></div>'); 
     tempDiv.css("display", "none"); 
     tempDiv.html(data); 
     var newUniqueContainer; 
     while((newUniqueContainer = tempDiv.find(".unique_container:first")).html() != null) 
     { 
      var oldUniqueContainer = $("#" + newUniqueContainer.attr("id") + ":first"); 
      oldUniqueContainer.empty(); 
      oldUniqueContainer.html(newUniqueContainer.html()); 
      registerForms(oldUniqueContainer); 
      newUniqueContainer.remove(); 
     } 
     tempDiv.remove(); 
    }); 
    // return false to prevent normal browser submit and page navigation 
    return false; 
    }); 
} 

它的作用是每當我提交表單,它激發一個Ajax請求給定的URL,等待響應,如果那裏有內容(狀態碼不是304,所以它不是「notmodified」) ,它得到的數據,並替換內容的原始 「unique_containers」 中新的數據

async.xhtml:

<html xmlns:mc="http://java.sun.com/jsf/composite/mc" 
     xmlns:c="http://java.sun.com/jsp/jstl/core"> 
    <c:if test="#{asyncBean.render1}"> 
     <h:panelGroup id="u1" styleClass="unique_container"> 
      <mc:component1></mc:component1> 
     </h:panelGroup> 
    </c:if> 
    <c:if test="#{asyncBean.render2}"> 
     <h:panelGroup id="u2" styleClass="unique_container"> 
      <mc:component2></mc:component2> 
     </h:panelGroup> 
    </c:if> 
    <c:if test="#{asyncBean.render3}"> 
     <h:panelGroup id="u3" styleClass="unique_container"> 
      <mc:component3></mc:component3> 
     </h:panelGroup> 
    </c:if> 
</html> 

AsyncBean.java:

@ManagedBean(name="asyncBean") 
@RequestScoped 
public class AsyncBean { 

    @ManagedProperty(value="#{param.renderu1}") 
    private boolean render1; 

    @ManagedProperty(value="#{param.renderu2}") 
    private boolean render2; 

    @ManagedProperty(value="#{param.renderu3}") 
    private boolean render3; 

    private boolean isRender1() { 
     return render1; 
    } 

    private void setRender1(boolean render1) { 
     this.render1 = render1; 
    } 

    private boolean isRender2() { 
     return render2; 
    } 

    private void setRender2(boolean render2) { 
     this.render2 = render2; 
    } 

    private boolean isRender3() { 
     return render3; 
    } 

    private void setRender3(boolean render3) { 
     this.render3 = render3; 
    } 
} 

如此,因爲如果只有第三複選框被選中exapmle,響應將是這樣的:

<html> 
    <span id="u3" class="unique_container"> 
     content of component3 
    </span> 
</html> 

其做工精細,它的簡單,所有的,但後來我開始使用RichFaces的爲我的一個組件 - 問題是,它使用jQuery的$(document).ready(fn)函數,並且當我使用RichFaces重新加載該組件時,它會中斷(它是一個樹組件,並且我無法打開節點)

i一直在尋找一種能夠做我的工作的溶劑,但是爲兼容性問題做好了準備(技術上,我想根據參數決定更新哪些部分,所以當原始頁面呈現,我還不知道要寫什麼「執行」和「渲染」屬性)

回答

2

這實際上是一個非常可怕的解決方案。您可以使用純JSF 2.0解決此問題,而無需使用jQuery,JSTL和自定義標記。您可以使用<f:ajax>來觸發ajax請求並渲染部分組件。您可以通過它們的rendered屬性有條件地呈現JSF組件。

這是一個基本的啓動示例,假設您運行的Servlet 3.0/EL 2.2的容器的/WEB-INF/web.xml聲明爲按照Servlet 3.0規範(否則.contains()將無法​​在EL中工作,並且您必須編寫自定義EL功能)。

<!DOCTYPE html> 
<html lang="en" 
    xmlns="http://www.w3.org/1999/xhtml" 
    xmlns:f="http://java.sun.com/jsf/core" 
    xmlns:h="http://java.sun.com/jsf/html" 
> 
    ... 
    <h:panelGroup id="panels"> 
     <h:panelGroup rendered="#{bean.panels.contains('u1')}"> 
      panel one 
     </h:panelGroup> 
     <h:panelGroup rendered="#{bean.panels.contains('u2')}"> 
      panel two 
     </h:panelGroup> 
     <h:panelGroup rendered="#{bean.panels.contains('u3')}"> 
      panel three 
     </h:panelGroup> 
    </h:panelGroup> 

    <h:form> 
     <h:selectManyCheckbox value="#{bean.panels}"> 
      <f:selectItem itemValue="u1" /> 
      <f:selectItem itemValue="u2" /> 
      <f:selectItem itemValue="u3" /> 
      <f:ajax render=":panels" /> 
     </h:selectManyCheckbox> 
    </h:form> 
    ... 
</html> 

@ManagedBean 
@RequestScoped 
public class Bean { 

    private List<String> panels; 

    public List<String> getPanels() { 
     return panels; 
    } 

    public void setPanels(List<String> panels) { 
     this.panels = panels; 
    } 

} 

這就是全部。