Skip to contentMethod: generate(JFormatter)
1: /**
2: * Copyright (C) 2016 Czech Technical University in Prague
3: *
4: * This program is free software: you can redistribute it and/or modify it under
5: * the terms of the GNU General Public License as published by the Free Software
6: * Foundation, either version 3 of the License, or (at your option) any
7: * later version.
8: *
9: * This program is distributed in the hope that it will be useful, but WITHOUT
10: * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11: * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
12: * details. You should have received a copy of the GNU General Public License
13: * along with this program. If not, see <http://www.gnu.org/licenses/>.
14: */
15: package com.sun.codemodel;
16:
17: import java.lang.annotation.Annotation;
18: import java.util.LinkedHashMap;
19: import java.util.Map;
20:
21: /**
22: * Represents an annotation on a program element.
23: *
24: * FIX to com.sun.codemodel.JAnnotationUse supporting JFieldRef as annotation values (constants)
25: */
26: public final class JAnnotationUse extends JAnnotationValue {
27:
28: /**
29: * The {@link Annotation} class
30: */
31: private final JClass clazz;
32:
33: /**
34: * Map of member values.
35: */
36: private Map<String,JAnnotationValue> memberValues;
37:
38: JAnnotationUse(JClass clazz){
39: this.clazz = clazz;
40: }
41:
42: private JCodeModel owner() {
43: return clazz.owner();
44: }
45:
46: private void addValue(String name, JAnnotationValue annotationValue) {
47: // Use ordered map to keep the code generation the same on any JVM.
48: // Lazily created.
49: if(memberValues==null)
50: memberValues = new LinkedHashMap<String, JAnnotationValue>();
51: memberValues.put(name,annotationValue);
52: }
53:
54: /**
55: * Adds a member value pair to this annotation
56: *
57: * @param name
58: * The simple name for this annotation
59: *
60: * @param value
61: * The boolean value for this annotation
62: * @return
63: * The JAnnotationUse. More member value pairs can
64: * be added to it using the same or the overloaded methods.
65: *
66: */
67: public JAnnotationUse param(String name, boolean value){
68: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
69: return this;
70: }
71:
72: /**
73: * Adds a member value pair to this annotation
74: * @param name
75: * The simple name for this annotation
76: *
77: * @param value
78: * The byte member value for this annotation
79: * @return
80: * The JAnnotationUse. More member value pairs can
81: * be added to it using the same or the overloaded methods.
82: *
83: */
84: public JAnnotationUse param(String name, byte value){
85: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
86: return this;
87: }
88:
89: /**
90: * Adds a member value pair to this annotation
91: * @param name
92: * The simple name for this annotation
93: *
94: * @param value
95: * The char member value for this annotation
96: * @return
97: * The JAnnotationUse. More member value pairs can
98: * be added to it using the same or the overloaded methods.
99: *
100: */
101: public JAnnotationUse param(String name, char value){
102: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
103: return this;
104: }
105:
106: /**
107: * Adds a member value pair to this annotation
108: * @param name
109: * The simple name for this annotation
110: *
111: * @param value
112: * The double member value for this annotation
113: * @return
114: * The JAnnotationUse. More member value pairs can
115: * be added to it using the same or the overloaded methods.
116: *
117: */
118: public JAnnotationUse param(String name, double value){
119: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
120: return this;
121: }
122:
123: /**
124: * Adds a member value pair to this annotation
125: * @param name
126: * The simple name for this annotation
127: *
128: * @param value
129: * The float member value for this annotation
130: * @return
131: * The JAnnotationUse. More member value pairs can
132: * be added to it using the same or the overloaded methods.
133: *
134: */
135: public JAnnotationUse param(String name, float value){
136: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
137: return this;
138: }
139:
140: /**
141: * Adds a member value pair to this annotation
142: * @param name
143: * The simple name for this annotation
144: *
145: * @param value
146: * The long member value for this annotation
147: * @return
148: * The JAnnotationUse. More member value pairs can
149: * be added to it using the same or the overloaded methods.
150: *
151: */
152: public JAnnotationUse param(String name, long value){
153: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
154: return this;
155: }
156:
157: /**
158: * Adds a member value pair to this annotation
159: * @param name
160: * The simple name for this annotation
161: *
162: * @param value
163: * The short member value for this annotation
164: * @return
165: * The JAnnotationUse. More member value pairs can
166: * be added to it using the same or the overloaded methods.
167: *
168: */
169: public JAnnotationUse param(String name, short value){
170: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
171: return this;
172: }
173:
174: /**
175: * Adds a member value pair to this annotation
176: * @param name
177: * The simple name for this annotation
178: *
179: * @param value
180: * The int member value for this annotation
181: * @return
182: * The JAnnotationUse. More member value pairs can
183: * be added to it using the same or the overloaded methods.
184: *
185: */
186: public JAnnotationUse param(String name, int value){
187: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
188: return this;
189: }
190:
191: /**
192: * Adds a member value pair to this annotation
193: * @param name
194: * The simple name for this annotation
195: *
196: * @param value
197: * The String member value for this annotation
198: * @return
199: * The JAnnotationUse. More member value pairs can
200: * be added to it using the same or the overloaded methods.
201: *
202: */
203: public JAnnotationUse param(String name, String value){
204: //Escape string values with quotes so that they can
205: //be generated accordingly
206: addValue(name, new JAnnotationStringValue(JExpr.lit(value)));
207: return this;
208: }
209:
210: /**
211: * Adds a member value pair to this annotation
212: * For adding class values as param
213: * @see #param(String, Class)
214: * @param name
215: * The simple name for this annotation
216: *
217: * @param value
218: * The annotation class which is member value for this annotation
219: * @return
220: * The JAnnotationUse. More member value pairs can
221: * be added to it using the same or the overloaded methods.
222: *
223: */
224: public JAnnotationUse annotationParam(String name, Class<? extends Annotation> value) {
225: JAnnotationUse annotationUse = new JAnnotationUse(owner().ref(value));
226: addValue(name, annotationUse);
227: return annotationUse;
228: }
229:
230: /**
231: * Adds a member value pair to this annotation
232: * @param name
233: * The simple name for this annotation
234: *
235: * @param value
236: * The enum class which is member value for this annotation
237: * @return
238: * The JAnnotationUse. More member value pairs can
239: * be added to it using the same or the overloaded methods.
240: *
241: */
242: public JAnnotationUse param(String name, final Enum<?> value) {
243: addValue(name, new JAnnotationValue() {
244: public void generate(JFormatter f) {
245: f.t(owner().ref(value.getDeclaringClass())).p('.').p(value.name());
246: }
247: });
248: return this;
249: }
250:
251: /**
252: * Adds a member value pair to this annotation
253: * @param name
254: * The simple name for this annotation
255: *
256: * @param value
257: * The JEnumConstant which is member value for this annotation
258: * @return
259: * The JAnnotationUse. More member value pairs can
260: * be added to it using the same or the overloaded methods.
261: *
262: */
263: public JAnnotationUse param(String name, JEnumConstant value){
264: addValue(name, new JAnnotationStringValue(value));
265: return this;
266: }
267:
268: /**
269: * Adds a member value pair to this annotation
270: * This can be used for e.g to specify
271: * <pre>
272: * @XmlCollectionItem(type=Integer.class);
273: * <pre>
274: * For adding a value of Class<? extends Annotation>
275: * @link
276: * #annotationParam(java.lang.String, java.lang.Class<? extends java.lang.annotation.Annotation>)
277: * @param name
278: * The simple name for this annotation param
279: *
280: * @param value
281: * The class type of the param
282: * @return
283: * The JAnnotationUse. More member value pairs can
284: * be added to it using the same or the overloaded methods.
285: *
286: *
287: *
288: */
289: public JAnnotationUse param(String name, final Class<?> value){
290: addValue(name, new JAnnotationStringValue(
291:                  new JExpressionImpl() {
292:                          public void generate(JFormatter f) {
293:                                  f.p(value.getName().replace('$', '.'));
294:                                  f.p(".class");
295:                         }
296:                  }));
297: return this;
298: }
299:
300: /**
301: * Adds a member value pair to this annotation based on the
302: * type represented by the given JType
303: *
304: * @param name The simple name for this annotation param
305: * @param type the JType representing the actual type
306: * @return The JAnnotationUse. More member value pairs can
307: * be added to it using the same or the overloaded methods.
308: */
309: public JAnnotationUse param(String name, JType type){
310: JClass clazz = type.boxify();
311: addValue(name, new JAnnotationStringValue ( clazz.dotclass() ));
312: return this;
313: }
314:
315: /**
316: * Adds a member value pair which is of type array to this annotation
317: * @param name
318: * The simple name for this annotation
319: *
320: * @return
321: * The JAnnotationArrayMember. For adding array values
322: * @see JAnnotationArrayMember
323: *
324: */
325: public JAnnotationArrayMember paramArray(String name){
326: JAnnotationArrayMember arrayMember = new JAnnotationArrayMember(owner());
327: addValue(name, arrayMember);
328: return arrayMember;
329: }
330:
331:
332: // /**
333: // * This can be used to add annotations inside annotations
334: // * for e.g @XmlCollection(values= @XmlCollectionItem(type=Foo.class))
335: // * @param className
336: // * The classname of the annotation to be included
337: // * @return
338: // * The JAnnotationUse that can be used as a member within this JAnnotationUse
339: // * @deprecated
340: // * use {@link JAnnotationArrayMember#annotate}
341: // */
342: // public JAnnotationUse annotate(String className) {
343: // JAnnotationUse annotationUse = new JAnnotationUse(owner().ref(className));
344: // return annotationUse;
345: // }
346:
347: /**
348: * This can be used to add annotations inside annotations
349: * for e.g @XmlCollection(values= @XmlCollectionItem(type=Foo.class))
350: * @param clazz
351: * The annotation class to be included
352: * @return
353: * The JAnnotationUse that can be used as a member within this JAnnotationUse
354: * @deprecated
355: * use {@link JAnnotationArrayMember#annotate}
356: */
357: public JAnnotationUse annotate(Class <? extends Annotation> clazz) {
358: JAnnotationUse annotationUse = new JAnnotationUse(owner().ref(clazz));
359: return annotationUse;
360: }
361:
362: public void generate(JFormatter f) {
363: f.p('@').g(clazz);
364: if(memberValues!=null) {
365: f.p('(');
366: boolean first = true;
367:
368: if(isOptimizable()) {
369: // short form
370: f.g(memberValues.get("value"));
371: } else {
372: for (Map.Entry<String, JAnnotationValue> mapEntry : memberValues.entrySet()) {
373: if (!first) f.p(',');
374: f.p(mapEntry.getKey()).p('=').g(mapEntry.getValue());
375: first = false;
376: }
377: }
378: f.p(')');
379: }
380: }
381:
382: private boolean isOptimizable() {
383: return memberValues.size()==1 && memberValues.containsKey("value");
384: }
385:
386: public JAnnotationUse param(String name, JFieldRef value){
387: addValue(name, new JAnnotationStringValue(value));
388: return this;
389: }
390: }