KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > editor > hints > HintsControllerImpl


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 package org.netbeans.modules.editor.hints;
20
21 import java.beans.PropertyChangeEvent JavaDoc;
22 import java.beans.PropertyChangeListener JavaDoc;
23 import java.beans.PropertyChangeSupport JavaDoc;
24 import java.io.IOException JavaDoc;
25 import java.util.ArrayList JavaDoc;
26 import java.util.Collection JavaDoc;
27 import java.util.Collections JavaDoc;
28 import java.util.Iterator JavaDoc;
29 import java.util.List JavaDoc;
30 import java.util.Set JavaDoc;
31 import javax.swing.event.ChangeEvent JavaDoc;
32 import javax.swing.event.ChangeListener JavaDoc;
33 import javax.swing.text.BadLocationException JavaDoc;
34 import javax.swing.text.Document JavaDoc;
35 import javax.swing.text.Position JavaDoc;
36 import javax.swing.text.StyledDocument JavaDoc;
37 import org.netbeans.editor.BaseDocument;
38 import org.netbeans.editor.Utilities;
39 import org.netbeans.spi.editor.hints.ErrorDescription;
40 import org.netbeans.spi.editor.hints.Fix;
41 import org.netbeans.spi.editor.hints.LazyFixList;
42 import org.openide.ErrorManager;
43 import org.openide.cookies.EditorCookie;
44 import org.openide.filesystems.FileObject;
45 import org.openide.loaders.DataObject;
46 import org.openide.text.CloneableEditorSupport;
47 import org.openide.text.EditorSupport;
48 import org.openide.text.NbDocument;
49 import org.openide.text.PositionBounds;
50 import org.openide.text.PositionRef;
51
52 /**
53  *
54  * @author Jan Lahoda
55  */

