This Bugzilla instance is a read-only archive of historic NetBeans bug reports. To report a bug in NetBeans please follow the project's instructions for reporting issues.

View | Details | Raw Unified | Return to bug 53454
Collapse All | Expand All

(-)editor/manifest.mf (+1 lines)
Lines 4-7 Link Here
4
OpenIDE-Module-Install: org/netbeans/modules/editor/EditorModule.class
4
OpenIDE-Module-Install: org/netbeans/modules/editor/EditorModule.class
5
OpenIDE-Module-Specification-Version: 1.18
5
OpenIDE-Module-Specification-Version: 1.18
6
OpenIDE-Module-Layer: org/netbeans/modules/editor/resources/layer.xml
6
OpenIDE-Module-Layer: org/netbeans/modules/editor/resources/layer.xml
7
OpenIDE-Module-Module-Dependencies: org.netbeans.modules.editor.lib/1 = @BUILD_NUMBER_SUBST@, org.netbeans.modules.editor.fold/1, org.netbeans.modules.editor.lib/1, org.netbeans.modules.editor.util/1, org.openidex.util/3, org.openide.loaders > 4.11
7
8
(-)editor/arch/arch-editor.xml (-3 / +35 lines)
Lines 678-684 Link Here
678
        </question>
678
        </question>
679
-->
679
-->
680
<answer id="lookup-register">
680
<answer id="lookup-register">
681
    No.
681
    <code>org.netbeans.modules.editor.hyperlink.LayerHyperlinkProviderManager</code>
682
    is registered using <code>META-INF/services</code>.
683
    <br/>
684
    It is an extension of <code>org.netbeans.lib.editor.hyperlink.HyperlinkProviderManager</code>
685
    allowing to instantiate the <code>org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider</code>
686
    instances from the xml layer of the System FS for particular mime-types.
682
</answer>
687
</answer>
683
688
684
689
Lines 983-988 Link Here
983
    <p>
988
    <p>
984
    Please see <a href="http://www.netbeans.org/source/browse/editor/src/org/netbeans/modules/editor/resources/layer.xml">layer.xml</a> for further details.
989
    Please see <a href="http://www.netbeans.org/source/browse/editor/src/org/netbeans/modules/editor/resources/layer.xml">layer.xml</a> for further details.
985
    </p>
990
    </p>
991
    
992
    <p>
993
    The <code>org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider</code>
994
    instances can be registered by editors for the particular mime-types
995
    into <i>Editors/|mime-type|/HyperlinkProviders</i>.
996
    <br/>
997
    There can be multiple providers registered and their order
998
    will be respected during querying by the hyperlinking infrastructure
999
    (first provider which recognizes the given offset as a hyperlinking point
1000
    will be used).
1001
    </p>
986
</answer>
1002
</answer>
987
1003
988
1004
Lines 1079-1086 Link Here
1079
The editor functionality are mainly implementations of the Swing Text package APIs
1095
The editor functionality are mainly implementations of the Swing Text package APIs
1080
plus extension features such as Syntax Coloring, Code Completion,
1096
plus extension features such as Syntax Coloring, Code Completion,
1081
Word Matching, Abbreviations or Macros.
1097
Word Matching, Abbreviations or Macros.
1082
There are no official APIs yet but the Code Folding API
1098
1083
and other extensions APIs are being formed.
1099
<h4>Hyperlink SPI</h4>
1100
<api group="java" name="EditorHyperlinkSPI" type="export" category="devel">
1101
    Hyperlink SPI in <code>org.netbeans.lib.editor.hyperlink.spi</code>
1102
    allows the editors for a particular mime-type to respond to the situation
1103
    when a user hovers over the text with a Ctrl key pressed.
1104
</api> 
1105
1106
<br/>
1107
The Hyperlink SPI resolves whether the text under the mouse is hyperlink-able
1108
and defines the span of the hyperlink and the action to be performed
1109
when the user clicks on the hyperlink.
1110
<br/>
1111
The SPI consists of a single <code>HyperlinkProvider</code>
1112
class that contains a javadoc with instructions
1113
about how to register the implementation in the xml layer for the given
1114
mime-type (mentioned in the layer section here as well).
1115
1084
</answer>
1116
</answer>
1085
1117
1086
1118
(-)editor/lib/manifest.mf (+1 lines)
Lines 2-5 Link Here
2
OpenIDE-Module: org.netbeans.modules.editor.lib/1
2
OpenIDE-Module: org.netbeans.modules.editor.lib/1
3
OpenIDE-Module-Localizing-Bundle: org/netbeans/modules/editor/lib/Bundle.properties
3
OpenIDE-Module-Localizing-Bundle: org/netbeans/modules/editor/lib/Bundle.properties
4
OpenIDE-Module-Specification-Version: 1.3
4
OpenIDE-Module-Specification-Version: 1.3
5
OpenIDE-Module-Implementation-Version: @BUILD_NUMBER_SUBST@
5
6
(-)editor/lib/nbproject/project.xml (+1 lines)
Lines 53-58 Link Here
53
                <package>org.netbeans.editor.ext.plain</package>
