2

我有两个大问题!

我正在尝试制作一个简单的 JSF 组件来扩展 h:outputText 的功能。

我已经尝试按照本指南进行操作,但不知何故我做对了一些事情。

我可以成功导入我的 taglib,一切似乎都很好,但是当我使用它时,我得到了这个异常:

javax.servlet.ServletException:表达式错误:命名对象:找不到 EmoticonOutputTextTag。

我能做些什么来解决这个问题?

我附上所有的代码。

由于这与我附加的代码有关,我该如何启用ValueExpressioninputText属性?Oracle 的指南没有帮助:/

META-INF/EmoticonOutputText.tld

<?xml version="1.0" encoding="UTF-8"?>
<taglib version="2.1" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-jsptaglibrary_2_1.xsd">
  <tlib-version>1.0</tlib-version>
  <short-name>eot</short-name>
  <uri>com.unilife.emoticonOutputText</uri>
  <tag>
    <name>EmoticonOutputText</name>
    <tag-class>com.unilife.emoticonOutputText.EmoticonOutputTextTag</tag-class>
    <body-content>scriptless</body-content>
    <attribute>
      <name>style</name>
      <rtexprvalue>true</rtexprvalue>
      <type>java.lang.String</type>
    </attribute>
    <attribute>
      <name>styleClass</name>
      <rtexprvalue>true</rtexprvalue>
      <type>java.lang.String</type>
    </attribute>
    <attribute>
      <name>inputText</name>
      <required>true</required>
      <rtexprvalue>true</rtexprvalue>
      <type>java.lang.String</type>
    </attribute>
  </tag>
</taglib>

/META-INF/faces-config.xml

    <?xml version='1.0' encoding='UTF-8'?>
<faces-config version="1.2" 
                xmlns="http://java.sun.com/xml/ns/javaee" 
                xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
                xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
         http://java.sun.com/xml/ns/javaee/web-facesconfig_1_2.xsd">
    <component>
        <component-type>
            com.unilife.emoticonoutputtext
        </component-type>
        <component-class>
            com.unilife.emoticonOutputText.EmoticonOutputText
        </component-class>
    </component>

    <render-kit>
        <renderer>
            <description>
                OutputText che permette il rendering di emoticons al posto delle combinazioni di tasti
            </description>
            <component-family>
                javax.faces.Output
            </component-family>
            <renderer-type>
                com.unilife.emoticonoutputtext
            </renderer-type>
            <renderer-class>
                com.unilife.emoticonOutputText.EmoticonOutputTextRenderer
            </renderer-class>
        </renderer>
    </render-kit>  
</faces-config>

/META-INF/unilife.taglib.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE facelet-taglib PUBLIC
"-//Sun Microsystems, Inc.//DTD Facelet Taglib 1.0//EN"
"http://java.sun.com/dtd/facelet-taglib_1_0.dtd">
<facelet-taglib>
    <namespace>http://unilife.it/tags</namespace>
    <tag>
        <tag-name>EmoticonOutputText</tag-name>
        <description>
            OutputText con la possibilità di mostrare Emoticons
        </description>
        <component>
            <component-type>EmoticonOutputTextTag</component-type>
            <renderer-type>EmoticonOutputTextRenderer</renderer-type>
        </component>
        <attribute>
            <name>style</name>            
            <type>java.lang.String</type>
        </attribute>
        <attribute>
            <name>styleClass</name>            
            <type>java.lang.String</type>
        </attribute>
        <attribute>
            <name>inputText</name>
            <required>true</required>            
            <type>java.lang.String</type>
        </attribute>
    </tag>
</facelet-taglib>

com.unilife.emoticonOutputText/EmoticonOutputText.java

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.unilife.emoticonOutputText;

import javax.faces.component.UIOutput;

/**
 *
 * @author stefano
 */
public class EmoticonOutputText extends UIOutput {

    private static final String COMP_FAMILY = "javax.faces.Output";

