OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/chromeos/input_method/input_method_util.h" | 5 #include "chrome/browser/chromeos/input_method/input_method_util.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 #include <functional> | 8 #include <functional> |
9 #include <map> | 9 #include <map> |
10 #include <utility> | 10 #include <utility> |
11 | 11 |
12 #include "base/basictypes.h" | 12 #include "base/basictypes.h" |
13 #include "base/memory/scoped_ptr.h" | 13 #include "base/memory/scoped_ptr.h" |
14 #include "base/prefs/pref_service.h" | 14 #include "base/prefs/pref_service.h" |
15 #include "base/string_util.h" | 15 #include "base/string_util.h" |
16 #include "base/strings/string_split.h" | 16 #include "base/strings/string_split.h" |
17 #include "base/utf_string_conversions.h" | 17 #include "base/utf_string_conversions.h" |
18 #include "chromeos/ime/component_extension_ime_manager.h" | 18 #include "chromeos/ime/component_extension_ime_manager.h" |
19 #include "chromeos/ime/extension_ime_util.h" | 19 #include "chromeos/ime/extension_ime_util.h" |
20 #include "chromeos/ime/input_method_delegate.h" | 20 #include "chromeos/ime/input_method_delegate.h" |
| 21 // TODO(nona): move this header from this file. |
21 #include "grit/generated_resources.h" | 22 #include "grit/generated_resources.h" |
22 #include "third_party/icu/public/common/unicode/uloc.h" | |
23 #include "ui/base/l10n/l10n_util.h" | |
24 #include "ui/base/l10n/l10n_util_collator.h" | |
25 | 23 |
26 namespace { | 24 namespace { |
27 | 25 |
28 // A mapping from an input method id to a string for the language indicator. The | 26 // A mapping from an input method id to a string for the language indicator. The |
29 // mapping is necessary since some input methods belong to the same language. | 27 // mapping is necessary since some input methods belong to the same language. |
30 // For example, both "xkb:us::eng" and "xkb:us:dvorak:eng" are for US English. | 28 // For example, both "xkb:us::eng" and "xkb:us:dvorak:eng" are for US English. |
31 const struct { | 29 const struct { |
32 const char* input_method_id; | 30 const char* input_method_id; |
33 const char* indicator_text; | 31 const char* indicator_text; |
34 } kMappingFromIdToIndicatorText[] = { | 32 } kMappingFromIdToIndicatorText[] = { |
(...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
252 { "xkb:ca:eng:eng", IDS_STATUSBAR_LAYOUT_CANADA_ENGLISH }, | 250 { "xkb:ca:eng:eng", IDS_STATUSBAR_LAYOUT_CANADA_ENGLISH }, |
253 { "xkb:il::heb", IDS_STATUSBAR_LAYOUT_ISRAEL }, | 251 { "xkb:il::heb", IDS_STATUSBAR_LAYOUT_ISRAEL }, |
254 { "xkb:kr:kr104:kor", IDS_STATUSBAR_LAYOUT_KOREA_104 }, | 252 { "xkb:kr:kr104:kor", IDS_STATUSBAR_LAYOUT_KOREA_104 }, |
255 { "xkb:is::ice", IDS_STATUSBAR_LAYOUT_ICELANDIC }, | 253 { "xkb:is::ice", IDS_STATUSBAR_LAYOUT_ICELANDIC }, |
256 | 254 |
257 { "english-m", IDS_STATUSBAR_LAYOUT_USA_MYSTERY }, | 255 { "english-m", IDS_STATUSBAR_LAYOUT_USA_MYSTERY }, |
258 }; | 256 }; |
259 const size_t kEnglishToResourceIdArraySize = | 257 const size_t kEnglishToResourceIdArraySize = |
260 arraysize(kEnglishToResourceIdArray); | 258 arraysize(kEnglishToResourceIdArray); |
261 | 259 |
262 // The comparator is used for sorting language codes by their | |
263 // corresponding language names, using the ICU collator. | |
264 struct CompareLanguageCodesByLanguageName | |
265 : std::binary_function<const std::string&, const std::string&, bool> { | |
266 CompareLanguageCodesByLanguageName(InputMethodUtil* util, | |
267 icu::Collator* collator) | |
268 : util_(util), collator_(collator) { | |
269 } | |
270 | |
271 // Calling GetLanguageDisplayNameFromCode() in the comparator is not | |
272 // efficient, but acceptable as the function is cheap, and the language | |
273 // list is short (about 60 at most). | |
274 bool operator()(const std::string& s1, const std::string& s2) const { | |
275 const string16 key1 = util_->GetLanguageDisplayNameFromCode(s1); | |
276 const string16 key2 = util_->GetLanguageDisplayNameFromCode(s2); | |
277 return l10n_util::StringComparator<string16>(collator_)(key1, key2); | |
278 } | |
279 | |
280 private: | |
281 InputMethodUtil* util_; | |
282 icu::Collator* collator_; | |
283 }; | |
284 | |
285 // The list of language that do not have associated input methods in IBus. | 260 // The list of language that do not have associated input methods in IBus. |
286 // For these languages, we associate input methods here. | 261 // For these languages, we associate input methods here. |
287 const struct ExtraLanguage { | 262 const struct ExtraLanguage { |
288 const char* language_code; | 263 const char* language_code; |
289 const char* input_method_id; | 264 const char* input_method_id; |
290 } kExtraLanguages[] = { | 265 } kExtraLanguages[] = { |
291 // Language Code Input Method ID | 266 // Language Code Input Method ID |
292 { "en-AU", "xkb:us::eng" }, // For Austrailia, use US keyboard layout. | 267 { "en-AU", "xkb:us::eng" }, // For Austrailia, use US keyboard layout. |
293 { "id", "xkb:us::eng" }, // For Indonesian, use US keyboard layout. | 268 { "id", "xkb:us::eng" }, // For Indonesian, use US keyboard layout. |
294 // The code "fil" comes from l10_util.cc. | 269 // The code "fil" comes from l10_util.cc. |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
335 DCHECK(out_string); | 310 DCHECK(out_string); |
336 HashType::const_iterator iter = english_to_resource_id_.find(english_string); | 311 HashType::const_iterator iter = english_to_resource_id_.find(english_string); |
337 if (iter == english_to_resource_id_.end()) { | 312 if (iter == english_to_resource_id_.end()) { |
338 // TODO(yusukes): Write Autotest which checks if all display names and all | 313 // TODO(yusukes): Write Autotest which checks if all display names and all |
339 // property names for supported input methods are listed in the resource | 314 // property names for supported input methods are listed in the resource |
340 // ID array (crosbug.com/4572). | 315 // ID array (crosbug.com/4572). |
341 LOG(ERROR) << "Resource ID is not found for: " << english_string; | 316 LOG(ERROR) << "Resource ID is not found for: " << english_string; |
342 return false; | 317 return false; |
343 } | 318 } |
344 | 319 |
345 *out_string = l10n_util::GetStringUTF16(iter->second); | 320 *out_string = delegate_->GetLocalizedString(iter->second); |
346 return true; | 321 return true; |
347 } | 322 } |
348 | 323 |
349 string16 InputMethodUtil::TranslateString( | 324 string16 InputMethodUtil::TranslateString( |
350 const std::string& english_string) const { | 325 const std::string& english_string) const { |
351 string16 localized_string; | 326 string16 localized_string; |
352 if (TranslateStringInternal(english_string, &localized_string)) { | 327 if (TranslateStringInternal(english_string, &localized_string)) { |
353 return localized_string; | 328 return localized_string; |
354 } | 329 } |
355 return UTF8ToUTF16(english_string); | 330 return UTF8ToUTF16(english_string); |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
442 } | 417 } |
443 | 418 |
444 string16 InputMethodUtil::GetInputMethodMediumName( | 419 string16 InputMethodUtil::GetInputMethodMediumName( |
445 const InputMethodDescriptor& input_method) const { | 420 const InputMethodDescriptor& input_method) const { |
446 // For the "Your input method has changed to..." bubble. In most cases | 421 // For the "Your input method has changed to..." bubble. In most cases |
447 // it uses the same name as the short name, unless found in a table | 422 // it uses the same name as the short name, unless found in a table |
448 // for medium length names. | 423 // for medium length names. |
449 for (size_t i = 0; i < kMappingImeIdToMediumLenNameResourceIdLen; ++i) { | 424 for (size_t i = 0; i < kMappingImeIdToMediumLenNameResourceIdLen; ++i) { |
450 if (kMappingImeIdToMediumLenNameResourceId[i].input_method_id == | 425 if (kMappingImeIdToMediumLenNameResourceId[i].input_method_id == |
451 input_method.id()) { | 426 input_method.id()) { |
452 return l10n_util::GetStringUTF16( | 427 return delegate_->GetLocalizedString( |
453 kMappingImeIdToMediumLenNameResourceId[i].resource_id); | 428 kMappingImeIdToMediumLenNameResourceId[i].resource_id); |
454 } | 429 } |
455 } | 430 } |
456 return GetInputMethodShortName(input_method); | 431 return GetInputMethodShortName(input_method); |
457 } | 432 } |
458 | 433 |
459 string16 InputMethodUtil::GetInputMethodLongName( | 434 string16 InputMethodUtil::GetInputMethodLongName( |
460 const InputMethodDescriptor& input_method) const { | 435 const InputMethodDescriptor& input_method) const { |
461 if (!input_method.name().empty()) { | 436 if (!input_method.name().empty()) { |
462 // If the descriptor has a name, use it. | 437 // If the descriptor has a name, use it. |
463 return UTF8ToUTF16(input_method.name()); | 438 return UTF8ToUTF16(input_method.name()); |
464 } | 439 } |
465 | 440 |
466 // We don't show language here. Name of keyboard layout or input method | 441 // We don't show language here. Name of keyboard layout or input method |
467 // usually imply (or explicitly include) its language. | 442 // usually imply (or explicitly include) its language. |
468 | 443 |
469 // Special case for German, French and Dutch: these languages have multiple | 444 // Special case for German, French and Dutch: these languages have multiple |
470 // keyboard layouts and share the same layout of keyboard (Belgian). We need | 445 // keyboard layouts and share the same layout of keyboard (Belgian). We need |
471 // to show explicitly the language for the layout. For Arabic, Amharic, and | 446 // to show explicitly the language for the layout. For Arabic, Amharic, and |
472 // Indic languages: they share "Standard Input Method". | 447 // Indic languages: they share "Standard Input Method". |
473 const string16 standard_input_method_text = l10n_util::GetStringUTF16( | 448 const string16 standard_input_method_text = delegate_->GetLocalizedString( |
474 IDS_OPTIONS_SETTINGS_LANGUAGES_M17N_STANDARD_INPUT_METHOD); | 449 IDS_OPTIONS_SETTINGS_LANGUAGES_M17N_STANDARD_INPUT_METHOD); |
475 const std::string language_code = input_method.language_code(); | 450 const std::string language_code = input_method.language_code(); |
476 | 451 |
477 string16 text = TranslateString(input_method.id()); | 452 string16 text = TranslateString(input_method.id()); |
478 if (text == standard_input_method_text || | 453 if (text == standard_input_method_text || |
479 language_code == "de" || | 454 language_code == "de" || |
480 language_code == "fr" || | 455 language_code == "fr" || |
481 language_code == "nl") { | 456 language_code == "nl") { |
482 const string16 language_name = l10n_util::GetDisplayNameForLocale( | 457 const string16 language_name = delegate_->GetDisplayLanguageName( |
483 language_code, delegate_->GetActiveLocale(), true); | 458 language_code); |
484 | 459 |
485 text = language_name + UTF8ToUTF16(" - ") + text; | 460 text = language_name + UTF8ToUTF16(" - ") + text; |
486 } | 461 } |
487 | 462 |
488 DCHECK(!text.empty()); | 463 DCHECK(!text.empty()); |
489 return text; | 464 return text; |
490 } | 465 } |
491 | 466 |
492 const InputMethodDescriptor* InputMethodUtil::GetInputMethodDescriptorFromId( | 467 const InputMethodDescriptor* InputMethodUtil::GetInputMethodDescriptorFromId( |
493 const std::string& input_method_id) const { | 468 const std::string& input_method_id) const { |
494 InputMethodIdToDescriptorMap::const_iterator iter | 469 InputMethodIdToDescriptorMap::const_iterator iter |
495 = id_to_descriptor_.find(input_method_id); | 470 = id_to_descriptor_.find(input_method_id); |
496 return (iter == id_to_descriptor_.end()) ? NULL : &(iter->second); | 471 return (iter == id_to_descriptor_.end()) ? NULL : &(iter->second); |
497 } | 472 } |
498 | 473 |
499 // static | |
500 string16 InputMethodUtil::GetLanguageDisplayNameFromCode( | |
501 const std::string& language_code) { | |
502 return l10n_util::GetDisplayNameForLocale( | |
503 language_code, delegate_->GetActiveLocale(), true); | |
504 } | |
505 | |
506 // static | |
507 string16 InputMethodUtil::GetLanguageNativeDisplayNameFromCode( | |
508 const std::string& language_code) { | |
509 return l10n_util::GetDisplayNameForLocale(language_code, language_code, true); | |
510 } | |
511 | |
512 std::vector<std::string> InputMethodUtil::GetExtraLanguageCodesFromId( | 474 std::vector<std::string> InputMethodUtil::GetExtraLanguageCodesFromId( |
513 const std::string& input_method_id) const { | 475 const std::string& input_method_id) const { |
514 std::vector<std::string> result; | 476 std::vector<std::string> result; |
515 for (size_t i = 0; i < kExtraLanguagesLength; ++i) { | 477 for (size_t i = 0; i < kExtraLanguagesLength; ++i) { |
516 if (input_method_id == kExtraLanguages[i].input_method_id) | 478 if (input_method_id == kExtraLanguages[i].input_method_id) |
517 result.push_back(kExtraLanguages[i].language_code); | 479 result.push_back(kExtraLanguages[i].language_code); |
518 } | 480 } |
519 return result; | 481 return result; |
520 } | 482 } |
521 | 483 |
(...skipping 175 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
697 if (iter != id_to_descriptor_.end()) { | 659 if (iter != id_to_descriptor_.end()) { |
698 const InputMethodDescriptor& input_method = iter->second; | 660 const InputMethodDescriptor& input_method = iter->second; |
699 language_code_to_ids_.insert( | 661 language_code_to_ids_.insert( |
700 std::make_pair(language_code, input_method.id())); | 662 std::make_pair(language_code, input_method.id())); |
701 } | 663 } |
702 } | 664 } |
703 } | 665 } |
704 | 666 |
705 } // namespace input_method | 667 } // namespace input_method |
706 } // namespace chromeos | 668 } // namespace chromeos |
OLD | NEW |