jdk/src/share/classes/java/text/CollationElementIterator.java
author ohair
Tue, 28 Dec 2010 15:53:50 -0800
changeset 7668 d4a77089c587
parent 7509 bc7eaae38fff
child 12848 da701d422d2c
permissions -rw-r--r--
6962318: Update copyright year Reviewed-by: xdono
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     1
/*
7668
d4a77089c587 6962318: Update copyright year
ohair
parents: 7509
diff changeset
     2
 * Copyright (c) 1996, 2010, 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: 4839
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: 4839
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: 4839
diff changeset
    21
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4839
diff changeset
    22
 * or visit www.oracle.com if you need additional information or have any
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4839
diff changeset
    23
 * questions.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    24
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    25
90ce3da70b43 Initial load
duke
parents:
diff changeset
    26
/*
90ce3da70b43 Initial load
duke
parents:
diff changeset
    27
 * (C) Copyright Taligent, Inc. 1996, 1997 - All Rights Reserved
90ce3da70b43 Initial load
duke
parents:
diff changeset
    28
 * (C) Copyright IBM Corp. 1996-1998 - All Rights Reserved
90ce3da70b43 Initial load
duke
parents:
diff changeset
    29
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    30
 *   The original version of this source code and documentation is copyrighted
90ce3da70b43 Initial load
duke
parents:
diff changeset
    31
 * and owned by Taligent, Inc., a wholly-owned subsidiary of IBM. These
90ce3da70b43 Initial load
duke
parents:
diff changeset
    32
 * materials are provided under terms of a License Agreement between Taligent
90ce3da70b43 Initial load
duke
parents:
diff changeset
    33
 * and Sun. This technology is protected by multiple US and International
90ce3da70b43 Initial load
duke
parents:
diff changeset
    34
 * patents. This notice and attribution to Taligent may not be removed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    35
 *   Taligent is a registered trademark of Taligent, Inc.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    36
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    37
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    38
90ce3da70b43 Initial load
duke
parents:
diff changeset
    39
package java.text;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    40
90ce3da70b43 Initial load
duke
parents:
diff changeset
    41
import java.lang.Character;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    42
import java.util.Vector;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    43
import sun.text.CollatorUtilities;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    44
import sun.text.normalizer.NormalizerBase;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    45
90ce3da70b43 Initial load
duke
parents:
diff changeset
    46
/**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    47
 * The <code>CollationElementIterator</code> class is used as an iterator
90ce3da70b43 Initial load
duke
parents:
diff changeset
    48
 * to walk through each character of an international string. Use the iterator
90ce3da70b43 Initial load
duke
parents:
diff changeset
    49
 * to return the ordering priority of the positioned character. The ordering
90ce3da70b43 Initial load
duke
parents:
diff changeset
    50
 * priority of a character, which we refer to as a key, defines how a character
90ce3da70b43 Initial load
duke
parents:
diff changeset
    51
 * is collated in the given collation object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    52
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    53
 * <p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    54
 * For example, consider the following in Spanish:
90ce3da70b43 Initial load
duke
parents:
diff changeset
    55
 * <blockquote>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    56
 * <pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    57
 * "ca" -> the first key is key('c') and second key is key('a').
90ce3da70b43 Initial load
duke
parents:
diff changeset
    58
 * "cha" -> the first key is key('ch') and second key is key('a').
90ce3da70b43 Initial load
duke
parents:
diff changeset
    59
 * </pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    60
 * </blockquote>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    61
 * And in German,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    62
 * <blockquote>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    63
 * <pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    64
 * "\u00e4b"-> the first key is key('a'), the second key is key('e'), and
90ce3da70b43 Initial load
duke
parents:
diff changeset
    65
 * the third key is key('b').
90ce3da70b43 Initial load
duke
parents:
diff changeset
    66
 * </pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    67
 * </blockquote>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    68
 * The key of a character is an integer composed of primary order(short),
90ce3da70b43 Initial load
duke
parents:
diff changeset
    69
 * secondary order(byte), and tertiary order(byte). Java strictly defines
90ce3da70b43 Initial load
duke
parents:
diff changeset
    70
 * the size and signedness of its primitive data types. Therefore, the static
90ce3da70b43 Initial load
duke
parents:
diff changeset
    71
 * functions <code>primaryOrder</code>, <code>secondaryOrder</code>, and
90ce3da70b43 Initial load
duke
parents:
diff changeset
    72
 * <code>tertiaryOrder</code> return <code>int</code>, <code>short</code>,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    73
 * and <code>short</code> respectively to ensure the correctness of the key
90ce3da70b43 Initial load
duke
parents:
diff changeset
    74
 * value.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    75
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    76
 * <p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    77
 * Example of the iterator usage,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    78
 * <blockquote>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    79
 * <pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    80
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    81
 *  String testString = "This is a test";
7509
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    82
 *  Collator col = Collator.getInstance();
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    83
 *  if (col instanceof RuleBasedCollator) {
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    84
 *      RuleBasedCollator ruleBasedCollator = (RuleBasedCollator)col;
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    85
 *      CollationElementIterator collationElementIterator = ruleBasedCollator.getCollationElementIterator(testString);
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    86
 *      int primaryOrder = CollationElementIterator.primaryOrder(collationElementIterator.next());
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    87
 *          :
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
    88
 *  }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    89
 * </pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    90
 * </blockquote>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    91
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    92
 * <p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    93
 * <code>CollationElementIterator.next</code> returns the collation order
90ce3da70b43 Initial load
duke
parents:
diff changeset
    94
 * of the next character. A collation order consists of primary order,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    95
 * secondary order and tertiary order. The data type of the collation
90ce3da70b43 Initial load
duke
parents:
diff changeset
    96
 * order is <strong>int</strong>. The first 16 bits of a collation order
90ce3da70b43 Initial load
duke
parents:
diff changeset
    97
 * is its primary order; the next 8 bits is the secondary order and the
90ce3da70b43 Initial load
duke
parents:
diff changeset
    98
 * last 8 bits is the tertiary order.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    99
 *
7509
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
   100
 * <p><b>Note:</b> <code>CollationElementIterator</code> is a part of
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
   101
 * <code>RuleBasedCollator</code> implementation. It is only usable
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
   102
 * with <code>RuleBasedCollator</code> instances.
bc7eaae38fff 6486695: [Col] Doc: CollationElementIterator example assumes Collator.getInstance return type
naoto
parents: 5506
diff changeset
   103
 *
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   104
 * @see                Collator
90ce3da70b43 Initial load
duke
parents:
diff changeset
   105
 * @see                RuleBasedCollator
90ce3da70b43 Initial load
duke
parents:
diff changeset
   106
 * @author             Helena Shih, Laura Werner, Richard Gillam
90ce3da70b43 Initial load
duke
parents:
diff changeset
   107
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   108
public final class CollationElementIterator
90ce3da70b43 Initial load
duke
parents:
diff changeset
   109
{
90ce3da70b43 Initial load
duke
parents:
diff changeset
   110
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   111
     * Null order which indicates the end of string is reached by the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   112
     * cursor.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   113
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   114
    public final static int NULLORDER = 0xffffffff;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   115
90ce3da70b43 Initial load
duke
parents:
diff changeset
   116
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   117
     * CollationElementIterator constructor.  This takes the source string and
90ce3da70b43 Initial load
duke
parents:
diff changeset
   118
     * the collation object.  The cursor will walk thru the source string based
90ce3da70b43 Initial load
duke
parents:
diff changeset
   119
     * on the predefined collation rules.  If the source string is empty,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   120
     * NULLORDER will be returned on the calls to next().
90ce3da70b43 Initial load
duke
parents:
diff changeset
   121
     * @param sourceText the source string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   122
     * @param order the collation object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   123
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   124
    CollationElementIterator(String sourceText, RuleBasedCollator owner) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   125
        this.owner = owner;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   126
        ordering = owner.getTables();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   127
        if ( sourceText.length() != 0 ) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   128
            NormalizerBase.Mode mode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   129
                CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   130
            text = new NormalizerBase(sourceText, mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   131
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   132
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   133
90ce3da70b43 Initial load
duke
parents:
diff changeset
   134
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   135
     * CollationElementIterator constructor.  This takes the source string and
90ce3da70b43 Initial load
duke
parents:
diff changeset
   136
     * the collation object.  The cursor will walk thru the source string based
90ce3da70b43 Initial load
duke
parents:
diff changeset
   137
     * on the predefined collation rules.  If the source string is empty,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   138
     * NULLORDER will be returned on the calls to next().
90ce3da70b43 Initial load
duke
parents:
diff changeset
   139
     * @param sourceText the source string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   140
     * @param order the collation object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   141
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   142
    CollationElementIterator(CharacterIterator sourceText, RuleBasedCollator owner) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   143
        this.owner = owner;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   144
        ordering = owner.getTables();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   145
        NormalizerBase.Mode mode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   146
            CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   147
        text = new NormalizerBase(sourceText, mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   148
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   149
90ce3da70b43 Initial load
duke
parents:
diff changeset
   150
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   151
     * Resets the cursor to the beginning of the string.  The next call
90ce3da70b43 Initial load
duke
parents:
diff changeset
   152
     * to next() will return the first collation element in the string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   153
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   154
    public void reset()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   155
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   156
        if (text != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   157
            text.reset();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   158
            NormalizerBase.Mode mode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   159
                CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   160
            text.setMode(mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   161
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   162
        buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   163
        expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   164
        swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   165
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   166
90ce3da70b43 Initial load
duke
parents:
diff changeset
   167
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   168
     * Get the next collation element in the string.  <p>This iterator iterates
90ce3da70b43 Initial load
duke
parents:
diff changeset
   169
     * over a sequence of collation elements that were built from the string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   170
     * Because there isn't necessarily a one-to-one mapping from characters to
90ce3da70b43 Initial load
duke
parents:
diff changeset
   171
     * collation elements, this doesn't mean the same thing as "return the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   172
     * collation element [or ordering priority] of the next character in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   173
     * string".</p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   174
     * <p>This function returns the collation element that the iterator is currently
90ce3da70b43 Initial load
duke
parents:
diff changeset
   175
     * pointing to and then updates the internal pointer to point to the next element.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   176
     * previous() updates the pointer first and then returns the element.  This
90ce3da70b43 Initial load
duke
parents:
diff changeset
   177
     * means that when you change direction while iterating (i.e., call next() and
90ce3da70b43 Initial load
duke
parents:
diff changeset
   178
     * then call previous(), or call previous() and then call next()), you'll get
90ce3da70b43 Initial load
duke
parents:
diff changeset
   179
     * back the same element twice.</p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   180
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   181
    public int next()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   182
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   183
        if (text == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   184
            return NULLORDER;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   185
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   186
        NormalizerBase.Mode textMode = text.getMode();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   187
        // convert the owner's mode to something the Normalizer understands
90ce3da70b43 Initial load
duke
parents:
diff changeset
   188
        NormalizerBase.Mode ownerMode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   189
            CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   190
        if (textMode != ownerMode) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   191
            text.setMode(ownerMode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   192
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   193
90ce3da70b43 Initial load
duke
parents:
diff changeset
   194
        // if buffer contains any decomposed char values
90ce3da70b43 Initial load
duke
parents:
diff changeset
   195
        // return their strength orders before continuing in
90ce3da70b43 Initial load
duke
parents:
diff changeset
   196
        // the Normalizer's CharacterIterator.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   197
        if (buffer != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   198
            if (expIndex < buffer.length) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   199
                return strengthOrder(buffer[expIndex++]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   200
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   201
                buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   202
                expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   203
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   204
        } else if (swapOrder != 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   205
            if (Character.isSupplementaryCodePoint(swapOrder)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   206
                char[] chars = Character.toChars(swapOrder);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   207
                swapOrder = chars[1];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   208
                return chars[0] << 16;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   209
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   210
            int order = swapOrder << 16;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   211
            swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   212
            return order;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   213
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   214
        int ch  = text.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   215
90ce3da70b43 Initial load
duke
parents:
diff changeset
   216
        // are we at the end of Normalizer's text?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   217
        if (ch == NormalizerBase.DONE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   218
            return NULLORDER;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   219
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   220
90ce3da70b43 Initial load
duke
parents:
diff changeset
   221
        int value = ordering.getUnicodeOrder(ch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   222
        if (value == RuleBasedCollator.UNMAPPED) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   223
            swapOrder = ch;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   224
            return UNMAPPEDCHARVALUE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   225
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   226
        else if (value >= RuleBasedCollator.CONTRACTCHARINDEX) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   227
            value = nextContractChar(ch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   228
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   229
        if (value >= RuleBasedCollator.EXPANDCHARINDEX) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   230
            buffer = ordering.getExpandValueList(value);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   231
            expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   232
            value = buffer[expIndex++];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   233
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   234
90ce3da70b43 Initial load
duke
parents:
diff changeset
   235
        if (ordering.isSEAsianSwapping()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   236
            int consonant;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   237
            if (isThaiPreVowel(ch)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   238
                consonant = text.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   239
                if (isThaiBaseConsonant(consonant)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   240
                    buffer = makeReorderedBuffer(consonant, value, buffer, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   241
                    value = buffer[0];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   242
                    expIndex = 1;
4839
6b3edc448285 5047314: [Col] Collator.compare() runs indefinitely for a certain set of Thai strings
peytoia
parents: 2
diff changeset
   243
                } else if (consonant != NormalizerBase.DONE) {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   244
                    text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   245
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   246
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   247
            if (isLaoPreVowel(ch)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   248
                consonant = text.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   249
                if (isLaoBaseConsonant(consonant)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   250
                    buffer = makeReorderedBuffer(consonant, value, buffer, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   251
                    value = buffer[0];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   252
                    expIndex = 1;
4839
6b3edc448285 5047314: [Col] Collator.compare() runs indefinitely for a certain set of Thai strings
peytoia
parents: 2
diff changeset
   253
                } else if (consonant != NormalizerBase.DONE) {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   254
                    text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   255
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   256
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   257
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   258
90ce3da70b43 Initial load
duke
parents:
diff changeset
   259
        return strengthOrder(value);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   260
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   261
90ce3da70b43 Initial load
duke
parents:
diff changeset
   262
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   263
     * Get the previous collation element in the string.  <p>This iterator iterates
90ce3da70b43 Initial load
duke
parents:
diff changeset
   264
     * over a sequence of collation elements that were built from the string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   265
     * Because there isn't necessarily a one-to-one mapping from characters to
90ce3da70b43 Initial load
duke
parents:
diff changeset
   266
     * collation elements, this doesn't mean the same thing as "return the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   267
     * collation element [or ordering priority] of the previous character in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   268
     * string".</p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   269
     * <p>This function updates the iterator's internal pointer to point to the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   270
     * collation element preceding the one it's currently pointing to and then
90ce3da70b43 Initial load
duke
parents:
diff changeset
   271
     * returns that element, while next() returns the current element and then
90ce3da70b43 Initial load
duke
parents:
diff changeset
   272
     * updates the pointer.  This means that when you change direction while
90ce3da70b43 Initial load
duke
parents:
diff changeset
   273
     * iterating (i.e., call next() and then call previous(), or call previous()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   274
     * and then call next()), you'll get back the same element twice.</p>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   275
     * @since 1.2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   276
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   277
    public int previous()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   278
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   279
        if (text == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   280
            return NULLORDER;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   281
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   282
        NormalizerBase.Mode textMode = text.getMode();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   283
        // convert the owner's mode to something the Normalizer understands
90ce3da70b43 Initial load
duke
parents:
diff changeset
   284
        NormalizerBase.Mode ownerMode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   285
            CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   286
        if (textMode != ownerMode) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   287
            text.setMode(ownerMode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   288
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   289
        if (buffer != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   290
            if (expIndex > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   291
                return strengthOrder(buffer[--expIndex]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   292
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   293
                buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   294
                expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   295
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   296
        } else if (swapOrder != 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   297
            if (Character.isSupplementaryCodePoint(swapOrder)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   298
                char[] chars = Character.toChars(swapOrder);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   299
                swapOrder = chars[1];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   300
                return chars[0] << 16;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   301
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   302
            int order = swapOrder << 16;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   303
            swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   304
            return order;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   305
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   306
        int ch = text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   307
        if (ch == NormalizerBase.DONE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   308
            return NULLORDER;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   309
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   310
90ce3da70b43 Initial load
duke
parents:
diff changeset
   311
        int value = ordering.getUnicodeOrder(ch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   312
90ce3da70b43 Initial load
duke
parents:
diff changeset
   313
        if (value == RuleBasedCollator.UNMAPPED) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   314
            swapOrder = UNMAPPEDCHARVALUE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   315
            return ch;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   316
        } else if (value >= RuleBasedCollator.CONTRACTCHARINDEX) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   317
            value = prevContractChar(ch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   318
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   319
        if (value >= RuleBasedCollator.EXPANDCHARINDEX) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   320
            buffer = ordering.getExpandValueList(value);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   321
            expIndex = buffer.length;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   322
            value = buffer[--expIndex];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   323
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   324
90ce3da70b43 Initial load
duke
parents:
diff changeset
   325
        if (ordering.isSEAsianSwapping()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   326
            int vowel;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   327
            if (isThaiBaseConsonant(ch)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   328
                vowel = text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   329
                if (isThaiPreVowel(vowel)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   330
                    buffer = makeReorderedBuffer(vowel, value, buffer, false);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   331
                    expIndex = buffer.length - 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   332
                    value = buffer[expIndex];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   333
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   334
                    text.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   335
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   336
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   337
            if (isLaoBaseConsonant(ch)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   338
                vowel = text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   339
                if (isLaoPreVowel(vowel)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   340
                    buffer = makeReorderedBuffer(vowel, value, buffer, false);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   341
                    expIndex = buffer.length - 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   342
                    value = buffer[expIndex];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   343
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   344
                    text.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   345
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   346
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   347
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   348
90ce3da70b43 Initial load
duke
parents:
diff changeset
   349
        return strengthOrder(value);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   350
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   351
90ce3da70b43 Initial load
duke
parents:
diff changeset
   352
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   353
     * Return the primary component of a collation element.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   354
     * @param order the collation element
90ce3da70b43 Initial load
duke
parents:
diff changeset
   355
     * @return the element's primary component
90ce3da70b43 Initial load
duke
parents:
diff changeset
   356
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   357
    public final static int primaryOrder(int order)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   358
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   359
        order &= RBCollationTables.PRIMARYORDERMASK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   360
        return (order >>> RBCollationTables.PRIMARYORDERSHIFT);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   361
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   362
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   363
     * Return the secondary component of a collation element.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   364
     * @param order the collation element
90ce3da70b43 Initial load
duke
parents:
diff changeset
   365
     * @return the element's secondary component
90ce3da70b43 Initial load
duke
parents:
diff changeset
   366
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   367
    public final static short secondaryOrder(int order)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   368
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   369
        order = order & RBCollationTables.SECONDARYORDERMASK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   370
        return ((short)(order >> RBCollationTables.SECONDARYORDERSHIFT));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   371
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   372
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   373
     * Return the tertiary component of a collation element.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   374
     * @param order the collation element
90ce3da70b43 Initial load
duke
parents:
diff changeset
   375
     * @return the element's tertiary component
90ce3da70b43 Initial load
duke
parents:
diff changeset
   376
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   377
    public final static short tertiaryOrder(int order)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   378
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   379
        return ((short)(order &= RBCollationTables.TERTIARYORDERMASK));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   380
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   381
90ce3da70b43 Initial load
duke
parents:
diff changeset
   382
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   383
     *  Get the comparison order in the desired strength.  Ignore the other
90ce3da70b43 Initial load
duke
parents:
diff changeset
   384
     *  differences.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   385
     *  @param order The order value
90ce3da70b43 Initial load
duke
parents:
diff changeset
   386
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   387
    final int strengthOrder(int order)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   388
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   389
        int s = owner.getStrength();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   390
        if (s == Collator.PRIMARY)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   391
        {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   392
            order &= RBCollationTables.PRIMARYDIFFERENCEONLY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   393
        } else if (s == Collator.SECONDARY)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   394
        {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   395
            order &= RBCollationTables.SECONDARYDIFFERENCEONLY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   396
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   397
        return order;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   398
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   399
90ce3da70b43 Initial load
duke
parents:
diff changeset
   400
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   401
     * Sets the iterator to point to the collation element corresponding to
90ce3da70b43 Initial load
duke
parents:
diff changeset
   402
     * the specified character (the parameter is a CHARACTER offset in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   403
     * original string, not an offset into its corresponding sequence of
90ce3da70b43 Initial load
duke
parents:
diff changeset
   404
     * collation elements).  The value returned by the next call to next()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   405
     * will be the collation element corresponding to the specified position
90ce3da70b43 Initial load
duke
parents:
diff changeset
   406
     * in the text.  If that position is in the middle of a contracting
90ce3da70b43 Initial load
duke
parents:
diff changeset
   407
     * character sequence, the result of the next call to next() is the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   408
     * collation element for that sequence.  This means that getOffset()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   409
     * is not guaranteed to return the same value as was passed to a preceding
90ce3da70b43 Initial load
duke
parents:
diff changeset
   410
     * call to setOffset().
90ce3da70b43 Initial load
duke
parents:
diff changeset
   411
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   412
     * @param newOffset The new character offset into the original text.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   413
     * @since 1.2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   414
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   415
    public void setOffset(int newOffset)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   416
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   417
        if (text != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   418
            if (newOffset < text.getBeginIndex()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   419
                || newOffset >= text.getEndIndex()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   420
                    text.setIndexOnly(newOffset);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   421
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   422
                int c = text.setIndex(newOffset);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   423
90ce3da70b43 Initial load
duke
parents:
diff changeset
   424
                // if the desired character isn't used in a contracting character
90ce3da70b43 Initial load
duke
parents:
diff changeset
   425
                // sequence, bypass all the backing-up logic-- we're sitting on
90ce3da70b43 Initial load
duke
parents:
diff changeset
   426
                // the right character already
90ce3da70b43 Initial load
duke
parents:
diff changeset
   427
                if (ordering.usedInContractSeq(c)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   428
                    // walk backwards through the string until we see a character
90ce3da70b43 Initial load
duke
parents:
diff changeset
   429
                    // that DOESN'T participate in a contracting character sequence
90ce3da70b43 Initial load
duke
parents:
diff changeset
   430
                    while (ordering.usedInContractSeq(c)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   431
                        c = text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   432
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   433
                    // now walk forward using this object's next() method until
90ce3da70b43 Initial load
duke
parents:
diff changeset
   434
                    // we pass the starting point and set our current position
90ce3da70b43 Initial load
duke
parents:
diff changeset
   435
                    // to the beginning of the last "character" before or at
90ce3da70b43 Initial load
duke
parents:
diff changeset
   436
                    // our starting position
90ce3da70b43 Initial load
duke
parents:
diff changeset
   437
                    int last = text.getIndex();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   438
                    while (text.getIndex() <= newOffset) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   439
                        last = text.getIndex();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   440
                        next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   441
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   442
                    text.setIndexOnly(last);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   443
                    // we don't need this, since last is the last index
90ce3da70b43 Initial load
duke
parents:
diff changeset
   444
                    // that is the starting of the contraction which encompass
90ce3da70b43 Initial load
duke
parents:
diff changeset
   445
                    // newOffset
90ce3da70b43 Initial load
duke
parents:
diff changeset
   446
                    // text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   447
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   448
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   449
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   450
        buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   451
        expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   452
        swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   453
    }
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 character offset in the original text corresponding to the next
90ce3da70b43 Initial load
duke
parents:
diff changeset
   457
     * collation element.  (That is, getOffset() returns the position in the text
90ce3da70b43 Initial load
duke
parents:
diff changeset
   458
     * corresponding to the collation element that will be returned by the next
90ce3da70b43 Initial load
duke
parents:
diff changeset
   459
     * call to next().)  This value will always be the index of the FIRST character
90ce3da70b43 Initial load
duke
parents:
diff changeset
   460
     * corresponding to the collation element (a contracting character sequence is
90ce3da70b43 Initial load
duke
parents:
diff changeset
   461
     * when two or more characters all correspond to the same collation element).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   462
     * This means if you do setOffset(x) followed immediately by getOffset(), getOffset()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   463
     * won't necessarily return x.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   464
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   465
     * @return The character offset in the original text corresponding to the collation
90ce3da70b43 Initial load
duke
parents:
diff changeset
   466
     * element that will be returned by the next call to next().
90ce3da70b43 Initial load
duke
parents:
diff changeset
   467
     * @since 1.2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   468
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   469
    public int getOffset()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   470
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   471
        return (text != null) ? text.getIndex() : 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   472
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   473
90ce3da70b43 Initial load
duke
parents:
diff changeset
   474
90ce3da70b43 Initial load
duke
parents:
diff changeset
   475
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   476
     * Return the maximum length of any expansion sequences that end
90ce3da70b43 Initial load
duke
parents:
diff changeset
   477
     * with the specified comparison order.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   478
     * @param order a collation order returned by previous or next.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   479
     * @return the maximum length of any expansion sequences ending
90ce3da70b43 Initial load
duke
parents:
diff changeset
   480
     *         with the specified order.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   481
     * @since 1.2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   482
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   483
    public int getMaxExpansion(int order)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   484
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   485
        return ordering.getMaxExpansion(order);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   486
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   487
90ce3da70b43 Initial load
duke
parents:
diff changeset
   488
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   489
     * Set a new string over which to iterate.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   490
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   491
     * @param source  the new source text
90ce3da70b43 Initial load
duke
parents:
diff changeset
   492
     * @since 1.2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   493
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   494
    public void setText(String source)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   495
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   496
        buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   497
        swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   498
        expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   499
        NormalizerBase.Mode mode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   500
            CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   501
        if (text == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   502
            text = new NormalizerBase(source, mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   503
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   504
            text.setMode(mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   505
            text.setText(source);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   506
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   507
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   508
90ce3da70b43 Initial load
duke
parents:
diff changeset
   509
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   510
     * Set a new string over which to iterate.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   511
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   512
     * @param source  the new source text.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   513
     * @since 1.2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   514
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   515
    public void setText(CharacterIterator source)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   516
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   517
        buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   518
        swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   519
        expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   520
        NormalizerBase.Mode mode =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   521
            CollatorUtilities.toNormalizerMode(owner.getDecomposition());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   522
        if (text == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   523
            text = new NormalizerBase(source, mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   524
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   525
            text.setMode(mode);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   526
            text.setText(source);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   527
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   528
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   529
90ce3da70b43 Initial load
duke
parents:
diff changeset
   530
    //============================================================
90ce3da70b43 Initial load
duke
parents:
diff changeset
   531
    // privates
90ce3da70b43 Initial load
duke
parents:
diff changeset
   532
    //============================================================
90ce3da70b43 Initial load
duke
parents:
diff changeset
   533
90ce3da70b43 Initial load
duke
parents:
diff changeset
   534
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   535
     * Determine if a character is a Thai vowel (which sorts after
90ce3da70b43 Initial load
duke
parents:
diff changeset
   536
     * its base consonant).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   537
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   538
    private final static boolean isThaiPreVowel(int ch) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   539
        return (ch >= 0x0e40) && (ch <= 0x0e44);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   540
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   541
90ce3da70b43 Initial load
duke
parents:
diff changeset
   542
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   543
     * Determine if a character is a Thai base consonant
90ce3da70b43 Initial load
duke
parents:
diff changeset
   544
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   545
    private final static boolean isThaiBaseConsonant(int ch) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   546
        return (ch >= 0x0e01) && (ch <= 0x0e2e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   547
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   548
90ce3da70b43 Initial load
duke
parents:
diff changeset
   549
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   550
     * Determine if a character is a Lao vowel (which sorts after
90ce3da70b43 Initial load
duke
parents:
diff changeset
   551
     * its base consonant).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   552
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   553
    private final static boolean isLaoPreVowel(int ch) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   554
        return (ch >= 0x0ec0) && (ch <= 0x0ec4);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   555
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   556
90ce3da70b43 Initial load
duke
parents:
diff changeset
   557
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   558
     * Determine if a character is a Lao base consonant
90ce3da70b43 Initial load
duke
parents:
diff changeset
   559
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   560
    private final static boolean isLaoBaseConsonant(int ch) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   561
        return (ch >= 0x0e81) && (ch <= 0x0eae);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   562
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   563
90ce3da70b43 Initial load
duke
parents:
diff changeset
   564
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   565
     * This method produces a buffer which contains the collation
90ce3da70b43 Initial load
duke
parents:
diff changeset
   566
     * elements for the two characters, with colFirst's values preceding
90ce3da70b43 Initial load
duke
parents:
diff changeset
   567
     * another character's.  Presumably, the other character precedes colFirst
90ce3da70b43 Initial load
duke
parents:
diff changeset
   568
     * in logical order (otherwise you wouldn't need this method would you?).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   569
     * The assumption is that the other char's value(s) have already been
90ce3da70b43 Initial load
duke
parents:
diff changeset
   570
     * computed.  If this char has a single element it is passed to this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   571
     * method as lastValue, and lastExpansion is null.  If it has an
90ce3da70b43 Initial load
duke
parents:
diff changeset
   572
     * expansion it is passed in lastExpansion, and colLastValue is ignored.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   573
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   574
    private int[] makeReorderedBuffer(int colFirst,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   575
                                      int lastValue,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   576
                                      int[] lastExpansion,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   577
                                      boolean forward) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   578
90ce3da70b43 Initial load
duke
parents:
diff changeset
   579
        int[] result;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   580
90ce3da70b43 Initial load
duke
parents:
diff changeset
   581
        int firstValue = ordering.getUnicodeOrder(colFirst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   582
        if (firstValue >= RuleBasedCollator.CONTRACTCHARINDEX) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   583
            firstValue = forward? nextContractChar(colFirst) : prevContractChar(colFirst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   584
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   585
90ce3da70b43 Initial load
duke
parents:
diff changeset
   586
        int[] firstExpansion = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   587
        if (firstValue >= RuleBasedCollator.EXPANDCHARINDEX) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   588
            firstExpansion = ordering.getExpandValueList(firstValue);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   589
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   590
90ce3da70b43 Initial load
duke
parents:
diff changeset
   591
        if (!forward) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   592
            int temp1 = firstValue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   593
            firstValue = lastValue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   594
            lastValue = temp1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   595
            int[] temp2 = firstExpansion;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   596
            firstExpansion = lastExpansion;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   597
            lastExpansion = temp2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   598
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   599
90ce3da70b43 Initial load
duke
parents:
diff changeset
   600
        if (firstExpansion == null && lastExpansion == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   601
            result = new int [2];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   602
            result[0] = firstValue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   603
            result[1] = lastValue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   604
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   605
        else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   606
            int firstLength = firstExpansion==null? 1 : firstExpansion.length;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   607
            int lastLength = lastExpansion==null? 1 : lastExpansion.length;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   608
            result = new int[firstLength + lastLength];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   609
90ce3da70b43 Initial load
duke
parents:
diff changeset
   610
            if (firstExpansion == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   611
                result[0] = firstValue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   612
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   613
            else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   614
                System.arraycopy(firstExpansion, 0, result, 0, firstLength);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   615
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   616
90ce3da70b43 Initial load
duke
parents:
diff changeset
   617
            if (lastExpansion == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   618
                result[firstLength] = lastValue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   619
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   620
            else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   621
                System.arraycopy(lastExpansion, 0, result, firstLength, lastLength);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   622
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   623
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   624
90ce3da70b43 Initial load
duke
parents:
diff changeset
   625
        return result;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   626
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   627
90ce3da70b43 Initial load
duke
parents:
diff changeset
   628
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   629
     *  Check if a comparison order is ignorable.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   630
     *  @return true if a character is ignorable, false otherwise.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   631
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   632
    final static boolean isIgnorable(int order)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   633
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   634
        return ((primaryOrder(order) == 0) ? true : false);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   635
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   636
90ce3da70b43 Initial load
duke
parents:
diff changeset
   637
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   638
     * Get the ordering priority of the next contracting character in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   639
     * string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   640
     * @param ch the starting character of a contracting character token
90ce3da70b43 Initial load
duke
parents:
diff changeset
   641
     * @return the next contracting character's ordering.  Returns NULLORDER
90ce3da70b43 Initial load
duke
parents:
diff changeset
   642
     * if the end of string is reached.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   643
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   644
    private int nextContractChar(int ch)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   645
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   646
        // First get the ordering of this single character,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   647
        // which is always the first element in the list
90ce3da70b43 Initial load
duke
parents:
diff changeset
   648
        Vector list = ordering.getContractValues(ch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   649
        EntryPair pair = (EntryPair)list.firstElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   650
        int order = pair.value;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   651
90ce3da70b43 Initial load
duke
parents:
diff changeset
   652
        // find out the length of the longest contracting character sequence in the list.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   653
        // There's logic in the builder code to make sure the longest sequence is always
90ce3da70b43 Initial load
duke
parents:
diff changeset
   654
        // the last.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   655
        pair = (EntryPair)list.lastElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   656
        int maxLength = pair.entryName.length();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   657
90ce3da70b43 Initial load
duke
parents:
diff changeset
   658
        // (the Normalizer is cloned here so that the seeking we do in the next loop
90ce3da70b43 Initial load
duke
parents:
diff changeset
   659
        // won't affect our real position in the text)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   660
        NormalizerBase tempText = (NormalizerBase)text.clone();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   661
90ce3da70b43 Initial load
duke
parents:
diff changeset
   662
        // extract the next maxLength characters in the string (we have to do this using the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   663
        // Normalizer to ensure that our offsets correspond to those the rest of the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   664
        // iterator is using) and store it in "fragment".
90ce3da70b43 Initial load
duke
parents:
diff changeset
   665
        tempText.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   666
        key.setLength(0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   667
        int c = tempText.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   668
        while (maxLength > 0 && c != NormalizerBase.DONE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   669
            if (Character.isSupplementaryCodePoint(c)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   670
                key.append(Character.toChars(c));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   671
                maxLength -= 2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   672
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   673
                key.append((char)c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   674
                --maxLength;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   675
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   676
            c = tempText.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   677
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   678
        String fragment = key.toString();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   679
        // now that we have that fragment, iterate through this list looking for the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   680
        // longest sequence that matches the characters in the actual text.  (maxLength
90ce3da70b43 Initial load
duke
parents:
diff changeset
   681
        // is used here to keep track of the length of the longest sequence)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   682
        // Upon exit from this loop, maxLength will contain the length of the matching
90ce3da70b43 Initial load
duke
parents:
diff changeset
   683
        // sequence and order will contain the collation-element value corresponding
90ce3da70b43 Initial load
duke
parents:
diff changeset
   684
        // to this sequence
90ce3da70b43 Initial load
duke
parents:
diff changeset
   685
        maxLength = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   686
        for (int i = list.size() - 1; i > 0; i--) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   687
            pair = (EntryPair)list.elementAt(i);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   688
            if (!pair.fwd)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   689
                continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   690
90ce3da70b43 Initial load
duke
parents:
diff changeset
   691
            if (fragment.startsWith(pair.entryName) && pair.entryName.length()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   692
                    > maxLength) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   693
                maxLength = pair.entryName.length();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   694
                order = pair.value;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   695
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   696
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   697
90ce3da70b43 Initial load
duke
parents:
diff changeset
   698
        // seek our current iteration position to the end of the matching sequence
90ce3da70b43 Initial load
duke
parents:
diff changeset
   699
        // and return the appropriate collation-element value (if there was no matching
90ce3da70b43 Initial load
duke
parents:
diff changeset
   700
        // sequence, we're already seeked to the right position and order already contains
90ce3da70b43 Initial load
duke
parents:
diff changeset
   701
        // the correct collation-element value for the single character)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   702
        while (maxLength > 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   703
            c = text.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   704
            maxLength -= Character.charCount(c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   705
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   706
        return order;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   707
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   708
90ce3da70b43 Initial load
duke
parents:
diff changeset
   709
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   710
     * Get the ordering priority of the previous contracting character in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   711
     * string.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   712
     * @param ch the starting character of a contracting character token
90ce3da70b43 Initial load
duke
parents:
diff changeset
   713
     * @return the next contracting character's ordering.  Returns NULLORDER
90ce3da70b43 Initial load
duke
parents:
diff changeset
   714
     * if the end of string is reached.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   715
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   716
    private int prevContractChar(int ch)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   717
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   718
        // This function is identical to nextContractChar(), except that we've
90ce3da70b43 Initial load
duke
parents:
diff changeset
   719
        // switched things so that the next() and previous() calls on the Normalizer
90ce3da70b43 Initial load
duke
parents:
diff changeset
   720
        // are switched and so that we skip entry pairs with the fwd flag turned on
90ce3da70b43 Initial load
duke
parents:
diff changeset
   721
        // rather than off.  Notice that we still use append() and startsWith() when
90ce3da70b43 Initial load
duke
parents:
diff changeset
   722
        // working on the fragment.  This is because the entry pairs that are used
90ce3da70b43 Initial load
duke
parents:
diff changeset
   723
        // in reverse iteration have their names reversed already.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   724
        Vector list = ordering.getContractValues(ch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   725
        EntryPair pair = (EntryPair)list.firstElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   726
        int order = pair.value;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   727
90ce3da70b43 Initial load
duke
parents:
diff changeset
   728
        pair = (EntryPair)list.lastElement();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   729
        int maxLength = pair.entryName.length();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   730
90ce3da70b43 Initial load
duke
parents:
diff changeset
   731
        NormalizerBase tempText = (NormalizerBase)text.clone();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   732
90ce3da70b43 Initial load
duke
parents:
diff changeset
   733
        tempText.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   734
        key.setLength(0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   735
        int c = tempText.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   736
        while (maxLength > 0 && c != NormalizerBase.DONE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   737
            if (Character.isSupplementaryCodePoint(c)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   738
                key.append(Character.toChars(c));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   739
                maxLength -= 2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   740
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   741
                key.append((char)c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   742
                --maxLength;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   743
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   744
            c = tempText.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   745
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   746
        String fragment = key.toString();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   747
90ce3da70b43 Initial load
duke
parents:
diff changeset
   748
        maxLength = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   749
        for (int i = list.size() - 1; i > 0; i--) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   750
            pair = (EntryPair)list.elementAt(i);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   751
            if (pair.fwd)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   752
                continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   753
90ce3da70b43 Initial load
duke
parents:
diff changeset
   754
            if (fragment.startsWith(pair.entryName) && pair.entryName.length()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   755
                    > maxLength) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   756
                maxLength = pair.entryName.length();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   757
                order = pair.value;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   758
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   759
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   760
90ce3da70b43 Initial load
duke
parents:
diff changeset
   761
        while (maxLength > 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   762
            c = text.previous();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   763
            maxLength -= Character.charCount(c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   764
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   765
        return order;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   766
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   767
90ce3da70b43 Initial load
duke
parents:
diff changeset
   768
    final static int UNMAPPEDCHARVALUE = 0x7FFF0000;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   769
90ce3da70b43 Initial load
duke
parents:
diff changeset
   770
    private NormalizerBase text = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   771
    private int[] buffer = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   772
    private int expIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   773
    private StringBuffer key = new StringBuffer(5);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   774
    private int swapOrder = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   775
    private RBCollationTables ordering;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   776
    private RuleBasedCollator owner;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   777
}