KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > xml > schema > abe > nodes > ABEAbstractNode


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-2007 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20 package org.netbeans.modules.xml.schema.abe.nodes;
21
22 import java.beans.PropertyChangeEvent JavaDoc;
23 import java.beans.PropertyChangeListener JavaDoc;
24 import java.io.IOException JavaDoc;
25 import javax.swing.Action JavaDoc;
26 import org.netbeans.modules.refactoring.api.ui.RefactoringActionsFactory;
27 import org.netbeans.modules.xml.axi.AXIComponent;
28 import org.netbeans.modules.xml.axi.AXIComponent.ComponentType;
29 import org.netbeans.modules.xml.axi.AXIContainer;
30 import org.netbeans.modules.xml.axi.AXIModel;
31 import org.netbeans.modules.xml.axi.Attribute;
32 import org.netbeans.modules.xml.axi.ContentModel;
33 import org.netbeans.modules.xml.axi.Element;
34 import org.netbeans.modules.xml.axi.datatype.Datatype;
35 import org.netbeans.modules.xml.refactoring.CannotRefactorException;
36 import org.netbeans.modules.xml.refactoring.DeleteRequest;
37 import org.netbeans.modules.xml.refactoring.RefactoringManager;
38 import org.netbeans.modules.xml.refactoring.RenameRequest;
39 //import org.netbeans.modules.xml.refactoring.actions.FindUsagesAction;
40
//import org.netbeans.modules.xml.refactoring.actions.RefactorAction;
41
import org.netbeans.modules.xml.refactoring.ui.ReferenceableProvider;
42 import org.netbeans.modules.xml.schema.abe.InstanceDesignConstants;
43 import org.netbeans.modules.xml.schema.abe.InstanceUIContext;
44 import org.netbeans.modules.xml.schema.abe.StartTagPanel;
45 import org.netbeans.modules.xml.schema.abe.UIUtilities;
46 import org.netbeans.modules.xml.schema.abe.action.ShowDesignAction;
47 import org.netbeans.modules.xml.schema.model.SchemaComponent;
48 import org.netbeans.modules.xml.schema.model.SchemaModel;
49 import org.netbeans.modules.xml.schema.ui.basic.SchemaGotoType;
50 import org.netbeans.modules.xml.xam.Component;
51 import org.netbeans.modules.xml.xam.Nameable;
52 import org.netbeans.modules.xml.xam.NamedReferenceable;
53 import org.netbeans.modules.xml.xam.ui.XAMUtils;
54 import org.netbeans.modules.xml.xam.ui.actions.GoToAction;
55 import org.netbeans.modules.xml.xam.ui.actions.GotoType;
56 import org.netbeans.modules.xml.xam.ui.actions.SourceGotoType;
57 import org.netbeans.modules.xml.xam.ui.cookies.GetSuperCookie;
58 import org.netbeans.modules.xml.xam.ui.cookies.GotoCookie;
59 import org.openide.ErrorManager;
60 import org.openide.actions.DeleteAction;
61 import org.openide.actions.NewAction;
62 import org.openide.actions.PropertiesAction;
63 import org.openide.filesystems.FileObject;
64 import org.openide.loaders.DataObject;
65 import org.openide.nodes.AbstractNode;
66 import org.openide.nodes.Children;
67 import org.openide.nodes.Node;
68 import org.openide.nodes.Sheet;
69 import org.openide.util.Lookup;
70 import org.openide.util.NbBundle;
71 import org.openide.util.WeakListeners;
72 import org.openide.util.actions.SystemAction;
73 import org.openide.util.datatransfer.NewType;
74 import org.openide.util.lookup.AbstractLookup;
75 import org.openide.util.lookup.InstanceContent;
76 import org.openide.util.lookup.Lookups;
77 import org.openide.util.lookup.ProxyLookup;
78
79 /**
80  * Base class of all ABE nodes. Each node is associated with some
81  * AXI component. However, there are two ways to obtain the axi component
82  * from these nodes.
83  *
84  * 1. Call getAXIComponent()
85  * 2. Find it from the node's lookup()
86  *
87  * getAXIComponent() will return the component this node is associated with.
88  * In contrast, the component that you get from lookup is always the original.
89  * IN AXIOM there can be proxy components that act on behalf of an original or
90  * shared component. For example, lets say PO.xsd declares an element 'shipTo' and
91  * the type of this eleemnt is from a differnet source file Address.xsd.
92  *
93  * @author Samaresh (Samaresh.Panda@Sun.Com)
94  */

