KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > java > ui > nodes > elements > SourceEditSupport


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2006 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20 package org.netbeans.modules.java.ui.nodes.elements;
21
22
23 import java.awt.Component JavaDoc;
24 import java.io.IOException JavaDoc;
25 import java.lang.reflect.Modifier JavaDoc;
26 import java.util.*;
27 import java.beans.PropertyEditor JavaDoc;
28
29 import org.netbeans.modules.java.ui.nodes.editors.ModifierEditor;
30 import org.netbeans.modules.java.JavaNode;
31 import org.netbeans.modules.javacore.api.JavaModel;
32 import org.netbeans.modules.javacore.internalapi.JavaMetamodel;
33 import org.netbeans.jmi.javamodel.*;
34 import org.netbeans.api.java.queries.SourceLevelQuery;
35
36 import org.openide.*;
37 import org.openide.explorer.propertysheet.PropertyPanel;
38 import org.openide.filesystems.FileObject;
39 import org.openide.util.*;
40 import org.openide.util.datatransfer.NewType;
41
42 import javax.jmi.reflect.JmiException;
43
44 /** This class defines utilities for editing source using JMI API,
45 * e.g. creation new types for class elements, ...
46 *
47 * @author Petr Hamernik, Jan Pokorsky
48 */

49 public final class SourceEditSupport {
50
51     static final byte NT_INITIALIZER = 0;
52     static final byte NT_FIELD = 1;
53     static final byte NT_CONSTRUCTOR = 2;
54     static final byte NT_METHOD = 3;
55     static final byte NT_INNERCLASS = 4;
56     static final byte NT_INNERINTERFACE = 5;
57     static final byte NT_INNERENUM = 6;
58     static final byte NT_ENUMCONSTANT = 7;
59     static final byte NT_CLASS = 8;
60     static final byte NT_INTERFACE = 9;
61     static final byte NT_ENUM = 10;
62     static final byte NT_ANNOTATION_TYPE = 11;
63     static final byte NT_INNERANNOTATION_TYPE = 12;
64     static final byte NT_ANNOTATION_TYPE_METHOD = 13;
65     
66     static final String JavaDoc[] MENU_NAMES = {
67         getString("MENU_CREATE_BLOCK"), getString("MENU_CREATE_VARIABLE"), // NOI18N
68
getString("MENU_CREATE_CONSTRUCTOR"), getString("MENU_CREATE_METHOD"), // NOI18N
69
getString("MENU_CREATE_INNERCLASS"), getString("MENU_CREATE_INNERINTERFACE"), // NOI18N
70
getString("MENU_CREATE_INNERENUM"), getString("MENU_CREATE_CONSTANT"), // NOI18N
71
getString("MENU_CREATE_CLASS"), getString("MENU_CREATE_INTERFACE"), // NOI18N
72
getString("MENU_CREATE_ENUM"), getString("MENU_CREATE_ANN_TYPE"), // NOI18N
73
getString("MENU_CREATE_INNERANN_TYPE"), getString("MENU_CREATE_ANN_TYPE_METHOD"), // NOI18N
74
};
75
76     private static String JavaDoc getString(String JavaDoc key) {
77         return NbBundle.getMessage(SourceEditSupport.class, key);
78     }
79     
80     /**
81      * creates class new types
82      * @param element class
83      * @param supportJDK15 support new 1.5 features
84      * @return array of new type operations that are allowed
85      * @see #isJDK15Supported
86      */

87     public static NewType[] createClassNewTypes(JavaClass element, boolean supportJDK15) {
88         NewType[] ntypes;
89         if (supportJDK15) {
90             ntypes = new NewType[] {
91                 new ElementNewType(element, NT_INITIALIZER),
92                 new ElementNewType(element, NT_FIELD),
93                 new ElementNewType(element, NT_CONSTRUCTOR),
94                 new ElementNewType(element, NT_METHOD),
95                 new ElementNewType(element, NT_INNERCLASS),
96                 new ElementNewType(element, NT_INNERENUM),
97                 new ElementNewType(element, NT_INNERINTERFACE),
98                 new ElementNewType(element, NT_INNERANNOTATION_TYPE),
99             };
100         } else {
101             ntypes = new NewType[] {
102                 new ElementNewType(element, NT_INITIALIZER),
103                 new ElementNewType(element, NT_FIELD),
104                 new ElementNewType(element, NT_CONSTRUCTOR),
105                 new ElementNewType(element, NT_METHOD),
106                 new ElementNewType(element, NT_INNERCLASS),
107                 new ElementNewType(element, NT_INNERINTERFACE),
108             };
109         }
110         return ntypes;
111     }
112     
113     /**
114      * creates interface new types
115      * @param element interface
116      * @param supportJDK15 support new 1.5 features
117      * @return array of new type operations that are allowed
118      * @see #isJDK15Supported
119      */

120     public static NewType[] createInterfaceNewTypes(JavaClass element, boolean supportJDK15) {
121         NewType[] ntypes;
122         if (supportJDK15) {
123             ntypes = new NewType[] {
124                 new ElementNewType(element, NT_FIELD),
125                 new ElementNewType(element, NT_METHOD),
126                 new ElementNewType(element, NT_INNERCLASS),
127                 new ElementNewType(element, NT_INNERENUM),
128                 new ElementNewType(element, NT_INNERINTERFACE),
129                 new ElementNewType(element, NT_INNERANNOTATION_TYPE),
130             };
131         } else {
132             ntypes = new NewType[] {
133                 new ElementNewType(element, NT_FIELD),
134                 new ElementNewType(element, NT_METHOD),
135                 new ElementNewType(element, NT_INNERCLASS),
136                 new ElementNewType(element, NT_INNERINTERFACE),
137             };
138         }
139         return ntypes;
140     }
141     
142     /**
143      * creates enum new types
144      * @param element enum
145      * @return array of new type operations that are allowed
146      */

147     public static NewType[] createEnumNewTypes(JavaEnum element) {
148         return new NewType[] {
149                 new ElementNewType(element, NT_ENUMCONSTANT),
150                 new ElementNewType(element, NT_INITIALIZER),
151                 new ElementNewType(element, NT_FIELD),
152                 new ElementNewType(element, NT_CONSTRUCTOR),
153                 new ElementNewType(element, NT_METHOD),
154                 new ElementNewType(element, NT_INNERCLASS),
155                 new ElementNewType(element, NT_INNERENUM),
156                 new ElementNewType(element, NT_INNERINTERFACE),
157                 new ElementNewType(element, NT_INNERANNOTATION_TYPE),
158             };
159     }
160     
161     /**
162      * creates annotation type new types
163      * @param element annotation type
164      * @return array of new type operations that are allowed
165      */

166     public static NewType[] createInterfaceNewTypes(AnnotationType element) {
167         return new NewType[] {
168                    new ElementNewType(element, NT_FIELD),
169                    new ElementNewType(element, NT_ANNOTATION_TYPE_METHOD),
170                    new ElementNewType(element, NT_INNERCLASS),
171                    new ElementNewType(element, NT_INNERENUM),
172                    new ElementNewType(element, NT_INNERINTERFACE),
173                    new ElementNewType(element, NT_INNERANNOTATION_TYPE),
174                };
175     }
176
177     /**
178      * creates java node new types
179      * @param node node
180      * @return array of new type operations that are allowed
181      */

182     public static NewType[] createJavaNodeNewTypes(JavaNode node) {
183         NewType[] ntypes;
184         if (isJDK15Supported(node.getDataObject().getPrimaryFile())) {
185             ntypes = new NewType[] {
186                 new ElementNewType(node, NT_CLASS),
187                 new ElementNewType(node, NT_ENUM),
188                 new ElementNewType(node, NT_INTERFACE),
189                 new ElementNewType(node, NT_ANNOTATION_TYPE),
190             };
191         } else {
192             ntypes = new NewType[] {
193                 new ElementNewType(node, NT_CLASS),
194                 new ElementNewType(node, NT_INTERFACE),
195             };
196         }
197         return ntypes;
198     }
199     
200     public static boolean isJDK15Supported(FileObject source) {
201         String JavaDoc version = SourceLevelQuery.getSourceLevel(source);
202         return version != null && version.startsWith("1.5"); // NOI18N
203
}
204     
205     /** New types for JavaClass */
206     static final class ElementNewType extends NewType {
207         /** Class element where to create new element */
208         private final JavaClass element;
209         /** Resource where to create new element */
210         private final JavaNode node;
211
212         /** The kind of element to create */
213         byte kind;
214         private static final String JavaDoc NEW_FIELD_NAME = "newField"; // NOI18N
215
private static final String JavaDoc NEW_METHOD_NAME = "newMethod"; // NOI18N
216
private static final String JavaDoc NEW_ANN_TYPE_METHOD_NAME = "newMethod"; // NOI18N
217
private static final String JavaDoc NEW_INNERCLASS_NAME = "InnerClass"; // NOI18N
218
private static final String JavaDoc NEW_INNERINTERFACE_NAME = "InnerInterface"; // NOI18N
219
private static final String JavaDoc NEW_INNERENUM_NAME = "InnerEnum"; // NOI18N
220
private static final String JavaDoc NEW_INNERANN_TYPE_NAME = "InnerNewAnnotationType"; // NOI18N
221
private static final String JavaDoc NEW_CLASS_NAME = "NewClass"; // NOI18N
222
private static final String JavaDoc NEW_INTERFACE_NAME = "NewInterface"; // NOI18N
223
private static final String JavaDoc NEW_ENUM_NAME = "NewEnum"; // NOI18N
224
private static final String JavaDoc NEW_ANN_TYPE_NAME = "NewAnnotationType"; // NOI18N
225

226         /** Creates new type
227         * @param element Where to create new element.
228         * @param kind The kind of the element to create
229         */

230         public ElementNewType(JavaClass element, byte kind) {
231             this.element = element;
232             this.node = null;
233             this.kind = kind;
234         }
235
236         /** Creates new type
237         * @param node resource where to create new element.
238         * @param kind The kind of the element to create
239         */

240         public ElementNewType(JavaNode node, byte kind) {
241             this.element = null;
242             this.node = node;
243             this.kind = kind;
244         }
245
246         /** Get the name of the new type.
247         * @return localized name.
248         */

249         public String JavaDoc getName() {
250             return MENU_NAMES[kind];
251         }
252
253         /** Help context */
254         public org.openide.util.HelpCtx getHelpCtx() {
255             return new org.openide.util.HelpCtx (SourceEditSupport.class.getName () + ".newElement" + kind); // NOI18N
256
}
257
258         /** Creates new element */
259         public void create () throws IOException JavaDoc {
260             boolean fail = true;
261             try {
262                 JavaModel.getJavaRepository().beginTrans(true);
263                 try {
264                     createImpl();
265                     fail = false;
266                 } finally {
267                     JavaModel.getJavaRepository().endTrans(fail);
268                 }
269             } catch (JmiException ex) {
270                 IOException JavaDoc ioe = new IOException JavaDoc();
271                 ioe.initCause(ex);
272                 throw ioe;
273             }
274         }
275         
276         /**
277          *
278          * @throws JmiException
279          */

280         private void createImpl() throws JmiException {
281             JavaModelPackage jmodel = getModel();
282
283             switch (kind) {
284                 case NT_INITIALIZER:
285                     createInitializer(jmodel);
286                     break;
287                 case NT_FIELD:
288                     createField(jmodel);
289                     break;
290                 case NT_CONSTRUCTOR:
291                     createConstructor(jmodel);
292                     break;
293                 case NT_METHOD:
294                     createMethod(jmodel);
295                     break;
296                 case NT_INNERCLASS:
297                     createInnerClass(jmodel);
298                     break;
299                 case NT_INNERINTERFACE:
300                     createInnerInterface(jmodel);
301                     break;
302                 case NT_INNERENUM:
303                     createInnerEnum(jmodel);
304                     break;
305                 case NT_ENUMCONSTANT:
306                     createConstant(jmodel);
307                     break;
308                 case NT_CLASS:
309                     createClass(jmodel);
310                     break;
311                 case NT_INTERFACE:
312                     createInterface(jmodel);
313                     break;
314                 case NT_ENUM:
315                     createEnum(jmodel);
316                     break;
317                 case NT_ANNOTATION_TYPE:
318                     createAnnotationType(jmodel);
319                     break;
320                 case NT_INNERANNOTATION_TYPE:
321                     createInnerAnnotationType(jmodel);
322                     break;
323                 case NT_ANNOTATION_TYPE_METHOD:
324                     createAnnotationTypeMethod(jmodel);
325                     break;
326                 default:
327                     assert true: "Unknown new type: " + kind; // NOI18N
328
}
329         }
330
331         private void createInnerInterface(JavaModelPackage jmodel) throws JmiException {
332             // Adding inner interface
333
String JavaDoc name = NEW_INNERINTERFACE_NAME;
334             for (int index = 1; element.getInnerClass(name, true) != null; index++) {
335                 name = NEW_INNERINTERFACE_NAME + '_' + index;
336             }
337             JavaClass e = jmodel.getJavaClass().createJavaClass(
338                     name, null, Modifier.PUBLIC, null, null, null, null, null, null
339             );
340             e.setInterface(true);
341             ClassCustomizer cust = new ClassCustomizer(element, e);
342             if (openCustomizer(cust, "TIT_NewInnerInterface") && cust.isOK()) { // NOI18N
343
addFeature(e);
344             }
345         }
346
347         private void createInnerClass(JavaModelPackage jmodel) throws JmiException {
348             // Adding inner class
349
String JavaDoc name = NEW_INNERCLASS_NAME;
350             for (int index = 1; element.getInnerClass(name, true) != null; index++) {
351                 name = NEW_INNERCLASS_NAME + '_' + index;
352             }
353             JavaClass e = jmodel.getJavaClass().createJavaClass(
354                     name, null, Modifier.PUBLIC | Modifier.FINAL, null, null, null, null, null, null
355             );
356             e.setInterface(false);
357             ClassCustomizer cust = new ClassCustomizer(element, e);
358             if (openCustomizer(cust, "TIT_NewInnerClass") && cust.isOK()) { // NOI18N
359
addFeature(e);
360             }
361         }
362
363         private void createInterface(JavaModelPackage jmodel) throws JmiException {
364             // Adding inner interface
365
String JavaDoc name = NEW_INTERFACE_NAME;
366             Resource resource = getResource();
367             for (int index = 1; findTopLevelClass(resource, name) != null; index++) {
368                 name = NEW_INTERFACE_NAME + '_' + index;
369             }
370             JavaClass e = jmodel.getJavaClass().createJavaClass(
371                     name, null, 0, null, null, null, null, null, null
372             );
373             e.setInterface(true);
374             ClassCustomizer cust = new ClassCustomizer(resource, e);
375             org.openide.util.HelpCtx.setHelpIDString(cust, SourceEditSupport.class.getName() + "$AddNewInterface"); //NOI18N
376
if (openCustomizer(cust, "TIT_NewInterface") && cust.isOK()) { // NOI18N
377
resource.getClassifiers().add(e);
378             }
379         }
380
381         private void createClass(JavaModelPackage jmodel) throws JmiException {
382             // Adding inner class
383
String JavaDoc name = NEW_CLASS_NAME;
384             Resource resource = getResource();
385             
386             for (int index = 1; findTopLevelClass(resource, name) != null; index++) {
387                 name = NEW_CLASS_NAME + '_' + index;
388             }
389             JavaClass e = jmodel.getJavaClass().createJavaClass(
390                     name, null, Modifier.FINAL, null, null, null, null, null, null
391             );
392             e.setInterface(false);
393             ClassCustomizer cust = new ClassCustomizer(resource, e);
394             org.openide.util.HelpCtx.setHelpIDString(cust, SourceEditSupport.class.getName() + "$AddNewClass"); //NOI18N
395
if (openCustomizer(cust, "TIT_NewClass") && cust.isOK()) { // NOI18N
396
resource.getClassifiers().add(e);
397             }
398         }
399
400         private void createMethod(JavaModelPackage jmodel) throws JmiException {
401             // Adding method
402
Method e = jmodel.getMethod().createMethod();
403             Type voidType = jmodel.getType().resolve(PrimitiveTypeKindEnum.VOID.toString());
404             e.setType(voidType);
405
406             String JavaDoc name = NEW_METHOD_NAME;
407             for (int index = 1; element.getMethod(name, Collections.EMPTY_LIST, true) != null; index++) {
408                 name = NEW_METHOD_NAME + '_' + index;
409             }
410             e.setName(name);
411                     
412             e.setModifiers(Modifier.PUBLIC);
413             MethodCustomizer cust = new MethodCustomizer(element, e);
414             
415             boolean isOK = false;
416             while ((isOK = openCustomizer(cust, "TIT_NewMethod")) && !cust.isOK()); // NOI18N
417

418             if (isOK) {
419                 addFeature(e);
420             }
421         }
422
423         private void createConstructor(JavaModelPackage jmodel) throws JmiException {
424             // Adding constructor
425
Constructor e = jmodel.getConstructor().createConstructor();
426             if (!(this.element instanceof JavaEnum))
427                 e.setModifiers(Modifier.PUBLIC);
428             MethodCustomizer cust = new MethodCustomizer(element, e);
429             if (openCustomizer(cust, "TIT_NewConstructor") && cust.isOK()) { // NOI18N
430
addFeature(e);
431             }
432         }
433
434         private void createField(JavaModelPackage jmodel) throws JmiException {
435             // Adding field
436
Field e = jmodel.getField().createField();
437             Type type = jmodel.getType().resolve("int"); // NOI18N
438
e.setType(type);
439
440             String JavaDoc name = NEW_FIELD_NAME;
441             for (int index = 1; element.getField(name, true) != null; index++) {
442                 name = NEW_FIELD_NAME + '_' + index;
443             }
444             e.setName(name);
445                     
446             boolean outerIsClass = !element.isInterface();
447             e.setModifiers(outerIsClass? Modifier.PRIVATE : Modifier.PUBLIC | Modifier.STATIC);
448             FieldCustomizer cust = new FieldCustomizer(element, e);
449             if (openCustomizer(cust, "TIT_NewField") && cust.isOK()) { // NOI18N
450
addFeature(e);
451             }
452         }
453
454         private void createInitializer(JavaModelPackage jmodel) throws JmiException {
455             // Adding initializer
456
Initializer e = jmodel.getInitializer().createInitializer();
457             e.setModifiers(Modifier.STATIC);
458             addFeature(e);
459         }
460
461         private void createInnerEnum(JavaModelPackage jmodel) throws JmiException {
462             // Adding inner enum
463
String JavaDoc name = NEW_INNERENUM_NAME;
464             for (int index = 1; element.getInnerClass(name, true) != null; index++) {
465                 name = NEW_INNERENUM_NAME + '_' + index;
466             }
467             JavaEnum e = jmodel.getJavaEnum().createJavaEnum(
468                     name, null, Modifier.PUBLIC, null, null, null, null, null, null, null
469             );
470             EnumCustomizer cust = new EnumCustomizer(element, e);
471             if (openCustomizer(cust, "TIT_NewInnerEnum") && cust.isOK()) { // NOI18N
472
addFeature(e);
473             }
474         }
475
476         private void createEnum(JavaModelPackage jmodel) throws JmiException {
477             // Adding enum
478
String JavaDoc name = NEW_ENUM_NAME;
479             Resource resource = getResource();
480             for (int index = 1; findTopLevelClass(resource, name) != null; index++) {
481                 name = NEW_ENUM_NAME + '_' + index;
482             }
483             JavaEnum e = jmodel.getJavaEnum().createJavaEnum(
484                     name, null, 0, null, null, null, null, null, null, null
485             );
486             EnumCustomizer cust = new EnumCustomizer(resource, e);
487             if (openCustomizer(cust, "TIT_NewEnum") && cust.isOK()) { // NOI18N
488
resource.getClassifiers().add(e);
489             }
490         }
491         
492         private void createConstant(JavaModelPackage jmodel) throws JmiException {
493             JavaEnum en = (JavaEnum) this.element;
494             EnumConstant e = jmodel.getEnumConstant().createEnumConstant();
495
496             final String JavaDoc ENUM_NAME = en.getSimpleName();
497             String JavaDoc name = ENUM_NAME;
498             for (int index = 1; findConstant(en, name) != null; index++) {
499                 name = ENUM_NAME + '_' + index;
500             }
501             e.setName(name);
502                     
503             EnumConstantCustomizer cust = new EnumConstantCustomizer(en, e);
504             if (openCustomizer(cust, "TIT_NewConstant") && cust.isOK()) { // NOI18N
505
en.getConstants().add(e);
506             }
507             return;
508         }
509
510         private void createInnerAnnotationType(JavaModelPackage jmodel) throws JmiException {
511             // Adding inner annotation type
512
String JavaDoc name = NEW_INNERANN_TYPE_NAME;
513             for (int index = 1; element.getInnerClass(name, true) != null; index++) {
514                 name = NEW_INNERANN_TYPE_NAME + '_' + index;
515             }
516             AnnotationType at = jmodel.getAnnotationType().createAnnotationType(
517                     name, null, Modifier.PUBLIC, null, null, null, null, null, null
518             );
519             AnnotationTypeCustomizer cust = new AnnotationTypeCustomizer(element, at);
520             if (openCustomizer(cust, "TIT_NewInnerAnnType") && cust.isOK()) { // NOI18N
521
addFeature(at);
522             }
523         }
524
525         private void createAnnotationType(JavaModelPackage jmodel) throws JmiException {
526             // Adding enum
527
String JavaDoc name = NEW_ANN_TYPE_NAME;
528             Resource resource = getResource();
529             for (int index = 1; findTopLevelClass(resource, name) != null; index++) {
530                 name = NEW_ANN_TYPE_NAME + '_' + index;
531             }
532             AnnotationType at = jmodel.getAnnotationType().createAnnotationType(
533                     name, null, 0, null, null, null, null, null, null
534             );
535             AnnotationTypeCustomizer cust = new AnnotationTypeCustomizer(resource, at);
536             if (openCustomizer(cust, "TIT_NewAnnType") && cust.isOK()) { // NOI18N
537
resource.getClassifiers().add(at);
538             }
539         }
540
541         private void createAnnotationTypeMethod(JavaModelPackage jmodel) throws JmiException {
542             // Adding annotation type method
543
AnnotationType at = (AnnotationType) this.element;
544             String JavaDoc name = NEW_ANN_TYPE_METHOD_NAME;
545             for (int index = 1; findAttribute(at, name) != null; index++) {
546                 name = NEW_ANN_TYPE_METHOD_NAME + '_' + index;
547             }
548             Type type = jmodel.getType().resolve("java.lang.String"); // NOI18N
549
Attribute attr = jmodel.getAttribute().createAttribute(name, null, 0, null, null, null, null, null);
550             attr.setType(type);
551             AnnotationTypeMethodCustomizer cust = new AnnotationTypeMethodCustomizer(at, attr);
552             if (openCustomizer(cust, "TIT_NewAnnTypeMethod") && cust.isOK()) { // NOI18N
553
addFeature(attr);
554             }
555         }
556         
557         /* This method prevents features to be inserted into gurded blocks.
558          * It is a temporal solution - we need to fix the problem in javacore.
559          */

560         private void addFeature(Feature feature) {
561             List features = new ArrayList(element.getFeatures()); // [PENDING] workaround for buggy FeaturesListIterator
562
ListIterator iter = features.listIterator(features.size());
563             ClassMember f = iter.hasPrevious() ? (ClassMember)iter.previous() : null;
564             JavaMetamodel manager = JavaMetamodel.getManager();
565             if (f == null || !manager.isElementGuarded(f)) {
566                 element.getFeatures().add(feature);
567                 return;
568             }
569             do {
570                 f = (ClassMember)iter.previous();
571             } while (f != null && manager.isElementGuarded(f));
572             iter = element.getFeatures().listIterator();
573             if (f != null) {
574                 for (; iter.next() != f; );
575             }
576             iter.add(feature);
577         }
578         
579         private Resource getResource() {
580             return JavaModel.getResource(node.getDataObject().getPrimaryFile());
581         }
582         
583         private JavaModelPackage getModel() {
584             if (this.element != null) {
585                 return JavaMetamodel.getManager().getJavaExtent(this.element);
586             } else {
587                 return JavaMetamodel.getManager().getJavaExtent(getResource());
588             }
589         }
590     }
591     
592     /**
593      * finds attribute (annotation type method) in a annotation type
594      * @param at annotation type to query
595      * @param name name to find
596      * @return the attribute or <code>null</code>
597      * @throws JmiException
598      */

599     static Attribute findAttribute(AnnotationType at, String JavaDoc name) throws JmiException {
600         if (at == null) throw new NullPointerException JavaDoc("at"); // NOI18N
601
if (name == null) throw new NullPointerException JavaDoc("name"); // NOI18N
602
Iterator it = at.getFeatures().iterator();
603         while (it.hasNext()) {
604             Object JavaDoc o = it.next();
605             if (o instanceof Attribute && name.equals(((Attribute) o).getName())) {
606                 return (Attribute) o;
607             }
608         }
609         return null;
610     }
611     
612     /**
613      * finds constant in an enumeration
614      * @param en enumeration to query
615      * @param name name to find
616      * @return the constant or <code>null</code>
617      * @throws JmiException
618      */

619     static EnumConstant findConstant(JavaEnum en, String JavaDoc name) throws JmiException {
620         if (en == null) throw new NullPointerException JavaDoc("en"); // NOI18N
621
if (name == null) throw new NullPointerException JavaDoc("name"); // NOI18N
622
Iterator it = en.getConstants().iterator();
623         while (it.hasNext()) {
624             EnumConstant ec = (EnumConstant) it.next();
625             if (name.equals(ec.getName()))
626                 return ec;
627         }
628         return null;
629     }
630     
631     /**
632      * finds top level class in java resource
633      * @param res a java resource
634      * @param name name to find
635      * @return the class/interface/enum or <code>null</code>
636      * @throws JmiException
637      */

638     static JavaClass findTopLevelClass(Resource res, String JavaDoc name) throws JmiException {
639         if (res == null) throw new NullPointerException JavaDoc("res"); // NOI18N
640
if (name == null) throw new NullPointerException JavaDoc("name"); // NOI18N
641
Iterator it = res.getClassifiers().iterator();
642         while (it.hasNext()) {
643             JavaClass jc = (JavaClass) it.next();
644             if (name.equals(jc.getSimpleName()))
645                 return jc;
646         }
647         return null;
648     }
649     
650     /** Show dialog and allow user to modify new element.
651     * @param customizer The component to be displayed
652     * @param titleKey the key to resource bundle for the title of dialog
653     * @return <CODE>true</CODE> if user pressed OK button,
654     * otherwise <CODE>false</CODE> (for CANCEL)
655     */

656     static boolean openCustomizer(Component JavaDoc customizer, String JavaDoc titleKey) {
657         NotifyDescriptor desriptor = new NotifyDescriptor(
658                                          customizer,
659                                          ElementNode.getString(titleKey),
660                                          NotifyDescriptor.OK_CANCEL_OPTION,
661                                          NotifyDescriptor.PLAIN_MESSAGE,
662                                          null, null);
663
664         Object JavaDoc ret = DialogDisplayer.getDefault().notify(desriptor);
665         return (ret == NotifyDescriptor.OK_OPTION);
666     }
667     
668     static boolean isWriteable(Element element) {
669         JavaModel.getJavaRepository().beginTrans(false);
670         try {
671             boolean w = element.isValid();
672             if (w) {
673                 FileObject fo = JavaModel.getFileObject(element.getResource());
674                 w = fo != null && fo.canWrite();
675             }
676             return w;
677         } finally {
678             JavaModel.getJavaRepository().endTrans();
679         }
680     }
681     
682     private static final int ACCESS_MASK = Modifier.PRIVATE | Modifier.PROTECTED | Modifier.PUBLIC;
683     private static final int OTHERS_MASK = Modifier.ABSTRACT |
684             Modifier.FINAL | Modifier.STATIC | Modifier.SYNCHRONIZED |
685             Modifier.TRANSIENT | Modifier.VOLATILE | Modifier.NATIVE | Modifier.STRICT;
686     
687     public static PropertyPanel createAccessModifiersPanel(ClassMember element, int mask) {
688         mask = mask & ACCESS_MASK;
689         PropertyPanel pp = createModifiersPanel(element, mask);
690         pp.getProperty().setValue(ModifierEditor.CUSTOM_EDITOR_TYPE, ModifierEditor.ACCESS_MODIFIERS_CUSTOM_EDITOR);
691         return pp;
692     }
693
694     public static PropertyPanel createOtherModifiersPanel(ClassMember element, int mask) {
695         mask = mask & OTHERS_MASK;
696         PropertyPanel pp = createModifiersPanel(element, mask);
697         pp.getProperty().setValue(ModifierEditor.CUSTOM_EDITOR_TYPE, ModifierEditor.OTHERS_MODIFIERS_CUSTOM_EDITOR);
698         return pp;
699     }
700     
701     public static PropertyPanel createModifiersPanel(ClassMember element) {
702         return createModifiersPanel(element, getModifiersMask(element));
703     }
704     
705     private static PropertyPanel createModifiersPanel(ClassMember element, int mask) {
706         PropertyPanel modifPanel = new PropertyPanel(
707                 ElementNode.createModifiersProperty(element, true, mask),
708                 PropertyPanel.PREF_CUSTOM_EDITOR
709         );
710         PropertyEditor JavaDoc propEdit = modifPanel.getProperty().getPropertyEditor();
711         if (propEdit instanceof ModifierEditor) {
712             ((ModifierEditor) propEdit).setMask(mask);
713         }
714         return modifPanel;
715     }
716
717     /* Get the possible modifiers for the member.
718      * @return the mask of possible modifiers for this class member. */

719     public static int getModifiersMask(ClassMember member) throws JmiException {
720         int mask = 0;
721         if (member instanceof Field) {
722             mask = getModifiersMask((Field) member);
723         } else if (member instanceof Method) {
724             mask = getModifiersMask((Method) member);
725         } else if (member instanceof Constructor) {
726             mask = getModifiersMask((Constructor) member);
727         } else if (member instanceof Attribute) {
728             mask = getAttributeModifiersMask();
729         } else if (member instanceof JavaClass) {
730             mask = getModifiersMask((JavaClass) member);
731         } else {
732             ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL,
733                     new IllegalStateException JavaDoc("SourceNodes.getModifiersMask: unknown member: " + member)); // NOI18N
734
}
735         return mask;
736     }
737
738     private static int getModifiersMask(Field member) throws JmiException {
739         if (isDeclaredInInterface(member)) {
740             return Modifier.PUBLIC | Modifier.STATIC | Modifier.FINAL;
741         }
742         else {
743             return Modifier.PUBLIC | Modifier.PROTECTED | Modifier.PRIVATE |
744                    Modifier.STATIC | Modifier.FINAL | Modifier.TRANSIENT |
745                    Modifier.VOLATILE;
746         }
747     }
748
749     private static int getModifiersMask(Method member) throws JmiException {
750         if (isDeclaredInInterface(member)) {
751             return Modifier.PUBLIC | Modifier.ABSTRACT;
752         }
753         else {
754             return Modifier.PUBLIC | Modifier.PROTECTED | Modifier.PRIVATE |
755                    Modifier.ABSTRACT | Modifier.STATIC | Modifier.FINAL |
756                    Modifier.NATIVE | Modifier.SYNCHRONIZED;
757         }
758     }
759
760     private static int getModifiersMask(Constructor member) {
761         return Modifier.PUBLIC | Modifier.PROTECTED | Modifier.PRIVATE;
762     }
763
764     private static int getAttributeModifiersMask() {
765         return Modifier.PUBLIC | Modifier.ABSTRACT;
766     }
767
768     private static int getModifiersMask(JavaClass member) throws JmiException {
769         int ret = Modifier.PUBLIC | Modifier.ABSTRACT;
770
771         if (!member.isInterface()) {
772             ret |= Modifier.FINAL;
773         }
774
775         if (isInner(member)) {
776             ret |= Modifier.PROTECTED | Modifier.PRIVATE | Modifier.STATIC;
777         }
778         return ret;
779     }
780     
781     /** Test if this is an inner class.
782     * If so, it has a declaring class.
783     * @return <code>true</code> if so
784     */