56 public final class HintsControllerImpl {
57     
58     /**
59      * Creates a new instance of HintsControllerImpl
60      */

61     private HintsControllerImpl() {
62     }
63     
64     public static Collection JavaDoc<FileObject> coveredFiles() {
65         return AnnotationHolder.coveredFiles();
66     }
67     
68     public static List JavaDoc<ErrorDescription> getErrors(FileObject file) {
69         AnnotationHolder holder = AnnotationHolder.getInstance(file);
70         
71         if (holder == null) {
72             return Collections.<ErrorDescription>emptyList();
73         }
74         
75         return holder.getErrors();
76     }
77     
78     public static void setErrors(Document JavaDoc doc, String JavaDoc layer, Collection JavaDoc<? extends ErrorDescription> errors) {
79         DataObject od = (DataObject) doc.getProperty(Document.StreamDescriptionProperty);
80         
81         if (od == null)
82             return ;
83         
84         try {
85             setErrorsImpl(od.getPrimaryFile(), layer, errors);
86         } catch (IOException JavaDoc e) {
87             ErrorManager.getDefault().notify(e);
88         }
89     }
90     
91     public static void setErrors(FileObject file, String JavaDoc layer, Collection JavaDoc<? extends ErrorDescription> errors) {
92         try {
93             setErrorsImpl(file, layer, errors);
94         } catch (IOException JavaDoc e) {
95             ErrorManager.getDefault().notify(e);
96         }
97     }
98     
99     private static void setErrorsImpl(FileObject file, String JavaDoc layer, Collection JavaDoc<? extends ErrorDescription> errors) throws IOException JavaDoc {
100         AnnotationHolder holder = AnnotationHolder.getInstance(file);
101         
102         if (holder != null) {
103             holder.setErrorDescriptions(layer,errors);
104         }
105         
106 // updateInError(file);
107
//
108
// fireChanges();
109
}
110     
111     private static void computeLineSpan(Document JavaDoc doc, int[] offsets) throws BadLocationException JavaDoc {
112         String JavaDoc text = doc.getText(offsets[0], offsets[1] - offsets[0]);
113         int column = 0;
114         int length = text.length();
115         
116         while (column < text.length() && Character.isWhitespace(text.charAt(column))) {
117             column++;
118         }
119         
120         while (length > 0 && Character.isWhitespace(text.charAt(length - 1)))
121             length--;
122         
123         offsets[1] = offsets[0] + length;
124         offsets[0] += column;
125         
126         if (offsets[1] < offsets[0]) {
127             //may happen on lines without non-whitespace characters
128
offsets[0] = offsets[1];
129         }
130     }
131     
132     static int[] computeLineSpan(Document JavaDoc doc, int lineNumber) throws BadLocationException JavaDoc {
133         int lineStartOffset = NbDocument.findLineOffset((StyledDocument JavaDoc) doc, lineNumber - 1);
134         int lineEndOffset;
135         
136         if (doc instanceof BaseDocument) {
137             lineEndOffset = Utilities.getRowEnd((BaseDocument) doc, lineStartOffset);
138         } else {
139             //XXX: performance:
140
String JavaDoc lineText = doc.getText(lineStartOffset, doc.getLength() - lineStartOffset);
141             
142             lineText = lineText.indexOf('\n') != (-1) ? lineText.substring(0, lineText.indexOf('\n')) : lineText;
143             lineEndOffset = lineStartOffset + lineText.length();
144         }
145         
146         int[] span = new int[] {lineStartOffset, lineEndOffset};
147         
148         computeLineSpan(doc, span);
149         
150         return span;
151     }
152     
153     public static PositionBounds fullLine(Document JavaDoc doc, int lineNumber) {
154         DataObject file = (DataObject) doc.getProperty(Document.StreamDescriptionProperty);
155         
156         if (file == null)
157             return null;
158         
159         try {
160             int[] span = computeLineSpan(doc, lineNumber);
161             
162             return linePart(file.getPrimaryFile(), span[0], span[1]);
163         } catch (BadLocationException JavaDoc e) {
164             ErrorManager.getDefault().notify(e);
165             return null;
166         }
167     }
168
169     public static PositionBounds linePart(Document JavaDoc doc, final Position JavaDoc start, final Position JavaDoc end) {
170         DataObject od = (DataObject) doc.getProperty(Document.StreamDescriptionProperty);
171         
172         if (od == null)
173             return null;
174         
175         EditorCookie ec = od.getCookie(EditorCookie.class);
176         
177         if (ec instanceof CloneableEditorSupport) {
178             final CloneableEditorSupport ces = (CloneableEditorSupport) ec;
179             
180             final PositionRef[] refs = new PositionRef[2];
181             
182             doc.render(new Runnable JavaDoc() {
183                 public void run() {
184                     refs[0] = ces.createPositionRef(start.getOffset(), Position.Bias.Forward);
185                     refs[1] = ces.createPositionRef(end.getOffset(), Position.Bias.Backward);
186                 }
187             });
188             
189             return new PositionBounds(refs[0], refs[1]);
190         }
191         
192         if (ec instanceof EditorSupport) {
193             final EditorSupport es = (EditorSupport) ec;
194             
195             final PositionRef[] refs = new PositionRef[2];
196             
197             doc.render(new Runnable JavaDoc() {
198                 public void run() {
199                     refs[0] = es.createPositionRef(start.getOffset(), Position.Bias.Forward);
200                     refs[1] = es.createPositionRef(end.getOffset(), Position.Bias.Backward);
201                 }
202             });
203             
204             return new PositionBounds(refs[0], refs[1]);
205         }
206         
207         return null;
208     }
209
210     public static PositionBounds linePart(FileObject file, int start, int end) {
211         try {
212             DataObject od = DataObject.find(file);
213             
214             if (od == null)
215                 return null;
216             
217             EditorCookie ec = od.getCookie(EditorCookie.class);
218             
219             if (!(ec instanceof CloneableEditorSupport)) {
220                 return null;
221             }
222             
223             final CloneableEditorSupport ces = (CloneableEditorSupport) ec;
224             
225             return new PositionBounds(ces.createPositionRef(start, Position.Bias.Forward), ces.createPositionRef(end, Position.Bias.Backward));
226         } catch (IOException JavaDoc e) {
227             ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, e);
228             return null;
229         }
230     }
231
232     public static boolean isInError(Set JavaDoc<FileObject> fos) {
233         for (Iterator JavaDoc<FileObject> i = fos.iterator(); i.hasNext(); ) {
234             FileObject f = i.next();
235             
236             if (isInError(f)) {
237                 return true;
238             }
239         }
240         
241         return false;
242     }
243     
244     public static boolean isInError(FileObject fo) {
245 // if (/*ProvidersList.getEagerness() == ProvidersList.EAGER_ON_DEMAND && */fo.isData() && !PersistentCache.getDefault().isKnown(fo)) {
246
// //never heard of it:
247
// HintsOperator.getDefault().enqueue(fo);
248
// }
249

250         //temporarily disabling error markers on file icons:
251
// return PersistentCache.getDefault().hasErrors(fo);
252
return false;
253     }
254     
255 // private static void updateInError(FileObject fo) {
256
// //temporarily disabling error markers on file icons:
257
// if (true)
258
// return;
259
//
260
// boolean hasErrors = false;
261
// AnnotationHolder layers = doc2Annotation.get(fo);
262
//
263
// if (layers != null) {
264
// hasErrors = layers.hasErrors();
265
// }
266
//
267
// FileObject recursive = fo;
268
//
269
// while (recursive != null) {
270
// if (hasErrors) {
271
// PersistentCache.getDefault().addErrorFile(recursive, fo);
272
// } else {
273
// PersistentCache.getDefault().removeErrorFile(recursive, fo);
274
// }
275
// recursive = recursive.getParent();
276
// }
277
// }
278

