1

我有一个简单的要求:我的列数<tr:table/>是动态的。我将有一个对象列表,someBean.features它将确定渲染的列数。

下图应该阐明我的要求。

具有动态列的表

在给我的代码中,使用了 JSTL<c:forEach/>标记,这在 JSF 环境中使用时显然会产生问题。他们做了这样的事情:

<tr:table value="#{someBean.values}">
    <tr:column headerText="Name">
        <tr:outputText value="#{someBean.name}"/>
    </tr:column>
    <c:forEach var="col" items="#{someBean.features}">
        <tr:column headerText="Column-#{col.id}">
            <tr:outputText value="#{col.name}"/>
        </tr:column>
    </c:forEach>
</tr:table>

但是当我分析上面的代码时,作为上面标签someBean.getValues输入的方法<tr:table/>被调用了数千次而不是大约 20 次。这 - 正如我所想的那样 - 是因为<c:forEach/>标签是一个编译时标签,其中<tr:*/>渲染时间标签也是如此。

所以,这就是我打算做的(替换<c:forEach/><tr:iterator/>

<tr:table value="#{someBean.values}">
    <tr:column headerText="Name">
        <tr:outputText value="#{someBean.name}"/>
    </tr:column>
    <tr:iterator var="col" value="#{someBean.features}">
        <tr:column headerText="Column-#{col.id}">
            <tr:outputText value="#{col.name}"/>
        </tr:column>
    </tr:iterator>
</tr:table>

但是,出于某种原因,<tr:iterator/>它似乎不喜欢被放置在 a 中<tr:table/>并且它永远不会被执行。

任何解决方案、提示、指南将不胜感激。

哦,我们正在使用带有 MyFaces Trinidad 1.0.13 实现的 JSF 1.1。

谢谢。

4

2 回答 2

1

getter 调用是一种特别便宜的操作。如果您的吸气剂按照他们的意图完成他们的工作,只是返回 bean 属性,那么这应该不会造成伤害。

这种担忧给我的印象是,您在 getter 方法而不是构造函数或某些仅在请求时调用一次的事件方法中错误地执行了一些昂贵的业务工作。你真的应该相应地解决这个问题。Getter 不应该做任何商业工作,或者最多只是做一些延迟加载。

至于为什么<c:forEach>有效和<tr:iterator>无效,那是因为 JSTL 标记在视图构建期间运行,而不是在视图呈现期间运行,并且组件的唯一有效子项UIDataUIColumn组件。基本上,当要构建视图时,所有 JSTL 标记都将运行,您最终会得到一个纯 JSF 视图,所有这些都<tr:column>已经在正确的位置。当要呈现视图时,所有 JSF 标记都将运行,您最终会得到一个纯 HTML 结果,然后可以将其发送到浏览器。

也可以看看:

于 2011-06-11T16:32:02.320 回答
1

我认为的唯一方法(您可能已经知道;))是编写扩展UIXTable并提供自定义标记处理程序来处理<tr:columns items="#{columns}">列数组并将其扩展为 html 列

于 2011-07-02T20:27:39.310 回答