2 *******************************************************************************
\r
3 * Copyright (C) 2002-2005, International Business Machines Corporation and *
\r
4 * others. All Rights Reserved. *
\r
5 *******************************************************************************
\r
8 package com.ibm.icu.dev.tool.layout;
\r
10 import com.ibm.icu.text.UTF16;
\r
11 import java.util.Vector;
\r
16 * To change the template for this generated type comment go to
\r
17 * Window>Preferences>Java>Code Generation>Code and Comments
\r
19 public class DecompTable implements LookupSubtable
\r
21 static class DecompEntry
\r
23 private int composed;
\r
24 private int[] decomp;
\r
26 DecompEntry(int composedChar, String decomposition)
\r
28 int decompCount = UTF16.countCodePoint(decomposition);
\r
30 composed = composedChar;
\r
31 decomp = new int[decompCount];
\r
35 for (int in = 0; in < decomposition.length(); in += UTF16.getCharCount(cp)) {
\r
36 cp = UTF16.charAt(decomposition, in);
\r
41 public int getComposedCharacter()
\r
46 public int[] getDecomposition()
\r
51 public int getDecompositionCount()
\r
53 return decomp.length;
\r
56 public int getDecomposedCharacter(int i)
\r
58 if (i >= 0 && i < decomp.length) {
\r
65 public int compareTo(DecompEntry that)
\r
67 return this.composed - that.composed;
\r
71 // Straight insertion sort from Knuth vol. III, pg. 81
\r
73 public static void sort(DecompEntry[] table, Vector decompVector)
\r
75 for (int j = 0; j < table.length; j += 1) {
\r
77 DecompEntry v = (DecompEntry) decompVector.elementAt(j);
\r
79 for (i = j - 1; i >= 0; i -= 1) {
\r
80 if (v.compareTo(table[i]) >= 0) {
\r
84 table[i + 1] = table[i];
\r
92 private Vector decompVector;
\r
93 private DecompEntry[] decompEntries;
\r
94 private int snapshotSize;
\r
96 public DecompTable()
\r
98 decompVector = new Vector();
\r
99 decompEntries = null;
\r
103 public void add(int composed, String decomposition)
\r
105 DecompEntry entry = new DecompEntry(composed, decomposition);
\r
107 decompVector.addElement(entry);
\r
110 public int getComposedCharacter(int i)
\r
112 if (i < 0 || i > decompEntries.length) {
\r
116 return decompEntries[i].getComposedCharacter();
\r
119 public int getDecompositionCount(int i)
\r
121 if (i < 0 || i > decompEntries.length) {
\r
125 return decompEntries[i].getDecompositionCount();
\r
128 public boolean hasEntries()
\r
130 return decompVector.size() > 0;
\r
133 private void snapshot()
\r
135 if (snapshotSize != decompVector.size()) {
\r
136 snapshotSize = decompVector.size();
\r
137 decompEntries = new DecompEntry[snapshotSize];
\r
138 DecompEntry.sort(decompEntries, decompVector);
\r
142 public void writeLookupSubtable(OpenTypeTableWriter writer)
\r
146 int multipleSubstitutionsBase = writer.getOutputIndex();
\r
147 int coverageTableIndex, sequenceOffsetIndex;
\r
148 int sequenceCount = decompEntries.length;
\r
150 writer.writeData(1); // format = 1
\r
152 coverageTableIndex = writer.getOutputIndex();
\r
153 writer.writeData(0); // coverage table offset (fixed later)
\r
155 writer.writeData(sequenceCount);
\r
157 sequenceOffsetIndex = writer.getOutputIndex();
\r
158 for (int s = 0; s < sequenceCount; s += 1) {
\r
159 writer.writeData(0); // offset to sequence table (fixed later);
\r
162 for (int s = 0; s < sequenceCount; s += 1) {
\r
163 DecompEntry entry = decompEntries[s];
\r
164 int decompCount = entry.getDecompositionCount();
\r
166 writer.fixOffset(sequenceOffsetIndex++, multipleSubstitutionsBase);
\r
168 writer.writeData(decompCount); // glyphCount
\r
170 for (int g = 0; g < decompCount; g += 1) {
\r
171 writer.writeData(entry.getDecomposedCharacter(g));
\r
175 // write a format 1 coverage table
\r
176 writer.fixOffset(coverageTableIndex, multipleSubstitutionsBase);
\r
177 writer.writeData(1); // format = 1
\r
178 writer.writeData(sequenceCount); // glyphCount
\r
180 for (int i = 0; i < sequenceCount; i += 1) {
\r
181 writer.writeData(decompEntries[i].getComposedCharacter());
\r