KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > jface > text > source > AnnotationBarHoverManager


1 /*******************************************************************************
2  * Copyright (c) 2000, 2007 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM Corporation - initial API and implementation
10  *******************************************************************************/

11
12 package org.eclipse.jface.text.source;
13
14
15 import java.util.Iterator JavaDoc;
16
17 import org.eclipse.swt.SWT;
18 import org.eclipse.swt.custom.StyledText;
19 import org.eclipse.swt.events.ControlEvent;
20 import org.eclipse.swt.events.ControlListener;
21 import org.eclipse.swt.events.DisposeEvent;
22 import org.eclipse.swt.events.DisposeListener;
23 import org.eclipse.swt.events.KeyEvent;
24 import org.eclipse.swt.events.KeyListener;
25 import org.eclipse.swt.events.MouseEvent;
26 import org.eclipse.swt.events.MouseListener;
27 import org.eclipse.swt.events.MouseMoveListener;
28 import org.eclipse.swt.events.MouseTrackAdapter;
29 import org.eclipse.swt.events.ShellEvent;
30 import org.eclipse.swt.events.ShellListener;
31 import org.eclipse.swt.graphics.Point;
32 import org.eclipse.swt.graphics.Rectangle;
33 import org.eclipse.swt.widgets.Control;
34 import org.eclipse.swt.widgets.Display;
35 import org.eclipse.swt.widgets.Event;
36 import org.eclipse.swt.widgets.Listener;
37
38 import org.eclipse.core.runtime.Assert;
39
40 import org.eclipse.jface.text.AbstractHoverInformationControlManager;
41 import org.eclipse.jface.text.AbstractInformationControlManager;
42 import org.eclipse.jface.text.BadLocationException;
43 import org.eclipse.jface.text.IDocument;
44 import org.eclipse.jface.text.IInformationControl;
45 import org.eclipse.jface.text.IInformationControlCreator;
46 import org.eclipse.jface.text.IRegion;
47 import org.eclipse.jface.text.ITextViewerExtension5;
48 import org.eclipse.jface.text.JFaceTextUtil;
49 import org.eclipse.jface.text.Region;
50 import org.eclipse.jface.text.TextUtilities;
51
52
53 /**
54  * This manager controls the layout, content, and visibility of an information
55  * control in reaction to mouse hover events issued by the vertical ruler of a
56  * source viewer.
57  * @since 2.0
58  */

