2014-12-11 1 views
2

키 업 이벤트에 의해 트리거되는 백킹 빈 메서드의 결과를 기반으로 요소를 표시하거나 숨기는 페이지를 구현하려고합니다. 입력. 필자가 작성한 내용은 예기치 않게 작동합니다. 즉, 내 panelGroup 내부의 내용은 페이지로드 후에 전혀 변경되지 않고 대신 내 outputText 요소에 표시 될 것으로 예상되는 내용이 포함 된 페이지 상단에 와일드 스팬이 표시됩니다. 이것은 JSF 1.2 및 richfaces 3.3에서 실행되는 레거시 응용 프로그램이므로이 기능을 사용하지 못할 수도 있습니다 (here). 또한 테이블 사용에 대해 사과하지만 불행히도 CSS/div로 적절한 레이아웃을 사용하도록이 오래된 앱을 리팩터링하는 것은이 기능 요청의 범위를 벗어납니다.RichFaces를 사용하여 AJAX라는 백킹 빈 메서드를 통해 페이지 요소를 동적으로 표시/숨기기

다음은 문제를 설명하는 예제 jstl 템플릿입니다. "string1/2 reversed"출력 패널은 문자열 길이가 5보다 큰 경우에만 표시해야하며 input을 입력하는 동안 outputText 요소의 텍스트를 업데이트해야합니다. 대신에 outputPanels은 정적으로 유지되고 테이블 위에 새로운 범위가 작성됩니다.

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml" 
     xmlns:ui="http://java.sun.com/jsf/facelets" 
     xmlns:h="http://java.sun.com/jsf/html" 
     xmlns:c="http://java.sun.com/jstl/core" 
     xmlns:f="http://java.sun.com/jsf/core" 
     xmlns:a4j="http://richfaces.org/a4j" 
     xmlns:rich="http://richfaces.org/rich"> 
    <head> 
     <title>ajax test</title> 
    </head> 
    <body> 
     <h:panelGroup id="wrapper"> 
      <a4j:keepAlive beanName="AjaxTestBacking" /> 
      <p /> 
      <h:form> 
       <table> 
        <tr> 
         <td >string1:</td> 
         <td> 
          <h:inputText style="width: 200px" value="#{AjaxTestBacking.string1}"> 
           <a4j:support event="onkeyup" action="#{AjaxTestBacking.updateString1}" reRender="string1panel"/> 
          </h:inputText> 
         </td> 
        </tr> 
        <h:panelGroup id="string1panel" rendered="#{AjaxTestBacking.displayString1Xform}"> 
         <tr> 
          <td>string1 reversed:</td> 
          <td> 
           <h:outputText style="width: 200px" value="#{AjaxTestBacking.string1Xform}" /> 
          </td> 
         </tr> 
        </h:panelGroup>     
        <tr> 
         <td>string2:</td> 
         <td> 
          <h:inputText style="width: 200px" value="#{AjaxTestBacking.string2}"> 
           <a4j:support event="onkeyup" action="#{AjaxTestBacking.updateString2}" reRender="string2panel"/> 
          </h:inputText> 
         </td> 
        </tr> 
        <h:panelGroup id="string2panel" rendered="#{AjaxTestBacking.displayString2Xform}"> 
         <tr> 
          <td>string2 reversed:</td> 
          <td > 
           <h:outputText style="width: 200px" value="#{AjaxTestBacking.string2Xform}" /> 
          </td> 
         </tr> 
        </h:panelGroup> 
       </table> 
      </h:form> 
     </h:panelGroup> 
    </body> 
</html> 

및 백업 콩 :

import java.io.Serializable; 

@SuppressWarnings("serial") 
public class AjaxTestManager extends AbstractManager implements Serializable { 

    private String string1; 
    private String string2; 

    private String string1Xform; 
    private String string2Xform; 

    private Boolean displayString1Xform; 
    private Boolean displayString2Xform; 

    public AjaxTestManager() { 
     string1 = "test string 1"; 
     string2 = "test string 2"; 
     updateString1(); 
     updateString2(); 
    } 

    public void updateString1() { 
     string1Xform = new StringBuilder(string1).reverse().toString(); 
     displayString1Xform =string1Xform.length() > 5 ? true : false; 
    } 

    public void updateString2() { 
     string2Xform = new StringBuilder(string2).reverse().toString(); 
     displayString2Xform = string2Xform.length() > 5 ? true : false; 
    } 

    public String getString1() { 
     return string1; 
    } 

    public void setString1(String string1) { 
     this.string1 = string1; 
    } 

    public String getString2() { 
     return string2; 
    } 

    public void setString2(String string2) { 
     this.string2 = string2; 
    } 

    public String getString1Xform() { 
     return string1Xform; 
    } 

    public void setString1Xform(String string1Xform) { 
     this.string1Xform = string1Xform; 
    } 

    public String getString2Xform() { 
     return string2Xform; 
    } 

    public void setString2Xform(String string2Xform) { 
     this.string2Xform = string2Xform; 
    } 


