在 JSF 2.0 中检索其他组件的客户端 ID
Posted
技术标签:
【中文标题】在 JSF 2.0 中检索其他组件的客户端 ID【英文标题】:Retrieving other component's client ID in JSF 2.0 【发布时间】:2012-08-20 22:08:36 【问题描述】:JSF 2.0 是否有用于查找另一个组件的客户端 ID 的内置方法? SO上有大约一千个与客户端ID相关的问题,并且有很多hackish方法可以做到这一点,但我想知道JSF 2.0是否带来了一种我不知道的更简单的方法。
#component.clientId
计算为给定组件自己的客户端 ID,但我想引用另一个组件的 ID。
This 博客文章提到了component.clientId
,它还说#someComponent.clientId
有效,但据我所知,它没有。我相信他是在 JSF 2.0 的任何参考实现出现之前写的,所以他只是通过 JSR,也许功能发生了变化。我不确定。
我知道 PrimeFaces 和 RichFaces 都有自己的函数来返回客户端 ID,但我只是想知道是否有用于此的内置 JSF 2.0 方法。以下是一些示例:
这可以返回 outputText 的 ID。
`<h:outputText value="My client ID : #component.clientId" />`
根据上面的博客文章,这应该有效,但它没有。我只是没有输出。
`<h:button id="sampleButton" value="Sample" />`
`<h:outputText value="sampleButton's client ID : #sampleButton.clientId" />`
这适用于 PrimeFaces:
`<h:outputText value="PrimeFaces : sampleButton's client ID : #p:component('sampleButton')" />`
适用于 RichFaces:
`<h:outputText value="RichFaces : sampleButton's client ID : #rich:clientId('sampleButton')" />`
此外,如果可能的话,我正在寻找在更改 javax.faces.SEPARATOR_CHAR
值或在引用组件之外添加/删除容器时不会中断的解决方案。我花了很多时间来追踪由硬编码 ID 路径引起的问题。
【问题讨论】:
【参考方案1】:您需要在视图范围内通过binding
属性为组件分配一个变量名。
<h:button id="sampleButton" binding="#sampleButton" value="Sample" />
<h:outputText value="sampleButton's client ID : #sampleButton.clientId" />
【讨论】:
太好了。我假设binding
属性专门用于将组件公开给支持bean - 我没有意识到您也可以在范围上发布组件。非常感谢。
我也不知道你能做到这一点!我没有在文档中看到任何关于使用绑定/EL 的引用。这是 JSF 2.x 中的新功能吗? (即它在 1.2 中也可用吗?)
它一直在 JSF/EL 中。它不是特定于 JSF2。另请参阅此相关问题/答案:***.com/questions/8168302/…
没有碰撞或错误/错误绑定的问题吗?我很想拥有 clientId,但如果我冒着在组件上获取错误值的风险......那将是一个杀手
@Toskan:我不确定我是否理解你的担忧。【参考方案2】:
这对我有用。我很想知道写这样的回复是否可以。
client.html
<h:outputText value="#UIHelper.clientId('look-up-address-panel-id')" />
UIHelper.java
@ManagedBean(name = "UIHelper", eager = true)
@ApplicationScoped
public class UIHelper
public String clientId(final String id)
FacesContext context = FacesContext.getCurrentInstance();
UIViewRoot root = context.getViewRoot();
final UIComponent[] found = new UIComponent[1];
root.visitTree(new FullVisitContext(context), new VisitCallback()
@Override
public VisitResult visit(VisitContext context, UIComponent component)
if (component.getId().equals(id))
found[0] = component;
return VisitResult.COMPLETE;
return VisitResult.ACCEPT;
);
return found[0] == null ? "" : "#" + found[0].getClientId().replace(":", "\\\\:");
【讨论】:
【参考方案3】:因为这是我的谷歌搜索的第一批结果之一,我想知道为什么我得到了一个
javax.el.PropertyNotFoundException(找不到属性“itemId”[...])
在尝试接受的解决方案时,我想分享我的 JSF 1.2 解决方案:
UIComponent
的方法getClientId
需要一个FacesContext
参数(参见UIComponent documentation)。所以添加一个绑定到支持 bean 以及另一个返回 clientId 的方法:
xhtml:
<h:button id="sampleButton" binding="#backingBean.sampleButton" value="Sample" />
<h:outputText value="sampleButton's client ID : #backingBean.sampleButtonClientId" />
豆子:
private UIComponent sampleButton;
public UIComponent getSampleButton()
return sampleButton;
public void setSampleButton(final UIComponent sampleButton)
this.sampleButton = sampleButton;
public String getSampleButtonClientId()
final FacesContext context = FacesContext.getCurrentInstance();
return sampleButton.getClientId(context);
请注意,您将组件绑定到的 bean 应该是请求范围的,否则您最终可能会得到 java.lang.IllegalStateException (duplicate Id for a component)
(与 this topic 相比)。
【讨论】:
以上是关于在 JSF 2.0 中检索其他组件的客户端 ID的主要内容,如果未能解决你的问题,请参考以下文章
JSF 2.0 AJAX:使用 jsf.ajax.request(或其他方式)从 javascript 调用 bean 方法