Hi, I'm trying to write a custom converter that converts the casing of text. Therefor I want a "type" attribute that let's me choose if I want to convert to lower case, UPPER CASE or Title Case. This is what I've done so far:
*Created converter class* I've created a class, CaseConverter.java: package my.company.conversion; import javax.faces.component.UIComponent; import javax.faces.context.FacesContext; import javax.faces.convert.Converter; public class CaseConverter implements Converter { private String type = "lower"; public Object getAsObject(FacesContext context, UIComponent component, String string) { String result = ""; if ("upper".equals(getType())){ return string.toUpperCase(); } else if ("title".equals(getType())) { return toTitleCase(string); } else { return string.toLowerCase(); } return result; } private String toTitleCase(String string){ // left out for brevity } public synchronized String getAsString(FacesContext context, UIComponent component, Object object) { return object.toString(); } public void setType(String type) { if (type != null) { this.type = type.toLowerCase(); } } public String getType() { return type; } } *Registered converter in faces-config.xml* As follows: <converter> <description>Case converter for text values</description> <converter-id>convertCase</converter-id> <converter-class>my.company.conversion.CaseConverter</converter-class> </converter> *Added to Facelets taglib* I already had a my.taglib.xml file for some composition components, so I added my converter there: <tag> <tag-name>convertCase</tag-name> <converter> <converter-id>convertCase</converter-id> </converter> </tag> *Used the converter in a page* I added the converter to a page, like this: <my:field id="jobTitle" bean="#{pageFlowScope.selectedEmployee}" > <my:convertCase type="title"/> </my:field> The <my:field> component is a Facelets Composition Component, defined as follows: <ui:composition> <c:if test="#{empty autoComplete}"> <c:set var="autoComplete" value="on" /> </c:if> <c:if test="#{empty simple}"> <c:set var="simple" value="false" /> </c:if> <!-- This is a work around for bug TRINIDAD-1390. --> <c:if test="#{empty maximumLength}"> <c:if test="#{columns gt 1}"> <c:set var="maximumLength" value="2147483647" /> </c:if> </c:if> <!-- This is a work around for bug TRINIDAD-1417. --> <c:if test="#{not empty partialTriggers}"> <c:set var="partialTriggers" value="#{my:getStringArray(partialTriggers)}" /> </c:if> <tr:inputText value="#{bean[id]}" id="#{id}" required="#{required}" readOnly="#{readOnly}" label="#{msg[id]}:" secret="#{secret}" maximumLength="#{maximumLength}" columns="#{columns}" rows="#{rows}" wrap="#{wrap}" autoComplete="#{autoComplete}" simple="#{simple}" partialTriggers="#{partialTriggers}" > <ui:insert/> </tr:inputText> </ui:composition> *Versions used:* Apache MyFaces 1.2.4 Apache MyFaces Trinidad 1.2.10 Facelets 1.1.14 *Problem description: *Everything works fine, except that the method setType() is only called before a call to getAsString(). I figured out that: - Everytime the converter is needed, a new instance of the class is constructed. - Before every call to getAsString() the setType() is called with the value set in the tag attribute ("title" in this case). - Before a call to getAsObject() the setType() method is *not *called. This causes the strings to always be converted to lower case, which is de default. Is this normal behaviour? What should I do to get it right? I hope someine can help... Best regards, Bart Kummel