53
                <package>org.netbeans.editor.ext.plain</package>
54
                <package>org.netbeans.editor.view.spi</package>
54
                <package>org.netbeans.editor.view.spi</package>
55
                <package>org.netbeans.lib.editor.view</package>
55
                <package>org.netbeans.lib.editor.view</package>
56
                <package>org.netbeans.lib.editor.hyperlink.spi</package>
56
            </public-packages>
57
            </public-packages>
57
            <javadoc/>
58
            <javadoc/>
58
        </data>
59
        </data>
(-)editor/libsrc/org/netbeans/editor/BaseKit.java (+3 lines)
Lines 503-508 Link Here
503
503
504
        c.enableInputMethods(enableIM);
504
        c.enableInputMethods(enableIM);
505
        executeInstallActions(c);
505
        executeInstallActions(c);
506
        
507
        c.putClientProperty("hyperlink-operation",
508
                org.netbeans.lib.editor.hyperlink.HyperlinkOperation.create(c, getContentType()));
506
    }
509
    }
507
510
508
    protected void executeInstallActions(JEditorPane c) {
511
    protected void executeInstallActions(JEditorPane c) {
(-)editor/libsrc/org/netbeans/lib/editor/hyperlink/DefaultHyperlinkProviderManager.java (+72 lines)
Added Link Here
1
/*
2
 *                 Sun Public License Notice
3
 *
4
 * The contents of this file are subject to the Sun Public License
5
 * Version 1.0 (the "License"). You may not use this file except in
6
 * compliance with the License. A copy of the License is available at
7
 * http://www.sun.com/
8
 *
9
 * The Original Code is NetBeans. The Initial Developer of the Original
10
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2004 Sun
11
 * Microsystems, Inc. All Rights Reserved.
12
 */
13
14
package org.netbeans.lib.editor.hyperlink;
15
16
import java.util.ArrayList;
17
import java.util.Collections;
18
import java.util.HashMap;
19
import java.util.List;
20
import java.util.Map;
21
import org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider;
22
23
/**
24
 * Default implementation of the provider manager.
25
 * <br>
26
 * The default empty list of hyperlink providers
27
 * can be extended by registering new ones for each mimetype.
28
 *
29
 * @author Miloslav Metelka
30
 */
31
public class DefaultHyperlinkProviderManager extends HyperlinkProviderManager {
32
    
33
    private Map mimeType2providerList = new HashMap();
34
    
35
    /**
36
     * Register a new HyperlinkProvider.
37
     *
38
     * @param mimeType mime-type for which the provider is being registered.
39
     * @param provider provider to register.
40
     */
41
    public synchronized void addHyperlinkProvider(String mimeType, HyperlinkProvider provider) {
42
        getProviderList(mimeType, true).add(provider);
43
    }
44
    
45
    /**
46
     * Unregister a HyperlinkProvider.
47
     *
48
     * @param mimeType mime-type for which the provider is being unregistered.
49
     * @param provider provider to unregister.
50
     */
51
    public synchronized void removeHyperlinkProvider(String mimeType, HyperlinkProvider provider) {
52
        List providerList = getProviderList(mimeType, false);
53
        if (providerList != null) {
54
            providerList.remove(provider);
55
        }
56
    }
57
    
58
    public synchronized List/*<HyperlinkProvider>*/ getHyperlinkProviders(String mimeType) {
59
        List providers = getProviderList(mimeType, false);
60
        return (providers != null) ? providers : Collections.EMPTY_LIST;
61
    }
62
    
63
    private List getProviderList(String mimeType, boolean forceCreation) {
64
        List providerList = (List)mimeType2providerList.get(mimeType);
65
        if (providerList == null && forceCreation) {
66
            providerList = new ArrayList();
67
            mimeType2providerList.put(mimeType, providerList);
68
        }
69
        return providerList;
70
    }
71
    
72
}
(-)editor/libsrc/org/netbeans/lib/editor/hyperlink/HyperlinkOperation.java (+302 lines)
Added Link Here
1
/*
2
 *                 Sun Public License Notice
3
 *
4
 * The contents of this file are subject to the Sun Public License
5
 * Version 1.0 (the "License"). You may not use this file except in
6
 * compliance with the License. A copy of the License is available at
7
 * http://www.sun.com/
8
 *
9
 * The Original Code is NetBeans. The Initial Developer of the Original
10
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2004 Sun
11
 * Microsystems, Inc. All Rights Reserved.
12
 */
13
14
package org.netbeans.lib.editor.hyperlink;
15
16
import java.awt.Color;
17
import java.awt.Cursor;
18
import java.awt.event.KeyEvent;
19
import java.awt.event.KeyListener;
20
import java.awt.event.MouseEvent;
21
import java.awt.event.MouseListener;
22
import java.awt.event.MouseMotionListener;
23
import java.beans.PropertyChangeEvent;
24
import java.beans.PropertyChangeListener;
25
import java.util.ArrayList;
26
import java.util.Collections;
27
import java.util.HashMap;
28
import java.util.Iterator;
29
import java.util.List;
30
import javax.swing.SwingUtilities;
31
import javax.swing.text.Document;
32
import javax.swing.text.JTextComponent;
33
import org.netbeans.editor.*;
34
import org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider;
35
36
/**
37
 *
38
 * @author Jan Lahoda
39
 */
40
public class HyperlinkOperation implements MouseListener, MouseMotionListener, PropertyChangeListener, KeyListener {
41
42
    private JTextComponent component;
43
    private Document       currentDocument;
44
    private HyperlinkLayer layer;
45
    private String         mimeType;
46
    private boolean        componentHadMouseCursor;
47
    private Cursor         oldComponentsMouseCursor;
48
    private boolean        hyperlinkUp;
49
    
50
    public static HyperlinkOperation create(JTextComponent component, String mimeType) {
51
        return new HyperlinkOperation(component, mimeType);
52
    }
53
    
54
    /** Creates a new instance of HoveringImpl */
55
    private HyperlinkOperation(JTextComponent component, String mimeType) {
56
        this.component = component;
57
        this.mimeType  = mimeType;
58
        this.oldComponentsMouseCursor = null;
59
        this.componentHadMouseCursor = false;
60
        this.hyperlinkUp = false;
61
        
62
        component.addPropertyChangeListener("document", this);
63
    }
64
    
65
    private void documentUpdated() {
66
        currentDocument = component.getDocument();
67
        
68
        if (currentDocument instanceof BaseDocument) {
69
            BaseDocument bd = (BaseDocument) currentDocument;
70
            
71
            bd.addLayer(layer = new HyperlinkLayer(), 1100);
72
            
73
            component.addMouseListener(this);
74
            component.addMouseMotionListener(this);
75
            component.addKeyListener(this);
76
        }
77
    }
78
    
79
    public void mouseMoved(MouseEvent e) {
80
        if ((e.getModifiersEx() & MouseEvent.CTRL_DOWN_MASK) == MouseEvent.CTRL_DOWN_MASK) {
81
            int position = component.viewToModel(e.getPoint());
82
            
83
            if (position < 0) {
84
                unHyperlink(true);
85
                
86
                return ;
87
            }
88
            
89
            performHyperlinking(position);
90
        } else {
91
            unHyperlink(true);
92
        }
93
    }
94
    
95
    public void mouseDragged(MouseEvent e) {
96
        //ignored
97
    }
98
    
99
    private void performHyperlinking(int position) {
100
        HyperlinkProvider provider = findProvider(position);
101
        
102
        if (provider != null) {
103
            int[] offsets = provider.getHyperlinkSpan(component.getDocument(), position);
104
            
105
            if (offsets != null)
106
                makeHyperlink(offsets[0], offsets[1]);
107
        } else {
108
            unHyperlink(true);
109
        }
110
    }
111
    
112
    private void performAction(int position) {
113
        HyperlinkProvider provider = findProvider(position);
114
        
115
        if (provider != null) {
116
            provider.performClickAction(component.getDocument(), position);
117
        }
118
    }
119
    
120
    private HyperlinkProvider findProvider(int position) {
121
        List/*<HyperlinkProvider>*/ providers = HyperlinkProviderManager.getDefault().getHyperlinkProviders(mimeType);
122
        
123
        for (Iterator/*<HyperlinkProvider>*/ i = providers.iterator(); i.hasNext(); ) {
124
            HyperlinkProvider provider = (HyperlinkProvider) i.next();
125
            
126
            if (provider.isHyperlinkPoint(component.getDocument(), position)) {
127
                return provider;
128
            }
129
        }
130
        
131
        return null;
132
    }
133
    
134
    private synchronized void makeHyperlink(final int start, final int end) {
135
        boolean makeCursorSnapshot = true;
136
        
137
        if (hyperlinkUp) {
138
            unHyperlink(false);
139
            makeCursorSnapshot = false;
140
        }
141
        
142
        hyperlinkUp = true;
143
            
144
        layer.hyperlinkStart = start;
145
        layer.hyperlinkEnd   = end;
146
        
147
        SwingUtilities.invokeLater(new Runnable() {
148
            public void run() {
149
                component.getUI().damageRange(component, start, end);
150
            }
151
        });
152
        
153
        if (makeCursorSnapshot) {
154
            if (componentHadMouseCursor = component.isCursorSet()) {
155
                oldComponentsMouseCursor = component.getCursor();
156
            } else {
157
                oldComponentsMouseCursor = null;
158
            }
159
            component.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
160
        }
161
    }
162
    
163
    private synchronized void unHyperlink(boolean removeCursor) {
164
        if (!hyperlinkUp)
165
            return ;
166
        
167
        final int start = layer.hyperlinkStart;
168
        final int end   = layer.hyperlinkEnd;
169
        
170
        layer.hyperlinkStart = -1;
171
        layer.hyperlinkEnd   = -1;
172
        
173
        if (start != (-1) && end != (-1)) {
174
            SwingUtilities.invokeLater(new Runnable() {
175
                public void run() {
176
                    component.getUI().damageRange(component, start, end);
177
                }
178
            });
179
        }
180
        
181
        if (componentHadMouseCursor && removeCursor) {
182
            component.setCursor(oldComponentsMouseCursor);
183
            componentHadMouseCursor = false;
184
            oldComponentsMouseCursor = null;
185
        }
186
        
187
        hyperlinkUp = false;
188
    }
189
    
190
    public void propertyChange(PropertyChangeEvent evt) {
191
        if (currentDocument != component.getDocument())
192
            documentUpdated();
193
    }
194
    
195
    public void keyTyped(KeyEvent e) {
196
        //ignored
197
    }
198
199
    public void keyReleased(KeyEvent e) {
200
        if (e.getKeyCode() == KeyEvent.VK_CONTROL)
201
            unHyperlink(true);
202
    }
203
204
    public void keyPressed(KeyEvent e) {
205
        //ignored
206
    }
207
208
    public void mouseReleased(MouseEvent e) {
209
        //ignored
210
    }
211
212
    public void mousePressed(MouseEvent e) {
213
        //ignored
214
    }
215
216
    public void mouseExited(MouseEvent e) {
217
        //ignored
218
    }
219
220
    public void mouseEntered(MouseEvent e) {
221
        //ignored
222
    }
223
224
    public void mouseClicked(MouseEvent e) {
225
        if ((e.getModifiersEx() & MouseEvent.CTRL_DOWN_MASK) == MouseEvent.CTRL_DOWN_MASK) {
226
            int position = component.viewToModel(e.getPoint());
227
            
228
            if (position < 0) {
229
                return ;
230
            }
231
            
232
            performAction(position);
233
        }
234
    }
235
    
236
    private static class HyperlinkLayer extends DrawLayer.AbstractLayer {
237
        
238
        private int hyperlinkStart = (-1);
239
        private int hyperlinkEnd = (-1);
240
        
241
        public static final String NAME = "hyperlink-layer";
242
        
243
        public static final int VISIBILITY = 1050;
244
        
245
        private boolean initialized = false;
246
        
247
        public HyperlinkLayer() {
248
            super(NAME);
249
            
250
            this.initialized = false;
251
        }
252
        
253
        private void checkDocument(Document doc) {
254
        }
255
        
256
        public boolean extendsEOL() {
257
            return true;
258
        }
259
        
260
        public synchronized void init(final DrawContext ctx) {
261
            if (!initialized) {
262
                Document doc = ctx.getEditorUI().getDocument();
263
                
264
                initialized = true;
265
                checkDocument(doc);
266
            }
267
            
268
            if (isActive())
269
                setNextActivityChangeOffset(hyperlinkStart);
270
        }
271
        
272
        private boolean isActive() {
273
            return hyperlinkStart != (-1) && hyperlinkEnd != (-1);
274
        }
275
        
276
        public boolean isActive(DrawContext ctx, MarkFactory.DrawMark mark) {
277
            return isActive();
278
        }
279
        
280
        private boolean isIn(int offset) {
281
            return offset >= hyperlinkStart && offset < hyperlinkEnd;
282
        }
283
        
284
        private static Coloring hoverColoring = new Coloring(null, 0, Color.BLUE, null, Color.BLUE, null);
285
        
286
        public void updateContext(DrawContext ctx) {
287
            if (!isActive())
288
                return ;
289
            
290
            int currentOffset = ctx.getFragmentOffset();
291
            
292
            if (isIn(currentOffset)) {
293
                hoverColoring.apply(ctx);
294
                
295
                if (isIn(currentOffset + ctx.getFragmentLength()))
296
                    setNextActivityChangeOffset(currentOffset + ctx.getFragmentLength());
297
            }
298
        }
299
        
300
    }
301
        
302
}
(-)editor/libsrc/org/netbeans/lib/editor/hyperlink/HyperlinkProviderManager.java (+71 lines)
Added Link Here
1
/*
2
 *                 Sun Public License Notice
3
 *
4
 * The contents of this file are subject to the Sun Public License
5
 * Version 1.0 (the "License"). You may not use this file except in
6
 * compliance with the License. A copy of the License is available at
7
 * http://www.sun.com/
8
 *
9
 * The Original Code is NetBeans. The Initial Developer of the Original
10
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2004 Sun
11
 * Microsystems, Inc. All Rights Reserved.
12
 */
13
14
package org.netbeans.lib.editor.hyperlink;
15
16
import java.util.List;
17
import org.openide.util.Lookup;
18
19
/**
20
 * This class provides a list of HyperlinkProvider(s) for a given mime type.
21
 * <br>
22
 * This class is first searched in the <code>Lookup</code>. If no implementation
23
 * is found then a default implementation {@link DefaultHyperlinkProviderManager}
24
 * is constructed.
25
 *
26
 * Besides the default implementation there is
27
 * {@link org.netbeans.modules.editor.hyperlink.LayerHyperlinkProviderManager}
28
 * in the editor module (non-library part)
29
 * which reads the hyperlink providers for the mime-types
30
 * from the xml layer in the System FS.
31
 * <br>
32
 * These two existing implementations should suffice for most uses.
33
 *
34
 * @author Jan Lahoda
35
 */
36
public abstract class HyperlinkProviderManager {
37
    
38
    private static HyperlinkProviderManager defaultManager;
39
    
40
    /**
41
     * Find the default hyperlink provider manager in the lookup (or construct
42
     * a simple default implementation if not found).
43
     *
44
     * @return non-null manager.
45
     */
46
    public static synchronized HyperlinkProviderManager getDefault() {
47
        if (defaultManager == null) {
48
            defaultManager = createDefault();
49
        }
50
        return defaultManager;
51
    }
52
    
53
    private static HyperlinkProviderManager createDefault() {
54
        HyperlinkProviderManager mgr = (HyperlinkProviderManager)Lookup.getDefault().
55
                lookup(HyperlinkProviderManager.class);
56
57
        if (mgr == null) { // not found in lookup -> use default
58
            mgr = new DefaultHyperlinkProviderManager();
59
        }
60
        return mgr;
61
    }
62
    
63
    /**
64
     * Provide List of HyperlinkProvider(s) for a given mime type.
65
     * 
66
     * @param mimeType mime type to test
67
     * @param List of HyperlinkProvider(s) for a given mime type.
68
     */
69
    public abstract List/*<HyperlinkProvider>*/ getHyperlinkProviders(String mimeType);
70
    
71
}
(-)editor/libsrc/org/netbeans/lib/editor/hyperlink/spi/HyperlinkProvider.java (+94 lines)
Added Link Here
1
/*
2
 *                 Sun Public License Notice
3
 *
4
 * The contents of this file are subject to the Sun Public License
5
 * Version 1.0 (the "License"). You may not use this file except in
6
 * compliance with the License. A copy of the License is available at
7
 * http://www.sun.com/
8
 *
9
 * The Original Code is NetBeans. The Initial Developer of the Original
10
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2004 Sun
11
 * Microsystems, Inc. All Rights Reserved.
12
 */
13
14
package org.netbeans.lib.editor.hyperlink.spi;
15
16
import javax.swing.text.Document;
17
18
/**
19
 * This interface should be implemented by anyone who whats to provide hyperlinking
20
 * functionality in the source code.
21
 * <br>
22
 * There should be one provider instance per mime-type.
23
 * Its methods are called for all the opened editors of the given mime-type
24
 * where the hyperlinking functionality gets requested.
25
 *
26
 * <p>
27
 * The providers need to be registered.
28
 * For NetBeans IDE, the default approach is to use System FileSystem.
29
 * <br>
30
 * The HyperlinkProvider(s) should be registered as ".instance" objects under
31
 * <code>Editors/&lt;mime-type&gt;/HyperlinkProviders</code> directory.
32
 * </p>
33
 * 
34
 * <p>
35
 * Please see {@link org.netbeans.lib.editor.hyperlink.HyperlinkProviderManager}
36
 * for more details.
37
 * </p>
38
 *
39
 * <p>
40
 * Note: there is no assurance on the order of calling of the methods in this class.
41
 * The callers may call the methods in any order and even do not call some of these methods
42
 * at all.
43
 * </p>
44
 *
45
 * @author Jan Lahoda
46
 * @since 1.0
47
 */
48
public interface HyperlinkProvider {
49
    
50
    /**
51
     * Should determine whether there should be a hyperlink on the given offset
52
     * in the given document. May be called any number of times for given parameters.
53
     * <br>
54
     * This method is called from event dispatch thread.
55
     * It should run very fast as it is called very often.
56
     *
57
     * @param doc document on which to operate.
58
     * @param offset &gt;=0 offset to test (it generally should be offset &lt; doc.getLength(), but
59
     *               the implementations should not depend on it)
60
     * @return true if the provided offset should be in a hyperlink
61
     *         false otherwise
62
     */
63
    boolean isHyperlinkPoint(Document doc, int offset);
64
    
65
    /**
66
     * Should determine the span of hyperlink on given offset. Generally, if
67
     * isHyperlinkPoint returns true for a given parameters, this class should
68
     * return a valid span, but it is not strictly required.
69
     * <br>
70
     * This method is called from event dispatch thread.
71
     * This method should run very fast as it is called very often.
72
     *
73
     * @param doc document on which to operate.
74
     * @param offset &gt;=0 offset to test (it generally should be offset &lt; doc.getLength(), but
75
     *               the implementations should not depend on it)
76
     * @return a two member array which contains starting and ending offset of a hyperlink
77
     *         that should be on a given offset
78
     */
79
    int[] getHyperlinkSpan(Document doc, int offset);
80
    
81
    /**
82
     * The implementor should perform an action
83
     * corresponding to clicking on the hyperlink on the given offset. The
84
     * nature of the action is given by the nature of given hyperlink, but
85
     * generally should open some resource or move cursor
86
     * to certain place in the current document.
87
     *
88
     * @param doc document on which to operate.
89
     * @param offset &gt;=0 offset to test (it generally should be offset &lt; doc.getLength(), but
90
     *               the implementations should not depend on it)
91
     */
92
    void performClickAction(Document doc, int offset);
93
    
94
}
(-)editor/src/META-INF/services/org.netbeans.lib.editor.hyperlink.HyperlinkProviderManager (+1 lines)
Added Link Here
1
org.netbeans.modules.editor.hyperlink.LayerHyperlinkProviderManager
(-)editor/src/org/netbeans/modules/editor/EditorModule.java (-1 / +1 lines)
Lines 149-155 Link Here
149
        } catch (Throwable t) {
149
        } catch (Throwable t) {
150
            t.printStackTrace();
150
            t.printStackTrace();
151
        }
151
        }
