]> gitweb.fperrin.net Git - Dictionary.git/blob - jars/icu4j-4_4_2-src/demos/src/com/ibm/icu/dev/demo/translit/TransliteratingTextComponent.java
go
[Dictionary.git] / jars / icu4j-4_4_2-src / demos / src / com / ibm / icu / dev / demo / translit / TransliteratingTextComponent.java
1 /*\r
2  *******************************************************************************\r
3  * Copyright (C) 1996-2010, International Business Machines Corporation and    *\r
4  * others. All Rights Reserved.                                                *\r
5  *******************************************************************************\r
6  */\r
7 package com.ibm.icu.dev.demo.translit;\r
8 \r
9 import java.awt.event.KeyEvent;\r
10 \r
11 import com.ibm.icu.dev.demo.impl.DumbTextComponent;\r
12 import com.ibm.icu.text.ReplaceableString;\r
13 import com.ibm.icu.text.Transliterator;\r
14 \r
15 /**\r
16  * A subclass of {@link DumbTextComponent} that passes key events through\r
17  * a {@link com.ibm.icu.text.Transliterator}.\r
18  *\r
19  * @author Alan Liu\r
20  */\r
21 public class TransliteratingTextComponent extends DumbTextComponent {\r
22 \r
23     /**\r
24      * For serialization\r
25      */\r
26     private static final long serialVersionUID = -8672128213174154047L;\r
27 \r
28     private static boolean DEBUG = false;\r
29 \r
30     private Transliterator translit = null;\r
31     \r
32     // NOTE: DISABLE THE START AND CURSOR UNTIL WE CAN GET IT TO WORK AT ALL\r
33 \r
34     // Index into getText() where the start of transliteration is.\r
35     // As we commit text during transliteration, we advance\r
36     // this.\r
37     //private int start = 0;\r
38 \r
39     // Index into getText() where the cursor is; cursor >= start\r
40     //private int cursor = 0;\r
41 \r
42 //    private static final String COPYRIGHT =\r
43 //        "\u00A9 IBM Corporation 1999. All rights reserved.";\r
44 \r
45     /**\r
46      * Constructor.\r
47      */\r
48     public TransliteratingTextComponent() {\r
49         super();\r
50         /*\r
51         addActionListener(new ActionListener() {\r
52             public void actionPerformed(ActionEvent e) {\r
53                 // We get an ActionEvent only when the selection changes\r
54                 resetTransliterationStart();\r
55             }\r
56         });\r
57         */\r
58     }\r
59 \r
60     /**\r
61      * {@link DumbTextComponent} API.  Framework method that is called\r
62      * when a <code>KeyEvent</code> is received.  This implementation\r
63      * runs the new character through the current\r
64      * <code>Transliterator</code>, if one is set, and inserts the\r
65      * transliterated text into the buffer.\r
66      */\r
67     protected void handleKeyTyped(KeyEvent e) {\r
68         char ch = e.getKeyChar();\r
69         \r
70         if (translit == null) {\r
71             setKeyStart(-1);\r
72             super.handleKeyTyped(e);\r
73             return;\r
74         }\r
75 \r
76         transliterate(ch, false);\r
77     }\r
78     \r
79     public void flush() {\r
80         if (translit != null) transliterate('\uFFFF', true);\r
81     }\r
82     \r
83     \r
84     protected void transliterate(char ch, boolean flush) {\r
85 \r
86         // ------------------------------------------------------------\r
87         // The following case motivates the two lines that recompute\r
88         // start and cursor below.\r
89 \r
90         //      "     "   \r
91         // a b c q r|s t u m m\r
92         // 0 1 2 3 4 5 6 7 8 9\r
93         //       0 1 2\r
94 \r
95         // start 3, cursor 5, sel 6 -> { 0, 3, 2 }\r
96         // : new int[] { 0, sel - start, cursor - start };\r
97         \r
98         // sz>99|9\r
99 \r
100         //      "     {   "\r
101         // a b c q r 9 9|9 t u m m\r
102         // 0 1 2 3 4 5 6 7 8 9 a b\r
103         //       0 1 2 3 4\r
104 \r
105         // { 3, 5, 4 } -> start 6, cursor 7, sel 8\r
106         // : start += index[0];\r
107         // : cursor = start + index[2] - index[0];\r
108         // ------------------------------------------------------------\r
109 \r
110         // Need to save start because calls to replaceRange will update\r
111         // start and cursor.\r
112         //int saveStart = start;\r
113 \r
114         int end = flush ? getSelectionEnd() : getSelectionStart();\r
115         String sourceText = getText().substring(0,end);\r
116         ReplaceableString buf = new ReplaceableString(sourceText);\r
117         /*buf.replace(0, 1, getText().substring(start,\r
118                                               getSelectionStart()));*/\r
119 \r
120         Transliterator.Position index = new Transliterator.Position();\r
121         index.contextLimit = buf.length();\r
122         index.contextStart = 0;\r
123         index.start = getKeyStart();\r
124         if (index.start == -1) index.start = getSelectionStart();\r
125         index.limit = buf.length();\r
126 \r
127       //  StringBuffer log = null;\r
128         if (DEBUG) {\r
129             System.out.println("Transliterator: " + translit.getID());\r
130             System.out.println("From:\t" + '"' + buf.toString() + '"'\r
131                 + "; {cs: " + index.contextStart\r
132                 + ", s: " + index.start\r
133                 + ", l: " + index.limit\r
134                 + ", cl: " + index.contextLimit \r
135                 + "}" + "; '" + ch + "'"\r
136                 + " " + getKeyStart()\r
137             );\r
138         }\r
139 \r
140         if (flush) {\r
141             translit.finishTransliteration(buf, index);\r
142         } else {\r
143             translit.transliterate(buf, index, ch);\r
144         }\r
145         \r
146         if (DEBUG) {\r
147             System.out.println("To:\t" + '"' + buf.toString() + '"'\r
148                 + "; {cs: " + index.contextStart\r
149                 + ", s: " + index.start\r
150                 + ", l: " + index.limit\r
151                 + ", cl: " + index.contextLimit \r
152                 + "}"\r
153                 );\r
154             System.out.println();\r
155         }\r
156         /*\r
157         buf.replace(buf.length(), buf.length(), String.valueOf(ch));\r
158         translit.transliterate(buf);\r
159         */\r
160         \r
161         String result = buf.toString();\r
162         //if (result.equals(sourceText + ch)) return;\r
163         \r
164         replaceRange(result, 0, getSelectionEnd());\r
165         setKeyStart(index.start);\r
166         \r
167         // At this point start has been changed by the callback to\r
168         // resetTransliteratorStart() via replaceRange() -- so use our\r
169         // local copy, saveStart.\r
170 \r
171         // The START index is zero-based.  On entry to transliterate(),\r
172         // it was zero.  We can therefore just add it to our original\r
173         // getText()-based index value of start (in saveStart) to get\r
174         // the new getText()-based start.\r
175 //        start = saveStart + index.contextStart;\r
176 \r
177         // Make the cursor getText()-based.  The CURSOR index is zero-based.\r
178 //        cursor = start + index.start - index.contextStart;\r
179 \r
180 /*\r
181         if (DEBUG) {\r
182             String out = buf.toString();\r
183             log.append(out.substring(0, index.contextStart)).\r
184                 append('{').\r
185                 append(out.substring(index.contextStart, index.start)).\r
186                 append('|').\r
187                 append(out.substring(index.start)).\r
188                 append('"');\r
189             log.append(", {" + index.contextStart + ", " + index.contextLimit + ", " + index.start + "}, ");\r
190 //            log.append("start " + start + ", cursor " + cursor);\r
191             log.append(", sel " + getSelectionStart());\r
192             System.out.println(escape(log.toString()));\r
193         }\r
194         */\r
195     }\r
196     \r
197     /**\r
198      * Set the {@link com.ibm.icu.text.Transliterator} and direction to\r
199      * use to process incoming <code>KeyEvent</code>s.\r
200      * @param t the {@link com.ibm.icu.text.Transliterator} to use\r
201      */\r
202     public void setTransliterator(Transliterator t) {\r
203         /*\r
204         if (translit != t) { // [sic] pointer compare ok; singletons\r
205             resetTransliterationStart();\r
206         }\r
207         */\r
208         translit = t;\r
209     }\r
210 \r
211     public Transliterator getTransliterator() {\r
212         return translit;\r
213     }\r
214 \r
215     /**\r
216      * Reset the start point at which transliteration begins.  This\r
217      * needs to be done when the user moves the cursor or when the\r
218      * current {@link com.ibm.icu.text.Transliterator} is changed. \r
219      */\r
220      /*\r
221     private void resetTransliterationStart() {\r
222         start = getSelectionStart();\r
223         cursor = start;\r
224     }\r
225     */\r
226 \r
227     /**\r
228      * Escape non-ASCII characters as Unicode.\r
229      * JUST FOR DEBUGGING OUTPUT.\r
230      */\r
231     public static final String escape(String s) {\r
232         StringBuffer buf = new StringBuffer();\r
233         for (int i=0; i<s.length(); ++i) {\r
234             char c = s.charAt(i);\r
235             if (c >= ' ' && c <= 0x007F) {\r
236                 if (c == '\\') {\r
237                     buf.append("\\\\"); // That is, "\\"\r
238                 } else {\r
239                     buf.append(c);\r
240                 }\r
241             } else {\r
242                 buf.append("\\u");\r
243                 if (c < 0x1000) {\r
244                     buf.append('0');\r
245                     if (c < 0x100) {\r
246                         buf.append('0');\r
247                         if (c < 0x10) {\r
248                             buf.append('0');\r
249                         }\r
250                     }\r
251                 }\r
252                 buf.append(Integer.toHexString(c));\r
253             }\r
254         }\r
255         return buf.toString();\r
256     }\r
257 }\r