【发布时间】:2015-11-14 19:45:51
【问题描述】:
为了支持我们组织的组件库,我想创建一个增强的 selectManyMenu。一个要求是它类似于具有下拉菜单的类型,其菜单项具有显示它们是否被选中的复选框。最重要的是,我想要下拉列表的第一行,该区域始终可见以显示“气泡”,因为缺少更好的术语,包含所选项目的标签以及“X”按钮删除每一个,类似于“标签”小部件。
我想创建一个 JSF 自定义组件,而不是用一些 jQuery 插件来装饰现有的 <h:selectManyMenu>,该插件隐藏它并使用一堆我不知道它是如何工作的混淆 javascript 呈现它自己的小部件。老实说,我发现没有一个非常适合我们的 UI,而且从根本上说,当 JSF 具有如此强大的自定义组件功能时,我不觉得这是对 JSF 的良好使用,在一些 jQuery 小部件中添加.
为了解决我当前的问题,我设置了一个自定义组件类,它扩展了UIInput,并提供了encode*() 方法来呈现带有<option> 标记的<select>,与<h:selectManyMenu> 相同。 decode() 方法有问题:
@Override
public void decode(FacesContext context) {
Map<String, String> requestParams = context.getExternalContext().getRequestParameterMap();
String clientId = getClientId();
Object param = requestParams.get(clientId);
LOG.debug("param: {}", param);
}
问题是param 无论我选择了多少项目,最终都是一个字符串。我已经在前端验证了当我使用 <h:selectManyMenu> 时发送的 POST 请求完全相同,所以我猜我必须在 decode() 中对请求中的所有值做一些不同的事情。
对于加分,任何人都可以指出我对源代码的一些简明解释,例如<h:inputText>。我可以浏览我们正在使用的 JSF 实现的源代码 Mojarra,但它非常难以理解,因为它使用单独的渲染器,以及各种工厂和东西来选择要使用的渲染器等等。我已经得到了到目前为止,我们依靠复合组件,必要时使用支持组件,但我认为这个和其他一些即将推出的组件超出了复合组件可以有效使用的范围。
另外,这是实现我所追求的最佳方法吗?为现有的<h:selectManyMenu> 创建一个自定义渲染器会更好吗?这似乎是一个更优雅的解决方案,因为这个组件基本上是一个 selectManyMenu,只是呈现方式略有不同,前端有一些 javascript。
【问题讨论】: