]> gitweb.fperrin.net Git - Dictionary.git/blob - jars/icu4j-4_4_2-src/main/classes/currdata/src/com/ibm/icu/impl/ICUCurrencyDisplayInfoProvider.java
go
[Dictionary.git] / jars / icu4j-4_4_2-src / main / classes / currdata / src / com / ibm / icu / impl / ICUCurrencyDisplayInfoProvider.java
1 /*\r
2  *******************************************************************************\r
3  * Copyright (C) 2009-2010, International Business Machines Corporation and    *\r
4  * others. All Rights Reserved.                                                *\r
5  *******************************************************************************\r
6  */\r
7 package com.ibm.icu.impl;\r
8 \r
9 import java.lang.ref.SoftReference;\r
10 import java.util.Collections;\r
11 import java.util.HashMap;\r
12 import java.util.HashSet;\r
13 import java.util.Map;\r
14 import java.util.Set;\r
15 import java.util.TreeMap;\r
16 \r
17 import com.ibm.icu.impl.CurrencyData.CurrencyDisplayInfo;\r
18 import com.ibm.icu.impl.CurrencyData.CurrencyDisplayInfoProvider;\r
19 import com.ibm.icu.impl.CurrencyData.CurrencyFormatInfo;\r
20 import com.ibm.icu.impl.CurrencyData.CurrencySpacingInfo;\r
21 import com.ibm.icu.util.ULocale;\r
22 import com.ibm.icu.util.UResourceBundle;\r
23 \r
24 public class ICUCurrencyDisplayInfoProvider implements CurrencyDisplayInfoProvider {\r
25     public ICUCurrencyDisplayInfoProvider() {\r
26     }\r
27 \r
28     public CurrencyDisplayInfo getInstance(ULocale locale, boolean withFallback) {\r
29         ICUResourceBundle rb = (ICUResourceBundle) UResourceBundle.getBundleInstance(\r
30                 ICUResourceBundle.ICU_CURR_BASE_NAME, locale);\r
31         if (!withFallback) {\r
32             int status = rb.getLoadingStatus();\r
33             if (status == ICUResourceBundle.FROM_DEFAULT || status == ICUResourceBundle.FROM_ROOT) {\r
34                 return CurrencyData.DefaultInfo.getWithFallback(false);\r
35             }\r
36         }\r
37         return new ICUCurrencyDisplayInfo(rb, withFallback);\r
38     }\r
39 \r
40     public boolean hasData() {\r
41         return true;\r
42     }\r
43 \r
44     static class ICUCurrencyDisplayInfo extends CurrencyDisplayInfo {\r
45         private final boolean fallback;\r
46         private final ICUResourceBundle rb;\r
47         private final ICUResourceBundle currencies;\r
48         private final ICUResourceBundle plurals;\r
49         private SoftReference<Map<String, String>> _symbolMapRef;\r
50         private SoftReference<Map<String, String>> _nameMapRef;\r
51 \r
52         public ICUCurrencyDisplayInfo(ICUResourceBundle rb, boolean fallback) {\r
53             this.fallback = fallback;\r
54             this.rb = rb;\r
55             this.currencies = rb.findTopLevel("Currencies");\r
56             this.plurals = rb.findTopLevel("CurrencyPlurals");\r
57        }\r
58 \r
59         @Override\r
60         public ULocale getLocale() {\r
61             return rb.getULocale();\r
62         }\r
63 \r
64         @Override\r
65         public String getName(String isoCode) {\r
66             return getName(isoCode, false);\r
67         }\r
68 \r
69         @Override\r
70         public String getSymbol(String isoCode) {\r
71             return getName(isoCode, true);\r
72         }\r
73 \r
74         private String getName(String isoCode, boolean symbolName) {\r
75             if (currencies != null) {\r
76                 ICUResourceBundle result = currencies.findWithFallback(isoCode);\r
77                 if (result != null) {\r
78                     if (!fallback) {\r
79                         int status = result.getLoadingStatus();\r
80                         if (status == ICUResourceBundle.FROM_DEFAULT ||\r
81                                 status == ICUResourceBundle.FROM_ROOT) {\r
82                             return null;\r
83                         }\r
84                     }\r
85                     return result.getString(symbolName ? 0 : 1);\r
86                 }\r
87             }\r
88 \r
89             return fallback ? isoCode : null;\r
90         }\r
91 \r
92         @Override\r
93         public String getPluralName(String isoCode, String pluralKey ) {\r
94             // See http://unicode.org/reports/tr35/#Currencies, especially the fallback rule.\r
95             if (plurals != null) {\r
96                 ICUResourceBundle pluralsBundle = plurals.findWithFallback(isoCode);\r
97                 if (pluralsBundle != null) {\r
98                     ICUResourceBundle pluralBundle = pluralsBundle.findWithFallback(pluralKey);\r
99                     if (pluralBundle == null) {\r
100                         if (!fallback) {\r
101                             return null;\r
102                         }\r
103                         pluralBundle = pluralsBundle.findWithFallback("other");\r
104                         if (pluralBundle == null) {\r
105                             return getName(isoCode);\r
106                         }\r
107                     }\r
108                     return pluralBundle.getString();\r
109                 }\r
110             }\r
111 \r
112             return fallback ? getName(isoCode) : null;\r
113         }\r
114 \r
115         @Override\r
116         public Map<String, String> symbolMap() {\r
117             Map<String, String> map = _symbolMapRef == null ? null : _symbolMapRef.get();\r
118             if (map == null) {\r
119                 map = _createSymbolMap();\r
120                 // atomic and idempotent\r
121                 _symbolMapRef = new SoftReference<Map<String, String>>(map);\r
122             }\r
123             return map;\r
124         }\r
125 \r
126         @Override\r
127         public Map<String, String> nameMap() {\r
128             Map<String, String> map = _nameMapRef == null ? null : _nameMapRef.get();\r
129             if (map == null) {\r
130                 map = _createNameMap();\r
131                 // atomic and idempotent\r
132                 _nameMapRef = new SoftReference<Map<String, String>>(map);\r
133             }\r
134             return map;\r
135         }\r
136 \r
137        @Override\r
138         public Map<String, String> getUnitPatterns() {\r
139             Map<String, String> result = new HashMap<String, String>();\r
140 \r
141             ULocale locale = rb.getULocale();\r
142             for (;locale != null; locale = locale.getFallback()) {\r
143                 ICUResourceBundle r = (ICUResourceBundle) UResourceBundle.getBundleInstance(\r
144                         ICUResourceBundle.ICU_CURR_BASE_NAME, locale);\r
145                 if (r == null) {\r
146                     continue;\r
147                 }\r
148                 ICUResourceBundle cr = r.findWithFallback("CurrencyUnitPatterns");\r
149                 if (cr == null) {\r
150                     continue;\r
151                 }\r
152                 for (int index = 0, size = cr.getSize(); index < size; ++index) {\r
153                     ICUResourceBundle b = (ICUResourceBundle) cr.get(index);\r
154                     String key = b.getKey();\r
155                     if (result.containsKey(key)) {\r
156                         continue;\r
157                     }\r
158                     result.put(key, b.getString());\r
159                 }\r
160             }\r
161 \r
162             // Default result is the empty map. Callers who require a pattern will have to\r
163             // supply a default.\r
164             return Collections.unmodifiableMap(result);\r
165         }\r
166 \r
167         @Override\r
168         public CurrencyFormatInfo getFormatInfo(String isoCode) {\r
169             ICUResourceBundle crb = currencies.findWithFallback(isoCode);\r
170             if (crb != null && crb.getSize() > 2) {\r
171                 crb = crb.at(2);\r
172                 if (crb != null) {\r
173                   String pattern = crb.getString(0);\r
174                   char separator = crb.getString(1).charAt(0);\r
175                   char groupingSeparator = crb.getString(2).charAt(0);\r
176                   return new CurrencyFormatInfo(pattern, separator, groupingSeparator);\r
177                 }\r
178             }\r
179             return null;\r
180         }\r
181 \r
182         @Override\r
183         public CurrencySpacingInfo getSpacingInfo() {\r
184             ICUResourceBundle srb = rb.findWithFallback("currencySpacing");\r
185             if (srb != null) {\r
186                 ICUResourceBundle brb = srb.findWithFallback("beforeCurrency");\r
187                 ICUResourceBundle arb = srb.findWithFallback("afterCurrency");\r
188                 if (brb != null && brb != null) {\r
189                     String beforeCurrencyMatch = brb.findWithFallback("currencyMatch").getString();\r
190                     String beforeContextMatch = brb.findWithFallback("surroundingMatch").getString();\r
191                     String beforeInsert = brb.findWithFallback("insertBetween").getString();\r
192                     String afterCurrencyMatch = arb.findWithFallback("currencyMatch").getString();\r
193                     String afterContextMatch = arb.findWithFallback("surroundingMatch").getString();\r
194                     String afterInsert = arb.findWithFallback("insertBetween").getString();\r
195 \r
196                     return new CurrencySpacingInfo(\r
197                             beforeCurrencyMatch, beforeContextMatch, beforeInsert,\r
198                             afterCurrencyMatch, afterContextMatch, afterInsert);\r
199                 }\r
200             }\r
201             return fallback ? CurrencySpacingInfo.DEFAULT : null;\r
202         }\r
203 \r
204         private Map<String, String> _createSymbolMap() {\r
205             Map<String, String> result = new HashMap<String, String>();\r
206 \r
207             for (ULocale locale = rb.getULocale(); locale != null; locale = locale.getFallback()) {\r
208                 ICUResourceBundle bundle = (ICUResourceBundle)\r
209                     UResourceBundle.getBundleInstance(ICUResourceBundle.ICU_CURR_BASE_NAME, locale);\r
210                 ICUResourceBundle curr = bundle.findTopLevel("Currencies");\r
211                 if (curr == null) {\r
212                     continue;\r
213                 }\r
214                 for (int i = 0; i < curr.getSize(); ++i) {\r
215                     ICUResourceBundle item = curr.at(i);\r
216                     String isoCode = item.getKey();\r
217                     if (!result.containsKey(isoCode)) {\r
218                         // put the code itself\r
219                         result.put(isoCode, isoCode);\r
220                         // 0 == symbol element\r
221                         String symbol = item.getString(0);\r
222                         result.put(symbol, isoCode);\r
223                     }\r
224                 }\r
225             }\r
226 \r
227             return Collections.unmodifiableMap(result);\r
228         }\r
229 \r
230         private Map<String, String> _createNameMap() {\r
231             // ignore case variants\r
232             Map<String, String> result = new TreeMap<String, String>(String.CASE_INSENSITIVE_ORDER);\r
233 \r
234             Set<String> visited = new HashSet<String>();\r
235             Map<String, Set<String>> visitedPlurals = new HashMap<String, Set<String>>();\r
236             for (ULocale locale = rb.getULocale(); locale != null; locale = locale.getFallback()) {\r
237                 ICUResourceBundle bundle = (ICUResourceBundle)\r
238                     UResourceBundle.getBundleInstance(ICUResourceBundle.ICU_CURR_BASE_NAME, locale);\r
239                 ICUResourceBundle curr = bundle.findTopLevel("Currencies");\r
240                 if (curr != null) {\r
241                     for (int i = 0; i < curr.getSize(); ++i) {\r
242                         ICUResourceBundle item = curr.at(i);\r
243                         String isoCode = item.getKey();\r
244                         if (!visited.contains(isoCode)) {\r
245                             visited.add(isoCode);\r
246                             // 1 == name element\r
247                             String name = item.getString(1);\r
248                             result.put(name, isoCode);\r
249                         }\r
250                     }\r
251                 }\r
252 \r
253                 ICUResourceBundle plurals = bundle.findTopLevel("CurrencyPlurals");\r
254                 if (plurals != null) {\r
255                     for (int i = 0; i < plurals.getSize(); ++i) {\r
256                         ICUResourceBundle item = plurals.at(i);\r
257                         String isoCode = item.getKey();\r
258                         Set<String> pluralSet = visitedPlurals.get(isoCode);\r
259                         if (pluralSet == null) {\r
260                             pluralSet = new HashSet<String>();\r
261                             visitedPlurals.put(isoCode, pluralSet);\r
262                         }\r
263                         for (int j = 0; j < item.getSize(); ++j) {\r
264                             ICUResourceBundle plural = item.at(j);\r
265                             String pluralType = plural.getKey();\r
266                             if (!pluralSet.contains(pluralType)) {\r
267                                 String pluralName = plural.getString();\r
268                                 result.put(pluralName, isoCode);\r
269                                 pluralSet.add(pluralType);\r
270                             }\r
271                         }\r
272                     }\r
273                 }\r
274             }\r
275 \r
276             return Collections.unmodifiableMap(result);\r
277         }\r
278     }\r
279 }\r