59 public class AnnotationBarHoverManager extends AbstractHoverInformationControlManager {
60
61     /**
62      * The information control closer for the hover information. Closes the information control as
63      * soon as the mouse pointer leaves the subject area, a mouse button is pressed, the user presses a key,
64      * or the subject control is resized or moved.
65      *
66      * @since 3.0
67      */

68     protected class Closer extends MouseTrackAdapter implements IInformationControlCloser, MouseListener, MouseMoveListener, ControlListener, KeyListener, DisposeListener, ShellListener, Listener {
69
70         /** The closer's subject control */
71         private Control fSubjectControl;
72         /** The subject area */
73         private Rectangle fSubjectArea;
74         /** Indicates whether this closer is active */
75         private boolean fIsActive= false;
76         /** The information control. */
77         private IInformationControl fInformationControlToClose;
78         /**
79          * <code>true</code> if a wheel handler is installed.
80          * @since 3.2
81          */

82         private boolean fHasWheelFilter= false;
83         /**
84          * The cached display.
85          * @since 3.2
86          */

87         private Display fDisplay;
88
89
90         /**
91          * Creates a new information control closer.
92          */

93         public Closer() {
94         }
95
96         /*
97          * @see IInformationControlCloser#setSubjectControl(Control)
98          */

99         public void setSubjectControl(Control control) {
100             fSubjectControl= control;
101         }
102
103         /*
104          * @see IInformationControlCloser#setHoverControl(IHoverControl)
105          */

106         public void setInformationControl(IInformationControl control) {
107             fInformationControlToClose= control;
108         }
109
110         /*
111          * @see IInformationControlCloser#start(Rectangle)
112          */

113         public void start(Rectangle subjectArea) {
114
115             if (fIsActive) return;
116             fIsActive= true;
117
118             fSubjectArea= subjectArea;
119
120             fInformationControlToClose.addDisposeListener(this);
121             if (fSubjectControl != null && !fSubjectControl.isDisposed()) {
122                 fSubjectControl.addMouseListener(this);
123                 fSubjectControl.addMouseMoveListener(this);
124                 fSubjectControl.addMouseTrackListener(this);
125                 fSubjectControl.getShell().addShellListener(this);
126                 fSubjectControl.addControlListener(this);
127                 fSubjectControl.addKeyListener(this);
128                 
129                 fDisplay= fSubjectControl.getDisplay();
130                 if (!fDisplay.isDisposed() && fHideOnMouseWheel) {
131                     fHasWheelFilter= true;
132                     fDisplay.addFilter(SWT.MouseWheel, this);
133                 }
134             }
135         }
136
137         /*
138          * @see IInformationControlCloser#stop()
139          */

140         public void stop() {
141             stop(false);
142         }
143
144         /**
145          * Stops the information control and if <code>delayRestart</code> is set
146          * allows restart only after a certain delay.
147          *
148          * @param delayRestart <code>true</code> if restart should be delayed
149          */

150         protected void stop(boolean delayRestart) {
151
152             if (!fIsActive)
153                 return;
154             fIsActive= false;
155
156             hideInformationControl();
157
158             if (fSubjectControl != null && !fSubjectControl.isDisposed()) {
159                 fSubjectControl.removeMouseListener(this);
160                 fSubjectControl.removeMouseMoveListener(this);
161                 fSubjectControl.removeMouseTrackListener(this);
162                 fSubjectControl.getShell().removeShellListener(this);
163                 fSubjectControl.removeControlListener(this);
164                 fSubjectControl.removeKeyListener(this);
165             }
166             
167             if (fDisplay != null && !fDisplay.isDisposed() && fHasWheelFilter)
168                 fDisplay.removeFilter(SWT.MouseWheel, this);
169             fHasWheelFilter= false;
170             
171             fDisplay= null;
172             
173         }
174
175         /*
176          * @see org.eclipse.swt.events.MouseMoveListener#mouseMove(org.eclipse.swt.events.MouseEvent)
177          */

178         public void mouseMove(MouseEvent event) {
179             if (!fSubjectArea.contains(event.x, event.y))
180                 stop();
181         }
182
183         /*
184          * @see org.eclipse.swt.events.MouseListener#mouseUp(org.eclipse.swt.events.MouseEvent)
185          */

186         public void mouseUp(MouseEvent event) {
187         }
188
189         /*
190          * @see MouseListener#mouseDown(MouseEvent)
191          */

192         public void mouseDown(MouseEvent event) {
193             stop();
194         }
195
196         /*
197          * @see MouseListener#mouseDoubleClick(MouseEvent)
198          */

199         public void mouseDoubleClick(MouseEvent event) {
200             stop();
201         }
202         
203         /*
204          * @see org.eclipse.swt.widgets.Listener#handleEvent(org.eclipse.swt.widgets.Event)
205          * @since 3.2
206          */

207         public void handleEvent(Event event) {
208             if (event.type == SWT.MouseWheel)
209                 stop();
210         }
211
212         /*
213          * @see MouseTrackAdapter#mouseExit(MouseEvent)
214          */

215         public void mouseExit(MouseEvent event) {
216             if (!fAllowMouseExit)
217                 stop();
218         }
219
220         /*
221          * @see ControlListener#controlResized(ControlEvent)
222          */

223         public void controlResized(ControlEvent event) {
224             stop();
225         }
226
227         /*
228          * @see ControlListener#controlMoved(ControlEvent)
229          */

230         public void controlMoved(ControlEvent event) {
231             stop();
232         }
233
234         /*
235          * @see KeyListener#keyReleased(KeyEvent)
236          */

237         public void keyReleased(KeyEvent event) {
238         }
239
240         /*
241          * @see KeyListener#keyPressed(KeyEvent)
242          */

243         public void keyPressed(KeyEvent event) {
244             stop(true);
245         }
246
247         /*
248          * @see org.eclipse.swt.events.ShellListener#shellActivated(org.eclipse.swt.events.ShellEvent)
249          * @since 3.1
250          */

251         public void shellActivated(ShellEvent e) {
252         }
253
254         /*
255          * @see org.eclipse.swt.events.ShellListener#shellClosed(org.eclipse.swt.events.ShellEvent)
256          * @since 3.1
257          */

258         public void shellClosed(ShellEvent e) {
259         }
260
261         /*
262          * @see org.eclipse.swt.events.ShellListener#shellDeactivated(org.eclipse.swt.events.ShellEvent)
263          * @since 3.1
264          */

265         public void shellDeactivated(ShellEvent e) {
266             stop();
267         }
268
269         /*
270          * @see org.eclipse.swt.events.ShellListener#shellDeiconified(org.eclipse.swt.events.ShellEvent)
271          * @since 3.1
272          */

273         public void shellDeiconified(ShellEvent e) {
274         }
275
276         /*
277          * @see org.eclipse.swt.events.ShellListener#shellIconified(org.eclipse.swt.events.ShellEvent)
278          * @since 3.1
279          */

280         public void shellIconified(ShellEvent e) {
281         }
282
283         /*
284          * @see org.eclipse.swt.events.DisposeListener#widgetDisposed(org.eclipse.swt.events.DisposeEvent)
285          */

286         public void widgetDisposed(DisposeEvent e) {
287             stop();
288         }
289     }
290
291     /** The source viewer the manager is connected to */
292     private ISourceViewer fSourceViewer;
293     /** The vertical ruler the manager is registered with */
294     private IVerticalRulerInfo fVerticalRulerInfo;
295     /** The annotation hover the manager uses to retrieve the information to display. Can be <code>null</code>. */
296     private IAnnotationHover fAnnotationHover;
297     /**
298      * Indicates whether the mouse cursor is allowed to leave the subject area without closing the hover.
299      * @since 3.0
300      */

301     protected boolean fAllowMouseExit= false;
302     /**
303      * Whether we should hide the over on mouse wheel action.
304      *
305      * @since 3.2
306      */

307     private boolean fHideOnMouseWheel= true;
308     
309     /**
310      * The current annotation hover.
311      * @since 3.2
312      */

313     private IAnnotationHover fCurrentHover;
314
315     /**
316      * Creates an annotation hover manager with the given parameters. In addition,
317      * the hovers anchor is RIGHT and the margin is 5 points to the right.
318      *
319      * @param sourceViewer the source viewer this manager connects to
320      * @param ruler the vertical ruler this manager connects to
321      * @param annotationHover the annotation hover providing the information to be displayed
322      * @param creator the information control creator
323      * @deprecated As of 2.1, replaced by {@link AnnotationBarHoverManager#AnnotationBarHoverManager(IVerticalRulerInfo, ISourceViewer, IAnnotationHover, IInformationControlCreator)}
324      */

325     public AnnotationBarHoverManager(ISourceViewer sourceViewer, IVerticalRuler ruler, IAnnotationHover annotationHover, IInformationControlCreator creator) {
326         this(ruler, sourceViewer, annotationHover, creator);
327     }
328
329     /**
330      * Creates an annotation hover manager with the given parameters. In addition,
331      * the hovers anchor is RIGHT and the margin is 5 points to the right.
332      *
333      * @param rulerInfo the vertical ruler this manager connects to
334      * @param sourceViewer the source viewer this manager connects to
335      * @param annotationHover the annotation hover providing the information to be displayed or <code>null</code> if none
336      * @param creator the information control creator
337      * @since 2.1
338      */

339     public AnnotationBarHoverManager(IVerticalRulerInfo rulerInfo, ISourceViewer sourceViewer, IAnnotationHover annotationHover, IInformationControlCreator creator) {
340         super(creator);
341
342         Assert.isNotNull(sourceViewer);
343
344         fSourceViewer= sourceViewer;
345         fVerticalRulerInfo= rulerInfo;
346         fAnnotationHover= annotationHover;
347
348         setAnchor(ANCHOR_RIGHT);
349         setMargins(5, 0);
350         setCloser(new Closer());
351     }
352
353     /*
354      * @see org.eclipse.jface.text.AbstractInformationControlManager#computeInformation()
355      */

356     protected void computeInformation() {
357         fAllowMouseExit= false;
358         MouseEvent event= getHoverEvent();
359         IAnnotationHover hover= getHover(event);
360         if (hover == null) {
361             setInformation(null, null);
362             return;
363         }
364
365         int line= getHoverLine(event);
366
367         if (hover instanceof IAnnotationHoverExtension) {
368             IAnnotationHoverExtension extension= (IAnnotationHoverExtension) hover;
369             ILineRange range= extension.getHoverLineRange(fSourceViewer, line);
370             setCustomInformationControlCreator(extension.getHoverControlCreator());
371             range= adaptLineRange(range, line);
372             if (range != null)
373                 setInformation(extension.getHoverInfo(fSourceViewer, range, computeNumberOfVisibleLines()), computeArea(range));
374             else
375                 setInformation(null, null);
376
377         } else {
378             setCustomInformationControlCreator(null);
379             setInformation(hover.getHoverInfo(fSourceViewer, line), computeArea(line));
380         }
381
382     }
383     
384     /*
385      * @see org.eclipse.jface.text.AbstractInformationControlManager#showInformationControl(org.eclipse.swt.graphics.Rectangle)
386      * @since 3.2
387      */

388     protected void showInformationControl(Rectangle subjectArea) {
389         super.showInformationControl(subjectArea);
390         fCurrentHover= getHover(getHoverEvent());
391     }
392     
393     /*
394      * @see org.eclipse.jface.text.AbstractInformationControlManager#hideInformationControl()
395      * @since 3.2
396      */

397     protected void hideInformationControl() {
398         fCurrentHover= null;
399         super.hideInformationControl();
400     }
401
402     /**
403      * Adapts a given line range so that the result is a line range that does
404      * not overlap with any collapsed region and fits into the view port of the
405      * attached viewer.
406      *
407      * @param lineRange the original line range
408      * @param line the anchor line
409      * @return the adapted line range
410      * @since 3.0
411      */

412     private ILineRange adaptLineRange(ILineRange lineRange, int line) {
413         if (lineRange != null) {
414             lineRange= adaptLineRangeToFolding(lineRange, line);
415             if (lineRange != null)
416                 return adaptLineRangeToViewport(lineRange);
417         }
418         return null;
419     }
420
421     /**
422      * Adapts a given line range so that the result is a line range that does
423      * not overlap with any collapsed region of the attached viewer.
424      *
425      * @param lineRange the original line range
426      * @param line the anchor line
427      * @return the adapted line range
428      * @since 3.0
429      */

430     private ILineRange adaptLineRangeToFolding(ILineRange lineRange, int line) {
431
432         if (fSourceViewer instanceof ITextViewerExtension5) {
433             ITextViewerExtension5 extension= (ITextViewerExtension5) fSourceViewer;
434
435             try {
436                 IRegion region= convertToRegion(lineRange);
437                 IRegion[] coverage= extension.getCoveredModelRanges(region);
438                 if (coverage != null && coverage.length > 0) {
439                     IRegion container= findRegionContainingLine(coverage, line);
440                     if (container != null)
441                         return convertToLineRange(container);
442                 }
443
444             } catch (BadLocationException x) {
445             }
446
447             return null;
448         }
449
450         return lineRange;
451     }
452
453     /**
454      * Adapts a given line range so that the result is a line range that fits
455      * into the view port of the attached viewer.
456      *
457      * @param lineRange the original line range
458      * @return the adapted line range
459      * @since 3.0
460      */

461     private ILineRange adaptLineRangeToViewport(ILineRange lineRange) {
462
463         try {
464             StyledText text= fSourceViewer.getTextWidget();
465
466             int topLine= text.getTopIndex();
467             int rangeTopLine= getWidgetLineNumber(lineRange.getStartLine());
468             int topDelta= Math.max(topLine - rangeTopLine, 0);
469
470             Rectangle size= text.getClientArea();
471             Rectangle trim= text.computeTrim(0, 0, 0, 0);
472             int height= size.height - trim.height;
473             
474             int lines= JFaceTextUtil.getLineIndex(text, height) - text.getTopIndex();
475             
476             int bottomLine= topLine + lines;
477             
478             int rangeBottomLine= getWidgetLineNumber(lineRange.getStartLine() + lineRange.getNumberOfLines() - 1);
479             int bottomDelta= Math.max(rangeBottomLine - bottomLine, 0);
480
481             return new LineRange(lineRange.getStartLine() + topDelta, lineRange.getNumberOfLines() - bottomDelta - topDelta);
482
483         } catch (BadLocationException ex) {
484         }
485
486         return null;
487     }
488
489     /**
490      * Converts a line range into a character range.
491      *
492      * @param lineRange the line range
493      * @return the corresponding character range
494      * @throws BadLocationException in case the given line range is invalid
495      */

496     private IRegion convertToRegion(ILineRange lineRange) throws BadLocationException {
497         IDocument document= fSourceViewer.getDocument();
498         int startOffset= document.getLineOffset(lineRange.getStartLine());
499         int endLine= lineRange.getStartLine() + Math.max(0, lineRange.getNumberOfLines() - 1);
500         IRegion lineInfo= document.getLineInformation(endLine);
501         int endOffset= lineInfo.getOffset() + lineInfo.getLength();
502         return new Region(startOffset, endOffset - startOffset);
503     }
504
505     /**
506      * Returns the region out of the given set that contains the given line or
507      * <code>null</code>.
508      *
509      * @param regions the set of regions
510      * @param line the line
511      * @return the region of the set that contains the line
512      * @throws BadLocationException in case line is invalid
513      */

514     private IRegion findRegionContainingLine(IRegion[] regions, int line) throws BadLocationException {
515         IDocument document= fSourceViewer.getDocument();
516         IRegion lineInfo= document.getLineInformation(line);
517         for (int i= 0; i < regions.length; i++) {
518             if (TextUtilities.overlaps(regions[i], lineInfo))
519                 return regions[i];
520         }
521         return null;
522     }
523
524     /**
525      * Converts a given character region into a line range.
526      *
527      * @param region the character region
528      * @return the corresponding line range
529      * @throws BadLocationException in case the given region in invalid
530      */

531     private ILineRange convertToLineRange(IRegion region) throws BadLocationException {
532         IDocument document= fSourceViewer.getDocument();
533         int startLine= document.getLineOfOffset(region.getOffset());
534         int endLine= document.getLineOfOffset(region.getOffset() + region.getLength());
535         return new LineRange(startLine, endLine - startLine + 1);
536     }
537
538     /**
539      * Returns the visible area of the vertical ruler covered by the given line
540      * range.
541      *
542      * @param lineRange the line range
543      * @return the visible area
544      */

545     private Rectangle computeArea(ILineRange lineRange) {
546         try {
547             StyledText text= fSourceViewer.getTextWidget();
548             final int startLine= getWidgetLineNumber(lineRange.getStartLine());
549             int y= JFaceTextUtil.computeLineHeight(text, 0, startLine, startLine) - text.getTopPixel();
550             int height= JFaceTextUtil.computeLineHeight(text, startLine, startLine + lineRange.getNumberOfLines(), lineRange.getNumberOfLines());
551             Point size= fVerticalRulerInfo.getControl().getSize();
552             return new Rectangle(0, y, size.x, height);
553         } catch (BadLocationException x) {
554         }
555         return null;
556     }
557
558     /**
559      * Returns the number of the currently visible lines.
560      *
561      * @return the number of the currently visible lines
562      */

563     private int computeNumberOfVisibleLines() {
564         // Hack to reduce amount of copied code.
565
return LineNumberRulerColumn.getVisibleLinesInViewport(fSourceViewer.getTextWidget());
566     }
567
568     /**
569      * Determines the hover to be used to display information based on the source of the
570      * mouse hover event. If <code>fVerticalRulerInfo</code> is not a composite ruler, the
571      * standard hover is returned.
572      *
573      * @param event the source of the mouse hover event
574      * @return the hover depending on <code>source</code>, or <code>fAnnotationHover</code> if none can be found.
575      * @since 3.0
576      */

577     private IAnnotationHover getHover(MouseEvent event) {
578         if (event == null || event.getSource() == null)
579             return fAnnotationHover;
580
581         if (fVerticalRulerInfo instanceof CompositeRuler) {
582             CompositeRuler comp= (CompositeRuler) fVerticalRulerInfo;
583             for (Iterator JavaDoc it= comp.getDecoratorIterator(); it.hasNext();) {
584                 Object JavaDoc o= it.next();
585                 if (o instanceof IVerticalRulerInfoExtension && o instanceof IVerticalRulerInfo) {
586                     if (((IVerticalRulerInfo) o).getControl() == event.getSource()) {
587                         IAnnotationHover hover= ((IVerticalRulerInfoExtension) o).getHover();
588                         if (hover != null)
589                             return hover;
590                     }
591                 }
592             }
593         }
594         return fAnnotationHover;
595     }
596
597     /**
598      * Returns the line of interest deduced from the mouse hover event.
599      *
600      * @param event a mouse hover event that triggered hovering
601      * @return the document model line number on which the hover event occurred or <code>-1</code> if there is no event
602      * @since 3.0
603      */

604     private int getHoverLine(MouseEvent event) {
605         return event == null ? -1 : fVerticalRulerInfo.toDocumentLineNumber(event.y);
606     }
607
608     /**
609      * Returns for the widget line number for the given document line number.
610      *
611      * @param line the absolute line number
612      * @return the line number relative to the viewer's visible region
613      * @throws BadLocationException if <code>line</code> is not valid in the viewer's document
614      */

615     private int getWidgetLineNumber(int line) throws BadLocationException {
616         if (fSourceViewer instanceof ITextViewerExtension5) {
617             ITextViewerExtension5 extension= (ITextViewerExtension5) fSourceViewer;
618             return extension.modelLine2WidgetLine(line);
619         }
620
621         IRegion region= fSourceViewer.getVisibleRegion();
622         int firstLine= fSourceViewer.getDocument().getLineOfOffset(region.getOffset());
623         return line - firstLine;
624     }
625
626     /**
627      * Determines graphical area covered by the given line.
628      *
629      * @param line the number of the line in the viewer whose graphical extend in the vertical ruler must be computed
630      * @return the graphical extend of the given line
631      */

632     private Rectangle computeArea(int line) {
633         try {
634             StyledText text= fSourceViewer.getTextWidget();
635             int widgetLine= getWidgetLineNumber(line);
636             int y= JFaceTextUtil.computeLineHeight(text, 0, widgetLine, widgetLine) - text.getTopPixel();
637             Point size= fVerticalRulerInfo.getControl().getSize();
638             return new Rectangle(0, y, size.x, text.getLineHeight(text.getOffsetAtLine(widgetLine)));
639         } catch (IllegalArgumentException JavaDoc ex) {
640         } catch (BadLocationException ex) {
641         }
642         return null;
643     }
644
645     /**
646      * Returns the annotation hover for this hover manager.
647      *
648      * @return the annotation hover for this hover manager or <code>null</code> if none
649      * @since 2.1
650      */

651     protected IAnnotationHover getAnnotationHover() {
652         return fAnnotationHover;
653     }
654
655     /**
656      * Returns the source viewer for this hover manager.
657      *
658      * @return the source viewer for this hover manager
659      * @since 2.1
660      */

661     protected ISourceViewer getSourceViewer() {
662         return fSourceViewer;
663     }
664
665     /**
666      * Returns the vertical ruler info for this hover manager
667      *
668      * @return the vertical ruler info for this hover manager
669      * @since 2.1
670      */

671     protected IVerticalRulerInfo getVerticalRulerInfo() {
672         return fVerticalRulerInfo;
673     }
674
675     /*
676      * @see org.eclipse.jface.text.AbstractInformationControlManager#computeSizeConstraints(org.eclipse.swt.widgets.Control, org.eclipse.swt.graphics.Rectangle, org.eclipse.jface.text.IInformationControl)
677      * @since 3.0
678      */

679     protected Point computeSizeConstraints(Control subjectControl, Rectangle subjectArea, IInformationControl informationControl) {
680
681         Point constraints= super.computeSizeConstraints(subjectControl, subjectArea, informationControl);
682
683         StyledText styledText= fSourceViewer.getTextWidget();
684         if (styledText != null) {
685             Rectangle r= styledText.getClientArea();
686             if (r != null) {
687                 constraints.x= r.width;
688                 constraints.y= r.height;
689             }
690         }
691
692         return constraints;
693     }
694
695     /*
696      * @see org.eclipse.jface.text.AbstractInformationControlManager#computeLocation(org.eclipse.swt.graphics.Rectangle, org.eclipse.swt.graphics.Point, org.eclipse.jface.text.AbstractInformationControlManager.Anchor)
697      * @since 3.0
698      */

699     protected Point computeLocation(Rectangle subjectArea, Point controlSize, Anchor anchor) {
700         MouseEvent event= getHoverEvent();
701         IAnnotationHover hover= getHover(event);
702
703         boolean allowMouseExit= false;
704         if (hover instanceof IAnnotationHoverExtension) {
705             IAnnotationHoverExtension extension= (IAnnotationHoverExtension) hover;
706             allowMouseExit= extension.canHandleMouseCursor();
707         }
708         boolean hideOnMouseWheel= true;
709         if (hover instanceof IAnnotationHoverExtension2) {
710             IAnnotationHoverExtension2 extension= (IAnnotationHoverExtension2) hover;
711             hideOnMouseWheel= !extension.canHandleMouseWheel();
712         }
713         fHideOnMouseWheel= hideOnMouseWheel;
714
715         if (allowMouseExit) {
716             fAllowMouseExit= true;
717
718             Control subjectControl= getSubjectControl();
719             // return a location that just overlaps the annotation on the bar
720
if (anchor == AbstractInformationControlManager.ANCHOR_RIGHT)
721                 return subjectControl.toDisplay(subjectArea.x - 4, subjectArea.y - 2);
722             else if (anchor == AbstractInformationControlManager.ANCHOR_LEFT)
723                 return subjectControl.toDisplay(subjectArea.x + subjectArea.width - controlSize.x + 4, subjectArea.y - 2);
724         }
725
726         fAllowMouseExit= false;
727         return super.computeLocation(subjectArea, controlSize, anchor);
728     }
729
730     /**
731      * Returns the currently shown annotation hover or <code>null</code> if none
732      * hover is shown.
733      *
734      * @return the currently shown annotation hover or <code>null</code>
735      * @since 3.2
736      */

737     public IAnnotationHover getCurrentAnnotationHover() {
738         return fCurrentHover;
739     }
740 }
741
742
Popular Tags