152
152
            
153
        // Registration of the editor kits to JEditorPane
153
        // Registration of the editor kits to JEditorPane
154
//        for (int i = 0; i < replacements.length; i++) {
154
//        for (int i = 0; i < replacements.length; i++) {
155
//            JEditorPane.registerEditorKitForContentType(
155
//            JEditorPane.registerEditorKitForContentType(
(-)editor/src/org/netbeans/modules/editor/hyperlink/LayerHyperlinkProviderManager.java (+74 lines)
Added Link Here
1
/*
2
 *                 Sun Public License Notice
3
 *
4
 * The contents of this file are subject to the Sun Public License
5
 * Version 1.0 (the "License"). You may not use this file except in
6
 * compliance with the License. A copy of the License is available at
7
 * http://www.sun.com/
8
 *
9
 * The Original Code is NetBeans. The Initial Developer of the Original
10
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2004 Sun
11
 * Microsystems, Inc. All Rights Reserved.
12
 */
13
14
package org.netbeans.modules.editor.hyperlink;
15
16
import java.util.ArrayList;
17
import java.util.Collections;
18
import java.util.List;
19
import org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider;
20
import org.netbeans.lib.editor.hyperlink.HyperlinkProviderManager;
21
import org.openide.ErrorManager;
22
import org.openide.filesystems.FileObject;
23
import org.openide.filesystems.Repository;
24
import org.openide.loaders.DataObject;
25
import org.openide.loaders.DataObjectNotFoundException;
26
import org.openide.loaders.FolderLookup;
27
import org.openide.util.Lookup;
28
29
/**
30
 * Finds hyperlink providers in the System FileSystem. The HyperlinkProvider(s) should
31
 * be registered as ".instance" objects under <code>Editors/&lt;mime-type&gt;/HyperlinkProviders</code>
32
 * directory.
33
 *
34
 * @author Jan Lahoda
35
 */
