将JSF dataTable中组件的id设置为数组中当前项的值



我有一个数据表,我想将每一行的id设置为构建表的数组中当前项(具有id字段的对象)的id。

的例子:

<h:dataTable
   value="#{bean.list}"
   var="item">
      <h:column>
         <h:outputText id="#{item.id}" .... />
      </h:column>
</h:dataTable>

这不能工作,因为我得到:javax.servlet.ServletException: Empty id attribute is not allowed .

是不可能这样设置id由于JSF如何构建它的id,还是我做错了什么?

从JSF UI组件,idbinding属性是在视图构建时评估的,当XHTML/JSP文件中的XML树结构被解析并转换为JSF组件树时,FacesContext#getViewRoot()可用。然而,<h:dataTable>在视图呈现期间迭代,即JSF组件树需要通过UIViewRoot#encodeAll()生成HTML代码的时刻。因此,在计算id属性的那一刻,#{item}在EL作用域中无处可用,并计算为null,最终打印一个空字符串。

基本上有3种解决方案:

  1. 使用像JSTL <c:forEach>这样的视图构建时间标签,以便#{item}在视图构建时间期间也可用。

    <table>
        <c:forEach items="#{bean.list}" var="item">
            <tr><td><h:outputText id="#{item.id}" ... />
    

    参见JSF2 Facelets中的JSTL…有道理吗?

  2. 不要把它打印成JSF组件的ID,而是普通HTML元素的ID。

    <span id="#{item.id}">
    

    请注意,根据HTML规范6.2章,以数字开头的id在HTML中是无效的。你可能想用一些字符串作为前缀,像这样:

    <span id="item_#{item.id}">
    
  3. 不要使用动态ID。只需使用固定ID。无论如何,JSF都会根据行索引自动生成一个唯一的ID。

    <h:outputText id="foo" ... />
    

    如果它位于<h:form id="formId"><h:dataTable id="tableId">内,则最终会出现在<span id="formId:tableId:0:foo">中。0是基于0的行索引,每一行递增。这样就保证了在每一行中都有一个唯一的ID,而不需要自己担心。

不能这样在id属性中使用EL。id属性应该在视图构建时可用,但在视图呈现时评估EL。这太迟了,所以当id被选中时,它是空的。

相关内容

  • 没有找到相关文章

最新更新