    public Boolean getDisplayString1Xform() { 
     return displayString1Xform; 
    } 


    public void setDisplayString1Xform(Boolean displayString1Xform) { 
     this.displayString1Xform = displayString1Xform; 
    } 


    public Boolean getDisplayString2Xform() { 
     return displayString2Xform; 
    } 


    public void setDisplayString2Xform(Boolean displayString2Xform) { 
     this.displayString2Xform = displayString2Xform; 
    } 

} 

여기 richfaces에 대해 근본적으로 오해 뭔가를 해요 만약 내가 사과 - 내가 richfaces 아약스, 그래서 나와 함께 곰하시기 바랍니다 멍청한 놈의 다소 해요! 나는이 코드를 내 동료와 공유했는데, 그는이 앱을 만든 사람이기도하다. 저는 Google에서 검색 한 결과 자바 스크립트 기반 답변을 찾았지만 richfaces 구성 요소를 사용하여이를 수행하는 방법을 이해하려고합니다. 기타 질문 : '렌더링 된'속성은 페이지의 일부분을 동적으로 표시/숨기기로 이동하는 방법입니까, 아니면 '표시'속성을 사용해야합니까? 또한 a4j에 대한 'reRender'속성은 : 원래 이해했던 요소의 jsf/'서버 측'ID이거나 here으로 표시된 클라이언트 측 요소 ID입니다. 그냥 내가 잘못 이해하고 있는지, JSF/richfaces 버전으로 제한되었거나 일반적으로 미친 짓인지 알아 내려고 노력했다. :)

답변

0

JSF 2.1과 비슷한 동작을 보았습니다. 요소에 렌더링 된 태그가 있고 ajax를 통해 요소를 표시하거나 숨길 계획 인 경우 다른 명명 컨테이너로 래핑하고 대신 부모 컨테이너를 다시 렌더링해야합니다. 이런 식으로 뭔가가 panelGroup 여기에 범위를 렌더링 및 스팬은 TR 태그 사이에 존재 할 수 없기 때문에 결과가 법적 HTML 아니라고

    <tr> 
        <td >string1:</td> 
        <td> 
         <h:inputText style="width: 200px" value="#{AjaxTestBacking.string1}"> 
          <a4j:support event="onkeyup" action="#{AjaxTestBacking.updateString1}" reRender="string1panelLabel,string1panelValue"/> 
         </h:inputText> 
        </td> 
       </tr> 
        <tr> 
         <td>      
          <h:panelGroup id="string1panelLabel"> 
          <h:panelGroup rendered="#{AjaxTestBacking.displayString1Xform}"> 
           string1 reversed: 
          </h:panelGroup> 
          </h:panelGroup>           
         </td> 
         <td> 
          <h:panelGroup id="string1panelValue"> 
          <h:panelGroup rendered="#{AjaxTestBacking.displayString1Xform}"> 
           <h:outputText style="width: 200px" value="#{AjaxTestBacking.string1Xform}" /> 
          </h:panelGroup> 
          </h:panelGroup>                   
         </td> 
        </tr> 

       <tr> 

주의 할 것. 대신 panelGroup은 테이블의 td 태그 내에 있어야합니다. 따라서 문제를 해결하기 위해 두 세트의 중첩 된 panelGroup을 가져야합니다. 또는 html을 생성하는 h : panelGrid로 html 테이블을 대체 할 수 있지만 JSF보다 친숙합니다.

사이드 노트에서 JSF 2.1에서 ui : fragment를 사용합니다. 왜냐하면 화면의 해당 부분을 panelGroup보다 더 분명히 표시하거나 숨길 의도가 있기 때문입니다.

+0

감사합니다. 이것이 표시/숨기기가 아닌 범위의 문제를 해결했습니다! 진행! 이제 패널 그룹이 인라인 대신 테이블 위의 스팬으로 표시되는 이유를 알아야합니다. – camobrite

+0

... 앱이 HTML 규칙을 위반하기 때문입니다. panelGroup은 span 또는 div로 렌더링 할 수 있습니다. 이 태그들 중 어느 것도 (tr 태그 사이에있는) 합법적이지 않습니다. panelGroup은 td 내부에 있어야합니다. 내 대답을 업데이트 할게. –

+0

감사합니다.이 대답 인 것 같습니다. 당신은 div 또는 span inbetween tr 태그를 가질 수없고 tr 요소에 대한 jsf 태그가 없습니다 - 전체 테이블을 jsf 방식으로 또는 전혀하지 않아도되는 것 같습니다 (내 디자인에 잘못된 디자인을 방지하기 위해). 나는 ui : fragment로 대체를 시도했지만 ajax를 인식하지 못하고 (다시 렌더링 할 DOM 요소가 없음) 레이아웃 <= none "을 사용하여 에 행을 래핑하지 않았습니다. 어느 쪽이든 일하다.진짜 대답은 폼을 '표 생략'하는 것인데, 을 사용하여 다시 돌아갈 수 있습니다. – camobrite

관련 문제