36
public final class LayerHyperlinkProviderManager extends HyperlinkProviderManager {
37
    
38
    private Lookup lookup;
39
    
40
    /**
41
     * Creates a new instance of LayerHyperlinkProviderManager
42
     */
43
    public LayerHyperlinkProviderManager() {
44
    }
45
46
    public List/*<HyperlinkProvider>*/ getHyperlinkProviders(String mimeType) {
47
        FileObject hyperlinkProvidersFolder = Repository.getDefault().getDefaultFileSystem().
48
                findResource("Editors/" + mimeType + "/HyperlinkProviders");
49
        
50
        if (hyperlinkProvidersFolder!= null
51
                && !hyperlinkProvidersFolder.isData()
52
                && hyperlinkProvidersFolder.isValid()
53
                && !hyperlinkProvidersFolder.isVirtual()
54
        ) {
55
        
56
            try {
57
                DataObject od = DataObject.find(hyperlinkProvidersFolder);
58
59
                if (od instanceof DataObject.Container) {
60
                    FolderLookup flookup = new FolderLookup((DataObject.Container) od);
61
62
                    return Collections.unmodifiableList(
63
                        new ArrayList(flookup.getLookup().lookup(
64
                            new Lookup.Template(HyperlinkProvider.class)).allInstances()));
65
                }
66
            } catch (DataObjectNotFoundException e) {
67
                ErrorManager.getDefault().notify(e);
68
            }
69
        }
70
71
        return Collections.EMPTY_LIST;
72
    }
73
    
74
}
(-)ide/golden/impl-deps.txt (+2 lines)
Lines 2-7 Link Here
2
  REQUIRES org.netbeans.modules.xml.core/2 (ide)
