0

我正在使用 JSF 2.0。

我的h:selectOneMenu页面上有一个包含值列表的值,并且h:inputText在同一页面上有一个值,其required应取决于h:selectOneMenu. 只有特定的一组值应该触发required检查,其他的则不会。

这是我尝试过的:

<h:inputText ... required="#{(selectedPaymentType.value == 'some value') || (selectedPaymentType.value == 'other value')}" />

在上面的代码#{selectedPaymentType}中定义在h:selectOneMenu binding.

还有 3 个像这样的值应该触发required属性到true. 这看起来有点笨拙。有更好的方法吗?

4

3 回答 3

2

如果在您的设计中可能,您可以使用枚举作为您的 PaymentType,其中包括一些接口,如

public interface RequireSomeMoreStuff {
   public boolean required();
}

public enum PaymentType implements RequireSomeMoreStuff {
   FOO { boolean required() { return true; } },
   BAR { boolean required() { return false; } }
}
于 2012-11-21T19:09:56.110 回答
2

Fant 给出了正确方向的提示,即您应该使用具有required属性的枚举,但似乎您并不完全确定如何正确实现它。诚然,范特的回答不够详尽。所以这里有一个更详细的答案。

基本上,您需要用如下所示的枚举替换所有下拉值:

public enum PaymentType {
    FOO("Some label for foo", true),
    BAR("Some label for bar", false),
    BAZ("Some label for baz", true);

    private String label;
    private boolean required;

    private PaymentType(String label, boolean required) {
        this.label = label; 
        this.required = required;
    }

    public String getLabel() { 
        return label;
    }

    public boolean isRequired() {
        return required;
    }
}

并按如下方式使用

<h:selectOneMenu binding="#{selectedPaymentType}" value="#{bean.selectedPaymentType}">
    <f:selectItems value="#{bean.availablePaymentTypes}" var="paymentType"
        itemValue="#{paymentType}" itemLabel="#{paymentType.label}" />
</h:selectOneMenu>
<h:inputText ... required="#{selectedPaymentType.value.required}" />

private PaymentType selectedPaymentType; // +getter+setter

public PaymentType[] getAvailablePaymentTypes() { 
    return PaymentType.values();
}

(或者,如果您使用的是 OmniFaces,请使用<o:importConstants>,那么您不需要这样的 getter <f:selectItems>;不,您在任何情况下都不需要转换器,JSF/EL 已经内置了枚举转换)

看,这个required属性现在已经被简化了很多,因为它已经在与所选值关联的模型中定义了。

于 2012-11-22T11:55:33.773 回答
-2

仅当您选择了某些值时,我才会使用a4j它来呈现 inputText selectOneMenu

<h:selectOneMenu value="#{MyBean.selectedValue}">
    <f:selectItems value="#{MyBean.listOfValues}" />
    <a4j:support event="onchange" reRender="requiredText" ajaxSingle="true"/>
</h:selectOneMenu>

<a4j:outputPanel id="requiredText">
    <h:inputText value="#{MyBean.inputValue}" rendered="#{(MyBean.selectedValue == value_1) || (MyBean.selectedValue == value_2) || ...}" />
</a4j:outputPanel>

为了避免 inputText 的rendered参数上出现大字符串,我建议您创建一个执行以下条件的布尔函数:rendered="#{MyBean.inputTextIsRendered}.

客户端解决方案

还有一个基于验证器的解决方案。这是我的方法:

  • JSF 代码

上面的selectOneMenu代码使用binding标签将在 中选择的值selectOneMenu与一个属性绑定,该属性将在验证器方法中检索,为inputText组件声明。

  • 验证器类

然后,您需要创建CheckInputValue验证器类。

public class CheckInputValue implements Validator {
    public CheckInputValue() {}

    public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException {

        //We retrieve thei binded value:
        UIInput confirmComponent = (UIInput) component.getAttributes().get("selectedValue");
        String theValue = confirmComponent.getSubmittedValue();

        //Here you check the retrieved value with the list of values that makes your inputText required.
        //In these cases you will chech the inputText is not empty and, if so, you return a ValidatorException:
        if(isEmpty){
            FacesMessage message = new FacesMessage();
            message.setDetail("inputText cannot be empty");
            message.setSummary("inputText cannot be empty");
            message.setSeverity(FacesMessage.SEVERITY_ERROR);
            throw new ValidatorException(message);
        }
    }
}
  • 面孔-config.xml

最后,您必须在以下位置声明您的验证器类faces-config.xml

<validator>
    <validator-id>CheckInputValue</validator-id>
    <validator-class>myPackage.myValidations.CheckInputValue</validator-class>
</validator>
于 2012-11-22T08:40:18.843 回答