使用p元素而不是span来渲染JSF h:message

Kee*_*oer 4 jsf message renderer

我想创建一个自定义消息渲染器,将h:message呈现为'p'html元素而不是'span'元素.它涉及以下消息标记:

<h:message id="firstNameErrorMsg" for="firstname" class="error-msg"  />
Run Code Online (Sandbox Code Playgroud)

我写了下面的代码,但那只是呈现一个空的'p'元素.我想我必须从原始组件中复制所有属性和文本并将其写入编写器.但是,我不知道在哪里可以找到所有内容,而且仅仅更换标签似乎需要做很多工作.

有没有更好的方法来将h:message标记呈现为'p'元素?

码:

@FacesRenderer(componentFamily = "javax.faces.Message", rendererType = "javax.faces.Message")
public class FoutmeldingRenderer extends Renderer {

    @Override
    public void encodeEnd(final FacesContext context, final UIComponent component) throws IOException {

        ResponseWriter writer = context.getResponseWriter();
        writer.startElement("p", component);
        writer.endElement("p");

    }
}
Run Code Online (Sandbox Code Playgroud)

Bal*_*usC 6

这不是"很多工作".它基本上是由标准JSF消息渲染器延伸,其copypasting的物质encodeEnd()由约200条线,然后编辑只有2条线来替换方法"span"通过"p".它可以在不到一分钟的时间内完成.

但是,是的,我同意这是一个简单的丑陋方法.

您可以考虑以下替代方案,这些方案不一定更容易,但至少更干净:

  1. 首先,在这种特定情况下使用a 而不是a 的语义价值是什么?说实话,我没有看到任何语义价值.所以,我建议保持一个.如果唯一的功能要求是让它看起来像a ,那么只需要输入一些CSS.例如<p><span><span><p>

    .error-msg {
        display: block;
        margin: 1em 0;
    }
    
    Run Code Online (Sandbox Code Playgroud)
  2. 您可以直接在EL中获取特定客户端ID的所有消息,如下所示,假设父表单具有ID formId:

    #{facesContext.getMessageList('formId:firstName')}
    
    Run Code Online (Sandbox Code Playgroud)

    因此,要打印第一条消息的摘要和详细信息,只需执行以下操作:

    <c:set var="message" value="#{facesContext.getMessageList('formId:firstName')[0]}" />
    <p title="#{message.detail}">#{message.summary}</p>
    
    Run Code Online (Sandbox Code Playgroud)

    您可以随时将其隐藏到自定义标记文件中,如下所示:

    <my:message id="firstNameErrorMsg" for="firstname" class="error-msg" />
    
    Run Code Online (Sandbox Code Playgroud)
  3. 使用OmniFaces<o:messages>.当var指定属性,那么你可以使用它像一个<ui:repeat>.

    <o:messages for="firstNameErrorMsg" var="message">
        <p title="#{message.detail}">#{message.summary}</p>
    </o:messages>
    
    Run Code Online (Sandbox Code Playgroud)