785     private static boolean isInner(JavaClass jclass) throws JmiException {
786         return (jclass.getDeclaringClass() != null);
787     }
788
789     private static boolean isDeclaredInInterface(ClassMember member) throws JmiException {
790         ClassDefinition cdef = member.getDeclaringClass();
791         return cdef instanceof JavaClass && ((JavaClass) cdef).isInterface();
792     }
793     
794     /**
795      * Gets all classes recursively, both top-level and inner.
796      * @param res java resource
797      * @return all classes
798      * @throws JmiException
799      */

800     public static List/*<JavaClass>*/ getAllClasses(Resource res) throws JmiException {
801         List/*<JavaClass>*/ l = new LinkedList/*<JavaClass>*/();
802         Iterator/*<JavaClass>*/ it = res.getClassifiers().iterator();
803         while (it.hasNext()) {
804             addAllClasses((JavaClass) it.next(), l);
805         }
806         return l;
807     }
808     
809     private static void addAllClasses(JavaClass jc, List/*<JavaClass>*/ container) throws JmiException {
810         container.add(jc);
811         Iterator it = jc.getFeatures().iterator();
812         while (it.hasNext()) {
813             Object JavaDoc feature = it.next();
814             if (feature instanceof JavaClass) {
815                 addAllClasses((JavaClass) feature, container);
816             }
817         }
818     }
819
820 }
821
Popular Tags