2012-10-10 24 views
0

我有一个包含多个组件的窗体,其中一些窗体有自己的验证和/或是必需的。然后,我也有几个selectOneMenu组件在其列表中具有相同的三个selectItem元素。我已经定义了三个commandButton,以便为所有列表(每个可能值一个commandButton)选择相同的值。JSF - 验证前从视图更新模型值

的JSF部

<table> 
    <tr> 
     <td> 
      <h:outputText value="ID:" /> 
     </td> 
     <td> 
      <h:inputText value="#{MyClass.id}" id="inTxt_id" required="true"> 
       <f:validator validatorId="CheckIDPattern" /> 
      </h:inpuText> 
      <h:message for="inTxt_id" errorClass="error" /> 
     </td> 
    </tr> 
</table> 
<table> 
    <tr> 
     <td> 
      <h:commandButton value="Select all opt1" action="#{MyClass.selectOpt1}" /> 
      <h:commandButton value="Select all opt2" action="#{MyClass.selectOpt2}" /> 
      <h:commandButton value="Select all opt3" action="#{MyClass.selectOpt3}" /> 
     </td> 
    </tr> 
    <tr> 
     <td> 
      <h:outputText value="List 1:" /> 
     </td> 
     <td> 
      <h:selectOneMenu value="#{MyClass.list1Val}"> 
       <f:selectItems value="#{MyClass.listOfOptions}" /> 
      </h:selectOneMenu> 
     </td> 
    <tr> 
     <td> 
      <h:outputText value="List 2:" /> 
     </td> 
     <td> 
      <h:selectOneMenu value="#{MyClass.list2Val}"> 
       <f:selectItems value="#{MyClass.listOfOptions}" /> 
      </h:selectOneMenu> 
     </td> 
    </tr> 
    <tr> 
     //Many other selectOneMenu components... 
    </tr> 
</table> 
<h:commandButton action="#{MyClass.saveLists}" value="Submit" /> 

MyClass.java

public String selectOpt1(){ 
    this.list1Val = 1; 
    this.list2Val = 1; 
    //... 
    return ""; 
} 

//The same idea for selectOpt2 and selectOpt3. 

在这种情况下,如果我的用户按下的我的 “全选” 按钮一个没有填充所述ID inputText,它收到错误信息,但我不想要它,因为我想他们还没有完成填写表单。我只想在用户按下“保存列表”按钮时执行验证。

我试着将immediate="true"添加到我的“全选”按钮中,它可以工作,但它不会更新模型中的视图,然后用户看不到值已经更改...所以它确实没有工作。

我想达到什么目的?我只想在最后一个按钮(提交)时执行验证。所以我的用户可以使用这些“全选”按钮,而不必填写以前的强制性组件。

我希望你能理解我的背景。随意要求澄清。 在此先感谢。

回答

2

如果您使用@ViewScoped豆你可以做以下修改:

首先改变你的selectOpt1法键入void

public void selectOpt1() 
{ 
    this.list1Val = 1; 
    this.list2Val = 1; 
    //... 
} 

举一个id您要在选择更新组件项目。我假设列表1在这种情况下:

<h:selectOneMenu id="list1" value="#{MyClass.list1Val}"> 
    //... 
</h:selectOneMenu> 

而在你的按钮,添加一个f:ajax标记,部分只提交该组件进行处理:

<h:commandButton value="Select all opt1" action="#{MyClass.selectOpt1}"> 
    <f:ajax execute="@this" render="list1" /> 
</h:commandButton> 

如果您打算更新多个组件,您可能添加他们的ID由空格分隔:

<f:ajax execute="@this" render="list1 list2" /> 

我希望它有帮助。

编辑

嗯,对不起,我没有注意到你正在使用JSF 1.x的在这种情况下,它不会工作。

虽然您可以使用库如RichFaces添加ajax功能。请看看这些主题:

RichFaces的

至于你提到你使用RichFaces的,你可以在f:ajax标签切换到a4j:support

<h:commandButton value="Select all opt1" action="#{MyClass.selectOpt1}"> 
    <a4j:support event="onclick" reRender=":list1" ajaxSingle="true" /> 
</h:commandButton> 

或者这样使用a4j:commandButton

<a4j:commandButton value="Select all opt1" reRender=":list1" ajaxSingle="true" /> 

有关此行为的更多信息,请看一看this

问候。

+0

嗯...这个bean会话范围,但我正在** JSF 1.2 **(因为某些原因我已经无法迁移到JSF 2.0 :()。可这是解决方案适合我的JSF版本?谢谢! – jmrodrigg

+0

好吧,这对JSF 1.x不起作用。一种选择是使用像RichFaces这样的库,因为这增加了ajax功能。我在过去使用它,它是一种易于入门查看我的编辑 – rbento

+0

感谢您的回答,它肯定是我的错,我没有详细说明我使用的是什么技术,是的,我也使用RichFaces,我使用'a4j:support',但是我不能正确地解决问题,谢谢你的相关话题,我会研究它 – jmrodrigg

0

考虑到本笃的建议,我真正想让它工作的唯一方法就是使用AJAX a4j

我已经在我的代码引入的变化是:

  1. 更换h:commandButton“全选”按钮与a4j:commandButton
  2. Define id标签为我的h:selectOneMenu组件,所以我可以reRender组件通过以前定义的a4j:commandButton

JSF原来的页面已被修改如下:

(...) 
<table> 
    <tr> 
     <td> 
      <a4j:commandButton value="Select all opt1" action="#{MyClass.selectOpt1}" 
       reRender="list1,list2,(...)" ajaxSingle="true" /> 
      <a4j:commandButton value="Select all opt2" action="#{MyClass.selectOpt2}" 
       reRender="list1,list2,(...)" ajaxSingle="true" /> 
      <a4j:commandButton value="Select all opt3" action="#{MyClass.selectOpt3}" 
       reRender="list1,list2,(...)" ajaxSingle="true" /> 
     </td> 
    </tr> 
    <tr> 
     <td> 
      <h:outputText value="List 1:" /> 
     </td> 
     <td> 
      <h:selectOneMenu value="#{MyClass.list1Val}" id="list1"> 
       <f:selectItems value="#{MyClass.listOfOptions}" /> 
      </h:selectOneMenu> 
     </td> 
    </tr> 
    <tr> 
     <td> 
      <h:outputText value="List 2:" /> 
     </td> 
     <td> 
      <h:selectOneMenu value="#{MyClass.list2Val}" id="list2"> 
       <f:selectItems value="#{MyClass.listOfOptions}" /> 
      </h:selectOneMenu> 
     </td> 
    </tr> 
(...) 

非常感谢盒饭您的意见!

2

只要让required属性取决于按下按钮。

<h:form id="form"> 
    <c:set var="saveButtonPressed" value="#{not empty param['form:save']}" /> 
    ... 
    <h:inputText ... required="#{saveButtonPressed}" /> 
    ... 
    <h:commandButton id="save" ... /> 
</h:form> 
+0

谢谢你采用这种不同的方法。我不知道这是可能的。虽然'a4j:commandButton'更适合我的目的,很高兴知道不同的解决方案。谢谢! – jmrodrigg

+0

不客气。 – BalusC

+0

@BususC THX很多次!我花了数小时寻找这样的解决方案! – ProgrammingIsAwsome