2
  REQUIRES org.netbeans.modules.xml.core/2 (ide)
3
MODULE org.netbeans.modules.dbschema/1 (ide)
3
MODULE org.netbeans.modules.dbschema/1 (ide)
4
  REQUIRES org.netbeans.modules.db/1 (ide)
4
  REQUIRES org.netbeans.modules.db/1 (ide)
5
MODULE org.netbeans.modules.editor/3 (ide)
6
  REQUIRES org.netbeans.modules.editor.lib/1 (ide)
5
MODULE org.netbeans.modules.j2ee.ddloaders/1 (j2ee)
7
MODULE org.netbeans.modules.j2ee.ddloaders/1 (j2ee)
6
  REQUIRES org.netbeans.modules.j2ee.dd/1 (j2ee)
8
  REQUIRES org.netbeans.modules.j2ee.dd/1 (j2ee)
7
  REQUIRES org.netbeans.modules.j2ee.ejbjarproject (j2ee)
9
  REQUIRES org.netbeans.modules.j2ee.ejbjarproject (j2ee)
(-)ide/golden/public-packages.txt (+1 lines)
Lines 143-148 Link Here
143
org.netbeans.lib.cvsclient.request
143
org.netbeans.lib.cvsclient.request
144
org.netbeans.lib.cvsclient.response
144
org.netbeans.lib.cvsclient.response
145
org.netbeans.lib.cvsclient.util
145
org.netbeans.lib.cvsclient.util
146
org.netbeans.lib.editor.hyperlink.spi
146
org.netbeans.lib.editor.view
147
org.netbeans.lib.editor.view
147
org.netbeans.modules.ant.freeform.spi
148
org.netbeans.modules.ant.freeform.spi
148
org.netbeans.modules.ant.freeform.spi.support
149
org.netbeans.modules.ant.freeform.spi.support
(-)java/editor/src/org/netbeans/modules/java/editor/hyperlink/JavaHyperlinkProvider.java (+120 lines)
Added Link Here
1
/*
2
 *                 Sun Public License Notice
3
 *
4
 * The contents of this file are subject to the Sun Public License
5
 * Version 1.0 (the "License"). You may not use this file except in
6
 * compliance with the License. A copy of the License is available at
7
 * http://www.sun.com/
8
 *
9
 * The Original Code is NetBeans. The Initial Developer of the Original
10
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2004 Sun
11
 * Microsystems, Inc. All Rights Reserved.
12
 */