    /**
     * Get the value of COMPONENT_FAMILY
     *
     * @return the value of COMPONENT_FAMILY
     */
    @Override
    public String getFamily() {
        return COMP_FAMILY;
    }

    private static final String RENDERER_TYPE = "com.unilife.emoticonoutputtext";

    /**
     * Get the value of RENDERER_TYPE
     *
     * @return the value of RENDERER_TYPE
     */
    @Override
    public String getRendererType() {
        return RENDERER_TYPE;
    }


    private String style;

    /**
     * Get the value of style
     *
     * @return the value of style
     */
    public String getStyle() {
        return style;
    }

    /**
     * Set the value of style
     *
     * @param style new value of style
     */
    public void setStyle(String style) {
        this.style = style;
    }
    private String styleClass;

    /**
     * Get the value of styleClass
     *
     * @return the value of styleClass
     */
    public String getStyleClass() {
        return styleClass;
    }

    /**
     * Set the value of styleClass
     *
     * @param styleClass new value of styleClass
     */
    public void setStyleClass(String styleClass) {
        this.styleClass = styleClass;
    }
    private String inputText;

    /**
     * Get the value of inputText
     *
     * @return the value of inputText
     */
    public String getInputText() {
        return inputText;
    }

    /**
     * Set the value of inputText
     *
     * @param inputText new value of inputText
     */
    public void setInputText(String inputText) {
        this.inputText = inputText;
    }
}

com.unilife.emoticonOutputText/EmoticonOutputTextRenderer.java

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.unilife.emoticonOutputText;

import java.io.IOException;
import java.util.HashMap;
import javax.faces.component.UIComponent;
import javax.faces.context.FacesContext;
import javax.faces.context.ResponseWriter;
import javax.faces.render.Renderer;
import javax.servlet.ServletContext;

/**
 *
 * @author stefano
 */
public class EmoticonOutputTextRenderer extends Renderer {

    //Contiene la corrispondenza tra la stringa da sostituire e il nome dell'emoticon
    private static final HashMap<String, String> emoticons = new HashMap<>();
    //Contiene il percorso dei files delle emoticon
    private final String basePath = ((ServletContext) (FacesContext.getCurrentInstance().getExternalContext().getContext())).getContextPath() + "/resources/images/emoticons/";

    public EmoticonOutputTextRenderer() {
        parseEmoticons();
    }

    private void parseEmoticons(){
        emoticons.put(":)", basePath + "smile");
        emoticons.put(":-)", basePath + "smile");
        emoticons.put("=)", basePath + "smile");
        emoticons.put(":(", basePath + "frown");
        emoticons.put(":-(", basePath + "frown");
        emoticons.put("=(", basePath + "frown");
        emoticons.put(":p", basePath + "tongue");
        emoticons.put(":-p", basePath + "tongue");
        emoticons.put("=p", basePath + "tongue");
        emoticons.put(":D", basePath + "grin");
        emoticons.put(":-D", basePath + "grin");
        emoticons.put("=D", basePath + "grin");
        emoticons.put(":o", basePath + "gasp");
        emoticons.put(":-o", basePath + "gasp");
        emoticons.put(";)", basePath + "wink");
        emoticons.put(";-)", basePath + "wink");
        emoticons.put("8)", basePath + "glasses");
        emoticons.put("8-)", basePath + "glasses");
        emoticons.put("8|", basePath + "sunglasses");
        emoticons.put("8-|", basePath + "glasses");
        emoticons.put(">:(", basePath + "grumpy");
        emoticons.put(">:-(", basePath + "grumpy");
        emoticons.put(":\\", basePath + "unsure");
        emoticons.put(":-\\", basePath + "unsure");
        emoticons.put(":/", basePath + "unsure");
        emoticons.put(":-/", basePath + "unsure");
        emoticons.put(":'(", basePath + "cry");
        emoticons.put("3:)", basePath + "devil");
        emoticons.put("3-:)", basePath + "devil");
        emoticons.put("O:)", basePath + "angel");
        emoticons.put("O-:)", basePath + "angel");
        emoticons.put(":*", basePath + "kiss");
        emoticons.put(":-*", basePath + "kiss");
        emoticons.put("<3", basePath + "heart");
        emoticons.put("^_^", basePath + "kiki");
        emoticons.put("-_-", basePath + "squint");
        emoticons.put("o.O", basePath + "confused");
        emoticons.put("O.o", basePath + "confused");
        emoticons.put(">:O", basePath + "upset");
        emoticons.put(">:-O", basePath + "upset");
        emoticons.put(":v", basePath + "pacman");
        emoticons.put(":3", basePath + "colonthree");
    }

