JSF延迟加载组件值



考虑一个简单的h:outputText组件:

<h:outputText value="#{myBean.myValue}"/>

我怎么能在页面被渲染后延迟加载该值,并显示自定义的"ajax加载"图标而不是值,而这是这样做的?

我在我的项目中使用PrimeFaces 3.5,因此任何特定于pf的实现都将受到欢迎。

建议在页面加载后调用remoteCommand(通过将autoRun属性设置为true来完成)并更新您的outputText

private String myValue;
// getter and setter
public void initMyValue() {
  // init myValue
}

在页面上,您应该有ajaxStatus组件用于查看加载图像,以及outputText。还有p:remoteCommand组件:

<p:ajaxStatus style="width:16px;height:16px;" id="ajaxStatusPanel">  
  <f:facet name="start">  
    <h:graphicImage value="ajaxloading.gif" />  
  </f:facet>
  <f:facet name="complete">  
    <h:outputText value="" />
  </f:facet>  
</p:ajaxStatus>
<h:outputText id="myText" value="#{myBean.myValue}"/>
<p:remoteCommand autoRun="true" actionListener="#{myBean.initMyValue}" update="myText"/>

EDIT:我认为你想延迟加载outputText的值,因为它包含一些长时间运行的计算,但是如果你想完全延迟outputText的渲染,首先在你的后台bean中添加boolean属性,并在initMyValue方法结束时将此属性设置为true:

private boolean loaded;
// getter and setter
public void initMyValue() {
  // init myValue
  loaded = true;
}

将其重新组织如下:

<h:panelGroup id="myPanel" layout="block">
  <h:graphicImage value="ajaxloading.gif" rendered="#{!myBean.loaded}"/>
  <h:outputText value="#{myBean.myValue}" rendered="#{myBean.loaded}"/>
</h:panelGroup>
<p:remoteCommand autoRun="true" actionListener="#{myBean.initMyValue}" update="myPanel"/>

可以使用BlockUI在组件加载时有条件地阻塞它。

  1. <h:outputText/>上定义preRenderComponent事件

       <h:outputText id="myText">
          <f:event name="preRenderComponent" id="started"/>
       </h:outputText>
    
  2. 定义一个带有事件id的<p:blockUI/>作为触发器

       <p:blockUI block="myText" trigger="started" />
    

您可以自定义块来显示图像或其他内容。

一个警告:我假设你需要这个,因为你在该组件的getter中做了一些繁重的工作。要知道,在该页的生命周期中,getter将被调用几次。因此,隐瞒手术花费很长时间的事实并不能改变事实。更好的设计是在持久作用域中预加载并缓存该组件的值,而不是像"加载"抽动器那样引人注意。

我最终是这样实现的:

<h:panelGroup id="loginLocation">
<p:graphicImage library="assets" name="small-kit-loader.gif" width="16" height="16" rendered="#{empty mybean.lastLoginLocation}"></p:graphicImage> 
<h:outputText value="#{myBean.lastLoginLocation}" rendered="#{!empty myBean.lastLoginLocation}"/>
</h:panelGroup>
<p:remoteCommand global="false" actionListener="#{actionBean.getUserLoginLocation(myBean.selectedUser)}" name="refreshLoginLocation" id="rc1" autoRun="true" update="loginLocation" process="@this"></p:remoteCommand>

我个人对这个实现不是很满意:

  1. 延迟加载状态存储在服务器端,而不是应该存储在客户端
  2. 我必须在我的支持bean (getUserLoginLocation)上实现单独的方法来检索值,并显式地将其存储在另一个属性(lastLoginLocation)中。如果在浏览器
  3. 中渲染页面后使用一个getter惰性调用,会简洁得多。
  4. 不容易重用-取决于后台bean 'loaded'标志(#{empty myBean。lastLoginLocation}),并且需要操作监听器来实际设置该值。任何基于这种方法的组合组件也将依赖于后台bean中的特定代码。

欢迎任何关于如何改进此代码的建议!:)

相关内容

  • 没有找到相关文章

最新更新