279     private static List JavaDoc<ChangeListener JavaDoc> listeners = new ArrayList JavaDoc<ChangeListener JavaDoc>();
280     
281     public static synchronized void addChangeListener(ChangeListener JavaDoc l) {
282         listeners.add(l);
283     }
284     
285     public static synchronized void removeChangeListener(ChangeListener JavaDoc l) {
286         listeners.remove(l);
287     }
288     
289     private static void fireChanges() {
290         List JavaDoc<ChangeListener JavaDoc> ls;
291         
292         synchronized (HintsControllerImpl.class) {
293             ls = new ArrayList JavaDoc<ChangeListener JavaDoc>(listeners);
294         }
295         
296         ChangeEvent JavaDoc e = new ChangeEvent JavaDoc(HintsControllerImpl.class);
297         
298         for (ChangeListener JavaDoc l : ls) {
299             l.stateChanged(e);
300         }
301     }
302     
303     public static class CompoundLazyFixList implements LazyFixList, PropertyChangeListener JavaDoc {
304         
305         private List JavaDoc<LazyFixList> delegates;
306         
307         private List JavaDoc<Fix> fixesCache;
308         private Boolean JavaDoc computedCache;
309         private Boolean JavaDoc probablyContainsFixesCache;
310         
311         private PropertyChangeSupport JavaDoc pcs;
312         
313         public CompoundLazyFixList(List JavaDoc<LazyFixList> delegates) {
314             this.delegates = delegates;
315             this.pcs = new PropertyChangeSupport JavaDoc(this);
316             
317             for (LazyFixList l : delegates) {
318                 l.addPropertyChangeListener(this);
319             }
320         }
321         
322         public void addPropertyChangeListener(PropertyChangeListener JavaDoc l) {
323             pcs.addPropertyChangeListener(l);
324         }
325
326         public void removePropertyChangeListener(PropertyChangeListener JavaDoc l) {
327             pcs.removePropertyChangeListener(l);
328         }
329
330         public synchronized boolean probablyContainsFixes() {
331             if (probablyContainsFixesCache == null) {
332                 boolean result = false;
333                 
334                 for (LazyFixList l : delegates) {
335                     result |= l.probablyContainsFixes();
336                 }
337                 
338                 probablyContainsFixesCache = Boolean.valueOf(result);
339             }
340             
341             return probablyContainsFixesCache;
342         }
343
344         public synchronized List JavaDoc<Fix> getFixes() {
345             if (fixesCache == null) {
346                 fixesCache = new ArrayList JavaDoc<Fix>();
347                 
348                 for (LazyFixList l : delegates) {
349                     fixesCache.addAll(l.getFixes());
350                 }
351             }
352             
353             return fixesCache;
354         }
355
356         public synchronized boolean isComputed() {
357             if (computedCache == null) {
358                 boolean result = true;
359                 
360                 for (LazyFixList l : delegates) {
361                     result &= l.isComputed();
362                 }
363                 
364                 computedCache = Boolean.valueOf(result);
365             }
366             
367             return computedCache;
368         }
369
370         public void propertyChange(PropertyChangeEvent JavaDoc evt) {
371             if (PROP_FIXES.equals(evt.getPropertyName())) {
372                 synchronized (this) {
373                     fixesCache = null;
374                 }
375                 pcs.firePropertyChange(PROP_FIXES, null, null);
376                 return;
377             }
378                 
379             if (PROP_COMPUTED.equals(evt.getPropertyName())) {
380                 synchronized (this) {
381                     computedCache = null;
382                 }
383                 pcs.firePropertyChange(PROP_COMPUTED, null, null);
384             }
385         }
386         
387     }
388     
389 }
390
Popular Tags