jdk/src/java.desktop/share/classes/javax/swing/text/WrappedPlainView.java
author alexsch
Mon, 21 Nov 2016 17:46:48 +0300
changeset 42717 367db14731fb
parent 42216 621af0ebf6c4
child 43075 668b6d00cc79
permissions -rw-r--r--
8169719: WrappedPlainView.modelToView() should return Rectangle2D Reviewed-by: prr, serb, ssadetsky
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     1
/*
30462
507bcb03c954 8076624: Fix missing doclint warnings in javax.swing.text
darcy
parents: 28059
diff changeset
     2
 * Copyright (c) 1998, 2015, Oracle and/or its affiliates. All rights reserved.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
90ce3da70b43 Initial load
duke
parents:
diff changeset
     4
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
90ce3da70b43 Initial load
duke
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
5506
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 3504
diff changeset
     7
 * published by the Free Software Foundation.  Oracle designates this
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
5506
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 3504
diff changeset
     9
 * by Oracle in the LICENSE file that accompanied this code.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    10
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
90ce3da70b43 Initial load
duke
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
90ce3da70b43 Initial load
duke
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
90ce3da70b43 Initial load
duke
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
90ce3da70b43 Initial load
duke
parents:
diff changeset
    15
 * accompanied this code).
90ce3da70b43 Initial load
duke
parents:
diff changeset
    16
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
90ce3da70b43 Initial load
duke
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    20
 *
5506
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 3504
diff changeset
    21
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 3504
diff changeset
    22
 * or visit www.oracle.com if you need additional information or have any
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 3504
diff changeset
    23
 * questions.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    24
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    25
package javax.swing.text;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    26
90ce3da70b43 Initial load
duke
parents:
diff changeset
    27
import java.awt.*;
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
    28
import java.awt.font.FontRenderContext;
42717
367db14731fb 8169719: WrappedPlainView.modelToView() should return Rectangle2D
alexsch
parents: 42216
diff changeset
    29
import java.awt.geom.Rectangle2D;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    30
import java.lang.ref.SoftReference;
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
    31
import java.security.AccessController;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
    32
import java.security.PrivilegedAction;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    33
import javax.swing.event.*;
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
    34
import static javax.swing.text.PlainView.isFPMethodOverriden;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    35
90ce3da70b43 Initial load
duke
parents:
diff changeset
    36
/**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    37
 * View of plain text (text with only one font and color)
90ce3da70b43 Initial load
duke
parents:
diff changeset
    38
 * that does line-wrapping.  This view expects that its
90ce3da70b43 Initial load
duke
parents:
diff changeset
    39
 * associated element has child elements that represent
90ce3da70b43 Initial load
duke
parents:
diff changeset
    40
 * the lines it should be wrapping.  It is implemented
90ce3da70b43 Initial load
duke
parents:
diff changeset
    41
 * as a vertical box that contains logical line views.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    42
 * The logical line views are nested classes that render
90ce3da70b43 Initial load
duke
parents:
diff changeset
    43
 * the logical line as multiple physical line if the logical
90ce3da70b43 Initial load
duke
parents:
diff changeset
    44
 * line is too wide to fit within the allocation.  The
90ce3da70b43 Initial load
duke
parents:
diff changeset
    45
 * line views draw upon the outer class for its state
90ce3da70b43 Initial load
duke
parents:
diff changeset
    46
 * to reduce their memory requirements.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    47
 * <p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    48
 * The line views do all of their rendering through the
90ce3da70b43 Initial load
duke
parents:
diff changeset
    49
 * <code>drawLine</code> method which in turn does all of
90ce3da70b43 Initial load
duke
parents:
diff changeset
    50
 * its rendering through the <code>drawSelectedText</code>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    51
 * and <code>drawUnselectedText</code> methods.  This
90ce3da70b43 Initial load
duke
parents:
diff changeset
    52
 * enables subclasses to easily specialize the rendering
90ce3da70b43 Initial load
duke
parents:
diff changeset
    53
 * without concern for the layout aspects.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    54
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    55
 * @author  Timothy Prinzing
90ce3da70b43 Initial load
duke
parents:
diff changeset
    56
 * @see     View
90ce3da70b43 Initial load
duke
parents:
diff changeset
    57
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    58
public class WrappedPlainView extends BoxView implements TabExpander {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    59
90ce3da70b43 Initial load
duke
parents:
diff changeset
    60
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    61
     * Creates a new WrappedPlainView.  Lines will be wrapped
90ce3da70b43 Initial load
duke
parents:
diff changeset
    62
     * on character boundaries.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    63
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    64
     * @param elem the element underlying the view
90ce3da70b43 Initial load
duke
parents:
diff changeset
    65
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    66
    public WrappedPlainView(Element elem) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    67
        this(elem, false);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    68
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
    69
90ce3da70b43 Initial load
duke
parents:
diff changeset
    70
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    71
     * Creates a new WrappedPlainView.  Lines can be wrapped on
90ce3da70b43 Initial load
duke
parents:
diff changeset
    72
     * either character or word boundaries depending upon the
90ce3da70b43 Initial load
duke
parents:
diff changeset
    73
     * setting of the wordWrap parameter.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    74
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    75
     * @param elem the element underlying the view
90ce3da70b43 Initial load
duke
parents:
diff changeset
    76
     * @param wordWrap should lines be wrapped on word boundaries?
90ce3da70b43 Initial load
duke
parents:
diff changeset
    77
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    78
    public WrappedPlainView(Element elem, boolean wordWrap) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    79
        super(elem, Y_AXIS);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    80
        this.wordWrap = wordWrap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    81
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
    82
90ce3da70b43 Initial load
duke
parents:
diff changeset
    83
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    84
     * Returns the tab size set for the document, defaulting to 8.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    85
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    86
     * @return the tab size
90ce3da70b43 Initial load
duke
parents:
diff changeset
    87
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    88
    protected int getTabSize() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    89
        Integer i = (Integer) getDocument().getProperty(PlainDocument.tabSizeAttribute);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    90
        int size = (i != null) ? i.intValue() : 8;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    91
        return size;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    92
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
    93
90ce3da70b43 Initial load
duke
parents:
diff changeset
    94
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    95
     * Renders a line of text, suppressing whitespace at the end
90ce3da70b43 Initial load
duke
parents:
diff changeset
    96
     * and expanding any tabs.  This is implemented to make calls
90ce3da70b43 Initial load
duke
parents:
diff changeset
    97
     * to the methods <code>drawUnselectedText</code> and
90ce3da70b43 Initial load
duke
parents:
diff changeset
    98
     * <code>drawSelectedText</code> so that the way selected and
90ce3da70b43 Initial load
duke
parents:
diff changeset
    99
     * unselected text are rendered can be customized.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   100
     *
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   101
     * @param p0 the starting document location to use &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   102
     * @param p1 the ending document location to use &gt;= p1
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   103
     * @param g the graphics context
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   104
     * @param x the starting X position &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   105
     * @param y the starting Y position &gt;= 0
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   106
     * @see #drawUnselectedText
90ce3da70b43 Initial load
duke
parents:
diff changeset
   107
     * @see #drawSelectedText
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   108
     *
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   109
     * @deprecated replaced by
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   110
     *     {@link #drawLine(int, int, Graphics2D, float, float)}
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   111
     */
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   112
    @Deprecated(since = "9")
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   113
    protected void drawLine(int p0, int p1, Graphics g, int x, int y) {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   114
        drawLineImpl(p0, p1, g, x, y, false);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   115
    }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   116
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   117
    private void drawLineImpl(int p0, int p1, Graphics g, float x, float y,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   118
                              boolean useFPAPI) {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   119
        Element lineMap = getElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   120
        Element line = lineMap.getElement(lineMap.getElementIndex(p0));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   121
        Element elem;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   122
90ce3da70b43 Initial load
duke
parents:
diff changeset
   123
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   124
            if (line.isLeaf()) {
5762
6b50a6f25d81 6857057: api/javax_swing/text/GlyphView/index.html#Methods test fails
rupashka
parents: 5597
diff changeset
   125
                 drawText(line, p0, p1, g, x, y);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   126
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   127
                // this line contains the composed text.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   128
                int idx = line.getElementIndex(p0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   129
                int lastIdx = line.getElementIndex(p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   130
                for(; idx <= lastIdx; idx++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   131
                    elem = line.getElement(idx);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   132
                    int start = Math.max(elem.getStartOffset(), p0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   133
                    int end = Math.min(elem.getEndOffset(), p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   134
                    x = drawText(elem, start, end, g, x, y);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   135
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   136
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   137
        } catch (BadLocationException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   138
            throw new StateInvariantError("Can't render: " + p0 + "," + p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   139
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   140
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   141
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   142
    /**
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   143
     * Renders a line of text, suppressing whitespace at the end
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   144
     * and expanding any tabs.  This is implemented to make calls
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   145
     * to the methods <code>drawUnselectedText</code> and
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   146
     * <code>drawSelectedText</code> so that the way selected and
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   147
     * unselected text are rendered can be customized.
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   148
     *
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   149
     * @param p0 the starting document location to use &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   150
     * @param p1 the ending document location to use &gt;= p1
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   151
     * @param g the graphics context
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   152
     * @param x the starting X position &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   153
     * @param y the starting Y position &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   154
     * @see #drawUnselectedText
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   155
     * @see #drawSelectedText
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   156
     *
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   157
     * @since 9
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   158
     */
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   159
    protected void drawLine(int p0, int p1, Graphics2D g, float x, float y) {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   160
        drawLineImpl(p0, p1, g, x, y, true);
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   161
    }
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   162
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   163
    private float drawText(Element elem, int p0, int p1, Graphics g,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   164
                           float x, float y)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   165
            throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   166
    {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   167
        p1 = Math.min(getDocument().getLength(), p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   168
        AttributeSet attr = elem.getAttributes();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   169
90ce3da70b43 Initial load
duke
parents:
diff changeset
   170
        if (Utilities.isComposedTextAttributeDefined(attr)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   171
            g.setColor(unselected);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   172
            x = Utilities.drawComposedText(this, attr, g, x, y,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   173
                                        p0-elem.getStartOffset(),
90ce3da70b43 Initial load
duke
parents:
diff changeset
   174
                                        p1-elem.getStartOffset());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   175
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   176
            if (sel0 == sel1 || selected == unselected) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   177
                // no selection, or it is invisible
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   178
                x = callDrawUnselectedText(g, x, y, p0, p1);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   179
            } else if ((p0 >= sel0 && p0 <= sel1) && (p1 >= sel0 && p1 <= sel1)) {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   180
                x = callDrawSelectedText(g, x, y, p0, p1);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   181
            } else if (sel0 >= p0 && sel0 <= p1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   182
                if (sel1 >= p0 && sel1 <= p1) {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   183
                    x = callDrawUnselectedText(g, x, y, p0, sel0);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   184
                    x = callDrawSelectedText(g, x, y, sel0, sel1);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   185
                    x = callDrawUnselectedText(g, x, y, sel1, p1);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   186
                } else {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   187
                    x = callDrawUnselectedText(g, x, y, p0, sel0);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   188
                    x = callDrawSelectedText(g, x, y, sel0, p1);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   189
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   190
            } else if (sel1 >= p0 && sel1 <= p1) {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   191
                x = callDrawSelectedText(g, x, y, p0, sel1);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   192
                x = callDrawUnselectedText(g, x, y, sel1, p1);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   193
            } else {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   194
                x = callDrawUnselectedText(g, x, y, p0, p1);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   195
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   196
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   197
90ce3da70b43 Initial load
duke
parents:
diff changeset
   198
        return x;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   199
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   200
90ce3da70b43 Initial load
duke
parents:
diff changeset
   201
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   202
     * Renders the given range in the model as normal unselected
90ce3da70b43 Initial load
duke
parents:
diff changeset
   203
     * text.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   204
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   205
     * @param g the graphics context
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   206
     * @param x the starting X coordinate &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   207
     * @param y the starting Y coordinate &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   208
     * @param p0 the beginning position in the model &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   209
     * @param p1 the ending position in the model &gt;= p0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   210
     * @return the X location of the end of the range &gt;= 0
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   211
     * @exception BadLocationException if the range is invalid
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   212
     *
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   213
     * @deprecated replaced by
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   214
     *     {@link #drawUnselectedText(Graphics2D, float, float, int, int)}
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   215
     */
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   216
    @Deprecated(since = "9")
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   217
    protected int drawUnselectedText(Graphics g, int x, int y,
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   218
                                     int p0, int p1) throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   219
    {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   220
        return (int) drawUnselectedTextImpl(g, x, y, p0, p1, false);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   221
    }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   222
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   223
    private float callDrawUnselectedText(Graphics g, float x, float y,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   224
                                         int p0, int p1)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   225
                                         throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   226
    {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   227
        return drawUnselectedTextOverridden && g instanceof Graphics2D
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   228
                ? drawUnselectedText((Graphics2D) g, x, y, p0, p1)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   229
                : drawUnselectedText(g, (int) x, (int) y, p0, p1);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   230
    }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   231
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   232
    private float drawUnselectedTextImpl(Graphics g, float x, float y,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   233
                                         int p0, int p1, boolean useFPAPI)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   234
            throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   235
    {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   236
        g.setColor(unselected);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   237
        Document doc = getDocument();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   238
        Segment segment = SegmentCache.getSharedSegment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   239
        doc.getText(p0, p1 - p0, segment);
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   240
        float ret = Utilities.drawTabbedText(this, segment, x, y, g, this, p0,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   241
                                             null, useFPAPI);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   242
        SegmentCache.releaseSharedSegment(segment);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   243
        return ret;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   244
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   245
90ce3da70b43 Initial load
duke
parents:
diff changeset
   246
    /**
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   247
     * Renders the given range in the model as normal unselected
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   248
     * text.
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   249
     *
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   250
     * @param g the graphics context
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   251
     * @param x the starting X coordinate &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   252
     * @param y the starting Y coordinate &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   253
     * @param p0 the beginning position in the model &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   254
     * @param p1 the ending position in the model &gt;= p0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   255
     * @return the X location of the end of the range &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   256
     * @exception BadLocationException if the range is invalid
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   257
     *
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   258
     * @since 9
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   259
     */
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   260
    protected float drawUnselectedText(Graphics2D g, float x, float y,
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   261
                                     int p0, int p1) throws BadLocationException {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   262
        return drawUnselectedTextImpl(g, x, y, p0, p1, true);
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   263
    }
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   264
    /**
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   265
     * Renders the given range in the model as selected text.  This
90ce3da70b43 Initial load
duke
parents:
diff changeset
   266
     * is implemented to render the text in the color specified in
90ce3da70b43 Initial load
duke
parents:
diff changeset
   267
     * the hosting component.  It assumes the highlighter will render
90ce3da70b43 Initial load
duke
parents:
diff changeset
   268
     * the selected background.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   269
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   270
     * @param g the graphics context
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   271
     * @param x the starting X coordinate &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   272
     * @param y the starting Y coordinate &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   273
     * @param p0 the beginning position in the model &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   274
     * @param p1 the ending position in the model &gt;= p0
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   275
     * @return the location of the end of the range.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   276
     * @exception BadLocationException if the range is invalid
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   277
     *
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   278
     * @deprecated replaced by
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   279
     *     {@link #drawSelectedText(Graphics2D, float, float, int, int)}
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   280
     */
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   281
    @Deprecated(since = "9")
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   282
    protected int drawSelectedText(Graphics g, int x, int y, int p0, int p1)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   283
            throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   284
    {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   285
        return (int) drawSelectedTextImpl(g, x, y, p0, p1, false);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   286
    }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   287
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   288
    private float callDrawSelectedText(Graphics g, float x, float y,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   289
                                       int p0, int p1)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   290
                                       throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   291
    {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   292
        return drawSelectedTextOverridden && g instanceof Graphics2D
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   293
                ? drawSelectedText((Graphics2D) g, x, y, p0, p1)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   294
                : drawSelectedText(g, (int) x, (int) y, p0, p1);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   295
    }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   296
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   297
    private float drawSelectedTextImpl(Graphics g, float x, float y,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   298
                                       int p0, int p1,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   299
                                       boolean useFPAPI)
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   300
            throws BadLocationException
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   301
    {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   302
        g.setColor(selected);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   303
        Document doc = getDocument();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   304
        Segment segment = SegmentCache.getSharedSegment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   305
        doc.getText(p0, p1 - p0, segment);
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   306
        float ret = Utilities.drawTabbedText(this, segment, x, y, g, this, p0,
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   307
                                             null, useFPAPI);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   308
        SegmentCache.releaseSharedSegment(segment);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   309
        return ret;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   310
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   311
90ce3da70b43 Initial load
duke
parents:
diff changeset
   312
    /**
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   313
     * Renders the given range in the model as selected text.  This
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   314
     * is implemented to render the text in the color specified in
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   315
     * the hosting component.  It assumes the highlighter will render
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   316
     * the selected background.
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   317
     *
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   318
     * @param g the graphics context
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   319
     * @param x the starting X coordinate &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   320
     * @param y the starting Y coordinate &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   321
     * @param p0 the beginning position in the model &gt;= 0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   322
     * @param p1 the ending position in the model &gt;= p0
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   323
     * @return the location of the end of the range.
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   324
     * @exception BadLocationException if the range is invalid
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   325
     *
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   326
     * @since 9
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   327
     */
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   328
    protected float drawSelectedText(Graphics2D g, float x, float y,
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   329
                                     int p0, int p1) throws BadLocationException {
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   330
        return drawSelectedTextImpl(g, x, y, p0, p1, true);
39553
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   331
    }
965a62655c4c 8132119: Provide public API for text related methods in SwingUtilities2
alexsch
parents: 30462
diff changeset
   332
    /**
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   333
     * Gives access to a buffer that can be used to fetch
90ce3da70b43 Initial load
duke
parents:
diff changeset
   334
     * text from the associated document.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   335
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   336
     * @return the buffer
90ce3da70b43 Initial load
duke
parents:
diff changeset
   337
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   338
    protected final Segment getLineBuffer() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   339
        if (lineBuffer == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   340
            lineBuffer = new Segment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   341
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   342
        return lineBuffer;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   343
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   344
90ce3da70b43 Initial load
duke
parents:
diff changeset
   345
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   346
     * This is called by the nested wrapped line
90ce3da70b43 Initial load
duke
parents:
diff changeset
   347
     * views to determine the break location.  This can
90ce3da70b43 Initial load
duke
parents:
diff changeset
   348
     * be reimplemented to alter the breaking behavior.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   349
     * It will either break at word or character boundaries
90ce3da70b43 Initial load
duke
parents:
diff changeset
   350
     * depending upon the break argument given at
90ce3da70b43 Initial load
duke
parents:
diff changeset
   351
     * construction.
30462
507bcb03c954 8076624: Fix missing doclint warnings in javax.swing.text
darcy
parents: 28059
diff changeset
   352
     * @param p0 the starting document location
507bcb03c954 8076624: Fix missing doclint warnings in javax.swing.text
darcy
parents: 28059
diff changeset
   353
     * @param p1 the ending document location to use
507bcb03c954 8076624: Fix missing doclint warnings in javax.swing.text
darcy
parents: 28059
diff changeset
   354
     * @return the break position
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   355
     */
42216
621af0ebf6c4 8169518: Suppress Deprecation warnings for deprecated Swing APIs
prr
parents: 41807
diff changeset
   356
    @SuppressWarnings("deprecation")
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   357
    protected int calculateBreakPosition(int p0, int p1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   358
        int p;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   359
        Segment segment = SegmentCache.getSharedSegment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   360
        loadText(segment, p0, p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   361
        int currentWidth = getWidth();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   362
        if (wordWrap) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   363
            p = p0 + Utilities.getBreakLocation(segment, metrics,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   364
                                                tabBase, tabBase + currentWidth,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   365
                                                this, p0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   366
        } else {
8533
0537e84f6e69 6760148: Certain fonts are not correctly soft wrapped when using JTextComponent.print()
rupashka
parents: 7668
diff changeset
   367
            p = p0 + Utilities.getTabbedTextOffset(segment, metrics,
0537e84f6e69 6760148: Certain fonts are not correctly soft wrapped when using JTextComponent.print()
rupashka
parents: 7668
diff changeset
   368
                                                   tabBase, tabBase + currentWidth,
0537e84f6e69 6760148: Certain fonts are not correctly soft wrapped when using JTextComponent.print()
rupashka
parents: 7668
diff changeset
   369
                                                   this, p0, false);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   370
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   371
        SegmentCache.releaseSharedSegment(segment);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   372
        return p;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   373
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   374
90ce3da70b43 Initial load
duke
parents:
diff changeset
   375
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   376
     * Loads all of the children to initialize the view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   377
     * This is called by the <code>setParent</code> method.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   378
     * Subclasses can reimplement this to initialize their
90ce3da70b43 Initial load
duke
parents:
diff changeset
   379
     * child views in a different manner.  The default
90ce3da70b43 Initial load
duke
parents:
diff changeset
   380
     * implementation creates a child view for each
90ce3da70b43 Initial load
duke
parents:
diff changeset
   381
     * child element.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   382
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   383
     * @param f the view factory
90ce3da70b43 Initial load
duke
parents:
diff changeset
   384
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   385
    protected void loadChildren(ViewFactory f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   386
        Element e = getElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   387
        int n = e.getElementCount();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   388
        if (n > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   389
            View[] added = new View[n];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   390
            for (int i = 0; i < n; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   391
                added[i] = new WrappedLine(e.getElement(i));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   392
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   393
            replace(0, 0, added);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   394
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   395
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   396
90ce3da70b43 Initial load
duke
parents:
diff changeset
   397
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   398
     * Update the child views in response to a
90ce3da70b43 Initial load
duke
parents:
diff changeset
   399
     * document event.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   400
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   401
    void updateChildren(DocumentEvent e, Shape a) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   402
        Element elem = getElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   403
        DocumentEvent.ElementChange ec = e.getChange(elem);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   404
        if (ec != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   405
            // the structure of this element changed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   406
            Element[] removedElems = ec.getChildrenRemoved();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   407
            Element[] addedElems = ec.getChildrenAdded();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   408
            View[] added = new View[addedElems.length];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   409
            for (int i = 0; i < addedElems.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   410
                added[i] = new WrappedLine(addedElems[i]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   411
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   412
            replace(ec.getIndex(), removedElems.length, added);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   413
90ce3da70b43 Initial load
duke
parents:
diff changeset
   414
            // should damge a little more intelligently.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   415
            if (a != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   416
                preferenceChanged(null, true, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   417
                getContainer().repaint();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   418
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   419
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   420
90ce3da70b43 Initial load
duke
parents:
diff changeset
   421
        // update font metrics which may be used by the child views
90ce3da70b43 Initial load
duke
parents:
diff changeset
   422
        updateMetrics();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   423
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   424
90ce3da70b43 Initial load
duke
parents:
diff changeset
   425
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   426
     * Load the text buffer with the given range
90ce3da70b43 Initial load
duke
parents:
diff changeset
   427
     * of text.  This is used by the fragments
90ce3da70b43 Initial load
duke
parents:
diff changeset
   428
     * broken off of this view as well as this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   429
     * view itself.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   430
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   431
    final void loadText(Segment segment, int p0, int p1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   432
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   433
            Document doc = getDocument();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   434
            doc.getText(p0, p1 - p0, segment);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   435
        } catch (BadLocationException bl) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   436
            throw new StateInvariantError("Can't get line text");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   437
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   438
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   439
90ce3da70b43 Initial load
duke
parents:
diff changeset
   440
    final void updateMetrics() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   441
        Component host = getContainer();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   442
        Font f = host.getFont();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   443
        metrics = host.getFontMetrics(f);
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   444
        if (useFloatingPointAPI) {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   445
            FontRenderContext frc = metrics.getFontRenderContext();
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   446
            float tabWidth = (float) f.getStringBounds("m", frc).getWidth();
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   447
            tabSize = getTabSize() * tabWidth;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   448
        } else {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   449
            tabSize = getTabSize() * metrics.charWidth('m');
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   450
        }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   451
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   452
90ce3da70b43 Initial load
duke
parents:
diff changeset
   453
    // --- TabExpander methods ------------------------------------------
90ce3da70b43 Initial load
duke
parents:
diff changeset
   454
90ce3da70b43 Initial load
duke
parents:
diff changeset
   455
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   456
     * Returns the next tab stop position after a given reference position.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   457
     * This implementation does not support things like centering so it
90ce3da70b43 Initial load
duke
parents:
diff changeset
   458
     * ignores the tabOffset argument.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   459
     *
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   460
     * @param x the current position &gt;= 0
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   461
     * @param tabOffset the position within the text stream
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   462
     *   that the tab occurred at &gt;= 0.
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   463
     * @return the tab stop, measured in points &gt;= 0
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   464
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   465
    public float nextTabStop(float x, int tabOffset) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   466
        if (tabSize == 0)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   467
            return x;
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   468
        float ntabs = (x - tabBase) / tabSize;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   469
        return tabBase + ((ntabs + 1) * tabSize);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   470
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   471
90ce3da70b43 Initial load
duke
parents:
diff changeset
   472
90ce3da70b43 Initial load
duke
parents:
diff changeset
   473
    // --- View methods -------------------------------------
90ce3da70b43 Initial load
duke
parents:
diff changeset
   474
90ce3da70b43 Initial load
duke
parents:
diff changeset
   475
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   476
     * Renders using the given rendering surface and area
90ce3da70b43 Initial load
duke
parents:
diff changeset
   477
     * on that surface.  This is implemented to stash the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   478
     * selection positions, selection colors, and font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   479
     * metrics for the nested lines to use.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   480
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   481
     * @param g the rendering surface to use
90ce3da70b43 Initial load
duke
parents:
diff changeset
   482
     * @param a the allocated region to render into
90ce3da70b43 Initial load
duke
parents:
diff changeset
   483
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   484
     * @see View#paint
90ce3da70b43 Initial load
duke
parents:
diff changeset
   485
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   486
    public void paint(Graphics g, Shape a) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   487
        Rectangle alloc = (Rectangle) a;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   488
        tabBase = alloc.x;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   489
        JTextComponent host = (JTextComponent) getContainer();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   490
        sel0 = host.getSelectionStart();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   491
        sel1 = host.getSelectionEnd();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   492
        unselected = (host.isEnabled()) ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   493
            host.getForeground() : host.getDisabledTextColor();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   494
        Caret c = host.getCaret();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   495
        selected = c.isSelectionVisible() && host.getHighlighter() != null ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   496
                        host.getSelectedTextColor() : unselected;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   497
        g.setFont(host.getFont());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   498
90ce3da70b43 Initial load
duke
parents:
diff changeset
   499
        // superclass paints the children
90ce3da70b43 Initial load
duke
parents:
diff changeset
   500
        super.paint(g, a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   501
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   502
90ce3da70b43 Initial load
duke
parents:
diff changeset
   503
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   504
     * Sets the size of the view.  This should cause
90ce3da70b43 Initial load
duke
parents:
diff changeset
   505
     * layout of the view along the given axis, if it
90ce3da70b43 Initial load
duke
parents:
diff changeset
   506
     * has any layout duties.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   507
     *
20158
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   508
     * @param width the width &gt;= 0
1c5d22e5b898 8025117: [cleanup] Eliminate doclint errors in javax/swing/text classes
yan
parents: 9035
diff changeset
   509
     * @param height the height &gt;= 0
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   510
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   511
    public void setSize(float width, float height) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   512
        updateMetrics();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   513
        if ((int) width != getWidth()) {
21278
ef8a3a2a72f2 8022746: List of spelling errors in API doc
malenkov
parents: 20158
diff changeset
   514
            // invalidate the view itself since the desired widths
ef8a3a2a72f2 8022746: List of spelling errors in API doc
malenkov
parents: 20158
diff changeset
   515
            // of the children will be based upon this views width.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   516
            preferenceChanged(null, true, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   517
            widthChanging = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   518
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   519
        super.setSize(width, height);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   520
        widthChanging = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   521
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   522
90ce3da70b43 Initial load
duke
parents:
diff changeset
   523
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   524
     * Determines the preferred span for this view along an
90ce3da70b43 Initial load
duke
parents:
diff changeset
   525
     * axis.  This is implemented to provide the superclass
90ce3da70b43 Initial load
duke
parents:
diff changeset
   526
     * behavior after first making sure that the current font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   527
     * metrics are cached (for the nested lines which use
90ce3da70b43 Initial load
duke
parents:
diff changeset
   528
     * the metrics to determine the height of the potentially
90ce3da70b43 Initial load
duke
parents:
diff changeset
   529
     * wrapped lines).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   530
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   531
     * @param axis may be either View.X_AXIS or View.Y_AXIS
90ce3da70b43 Initial load
duke
parents:
diff changeset
   532
     * @return  the span the view would like to be rendered into.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   533
     *           Typically the view is told to render into the span
90ce3da70b43 Initial load
duke
parents:
diff changeset
   534
     *           that is returned, although there is no guarantee.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   535
     *           The parent may choose to resize or break the view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   536
     * @see View#getPreferredSpan
90ce3da70b43 Initial load
duke
parents:
diff changeset
   537
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   538
    public float getPreferredSpan(int axis) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   539
        updateMetrics();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   540
        return super.getPreferredSpan(axis);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   541
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   542
90ce3da70b43 Initial load
duke
parents:
diff changeset
   543
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   544
     * Determines the minimum span for this view along an
90ce3da70b43 Initial load
duke
parents:
diff changeset
   545
     * axis.  This is implemented to provide the superclass
90ce3da70b43 Initial load
duke
parents:
diff changeset
   546
     * behavior after first making sure that the current font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   547
     * metrics are cached (for the nested lines which use
90ce3da70b43 Initial load
duke
parents:
diff changeset
   548
     * the metrics to determine the height of the potentially
90ce3da70b43 Initial load
duke
parents:
diff changeset
   549
     * wrapped lines).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   550
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   551
     * @param axis may be either View.X_AXIS or View.Y_AXIS
90ce3da70b43 Initial load
duke
parents:
diff changeset
   552
     * @return  the span the view would like to be rendered into.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   553
     *           Typically the view is told to render into the span
90ce3da70b43 Initial load
duke
parents:
diff changeset
   554
     *           that is returned, although there is no guarantee.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   555
     *           The parent may choose to resize or break the view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   556
     * @see View#getMinimumSpan
90ce3da70b43 Initial load
duke
parents:
diff changeset
   557
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   558
    public float getMinimumSpan(int axis) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   559
        updateMetrics();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   560
        return super.getMinimumSpan(axis);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   561
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   562
90ce3da70b43 Initial load
duke
parents:
diff changeset
   563
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   564
     * Determines the maximum span for this view along an
90ce3da70b43 Initial load
duke
parents:
diff changeset
   565
     * axis.  This is implemented to provide the superclass
90ce3da70b43 Initial load
duke
parents:
diff changeset
   566
     * behavior after first making sure that the current font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   567
     * metrics are cached (for the nested lines which use
90ce3da70b43 Initial load
duke
parents:
diff changeset
   568
     * the metrics to determine the height of the potentially
90ce3da70b43 Initial load
duke
parents:
diff changeset
   569
     * wrapped lines).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   570
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   571
     * @param axis may be either View.X_AXIS or View.Y_AXIS
90ce3da70b43 Initial load
duke
parents:
diff changeset
   572
     * @return  the span the view would like to be rendered into.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   573
     *           Typically the view is told to render into the span
90ce3da70b43 Initial load
duke
parents:
diff changeset
   574
     *           that is returned, although there is no guarantee.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   575
     *           The parent may choose to resize or break the view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   576
     * @see View#getMaximumSpan
90ce3da70b43 Initial load
duke
parents:
diff changeset
   577
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   578
    public float getMaximumSpan(int axis) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   579
        updateMetrics();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   580
        return super.getMaximumSpan(axis);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   581
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   582
90ce3da70b43 Initial load
duke
parents:
diff changeset
   583
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   584
     * Gives notification that something was inserted into the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   585
     * document in a location that this view is responsible for.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   586
     * This is implemented to simply update the children.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   587
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   588
     * @param e the change information from the associated document
90ce3da70b43 Initial load
duke
parents:
diff changeset
   589
     * @param a the current allocation of the view
90ce3da70b43 Initial load
duke
parents:
diff changeset
   590
     * @param f the factory to use to rebuild if the view has children
90ce3da70b43 Initial load
duke
parents:
diff changeset
   591
     * @see View#insertUpdate
90ce3da70b43 Initial load
duke
parents:
diff changeset
   592
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   593
    public void insertUpdate(DocumentEvent e, Shape a, ViewFactory f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   594
        updateChildren(e, a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   595
90ce3da70b43 Initial load
duke
parents:
diff changeset
   596
        Rectangle alloc = ((a != null) && isAllocationValid()) ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   597
            getInsideAllocation(a) : null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   598
        int pos = e.getOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   599
        View v = getViewAtPosition(pos, alloc);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   600
        if (v != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   601
            v.insertUpdate(e, alloc, f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   602
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   603
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   604
90ce3da70b43 Initial load
duke
parents:
diff changeset
   605
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   606
     * Gives notification that something was removed from the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   607
     * document in a location that this view is responsible for.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   608
     * This is implemented to simply update the children.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   609
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   610
     * @param e the change information from the associated document
90ce3da70b43 Initial load
duke
parents:
diff changeset
   611
     * @param a the current allocation of the view
90ce3da70b43 Initial load
duke
parents:
diff changeset
   612
     * @param f the factory to use to rebuild if the view has children
90ce3da70b43 Initial load
duke
parents:
diff changeset
   613
     * @see View#removeUpdate
90ce3da70b43 Initial load
duke
parents:
diff changeset
   614
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   615
    public void removeUpdate(DocumentEvent e, Shape a, ViewFactory f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   616
        updateChildren(e, a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   617
90ce3da70b43 Initial load
duke
parents:
diff changeset
   618
        Rectangle alloc = ((a != null) && isAllocationValid()) ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   619
            getInsideAllocation(a) : null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   620
        int pos = e.getOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   621
        View v = getViewAtPosition(pos, alloc);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   622
        if (v != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   623
            v.removeUpdate(e, alloc, f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   624
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   625
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   626
90ce3da70b43 Initial load
duke
parents:
diff changeset
   627
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   628
     * Gives notification from the document that attributes were changed
90ce3da70b43 Initial load
duke
parents:
diff changeset
   629
     * in a location that this view is responsible for.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   630
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   631
     * @param e the change information from the associated document
90ce3da70b43 Initial load
duke
parents:
diff changeset
   632
     * @param a the current allocation of the view
90ce3da70b43 Initial load
duke
parents:
diff changeset
   633
     * @param f the factory to use to rebuild if the view has children
90ce3da70b43 Initial load
duke
parents:
diff changeset
   634
     * @see View#changedUpdate
90ce3da70b43 Initial load
duke
parents:
diff changeset
   635
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   636
    public void changedUpdate(DocumentEvent e, Shape a, ViewFactory f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   637
        updateChildren(e, a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   638
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   639
90ce3da70b43 Initial load
duke
parents:
diff changeset
   640
    // --- variables -------------------------------------------
90ce3da70b43 Initial load
duke
parents:
diff changeset
   641
90ce3da70b43 Initial load
duke
parents:
diff changeset
   642
    FontMetrics metrics;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   643
    Segment lineBuffer;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   644
    boolean widthChanging;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   645
    int tabBase;
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   646
    float tabSize;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   647
    boolean wordWrap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   648
90ce3da70b43 Initial load
duke
parents:
diff changeset
   649
    int sel0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   650
    int sel1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   651
    Color unselected;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   652
    Color selected;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   653
90ce3da70b43 Initial load
duke
parents:
diff changeset
   654
90ce3da70b43 Initial load
duke
parents:
diff changeset
   655
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   656
     * Simple view of a line that wraps if it doesn't
90ce3da70b43 Initial load
duke
parents:
diff changeset
   657
     * fit withing the horizontal space allocated.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   658
     * This class tries to be lightweight by carrying little
90ce3da70b43 Initial load
duke
parents:
diff changeset
   659
     * state of it's own and sharing the state of the outer class
90ce3da70b43 Initial load
duke
parents:
diff changeset
   660
     * with it's sibblings.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   661
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   662
    class WrappedLine extends View {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   663
90ce3da70b43 Initial load
duke
parents:
diff changeset
   664
        WrappedLine(Element elem) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   665
            super(elem);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   666
            lineCount = -1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   667
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   668
90ce3da70b43 Initial load
duke
parents:
diff changeset
   669
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   670
         * Determines the preferred span for this view along an
90ce3da70b43 Initial load
duke
parents:
diff changeset
   671
         * axis.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   672
         *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   673
         * @param axis may be either X_AXIS or Y_AXIS
90ce3da70b43 Initial load
duke
parents:
diff changeset
   674
         * @return   the span the view would like to be rendered into.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   675
         *           Typically the view is told to render into the span
90ce3da70b43 Initial load
duke
parents:
diff changeset
   676
         *           that is returned, although there is no guarantee.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   677
         *           The parent may choose to resize or break the view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   678
         * @see View#getPreferredSpan
90ce3da70b43 Initial load
duke
parents:
diff changeset
   679
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   680
        public float getPreferredSpan(int axis) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   681
            switch (axis) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   682
            case View.X_AXIS:
90ce3da70b43 Initial load
duke
parents:
diff changeset
   683
                float width = getWidth();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   684
                if (width == Integer.MAX_VALUE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   685
                    // We have been initially set to MAX_VALUE, but we don't
90ce3da70b43 Initial load
duke
parents:
diff changeset
   686
                    // want this as our preferred.
5592
fc99326b0953 6925473: REGRESSION: JOptionPane in dialog is full-screen height
rupashka
parents: 3504
diff changeset
   687
                    return 100f;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   688
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   689
                return width;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   690
            case View.Y_AXIS:
5592
fc99326b0953 6925473: REGRESSION: JOptionPane in dialog is full-screen height
rupashka
parents: 3504
diff changeset
   691
                if (lineCount < 0 || widthChanging) {
fc99326b0953 6925473: REGRESSION: JOptionPane in dialog is full-screen height
rupashka
parents: 3504
diff changeset
   692
                    breakLines(getStartOffset());
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   693
                }
5592
fc99326b0953 6925473: REGRESSION: JOptionPane in dialog is full-screen height
rupashka
parents: 3504
diff changeset
   694
                return lineCount * metrics.getHeight();
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   695
            default:
90ce3da70b43 Initial load
duke
parents:
diff changeset
   696
                throw new IllegalArgumentException("Invalid axis: " + axis);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   697
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   698
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   699
90ce3da70b43 Initial load
duke
parents:
diff changeset
   700
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   701
         * Renders using the given rendering surface and area on that
90ce3da70b43 Initial load
duke
parents:
diff changeset
   702
         * surface.  The view may need to do layout and create child
90ce3da70b43 Initial load
duke
parents:
diff changeset
   703
         * views to enable itself to render into the given allocation.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   704
         *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   705
         * @param g the rendering surface to use
90ce3da70b43 Initial load
duke
parents:
diff changeset
   706
         * @param a the allocated region to render into
90ce3da70b43 Initial load
duke
parents:
diff changeset
   707
         * @see View#paint
90ce3da70b43 Initial load
duke
parents:
diff changeset
   708
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   709
        public void paint(Graphics g, Shape a) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   710
            Rectangle alloc = (Rectangle) a;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   711
            int y = alloc.y + metrics.getAscent();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   712
            int x = alloc.x;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   713
90ce3da70b43 Initial load
duke
parents:
diff changeset
   714
            JTextComponent host = (JTextComponent)getContainer();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   715
            Highlighter h = host.getHighlighter();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   716
            LayeredHighlighter dh = (h instanceof LayeredHighlighter) ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   717
                                     (LayeredHighlighter)h : null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   718
90ce3da70b43 Initial load
duke
parents:
diff changeset
   719
            int start = getStartOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   720
            int end = getEndOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   721
            int p0 = start;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   722
            int[] lineEnds = getLineEnds();
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   723
            boolean useDrawLineFP = drawLineOverridden && g instanceof Graphics2D;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   724
            for (int i = 0; i < lineCount; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   725
                int p1 = (lineEnds == null) ? end :
90ce3da70b43 Initial load
duke
parents:
diff changeset
   726
                                             start + lineEnds[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   727
                if (dh != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   728
                    int hOffset = (p1 == end)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   729
                                  ? (p1 - 1)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   730
                                  : p1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   731
                    dh.paintLayeredHighlights(g, p0, hOffset, a, host, this);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   732
                }
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   733
                if (useDrawLineFP) {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   734
                    drawLine(p0, p1, (Graphics2D) g, (float) x, (float) y);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   735
                } else {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   736
                    drawLine(p0, p1, g, x, y);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   737
                }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   738
                p0 = p1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   739
                y += metrics.getHeight();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   740
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   741
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   742
90ce3da70b43 Initial load
duke
parents:
diff changeset
   743
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   744
         * Provides a mapping from the document model coordinate space
90ce3da70b43 Initial load
duke
parents:
diff changeset
   745
         * to the coordinate space of the view mapped to it.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   746
         *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   747
         * @param pos the position to convert
90ce3da70b43 Initial load
duke
parents:
diff changeset
   748
         * @param a the allocated region to render into
90ce3da70b43 Initial load
duke
parents:
diff changeset
   749
         * @return the bounding box of the given position is returned
90ce3da70b43 Initial load
duke
parents:
diff changeset
   750
         * @exception BadLocationException  if the given position does not represent a
90ce3da70b43 Initial load
duke
parents:
diff changeset
   751
         *   valid location in the associated document
90ce3da70b43 Initial load
duke
parents:
diff changeset
   752
         * @see View#modelToView
90ce3da70b43 Initial load
duke
parents:
diff changeset
   753
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   754
        public Shape modelToView(int pos, Shape a, Position.Bias b)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   755
                throws BadLocationException {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   756
            Rectangle alloc = a.getBounds();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   757
            alloc.height = metrics.getHeight();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   758
            alloc.width = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   759
90ce3da70b43 Initial load
duke
parents:
diff changeset
   760
            int p0 = getStartOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   761
            if (pos < p0 || pos > getEndOffset()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   762
                throw new BadLocationException("Position out of range", pos);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   763
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   764
90ce3da70b43 Initial load
duke
parents:
diff changeset
   765
            int testP = (b == Position.Bias.Forward) ? pos :
90ce3da70b43 Initial load
duke
parents:
diff changeset
   766
                        Math.max(p0, pos - 1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   767
            int line = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   768
            int[] lineEnds = getLineEnds();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   769
            if (lineEnds != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   770
                line = findLine(testP - p0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   771
                if (line > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   772
                    p0 += lineEnds[line - 1];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   773
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   774
                alloc.y += alloc.height * line;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   775
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   776
90ce3da70b43 Initial load
duke
parents:
diff changeset
   777
            if (pos > p0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   778
                Segment segment = SegmentCache.getSharedSegment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   779
                loadText(segment, p0, pos);
42717
367db14731fb 8169719: WrappedPlainView.modelToView() should return Rectangle2D
alexsch
parents: 42216
diff changeset
   780
                float x = alloc.x;
367db14731fb 8169719: WrappedPlainView.modelToView() should return Rectangle2D
alexsch
parents: 42216
diff changeset
   781
                x += Utilities.getTabbedTextWidth(segment, metrics, x,
367db14731fb 8169719: WrappedPlainView.modelToView() should return Rectangle2D
alexsch
parents: 42216
diff changeset
   782
                                                  WrappedPlainView.this, p0);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   783
                SegmentCache.releaseSharedSegment(segment);
42717
367db14731fb 8169719: WrappedPlainView.modelToView() should return Rectangle2D
alexsch
parents: 42216
diff changeset
   784
                return new Rectangle2D.Float(x, alloc.y, alloc.width, alloc.height);
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   785
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   786
            return alloc;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   787
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   788
90ce3da70b43 Initial load
duke
parents:
diff changeset
   789
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   790
         * Provides a mapping from the view coordinate space to the logical
90ce3da70b43 Initial load
duke
parents:
diff changeset
   791
         * coordinate space of the model.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   792
         *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   793
         * @param fx the X coordinate
90ce3da70b43 Initial load
duke
parents:
diff changeset
   794
         * @param fy the Y coordinate
90ce3da70b43 Initial load
duke
parents:
diff changeset
   795
         * @param a the allocated region to render into
90ce3da70b43 Initial load
duke
parents:
diff changeset
   796
         * @return the location within the model that best represents the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   797
         *  given point in the view
90ce3da70b43 Initial load
duke
parents:
diff changeset
   798
         * @see View#viewToModel
90ce3da70b43 Initial load
duke
parents:
diff changeset
   799
         */
42216
621af0ebf6c4 8169518: Suppress Deprecation warnings for deprecated Swing APIs
prr
parents: 41807
diff changeset
   800
        @SuppressWarnings("deprecation")
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   801
        public int viewToModel(float fx, float fy, Shape a, Position.Bias[] bias) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   802
            // PENDING(prinz) implement bias properly
90ce3da70b43 Initial load
duke
parents:
diff changeset
   803
            bias[0] = Position.Bias.Forward;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   804
90ce3da70b43 Initial load
duke
parents:
diff changeset
   805
            Rectangle alloc = (Rectangle) a;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   806
            int x = (int) fx;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   807
            int y = (int) fy;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   808
            if (y < alloc.y) {
28059
e576535359cc 8067377: My hobby: caning, then then canning, the the can-can
martin
parents: 25859
diff changeset
   809
                // above the area covered by this icon, so the position
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   810
                // is assumed to be the start of the coverage for this view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   811
                return getStartOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   812
            } else if (y > alloc.y + alloc.height) {
28059
e576535359cc 8067377: My hobby: caning, then then canning, the the can-can
martin
parents: 25859
diff changeset
   813
                // below the area covered by this icon, so the position
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   814
                // is assumed to be the end of the coverage for this view.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   815
                return getEndOffset() - 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   816
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   817
                // positioned within the coverage of this view vertically,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   818
                // so we figure out which line the point corresponds to.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   819
                // if the line is greater than the number of lines contained, then
90ce3da70b43 Initial load
duke
parents:
diff changeset
   820
                // simply use the last line as it represents the last possible place
90ce3da70b43 Initial load
duke
parents:
diff changeset
   821
                // we can position to.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   822
                alloc.height = metrics.getHeight();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   823
                int line = (alloc.height > 0 ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   824
                            (y - alloc.y) / alloc.height : lineCount - 1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   825
                if (line >= lineCount) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   826
                    return getEndOffset() - 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   827
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   828
                    int p0 = getStartOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   829
                    int p1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   830
                    if (lineCount == 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   831
                        p1 = getEndOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   832
                    } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   833
                        int[] lineEnds = getLineEnds();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   834
                        p1 = p0 + lineEnds[line];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   835
                        if (line > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   836
                            p0 += lineEnds[line - 1];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   837
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   838
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   839
90ce3da70b43 Initial load
duke
parents:
diff changeset
   840
                    if (x < alloc.x) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   841
                        // point is to the left of the line
90ce3da70b43 Initial load
duke
parents:
diff changeset
   842
                        return p0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   843
                    } else if (x > alloc.x + alloc.width) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   844
                        // point is to the right of the line
90ce3da70b43 Initial load
duke
parents:
diff changeset
   845
                        return p1 - 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   846
                    } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   847
                        // Determine the offset into the text
90ce3da70b43 Initial load
duke
parents:
diff changeset
   848
                        Segment segment = SegmentCache.getSharedSegment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   849
                        loadText(segment, p0, p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   850
                        int n = Utilities.getTabbedTextOffset(segment, metrics,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   851
                                                   alloc.x, x,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   852
                                                   WrappedPlainView.this, p0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   853
                        SegmentCache.releaseSharedSegment(segment);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   854
                        return Math.min(p0 + n, p1 - 1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   855
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   856
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   857
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   858
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   859
90ce3da70b43 Initial load
duke
parents:
diff changeset
   860
        public void insertUpdate(DocumentEvent e, Shape a, ViewFactory f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   861
            update(e, a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   862
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   863
90ce3da70b43 Initial load
duke
parents:
diff changeset
   864
        public void removeUpdate(DocumentEvent e, Shape a, ViewFactory f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   865
            update(e, a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   866
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   867
90ce3da70b43 Initial load
duke
parents:
diff changeset
   868
        private void update(DocumentEvent ev, Shape a) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   869
            int oldCount = lineCount;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   870
            breakLines(ev.getOffset());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   871
            if (oldCount != lineCount) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   872
                WrappedPlainView.this.preferenceChanged(this, false, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   873
                // have to repaint any views after the receiver.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   874
                getContainer().repaint();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   875
            } else if (a != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   876
                Component c = getContainer();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   877
                Rectangle alloc = (Rectangle) a;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   878
                c.repaint(alloc.x, alloc.y, alloc.width, alloc.height);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   879
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   880
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   881
90ce3da70b43 Initial load
duke
parents:
diff changeset
   882
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   883
         * Returns line cache. If the cache was GC'ed, recreates it.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   884
         * If there's no cache, returns null
90ce3da70b43 Initial load
duke
parents:
diff changeset
   885
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   886
        final int[] getLineEnds() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   887
            if (lineCache == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   888
                return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   889
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   890
                int[] lineEnds = lineCache.get();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   891
                if (lineEnds == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   892
                    // Cache was GC'ed, so rebuild it
90ce3da70b43 Initial load
duke
parents:
diff changeset
   893
                    return breakLines(getStartOffset());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   894
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   895
                    return lineEnds;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   896
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   897
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   898
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   899
90ce3da70b43 Initial load
duke
parents:
diff changeset
   900
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   901
         * Creates line cache if text breaks into more than one physical line.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   902
         * @param startPos position to start breaking from
90ce3da70b43 Initial load
duke
parents:
diff changeset
   903
         * @return the cache created, ot null if text breaks into one line
90ce3da70b43 Initial load
duke
parents:
diff changeset
   904
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   905
        final int[] breakLines(int startPos) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   906
            int[] lineEnds = (lineCache == null) ? null : lineCache.get();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   907
            int[] oldLineEnds = lineEnds;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   908
            int start = getStartOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   909
            int lineIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   910
            if (lineEnds != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   911
                lineIndex = findLine(startPos - start);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   912
                if (lineIndex > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   913
                    lineIndex--;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   914
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   915
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   916
90ce3da70b43 Initial load
duke
parents:
diff changeset
   917
            int p0 = (lineIndex == 0) ? start : start + lineEnds[lineIndex - 1];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   918
            int p1 = getEndOffset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   919
            while (p0 < p1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   920
                int p = calculateBreakPosition(p0, p1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   921
                p0 = (p == p0) ? ++p : p;      // 4410243
90ce3da70b43 Initial load
duke
parents:
diff changeset
   922
90ce3da70b43 Initial load
duke
parents:
diff changeset
   923
                if (lineIndex == 0 && p0 >= p1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   924
                    // do not use cache if there's only one line
90ce3da70b43 Initial load
duke
parents:
diff changeset
   925
                    lineCache = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   926
                    lineEnds = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   927
                    lineIndex = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   928
                    break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   929
                } else if (lineEnds == null || lineIndex >= lineEnds.length) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   930
                    // we have 2+ lines, and the cache is not big enough
90ce3da70b43 Initial load
duke
parents:
diff changeset
   931
                    // we try to estimate total number of lines
90ce3da70b43 Initial load
duke
parents:
diff changeset
   932
                    double growFactor = ((double)(p1 - start) / (p0 - start));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   933
                    int newSize = (int)Math.ceil((lineIndex + 1) * growFactor);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   934
                    newSize = Math.max(newSize, lineIndex + 2);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   935
                    int[] tmp = new int[newSize];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   936
                    if (lineEnds != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   937
                        System.arraycopy(lineEnds, 0, tmp, 0, lineIndex);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   938
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   939
                    lineEnds = tmp;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   940
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   941
                lineEnds[lineIndex++] = p0 - start;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   942
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   943
90ce3da70b43 Initial load
duke
parents:
diff changeset
   944
            lineCount = lineIndex;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   945
            if (lineCount > 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   946
                // check if the cache is too big
90ce3da70b43 Initial load
duke
parents:
diff changeset
   947
                int maxCapacity = lineCount + lineCount / 3;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   948
                if (lineEnds.length > maxCapacity) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   949
                    int[] tmp = new int[maxCapacity];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   950
                    System.arraycopy(lineEnds, 0, tmp, 0, lineCount);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   951
                    lineEnds = tmp;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   952
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   953
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   954
90ce3da70b43 Initial load
duke
parents:
diff changeset
   955
            if (lineEnds != null && lineEnds != oldLineEnds) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   956
                lineCache = new SoftReference<int[]>(lineEnds);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   957
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   958
            return lineEnds;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   959
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   960
90ce3da70b43 Initial load
duke
parents:
diff changeset
   961
        /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   962
         * Binary search in the cache for line containing specified offset
90ce3da70b43 Initial load
duke
parents:
diff changeset
   963
         * (which is relative to the beginning of the view). This method
90ce3da70b43 Initial load
duke
parents:
diff changeset
   964
         * assumes that cache exists.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   965
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   966
        private int findLine(int offset) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   967
            int[] lineEnds = lineCache.get();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   968
            if (offset < lineEnds[0]) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   969
                return 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   970
            } else if (offset > lineEnds[lineCount - 1]) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   971
                return lineCount;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   972
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   973
                return findLine(lineEnds, offset, 0, lineCount - 1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   974
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   975
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   976
90ce3da70b43 Initial load
duke
parents:
diff changeset
   977
        private int findLine(int[] array, int offset, int min, int max) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   978
            if (max - min <= 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   979
                return max;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   980
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   981
                int mid = (max + min) / 2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   982
                return (offset < array[mid]) ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   983
                        findLine(array, offset, min, mid) :
90ce3da70b43 Initial load
duke
parents:
diff changeset
   984
                        findLine(array, offset, mid, max);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   985
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   986
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   987
90ce3da70b43 Initial load
duke
parents:
diff changeset
   988
        int lineCount;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   989
        SoftReference<int[]> lineCache = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   990
    }
41807
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   991
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   992
    private final boolean drawLineOverridden;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   993
    private final boolean drawSelectedTextOverridden;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   994
    private final boolean drawUnselectedTextOverridden;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   995
    private final boolean useFloatingPointAPI;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   996
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   997
    {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   998
        final Class<?> CLS = getClass();
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
   999
        final Class<?> INT = Integer.TYPE;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1000
        final Class<?> FP = Float.TYPE;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1001
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1002
        drawLineOverridden = AccessController
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1003
                .doPrivileged(new PrivilegedAction<Boolean>() {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1004
            @Override
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1005
            public Boolean run() {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1006
                Class<?>[] intTypes = {INT, INT, Graphics.class, INT, INT};
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1007
                Class<?>[] fpTypes = {INT, INT, Graphics2D.class, FP, FP};
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1008
                return isFPMethodOverriden("drawLine", CLS, intTypes, fpTypes);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1009
            }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1010
        });
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1011
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1012
        drawUnselectedTextOverridden = AccessController
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1013
                .doPrivileged(new PrivilegedAction<Boolean>() {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1014
            @Override
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1015
            public Boolean run() {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1016
                Class<?>[] intTypes = {Graphics.class, INT, INT, INT, INT};
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1017
                Class<?>[] fpTypes = {Graphics2D.class, FP, FP, INT, INT};
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1018
                return isFPMethodOverriden("drawUnselectedText", CLS, intTypes, fpTypes);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1019
            }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1020
        });
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1021
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1022
        drawSelectedTextOverridden = AccessController
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1023
                .doPrivileged(new PrivilegedAction<Boolean>() {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1024
            @Override
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1025
            public Boolean run() {
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1026
                Class<?>[] intTypes = {Graphics.class, INT, INT, INT, INT};
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1027
                Class<?>[] fpTypes = {Graphics2D.class, FP, FP, INT, INT};
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1028
                return isFPMethodOverriden("drawSelectedText", CLS, intTypes, fpTypes);
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1029
            }
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1030
        });
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1031
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1032
        useFloatingPointAPI = drawUnselectedTextOverridden || drawSelectedTextOverridden;
f9eb6cb54fed 8156217: Selected text is shifted on HiDPI display
alexsch
parents: 39553
diff changeset
  1033
    }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1034
}