View Javadoc
1   /*
2    * Copyright 2008 Werner Guttmann
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
5    * in compliance with the License. You may obtain a copy of the License at
6    *
7    * http://www.apache.org/licenses/LICENSE-2.0
8    *
9    * Unless required by applicable law or agreed to in writing, software distributed under the License
10   * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11   * or implied. See the License for the specific language governing permissions and limitations under
12   * the License.
13   */
14  package org.exolab.castor.builder.printing;
15  
16  import java.lang.reflect.Array;
17  import java.util.ArrayList;
18  
19  import org.exolab.javasource.JAnnotation;
20  import org.exolab.javasource.JClass;
21  import org.exolab.javasource.JEnum;
22  
23  /**
24   * Helper class that provides convenience methods used by Velocity templates during {@link JClass}
25   * printing.
26   */
27  public class TemplateHelper {
28  
29    /**
30     * Removes all line breaks from a given string.
31     * 
32     * @param string The string containing line breaks.
33     * @return A string without line breaks.
34     */
35    public String removeLineBreaks(String string) {
36      return string.replaceAll("\n", "");
37    }
38  
39    /**
40     * Takes a comment string and splits it into lines that have the maximum length of 70 chars,
41     * 
42     * @param comment The comment as string.
43     * @return The comment string splitted into a list.
44     */
45    public ArrayList<String> getLines(String comment) {
46      comment = removeLineBreaks(comment);
47      ArrayList<String> list = new ArrayList<String>();
48      do {
49        comment = computeLine(comment, list);
50      } while (comment.length() > 0);
51      return list;
52    }
53  
54    /**
55     * Helper methods that computes the next line for {@link #getLines(String)}.
56     * 
57     * @param comment The current comment string.
58     * @param list The current list.
59     * @return The comment without the next line.
60     */
61    private String computeLine(String comment, ArrayList<String> list) {
62      if (comment == null) {
63        return "";
64      }
65  
66      if (comment.length() <= 70) {
67        list.add(comment);
68        return "";
69      }
70  
71      int pos = comment.indexOf(' ', 70);
72      if (pos == -1) {
73        list.add(comment);
74        return "";
75      }
76  
77      String line = comment.substring(0, pos);
78      list.add(line);
79      return comment.substring(pos + 1);
80  
81    }
82  
83    /**
84     * Returns true if the {@link JClass} instance is instance of JEnum.
85     * 
86     * @param jClass The {@link JClass} instance to check.
87     * @return true if instance of JEnum.
88     */
89    public boolean isEnum(final JClass jClass) {
90      return (jClass instanceof JEnum);
91    }
92  
93    /**
94     * Converts the given {@link JAnnotation} to a string representation.
95     * 
96     * @param annotation The annotation to translate.
97     * @param shift The intent.
98     * @return A string representation of the annotation.
99     */
100   public String printAnnotation(final JAnnotation annotation, String shift) {
101     StringBuilder stringBuffer = new StringBuilder(32).append(shift).append("@")
102         .append(annotation.getAnnotationType().getLocalName()).append("(");
103     // Single element annotation?
104     String[] elementNames = annotation.getElementNames();
105     if (elementNames.length == 1 && elementNames[0].equals(JAnnotation.VALUE)) {
106       // Just output value
107       stringBuffer
108           .append(printAnnotationValue(annotation.getElementValueObject(JAnnotation.VALUE), shift));
109     } else if (elementNames.length > 0) {
110       // Max element name length?
111       int maxLength = 0;
112       for (String elementName : elementNames) {
113         int elementNameLength = elementName.length();
114         if (elementNameLength > maxLength) {
115           maxLength = elementNameLength;
116         }
117       }
118       // Output element name and values
119       stringBuffer.append('\n').append(shift + "    ");
120       for (int i = 0; i < elementNames.length; i++) {
121         int elementNameLength = elementNames[i].length();
122         // Output element name with padding
123         stringBuffer.append(elementNames[i]);
124         for (int p = 0; p < maxLength - elementNameLength; p++) {
125           stringBuffer.append(' ');
126         }
127         // Assignment operator
128         stringBuffer.append(" = ")
129             // Value
130             .append(printAnnotationValue(annotation.getElementValueObject(elementNames[i]), shift));
131         if (i < elementNames.length - 1) {
132           stringBuffer.append(",\n").append(shift + "    ");
133         }
134       }
135     }
136     stringBuffer.append(')');
137     return stringBuffer.toString();
138   }
139 
140   /**
141    * Helper method that translates an annotation value.
142    * 
143    * @param elementValue The value to translate.
144    * @param shift The intent,
145    * @return The string representation of the value.
146    */
147   private String printAnnotationValue(final Object elementValue, final String shift) {
148     // String?
149     if (elementValue instanceof String) {
150       return (String) elementValue;
151     } else if (elementValue instanceof JAnnotation) {
152       JAnnotation annotation = (JAnnotation) elementValue;
153       return printAnnotation(annotation, shift);
154     } else if (elementValue.getClass().isArray()) {
155       // Short hand for single item list
156       int listLength = Array.getLength(elementValue);
157       if (listLength == 1) {
158         return printAnnotationValue(Array.get(elementValue, 0), shift);
159       }
160       // Output list items
161       StringBuilder stringBuffer = new StringBuilder().append("\n{\n").append(shift);
162       for (int i = 0; i < listLength; i++) {
163         stringBuffer.append(shift).append(printAnnotationValue(Array.get(elementValue, i), shift));
164         if (i < listLength - 1) {
165           stringBuffer.append(',');
166         }
167         stringBuffer.append('\n');
168       }
169       stringBuffer.append('}');
170       return stringBuffer.toString();
171     }
172     throw new IllegalArgumentException("'" + elementValue + "' was not expected.");
173   }
174 
175 }