Source Code Cross Referenced for GlyphGutter.java in  » Swing-Library » abeille-forms-designer » org » netbeans » editor » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Swing Library » abeille forms designer » org.netbeans.editor 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         *                 Sun Public License Notice
003:         *
004:         * The contents of this file are subject to the Sun Public License
005:         * Version 1.0 (the "License"). You may not use this file except in
006:         * compliance with the License. A copy of the License is available at
007:         * http://www.sun.com/
008:         *
009:         * The Original Code is NetBeans. The Initial Developer of the Original
010:         * Code is Sun Microsystems, Inc. Portions Copyright 1997-2001 Sun
011:         * Microsystems, Inc. All Rights Reserved.
012:         */
013:
014:        package org.netbeans.editor;
015:
016:        import java.awt.Color;
017:        import java.awt.Dimension;
018:        import java.awt.Font;
019:        import java.awt.FontMetrics;
020:        import java.awt.Graphics;
021:        import java.awt.Image;
022:        import java.awt.Insets;
023:        import java.awt.Rectangle;
024:        import java.awt.Toolkit;
025:        import java.awt.event.ActionEvent;
026:        import java.awt.event.InputEvent;
027:        import java.awt.event.MouseAdapter;
028:        import java.awt.event.MouseEvent;
029:        import java.awt.event.MouseMotionListener;
030:        import java.awt.image.ImageObserver;
031:        import java.beans.PropertyChangeEvent;
032:        import java.beans.PropertyChangeListener;
033:        import java.net.MalformedURLException;
034:        import java.net.URL;
035:
036:        import javax.accessibility.Accessible;
037:        import javax.accessibility.AccessibleContext;
038:        import javax.accessibility.AccessibleRole;
039:        import javax.swing.Action;
040:        import javax.swing.JComponent;
041:        import javax.swing.JPopupMenu;
042:        import javax.swing.event.PopupMenuEvent;
043:        import javax.swing.event.PopupMenuListener;
044:        import javax.swing.text.BadLocationException;
045:
046:        /**
047:         * GlyphGutter is component for displaying line numbers and annotation glyph
048:         * icons. Component also allow to "cycle" through the annotations. It means that
049:         * if there is more than one annotation on the line, only one of them might be
050:         * visible. And clicking the special cycling button in the gutter the user can
051:         * cycle through the annotations.
052:         * 
053:         * @author David Konecny
054:         * @since 07/2001
055:         */
056:
057:        public class GlyphGutter extends JComponent implements 
058:                Annotations.AnnotationsListener, Accessible {
059:
060:            /** EditorUI which part this gutter is */
061:            private EditorUI editorUI;
062:
063:            /** Document to which this gutter is attached */
064:            private BaseDocument doc;
065:
066:            /** Annotations manager responsible for annotations for this line */
067:            private Annotations annos;
068:
069:            /** Cycling button image */
070:            private Image gutterButton;
071:
072:            /** Backroung color of the gutter */
073:            private Color backgroundColor;
074:
075:            /** Foreground color of the gutter. Used for drawing line numbers. */
076:            private Color foreColor;
077:
078:            /** Font used for drawing line numbers */
079:            private Font font;
080:
081:            /** Height of the line as it was calculated in EditorUI. */
082:            private int lineHeight;
083:
084:            /**
085:             * Flag whther the gutter was initialized or not. The painting is disabled
086:             * till the gutter is not initialized
087:             */
088:            private boolean init;
089:
090:            /**
091:             * Width of the column used for drawing line numbers. The value contains
092:             * also line number margins.
093:             */
094:            private int numberWidth;
095:
096:            /** Predefined width of the glyph icons */
097:            private final static int glyphWidth = 16;
098:
099:            /** Preddefined width of the cycling button */
100:            private final static int glyphButtonWidth = 9;
101:
102:            /** Whether the line numbers are shown or not */
103:            private boolean showLineNumbers = true;
104:
105:            /** Image observer used for glyph icons */
106:            private ImageObserver imgObserver = null;
107:
108:            /**
109:             * The gutter height is enlarged by number of lines which specifies this
110:             * constant
111:             */
112:            private static final int ENLARGE_GUTTER_HEIGHT = 300;
113:
114:            /**
115:             * The hightest line number. This value is used for calculating width of the
116:             * gutter
117:             */
118:            private int highestLineNumber = 0;
119:
120:            /** Whether the annotation glyph can be drawn over the line numbers */
121:            private boolean drawOverLineNumbers = false;
122:
123:            /*
124:             * These two variables are used for caching of count of line annos on the
125:             * line over which is the mouse caret. Just for sake of optimalization.
126:             */
127:            private int cachedCountOfAnnos = -1;
128:            private int cachedCountOfAnnosForLine = -1;
129:
130:            /** Property change listener on AnnotationTypes changes */
131:            private PropertyChangeListener annoTypesListener;
132:
133:            public GlyphGutter(EditorUI editorUI) {
134:                super ();
135:                this .editorUI = editorUI;
136:                init = false;
137:                doc = editorUI.getDocument();
138:                annos = doc.getAnnotations();
139:
140:                // Annotations class is model for this view, so the listener on changes
141:                // in
142:                // Annotations must be added here
143:                annos.addAnnotationsListener(this );
144:
145:                // do initialization
146:                init();
147:                update();
148:            }
149:
150:            /*
151:             * Read accessible context @return - accessible context
152:             */
153:            public AccessibleContext getAccessibleContext() {
154:                if (accessibleContext == null) {
155:                    accessibleContext = new AccessibleJComponent() {
156:                        public AccessibleRole getAccessibleRole() {
157:                            return AccessibleRole.PANEL;
158:                        }
159:                    };
160:                }
161:                return accessibleContext;
162:            }
163:
164:            /** Do initialization of the glyph gutter */
165:            protected void init() {
166:                URL imageURL = null;
167:
168:                try {
169:                    // cycling button
170:                    imageURL = new URL(
171:                            "nbresloc:/org/netbeans/editor/resources/glyphbutton.gif"); // NOI18N
172:                } catch (MalformedURLException ex) {
173:                    if (Boolean.getBoolean("netbeans.debug.exceptions")) // NOI18N
174:                        ex.printStackTrace();
175:                    return;
176:                }
177:
178:                if (imageURL != null)
179:                    gutterButton = Toolkit.getDefaultToolkit().getImage(
180:                            imageURL);
181:
182:                setToolTipText("");
183:                getAccessibleContext().setAccessibleName(
184:                        LocaleSupport.getString("ACSN_Glyph_Gutter")); // NOI18N
185:                getAccessibleContext().setAccessibleDescription(
186:                        LocaleSupport.getString("ACSD_Glyph_Gutter")); // NOI18N
187:
188:                // add mouse listener for cycling button
189:                // TODO: clicking the line number should select whole line
190:                // TODO: clicking the line number abd dragging the mouse should select
191:                // block of lines
192:                GutterMouseListener gutterMouseListener = new GutterMouseListener();
193:                addMouseListener(gutterMouseListener);
194:                addMouseMotionListener(gutterMouseListener);
195:
196:                // after the glyph icons are loaded it is necessary to repaint the
197:                // gutter
198:                imgObserver = new ImageObserver() {
199:                    public boolean imageUpdate(Image img, int infoflags, int x,
200:                            int y, int width, int height) {
201:                        if ((infoflags & ImageObserver.ALLBITS) == ImageObserver.ALLBITS) {
202:                            repaint();
203:                            return true;
204:                        }
205:                        return true;
206:                    }
207:                };
208:
209:                AnnotationTypes.getTypes().addPropertyChangeListener(
210:                        annoTypesListener = new PropertyChangeListener() {
211:                            public void propertyChange(PropertyChangeEvent evt) {
212:                                if (evt.getPropertyName() == AnnotationTypes.PROP_GLYPHS_OVER_LINE_NUMBERS
213:                                        || evt.getPropertyName() == AnnotationTypes.PROP_SHOW_GLYPH_GUTTER) {
214:                                    update();
215:                                }
216:                            }
217:                        });
218:
219:            }
220:
221:            /**
222:             * Update colors, fonts, sizes and invalidate itself. This method is called
223:             * from EditorUI.update()
224:             */
225:            public void update() {
226:                Coloring lineColoring = (Coloring) editorUI.getColoringMap()
227:                        .get(SettingsNames.LINE_NUMBER_COLORING);
228:                Coloring defaultColoring = (Coloring) editorUI
229:                        .getDefaultColoring();
230:
231:                // fix for issue #16940
232:                // the real cause of this problem is that closed document is not garbage
233:                // collected,
234:                // because of *some* references (see #16072) and so any change in
235:                // AnnotationTypes.PROP_*
236:                // properties is fired which must update this component although it is
237:                // not visible anymore
238:                if (lineColoring == null)
239:                    return;
240:
241:                if (lineColoring.getBackColor() != null)
242:                    backgroundColor = lineColoring.getBackColor();
243:                else
244:                    backgroundColor = defaultColoring.getBackColor();
245:
246:                if (lineColoring.getForeColor() != null)
247:                    foreColor = lineColoring.getForeColor();
248:                else
249:                    foreColor = defaultColoring.getForeColor();
250:
251:                if (lineColoring.getFont() != null)
252:                    font = lineColoring.getFont();
253:                else
254:                    font = defaultColoring.getFont();
255:
256:                lineHeight = editorUI.getLineHeight();
257:
258:                showLineNumbers = editorUI.lineNumberVisibleSetting;
259:
260:                drawOverLineNumbers = AnnotationTypes.getTypes()
261:                        .isGlyphsOverLineNumbers().booleanValue();
262:
263:                init = true;
264:
265:                // initialize the value with current number of lines
266:                highestLineNumber = getLineCount();
267:
268:                repaint();
269:                resize();
270:            }
271:
272:            protected void resize() {
273:                Dimension dim = new Dimension();
274:                dim.width = getWidthDimension();
275:                dim.height = getHeightDimension();
276:
277:                // enlarge the gutter so that inserting new lines into
278:                // document does not cause resizing too often
279:                dim.height += ENLARGE_GUTTER_HEIGHT * lineHeight;
280:
281:                numberWidth = getLineNumberWidth();
282:                if (!showLineNumbers)
283:                    numberWidth = 0;
284:
285:                setPreferredSize(dim);
286:
287:                revalidate();
288:            }
289:
290:            /** Return number of lines in the document */
291:            protected int getLineCount() {
292:                int lineCnt;
293:                try {
294:                    lineCnt = Utilities.getLineOffset(doc, doc.getLength()) + 1;
295:                } catch (BadLocationException e) {
296:                    lineCnt = 1;
297:                }
298:                return lineCnt;
299:            }
300:
301:            /** Gets number of digits in the number */
302:            protected int getDigitCount(int number) {
303:                return Integer.toString(number).length();
304:            }
305:
306:            protected int getLineNumberWidth() {
307:                int newWidth = 0;
308:                Insets insets = editorUI.getLineNumberMargin();
309:                if (insets != null) {
310:                    newWidth += insets.left + insets.right;
311:                }
312:                newWidth += getDigitCount(highestLineNumber)
313:                        * editorUI.getLineNumberDigitWidth();
314:                return newWidth;
315:            }
316:
317:            protected int getWidthDimension() {
318:                int newWidth = 0;
319:
320:                if (annos.isGlyphColumn()
321:                        || AnnotationTypes.getTypes().isShowGlyphGutter()
322:                                .booleanValue())
323:                    newWidth += glyphWidth;
324:
325:                if (annos.isGlyphButtonColumn())
326:                    newWidth += glyphButtonWidth;
327:
328:                if (showLineNumbers) {
329:                    int lineNumberWidth = getLineNumberWidth();
330:                    if (drawOverLineNumbers) {
331:                        if (lineNumberWidth > newWidth)
332:                            newWidth = lineNumberWidth;
333:                    } else
334:                        newWidth += lineNumberWidth;
335:                }
336:
337:                return newWidth;
338:            }
339:
340:            protected int getHeightDimension() {
341:                JComponent comp = editorUI.getComponent();
342:                if (comp == null)
343:                    return 0;
344:                return highestLineNumber * lineHeight
345:                        + (int) comp.getSize().getHeight();
346:            }
347:
348:            /** Paint the gutter itself */
349:            public void paintComponent(Graphics g) {
350:
351:                super .paintComponent(g);
352:
353:                // if the gutter was not initialized yet, skip the painting
354:                if (!init)
355:                    return;
356:
357:                Rectangle drawHere = g.getClipBounds();
358:
359:                // Fill clipping area with dirty brown/orange.
360:                g.setColor(backgroundColor);
361:                g.fillRect(drawHere.x, drawHere.y, drawHere.width,
362:                        drawHere.height);
363:
364:                // @JMT -- added to netbeans src. Draws a dark vertical line to make the
365:                // editor boundary more pronounced
366:                g.setColor(Color.black);
367:                int e_x = getWidth() - 1;
368:                g.drawLine(e_x, drawHere.y, e_x, drawHere.y + drawHere.height);
369:
370:                g.setFont(font);
371:                g.setColor(foreColor);
372:
373:                FontMetrics fm = FontMetricsCache.getFontMetrics(font, this );
374:                int rightMargin = 0;
375:                Insets margin = editorUI.getLineNumberMargin();
376:                if (margin != null)
377:                    rightMargin = margin.right;
378:
379:                // calculate the first line which must be drawn
380:                int line = (int) ((float) drawHere.y / (float) lineHeight);
381:                if (line > 0)
382:                    line--;
383:
384:                // calculate the Y of the first line
385:                int y = line * lineHeight;
386:
387:                int lineCount = Integer.MAX_VALUE;
388:
389:                if (showLineNumbers) {
390:                    lineCount = getLineCount();
391:                    int lastLine = (int) ((float) (drawHere.y + drawHere.height) / (float) lineHeight) + 1;
392:                    if (lastLine > highestLineNumber) {
393:                        int prevHighest = highestLineNumber;
394:                        highestLineNumber = lastLine;
395:                        if (getDigitCount(highestLineNumber) > getDigitCount(prevHighest)) {
396:                            resize();
397:                            return;
398:                        }
399:                    }
400:                }
401:
402:                // find the nearest visible line with an annotation
403:                int lineWithAnno = annos.getNextLineWithAnnotation(line);
404:
405:                // draw liune numbers and annotations while we are in visible area
406:                // "+(lineHeight/2)" means to don't draw less than half of the line
407:                // number
408:                while ((y + (lineHeight / 2)) <= (drawHere.y + drawHere.height)) {
409:                    // draw line numbers if they are turned on
410:                    if (showLineNumbers
411:                            && ((!drawOverLineNumbers) || (drawOverLineNumbers && line != lineWithAnno))) {
412:                        if (line < lineCount) {
413:                            int lineNumberWidth = fm.stringWidth(""
414:                                    + (line + 1));
415:                            g.drawString("" + (line + 1), numberWidth
416:                                    - lineNumberWidth - rightMargin, y
417:                                    + editorUI.getLineAscent());
418:                        }
419:                    }
420:
421:                    // draw anotation if we get to the line with some annotation
422:                    if (line == lineWithAnno) {
423:
424:                        int count = annos.getNumberOfAnnotations(line);
425:                        AnnotationDesc anno = annos.getActiveAnnotation(line);
426:
427:                        int xPos = numberWidth;
428:                        if (drawOverLineNumbers) {
429:                            xPos = getWidth() - glyphWidth;
430:                            if (count > 1)
431:                                xPos -= glyphButtonWidth;
432:                        }
433:
434:                        if (anno != null) {
435:                            // draw the glyph only when the annotation type has its own
436:                            // icon (no the default one)
437:                            // or in case there is more than one annotations on the line
438:                            if (!(count == 1 && anno.isDefaultGlyph())) {
439:                                if (prepareImage(anno.getGlyph(), imgObserver))
440:                                    g.drawImage(anno.getGlyph(), xPos, y
441:                                            + (lineHeight - anno.getGlyph()
442:                                                    .getHeight(null)) / 2 + 1,
443:                                            null);
444:                            }
445:                        }
446:
447:                        // draw cycling button if there is more than one annotations on
448:                        // the line
449:                        if (count > 1)
450:                            if (prepareImage(gutterButton, imgObserver)
451:                                    && prepareImage(anno.getGlyph(),
452:                                            imgObserver))
453:                                g.drawImage(gutterButton, xPos + glyphWidth, y
454:                                        + (lineHeight - anno.getGlyph()
455:                                                .getHeight(null)) / 2, null);
456:
457:                        // update the value with next line with some anntoation
458:                        lineWithAnno = annos
459:                                .getNextLineWithAnnotation(line + 1);
460:                    }
461:
462:                    y += lineHeight;
463:                    line++;
464:                }
465:            }
466:
467:            /** Data for the line has changed and the line must be redraw. */
468:            public void changedLine(int line) {
469:
470:                if (!init)
471:                    return;
472:
473:                // reset cache if there was some change
474:                cachedCountOfAnnos = -1;
475:
476:                // redraw also lines around - three lines will be redrawn
477:                if (line > 0)
478:                    line--;
479:                int y = line * lineHeight;
480:
481:                repaint(0, y, (int) getSize().getWidth(), 3 * lineHeight);
482:                checkSize();
483:            }
484:
485:            /** Repaint whole gutter. */
486:            public void changedAll() {
487:
488:                if (!init)
489:                    return;
490:
491:                // reset cache if there was some change
492:                cachedCountOfAnnos = -1;
493:
494:                int lineCnt;
495:                try {
496:                    lineCnt = Utilities.getLineOffset(doc, doc.getLength()) + 1;
497:                } catch (BadLocationException e) {
498:                    lineCnt = 1;
499:                }
500:
501:                repaint();
502:                checkSize();
503:            }
504:
505:            /** Check whether it is not necessary to resize the gutter */
506:            protected void checkSize() {
507:                int count = getLineCount();
508:                if (count > highestLineNumber) {
509:                    highestLineNumber = count;
510:                }
511:                Dimension dim = getPreferredSize();
512:                if (getWidthDimension() > dim.width
513:                        || getHeightDimension() > dim.height) {
514:                    resize();
515:                }
516:
517:            }
518:
519:            /** Get tooltip text for the mouse position */
520:            // TODO: does not work for asynchronous tooltip texts
521:            public String getToolTipText(MouseEvent e) {
522:                int line = (int) ((float) e.getY() / (float) lineHeight);
523:                if (annos.getNumberOfAnnotations(line) == 0)
524:                    return null;
525:                if (isMouseOverCycleButton(e)
526:                        && annos.getNumberOfAnnotations(line) > 1) {
527:                    return java.text.MessageFormat.format(LocaleSupport
528:                            .getString("cycling-glyph_tooltip"), // NOI18N
529:                            new Object[] { new Integer(annos
530:                                    .getNumberOfAnnotations(line)) });
531:                } else if (isMouseOverGlyph(e)) {
532:                    return annos.getActiveAnnotation(line)
533:                            .getShortDescription();
534:                } else
535:                    return null;
536:            }
537:
538:            /** Count the X position of the glyph on the line. */
539:            private int getXPosOfGlyph(int line) {
540:                int xPos = numberWidth;
541:                if (drawOverLineNumbers) {
542:                    xPos = getWidth() - glyphWidth;
543:                    if (cachedCountOfAnnos == -1
544:                            || cachedCountOfAnnosForLine != line) {
545:                        cachedCountOfAnnos = annos.getNumberOfAnnotations(line);
546:                        cachedCountOfAnnosForLine = line;
547:                    }
548:                    if (cachedCountOfAnnos > 1)
549:                        xPos -= glyphButtonWidth;
550:                }
551:                return xPos;
552:            }
553:
554:            /** Check whether the mouse is over some glyph icon or not */
555:            private boolean isMouseOverGlyph(MouseEvent e) {
556:                int line = (int) ((float) e.getY() / (float) lineHeight);
557:                if (e.getX() >= getXPosOfGlyph(line)
558:                        && e.getX() <= getXPosOfGlyph(line) + glyphWidth)
559:                    return true;
560:                else
561:                    return false;
562:            }
563:
564:            /** Check whether the mouse is over the cycling button or not */
565:            private boolean isMouseOverCycleButton(MouseEvent e) {
566:                int line = (int) ((float) e.getY() / (float) lineHeight);
567:                if (e.getX() >= getXPosOfGlyph(line) + glyphWidth
568:                        && e.getX() <= getXPosOfGlyph(line) + glyphWidth
569:                                + glyphButtonWidth)
570:                    return true;
571:                else
572:                    return false;
573:            }
574:
575:            class GutterMouseListener extends MouseAdapter implements 
576:                    MouseMotionListener {
577:
578:                /** start line of the dragging. */
579:                private int dragStartLine;
580:                /** end line of the dragging. */
581:                private int dragEndLine;
582:                /** end line of last selection. */
583:                private int currentEndLine;
584:                /** If true, the selection goes forwards. */
585:                private boolean selectForward;
586:
587:                public void mouseClicked(MouseEvent e) {
588:                    // cycling button was clicked by left mouse button
589:                    if ((e.getModifiers() & InputEvent.BUTTON1_MASK) == InputEvent.BUTTON1_MASK) {
590:                        if (isMouseOverCycleButton(e)) {
591:                            int line = (int) ((float) e.getY() / (float) lineHeight);
592:                            annos.activateNextAnnotation(line);
593:                        } else {
594:                            Action a = ImplementationProvider.getDefault()
595:                                    .getToggleBreakpointAction();
596:                            if (a != null) {
597:                                int line = (int) ((float) e.getY() / (float) lineHeight);
598:                                int currentLine = -1;
599:                                try {
600:                                    currentLine = Utilities.getLineOffset(doc,
601:                                            editorUI.getComponent().getCaret()
602:                                                    .getDot());
603:                                } catch (BadLocationException ex) {
604:                                }
605:                                if (line != currentLine) {
606:                                    int offset = Utilities
607:                                            .getRowStartFromLineOffset(doc,
608:                                                    line);
609:                                    JumpList.checkAddEntry();
610:                                    editorUI.getComponent().getCaret().setDot(
611:                                            offset);
612:                                }
613:                                a.actionPerformed(new ActionEvent(editorUI
614:                                        .getComponent(), 0, ""));
615:                            }
616:                        }
617:                    }
618:
619:                    // annotation glyph was clicked by right mouse button
620:                    if ((e.getModifiers() & InputEvent.BUTTON3_MASK) == InputEvent.BUTTON3_MASK) {
621:                        int line = (int) ((float) e.getY() / (float) lineHeight);
622:                        int offset;
623:                        if (annos.getActiveAnnotation(line) != null)
624:                            offset = annos.getActiveAnnotation(line)
625:                                    .getOffset();
626:                        else
627:                            offset = Utilities.getRowStartFromLineOffset(doc,
628:                                    line);
629:                        if (editorUI.getComponent().getCaret().getDot() != offset)
630:                            JumpList.checkAddEntry();
631:                        editorUI.getComponent().getCaret().setDot(offset);
632:                        JPopupMenu pm = annos.createPopupMenu(Utilities
633:                                .getKit(editorUI.getComponent()), line);
634:                        if (pm != null) {
635:                            pm.show(GlyphGutter.this , e.getX(), e.getY());
636:                        }
637:                        pm.addPopupMenuListener(new PopupMenuListener() {
638:                            public void popupMenuCanceled(PopupMenuEvent e2) {
639:                                editorUI.getComponent().requestFocus();
640:                            }
641:
642:                            public void popupMenuWillBecomeInvisible(
643:                                    PopupMenuEvent e2) {
644:                                editorUI.getComponent().requestFocus();
645:                            }
646:
647:                            public void popupMenuWillBecomeVisible(
648:                                    PopupMenuEvent e2) {
649:                            }
650:                        });
651:                    }
652:                }
653:
654:                public void mousePressed(MouseEvent e) {
655:                    // "click gutter selects line" functionality was disabled
656:                    // // only react when it is not a cycling button
657:                    // if ((e.getModifiers() & InputEvent.BUTTON1_MASK) ==
658:                    // InputEvent.BUTTON1_MASK) {
659:                    // if (! isMouseOverCycleButton(e)) {
660:                    // dragStartLine = (int)( (float)e.getY() / (float)lineHeight );
661:                    // updateSelection (true);
662:                    // }
663:                    // }
664:                }
665:
666:                public void mouseDragged(MouseEvent e) {
667:                    // "click gutter selects line" functionality was disabled
668:                    // dragEndLine = (int)( (float)e.getY() / (float)lineHeight );
669:                    // updateSelection (false);
670:                }
671:
672:                public void mouseMoved(MouseEvent e) {
673:                }
674:
675:                /** Updates the selection */
676:                private void updateSelection(boolean newSelection) {
677:                    javax.swing.text.JTextComponent comp = Utilities
678:                            .getLastActiveComponent();
679:                    try {
680:                        if (newSelection) {
681:                            selectForward = true;
682:                            // try to get the startOffset. In case of -1 it is most
683:                            // likely the end of the document
684:                            int rowStart = Utilities.getRowStartFromLineOffset(
685:                                    doc, dragStartLine);
686:                            if (rowStart < 0) {
687:                                rowStart = Utilities.getRowStart(doc, doc
688:                                        .getLength());
689:                                dragStartLine = Utilities.getLineOffset(doc,
690:                                        rowStart);
691:                            }
692:                            comp.setCaretPosition(rowStart);
693:                            int offSet = Utilities.getRowEnd(doc, rowStart);
694:                            if (offSet < doc.getLength()) {
695:                                offSet = offSet + 1;
696:                            }
697:                            comp.moveCaretPosition(offSet);
698:                            currentEndLine = dragEndLine = dragStartLine;
699:                        } else {
700:                            if (currentEndLine == dragEndLine)
701:                                return;
702:                            // select backwards
703:                            if (dragEndLine < dragStartLine) {
704:                                if (selectForward) {
705:                                    // selection start should be at start of (dragLine +
706:                                    // 1)
707:                                    int offSet = Utilities
708:                                            .getRowStartFromLineOffset(doc,
709:                                                    dragStartLine + 1);
710:                                    if (offSet < 0) {
711:                                        offSet = Utilities
712:                                                .getRowEnd(
713:                                                        doc,
714:                                                        Utilities
715:                                                                .getRowStartFromLineOffset(
716:                                                                        doc,
717:                                                                        dragStartLine));
718:                                    }
719:                                    comp.setCaretPosition(offSet);
720:                                    selectForward = false;
721:                                }
722:                                int rowStart = Utilities
723:                                        .getRowStartFromLineOffset(doc,
724:                                                dragEndLine);
725:                                if (rowStart < 0)
726:                                    rowStart = 0;
727:                                comp.moveCaretPosition(rowStart);
728:                            }
729:                            // select forwards
730:                            else {
731:                                if (!selectForward) {
732:                                    // select start should be at dragStartLine
733:                                    comp.setCaretPosition(Utilities
734:                                            .getRowStartFromLineOffset(doc,
735:                                                    dragStartLine));
736:                                    selectForward = true;
737:                                }
738:                                // try to get the begin of (endLine + 1)
739:                                int offSet = Utilities
740:                                        .getRowStartFromLineOffset(doc,
741:                                                dragEndLine + 1);
742:                                ;
743:                                // for last line or more -1 is returned, so set to
744:                                // docLength...
745:                                if (offSet < 0) {
746:                                    offSet = doc.getLength();
747:                                }
748:                                comp.moveCaretPosition(offSet);
749:                            }
750:                        }
751:                        currentEndLine = dragEndLine;
752:                    } catch (BadLocationException ble) {
753:                        System.err.println(ble);
754:                    }
755:                }
756:            }
757:
758:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.