    @Override
    public void encodeBegin(FacesContext context, UIComponent component) throws IOException {
        EmoticonOutputText eot = (EmoticonOutputText) component;
        ResponseWriter writer = context.getResponseWriter();
        //Aggiungiamo l'eventuale stile CSS o direttamente la classe
        writer.startElement("span", null);
        if(eot.getStyle()!=null && !eot.getStyle().isEmpty()){
            writer.writeAttribute("style", eot.getStyle(), null);
        }
        if(eot.getStyleClass()!=null && !eot.getStyleClass().isEmpty()){
            writer.writeAttribute("class", eot.getStyleClass(), null);
        }
        //Andiamo ad effettuare il parse vero e proprio, sostituendo le emoticons come le immagini
        for(String str : eot.getInputText().split(" ")){
            if(emoticons.containsKey(str)){ //Se riconosco l'emoticon allora scrivo l'immagine
                writer.startElement("img", null);
                writer.writeAttribute("src", emoticons.get(str) + ".gif", null);
                writer.endElement("img");
                writer.writeText(" ", null);
            } else { //Altrimenti aggiungo semplicemente la parola
                writer.writeText(str + " ", null);
            }
        }
    }
}

com.unilife.emoticonOutputText/EmoticonOutputTextTag.java

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.unilife.emoticonOutputText;

import javax.faces.component.UIComponent;
import javax.faces.webapp.UIComponentELTag;

/**
 *
 * @author stefano
 */
public class EmoticonOutputTextTag extends UIComponentELTag {

    private static final String COMP_TYPE = "com.unilife.emoticonoutputtext";
    private static final String RENDERER_TYPE = "com.unilife.emoticonoutputtext";
    private String style;
    private String styleClass;
    private String inputText;

    public void setStyle(String style) {
        this.style = style;
    }

    public void setStyleClass(String styleClass) {
        this.styleClass = styleClass;
    }

    public void setInputText(String inputText) {
        this.inputText = inputText;
    }

    @Override
    public String getComponentType() {
        return COMP_TYPE;
    }

    @Override
    public String getRendererType() {
        return RENDERER_TYPE;
    }

    @Override
    protected void setProperties(UIComponent component) {
        super.setProperties(component);
        EmoticonOutputText eot = (EmoticonOutputText)component;
        if(style != null){
            eot.setStyle(style);
        }
        if(styleClass != null){
            eot.setStyleClass(styleClass);
        }
        if(inputText != null){
            eot.setInputText(inputText);
        }
    }
}

如您所见,代码非常简单(实际上我什至不知道我错在哪里,因为我无法测试它,这是我第一次使用自定义组件!)

有没有人可以帮助我?

4

1 回答 1

0

表达式错误:命名对象:未找到 EmoticonOutputTextTag。

这意味着找不到给定的“组件类型”。标签的getComponentType()return com.unilife.emoticonoutputtext,但是您错误地在标签类名称上注册了它:

<component-type>EmoticonOutputTextTag</component-type>

相应地修复它。我也会在命名约定上更加一致。我还将开始逐步准确地遵循本教程,并使用一个工作示例而不是做与本教程中提到的不同的事情。

于 2012-04-30T17:40:18.693 回答