95 public abstract class ABEAbstractNode extends AbstractNode
96         implements GotoCookie, PropertyChangeListener JavaDoc, ReferenceableProvider {
97     
98     private InstanceUIContext context;
99     private AXIComponent axiComponent;
100     private Datatype datatype;
101     boolean uiNode = false;
102     private InstanceContent icont = new InstanceContent();
103     private boolean readOnly = false;
104     
105     /**
106      * Creates a new instance of ABEAbstractNode
107      */

108     public ABEAbstractNode(AXIComponent axiComponent, InstanceUIContext instanceUIContext) {
109         this(axiComponent, Children.LEAF, instanceUIContext, new InstanceContent());
110     }
111     
112     public ABEAbstractNode(AXIComponent axiComponent, Children children) {
113         this(axiComponent, children, null, new InstanceContent());
114     }
115     
116     private ABEAbstractNode(AXIComponent axiComponent, Children children,
117             final InstanceUIContext instanceUIContext, InstanceContent icont){
118         super(children, createLookup(axiComponent, icont, instanceUIContext));
119         this.icont = icont;
120         this.setAXIComponent(axiComponent);
121         this.setContext(instanceUIContext);
122         if(instanceUIContext != null){
123             uiNode = true;
124             this.icont.add(instanceUIContext);
125             instanceUIContext.addPropertyChangeListener(new PropertyChangeListener JavaDoc(){
126                 public void propertyChange(PropertyChangeEvent JavaDoc evt) {
127                     if(evt.getPropertyName().equals(InstanceDesignConstants.PROP_SHUTDOWN)){
128                         ABEAbstractNode.this.icont.remove(instanceUIContext);
129                         ABEAbstractNode.this.axiComponent = null;
130                     }
131                 }
132             });
133         }
134         this.icont.add(this);
135     }
136     
137     /**
138      * This was added for go to source.
139      * Keep the axiComponent in the node's lookup. If the component
140      * is a proxy, keep the original or shared component.
141      */

142     private static Lookup createLookup(final AXIComponent component, InstanceContent icont, InstanceUIContext context) {
143         AXIComponent lookupComponent = component;
144         if(component.getComponentType() == ComponentType.PROXY)
145             lookupComponent = component.getOriginal();
146         final AXIComponent tmpLookupComponent = component;
147         Lookup doLookup = null;
148         if(context != null){
149             doLookup = context.getSchemaDataObject().getNodeDelegate().getLookup();
150             doLookup = Lookups.exclude(doLookup, new Class JavaDoc[]{Node.class});
151         }
152         
153         return new ProxyLookup(new Lookup[]{
154             // schemamodel lookup
155
// exclude the DataObject here because the DataObject for the
156
// model this node is displayed in will be coming from the
157
// NodeDelegate. If this is not done there end up being two
158
// DataObjects in the lookup and this may cause a problem with
159
// save cookies, etc.
160
Lookups.exclude(
161                     component.getModel().getSchemaModel().getModelSource().getLookup(),
162                     new Class JavaDoc[] {DataObject.class}
163             ),
164             // axi component
165
Lookups.singleton(lookupComponent),
166             Lookups.singleton(new GetSuperCookie(){
167                 // this is for go to super definition.
168
public Component getSuper() {
169                     return UIUtilities.getSuperDefn(tmpLookupComponent);
170                 }
171             }),
172             //Schema DO's lookup
173
(doLookup == null ? Lookup.EMPTY : doLookup),
174             //and misc
175
new AbstractLookup(icont)
176         });
177     }
178     
179     
180     public void showSuperDefinition(){
181         InstanceUIContext context = (InstanceUIContext) getLookup().lookup(InstanceUIContext.class);
182         UIUtilities.showDefinition(context, getAXIComponent(), true);
183     }
184     
185     
186     /**
187      * Overwrites AbstractNode's createSheet to allow the creation of sheet.
188      */

189     protected Sheet createSheet() {
190         Sheet sheet = super.createSheet();
191         populateProperties(sheet);
192         return sheet;
193     }
194     
195     protected abstract void populateProperties(Sheet sheet);
196     
197     protected abstract String JavaDoc getTypeDisplayName();
198     
199     public String JavaDoc getDisplayName() {
200         String JavaDoc instanceName = super.getDisplayName();
201         return ((instanceName == null || instanceName.length() == 0)
202         ? "" : instanceName + " ") +
203                 "[" + getTypeDisplayName() + "]"; // NOI18N
204
}
205     
206     public final String JavaDoc getHtmlDisplayName() {
207         return super.getDisplayName();
208     }
209     
210     public Action JavaDoc[] getActions(boolean b) {
211         if(uiNode){
212             if(getAXIComponent().isReadOnly()){
213                 //filter out refactor action if this is a readonly file
214
SystemAction[] ret = new SystemAction[ALL_ACTIONS.length];
215                 for(int i = 0; i < ALL_ACTIONS.length; i++){
216                     String JavaDoc name = null;
217                     if(ALL_ACTIONS[i] != null)
218                         name = (String JavaDoc)ALL_ACTIONS[i].getValue(Action.NAME);
219                                 
220                     if(name != null && name.equals("Refactor") ){
221                         ret[i] = null;
222                     }else{
223                         ret[i] = ALL_ACTIONS[i];
224                     }
225                 }
226                 return ret;
227             }
228             return ALL_ACTIONS;
229         } else
230             return SUB_ACTIONS;
231     }
232     
233     private static final GotoType[] GOTO_TYPES = new GotoType[] {
234         new SourceGotoType(),
235         new SchemaGotoType(),
236     };
237     
238     
239     private static final SystemAction[] ALL_ACTIONS=
240             new SystemAction[]
241     {
242         /*SystemAction.get(CutAction.class),
243         SystemAction.get(CopyAction.class),
244         SystemAction.get(PasteAction.class),
245         null,*/

246         SystemAction.get(NewAction.class),
247         SystemAction.get(DeleteAction.class),
248         null,
249         SystemAction.get(GoToAction.class),
250         null,
251        // SystemAction.get(FindUsagesAction.class),
252
// SystemAction.get(RefactorAction.class),
253
(SystemAction)RefactoringActionsFactory.whereUsedAction(),
254         (SystemAction)RefactoringActionsFactory.editorSubmenuAction(),
255         null,
256         SystemAction.get(PropertiesAction.class)
257     };
258     
259     
260     private static final SystemAction[] SUB_ACTIONS=
261             new SystemAction[]
262     {
263         SystemAction.get(GoToAction.class),
264     };
265     
266     
267     public InstanceUIContext getContext() {
268         return context;
269     }
270     
271     public void setContext(InstanceUIContext context) {
272         this.context = context;
273     }
274     
275     public AXIComponent getAXIComponent() {
276         return axiComponent;
277     }
278     
279     private void setAXIComponent(AXIComponent axiComponent) {
280         this.axiComponent = axiComponent;
281         axiComponent.getModel().addPropertyChangeListener(
282                 WeakListeners.propertyChange(this, axiComponent.getModel())
283                 );
284     }
285     
286     public Datatype getDatatype() {
287         return datatype;
288     }
289     
290     public void propertyChange(PropertyChangeEvent JavaDoc evt) {
291         if (evt.getSource() == axiComponent &&
292                 evt.getPropertyName().equals(AXIContainer.PROP_NAME)) {
293             Object JavaDoc oldValue = evt.getOldValue();
294             String JavaDoc oldDisplayName = oldValue == null ? null : oldValue.toString();
295             fireDisplayNameChange(oldDisplayName, getDisplayName());
296         }
297     }
298     
299     public Action JavaDoc getPreferredAction() {
300         return SystemAction.get(ShowDesignAction.class);
301     }
302     
303     public NewType[] getNewTypes() {
304         return new NewType[0];
305     }
306
307     public GotoType[] getGotoTypes() {
308         return GOTO_TYPES;
309     }
310     
311     public void remove() {
312         if(!canWrite())
313             return;
314         UIUtilities.setBusyCursor(context);
315         try {
316             if(getReferenceable() != null) {
317                 safeDelete();
318                 return;
319             }
320             //use normal delete
321
doDelete();
322         } finally {
323             UIUtilities.setDefaultCursor(context);
324         }
325     }
326     
327     private void doDelete() {
328         if(getAXIComponent() == null ||
329                 getAXIComponent().getModel() == null)
330             return;
331         AXIModel model = getAXIComponent().getModel();
332         model.startTransaction();
333         try{
334             getAXIComponent().getParent().removeChild(getAXIComponent());
335         }finally{
336             model.endTransaction();
337         }
338     }
339     
340     public boolean isReadOnly() {
341         return readOnly;
342     }
343     
344     public void setReadOnly(boolean readOnly) {
345         this.readOnly = readOnly;
346     }
347     
348     public boolean canDestroy() {
349         return canWrite();
350     }
351     
352     public void destroy() throws IOException JavaDoc {
353         super.destroy();
354         remove();
355     }
356     
357     
358     
359     public boolean canWrite() {
360         // Check for null model since component may have been removed.
361
AXIComponent c = getAXIComponent();
362         if(c == null || (c.getModel() == null))
363             return false;
364         
365         AXIComponent o = c.getOriginal();
366         if(c != o && c.isReadOnly()) {
367             return false;
368         }
369         
370         SchemaModel model = c.getModel().getSchemaModel();
371         return XAMUtils.isWritable(model);
372     }
373     
374     
375     public void setName(String JavaDoc name) {
376         if(name == null || getName().equals(name))
377             return;
378         InstanceUIContext context = (InstanceUIContext) this.
379                 getLookup().lookup(InstanceUIContext.class);
380         AXIComponent axiComponent = getAXIComponent();
381         if(canWrite()){
382             if(org.netbeans.modules.xml.xam.dom.Utils.isValidNCName(name)){
383                 //call refactoring.
384
UIUtilities.setBusyCursor(context);
385                 try{
386                     setNameByRefactoring(name);
387                 }finally{
388                     //reset the wait cursor
389
UIUtilities.setDefaultCursor(context);
390                 }
391             }else{
392                 if(context != null){
393                     String JavaDoc errorMessage = NbBundle.getMessage(StartTagPanel.class,
394                             "MSG_NOT_A_NCNAME");
395                     UIUtilities.showErrorMessage(errorMessage, context);
396                 }
397             }
398         }else{
399             if(context != null){
400                 String JavaDoc errorMessage = NbBundle.getMessage(ABEAbstractNode.class,
401                         "MSG_IS_READONLY");
402                 UIUtilities.showErrorMessage(errorMessage, context);
403             }
404         }
405     }
406     
407     
408     public void setNameByRefactoring(String JavaDoc value) {
409         NamedReferenceable ref = getReferenceable();
410         if(ref == null){
411             //since this is a ref, it can not be renamed here.
412
//this often happens for references
413
/*setNameInModel(value);
414             return;*/

415             AXIComponent axiComponent = getAXIComponent();
416             if( (axiComponent instanceof Element) || (axiComponent instanceof Attribute) ){
417                 if(axiComponent instanceof Element){
418                     axiComponent = ((Element) axiComponent).getReferent();
419                 } else{
420                     axiComponent = ((Attribute) axiComponent).getReferent();
421                 }
422                 if(axiComponent == null){
423                     setNameInModel(value);
424                     return;
425                 }
426                 ref = getReferenceable(axiComponent);
427             }else{
428                 setNameInModel(value);
429                 return;
430             }
431         }
432         AXIModel model = getAXIComponent().getModel();
433         // try rename silently
434
RenameRequest request = new RenameRequest((Nameable)ref, value);
435         request.setScopeLocal();
436         try {
437             context.setUserInducedEventMode(true);
438             SchemaModel sm = model.getSchemaModel();
439             RefactoringManager.getInstance().execute(request, false);
440             model.sync();
441         } catch(CannotRefactorException ex) {
442             // call rename refactoring UI
443
/*
444             WhereUsedView wuv = new WhereUsedView(ref);
445             RenameRefactoringUI ui = new RenameRefactoringUI(wuv, request);
446             TopComponent activetc = TopComponent.getRegistry().getActivated();
447             if (activetc instanceof CloneableEditorSupport.Pane) {
448                 new RefactoringPanel(ui, activetc);
449             } else {
450                 new RefactoringPanel(ui);
451             }*/

452         } catch (IOException JavaDoc ex) {
453             ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, ex);
454         }
455     }
456     
457     public void setNameInModel(String JavaDoc name){
458         //local component so just rename
459
try {
460             axiComponent.getModel().startTransaction();
461             if(axiComponent instanceof Element)
462                 ((Element)axiComponent).setName(name);
463             else if(axiComponent instanceof ContentModel)
464                 ((ContentModel)axiComponent).setName(name);
465             else if(axiComponent instanceof Attribute)
466                 ((Attribute)axiComponent).setName(name);
467         } finally{
468             axiComponent.getModel().endTransaction();
469         }
470     }
471     
472     public NamedReferenceable getReferenceable() {
473         if(!getAXIComponent().getOriginal().isGlobal())
474             return null;
475         
476         SchemaComponent comp = getAXIComponent().getOriginal().getPeer();
477         if (comp instanceof NamedReferenceable && isValid() && comp.getModel().
478                 getModelSource().getLookup().lookup(FileObject.class) != null){
479             return NamedReferenceable.class.cast(comp);
480         }
481         return null;
482     }
483     
484     private NamedReferenceable getReferenceable(AXIComponent axiComponent) {
485         if(!axiComponent.getOriginal().isGlobal())
486             return null;
487         SchemaComponent comp = axiComponent.getOriginal().getPeer();
488         if (comp instanceof NamedReferenceable && isValid() && comp.getModel().
489                 getModelSource().getLookup().lookup(FileObject.class) != null){
490             return NamedReferenceable.class.cast(comp);
491         }
492         return null;
493     }
494     
495     protected boolean isValid() {
496         return getAXIComponent().getPeer().getModel() != null;
497     }
498     
499     private void safeDelete() {
500         final NamedReferenceable ref = getReferenceable();
501         // try delete silently
502
DeleteRequest request = new DeleteRequest(ref);
503         request.setScopeLocal();
504         AXIModel model = getAXIComponent().getModel();
505         try {
506             context.setUserInducedEventMode(true);
507             SchemaModel sm = model.getSchemaModel();
508             RefactoringManager.getInstance().execute(request, true);
509             model.sync();
510         } catch(CannotRefactorException ex) {
511             // call delete refactoring UI
512
//SwingUtilities.invokeLater();
513

514                     /*new Runnable(){
515                 public void run() {
516                     WhereUsedView wuv = new WhereUsedView(ref);
517                     DeleteRefactoringUI ui = new DeleteRefactoringUI(wuv, ref);
518                     TopComponent activetc = TopComponent.getRegistry().getActivated();
519                     if (activetc instanceof CloneableEditorSupport.Pane) {
520                         new RefactoringPanel(ui, activetc);
521                     } else {
522                         new RefactoringPanel(ui);
523                     }
524                 }
525             });*/

526         } catch (IOException JavaDoc ex) {
527             ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, ex);
528         }
529     }
530     
531     
532     public Sheet.Set getSharedSet(Sheet sheet){
533         Sheet.Set sharedSet = null;
534         sharedSet = sheet.get("shared");
535         if(sharedSet != null)
536             return sharedSet;
537         sharedSet = sheet.createPropertiesSet();
538         String JavaDoc shared = NbBundle.getMessage(ElementNode.class, "LBL_SHARED");
539         String JavaDoc sharedMessage = NbBundle.getMessage(ElementNode.class, "LBL_SHARED_MESSAGE");
540         sharedSet.setName("shared");//NOI18N
541
sharedSet.setDisplayName(shared);
542         sharedSet.setShortDescription(sharedMessage);
543         return sharedSet;
544     }
545     
546 }
547
Popular Tags