13
14
package org.netbeans.modules.java.editor.hyperlink;
15
16
import javax.swing.text.BadLocationException;
17
import javax.swing.text.Document;
18
import javax.swing.text.JTextComponent;
19
import org.netbeans.editor.BaseDocument;
20
import org.netbeans.editor.SyntaxSupport;
21
import org.netbeans.editor.TokenID;
22
import org.netbeans.editor.Utilities;
23
import org.netbeans.editor.ext.java.JavaTokenContext;
24
import org.netbeans.jmi.javamodel.ClassDefinition;
25
import org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider;
26
import org.openide.ErrorManager;
27
import org.netbeans.modules.editor.java.*;
28
29
30
/**
31
 * Implementation of the hyperlink provider for java language.
32
 * <br>
33
 * The hyperlinks are constructed for identifiers.
34
 * <br>
35
 * The click action corresponds to performing the goto-declaration action.
36
 *
37
 * @author Jan Lahoda
38
 */
39
public final class JavaHyperlinkProvider implements HyperlinkProvider {
40
    
41
    /** Creates a new instance of JavaHyperlinkProvider */
42
    public JavaHyperlinkProvider() {
43
    }
44
45
    public void performClickAction(Document originalDoc, int offset) {
46
        if (!(originalDoc instanceof BaseDocument))
47
            return ;
48
        
49
        BaseDocument doc = (BaseDocument) originalDoc;
50
        JTextComponent target = Utilities.getFocusedComponent();
51
        
52
        if (target.getDocument() != doc)
53
            return ;
54
        
55
        SyntaxSupport sup = doc.getSyntaxSupport();
56
        NbJavaJMISyntaxSupport nbJavaSup = (NbJavaJMISyntaxSupport)sup.get(NbJavaJMISyntaxSupport.class);
57
        
58
        JMIUtils jmiUtils = JMIUtils.get(doc);
59
        
60
        
61
        Object item = null;
62
        String itemDesc = null;
63
        jmiUtils.beginTrans(false);
64
        try {
65
            item = jmiUtils.findItemAtCaretPos(target);
66
            if (item instanceof NbJMIResultItem.VarResultItem) {
67
                int pos = nbJavaSup.findLocalDeclarationPosition(((NbJMIResultItem.VarResultItem)item).getItemText(), target.getCaretPosition());
68
                target.setCaretPosition(pos);
69
            } else {
70
                if (item instanceof ClassDefinition)
71
                    item = JMIUtils.getSourceElementIfExists((ClassDefinition)item);
72
                itemDesc = nbJavaSup.openSource(item, true);
73
            }
74
        } finally {
75
            jmiUtils.endTrans(false);
76
        }
77
    }
78
79
    public boolean isHyperlinkPoint(Document doc, int offset) {
80
        if (!(doc instanceof BaseDocument))
81
            return false;
82
        
83
        try {
84
            BaseDocument bdoc = (BaseDocument) doc;
85
            JTextComponent target = Utilities.getFocusedComponent();
86
            
87
            if (target.getDocument() != bdoc)
88
                return false;
89
            
90
            SyntaxSupport sup = bdoc.getSyntaxSupport();
91
            NbJavaJMISyntaxSupport nbJavaSup = (NbJavaJMISyntaxSupport)sup.get(NbJavaJMISyntaxSupport.class);
92
            
93
            TokenID token = nbJavaSup.getTokenID(offset);
94
            
95
            if (token == JavaTokenContext.IDENTIFIER)
96
                return true;
97
            
98
            return false;
99
        } catch (BadLocationException e) {
100
            ErrorManager.getDefault().notify(e);
101
            return false;
102
        }
103
    }
104
105
    public int[] getHyperlinkSpan(Document doc, int offset) {
106
        if (!(doc instanceof BaseDocument))
107
            return null;
108
        
109
        try {
110
            if (isHyperlinkPoint(doc, offset))
111
                return org.netbeans.editor.Utilities.getIdentifierBlock((BaseDocument) doc, offset);
112
            else
113
                return null;
114
        } catch (BadLocationException e) {
115
            ErrorManager.getDefault().notify(e);
116
            return null;
117
        }
118
    }
119
    
120
}
(-)java/editor/src/org/netbeans/modules/java/editor/resources/layer.xml (+7 lines)
Lines 135-140 Link Here
135
                        <file name="uncomment"/>
135
                        <file name="uncomment"/>
136
                    </folder>
136
                    </folder>
137
                </folder>
137
                </folder>
138
                
139
                <folder name="HyperlinkProviders">
140
                    <file name="JavaHyperlinkProvider.instance">
141
                        <attr name="instanceClass" stringvalue="org.netbeans.modules.java.editor.hyperlink.JavaHyperlinkProvider"/>
142
                        <attr name="instanceOf" stringvalue="org.netbeans.lib.editor.hyperlink.spi.HyperlinkProvider"/>
143
                    </file>
144
                </folder>
138
            </folder>
145
            </folder>
139
146
140
        </folder>
147
        </folder>

Return to bug 53454