Java/CPP: libphonenumber v5.1.2 - AYTF fix for numbers in national format in countrie...
[platform/upstream/libphonenumber.git] / cpp / src / phonenumbers / asyoutypeformatter.cc
1 // Copyright (C) 2011 The Libphonenumber Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include "phonenumbers/asyoutypeformatter.h"
16
17 #include <cctype>
18 #include <list>
19 #include <string>
20
21 #include <google/protobuf/message_lite.h>
22
23 #include "base/logging.h"
24 #include "base/memory/scoped_ptr.h"
25 #include "phonenumbers/phonemetadata.pb.h"
26 #include "phonenumbers/phonenumberutil.h"
27 #include "phonenumbers/regexp_cache.h"
28 #include "phonenumbers/regexp_factory.h"
29 #include "phonenumbers/stringutil.h"
30 #include "phonenumbers/unicodestring.h"
31
32 namespace i18n {
33 namespace phonenumbers {
34
35 using google::protobuf::RepeatedPtrField;
36
37 namespace {
38
39 const char kPlusSign = '+';
40
41 // A pattern that is used to match character classes in regular expressions.
42 // An example of a character class is [1-4].
43 const char kCharacterClassPattern[] = "\\[([^\\[\\]])*\\]";
44
45 // This is the minimum length of national number accrued that is required to
46 // trigger the formatter. The first element of the leading_digits_pattern of
47 // each number_format contains a regular expression that matches up to this
48 // number of digits.
49 const size_t kMinLeadingDigitsLength = 3;
50
51 // The digits that have not been entered yet will be represented by a \u2008,
52 // the punctuation space.
53 const char kDigitPlaceholder[] = "\xE2\x80\x88"; /* " " */
54
55 // Character used when appropriate to separate a prefix, such as a long NDD or a
56 // country calling code, from the national number.
57 const char kSeparatorBeforeNationalNumber = ' ';
58
59 // A set of characters that, if found in a national prefix formatting rules, are
60 // an indicator to us that we should separate the national prefix from the
61 // number when formatting.
62 const char kNationalPrefixSeparatorsPattern[] = "[- ]";
63
64 // Replaces any standalone digit in the pattern (not any inside a {} grouping)
65 // with \d. This function replaces the standalone digit regex used in the Java
66 // version which is currently not supported by RE2 because it uses a special
67 // construct (?=).
68 void ReplacePatternDigits(string* pattern) {
69   DCHECK(pattern);
70   string new_pattern;
71
72   for (string::const_iterator it = pattern->begin(); it != pattern->end();
73        ++it) {
74     const char current_char = *it;
75
76     if (isdigit(current_char)) {
77       if (it + 1 != pattern->end()) {
78         const char next_char = it[1];
79
80         if (next_char != ',' && next_char != '}') {
81           new_pattern += "\\d";
82         } else {
83           new_pattern += current_char;
84         }
85       } else {
86         new_pattern += "\\d";
87       }
88     } else {
89       new_pattern += current_char;
90     }
91   }
92   pattern->assign(new_pattern);
93 }
94
95 // Matches all the groups contained in 'input' against 'pattern'.
96 void MatchAllGroups(const string& pattern,
97                     const string& input,
98                     const AbstractRegExpFactory& regexp_factory,
99                     RegExpCache* cache,
100                     string* group) {
101   DCHECK(cache);
102   DCHECK(group);
103   string new_pattern(pattern);
104
105   // Transforms pattern "(...)(...)(...)" to "(.........)".
106   strrmm(&new_pattern, "()");
107   new_pattern = StrCat("(", new_pattern, ")");
108
109   const scoped_ptr<RegExpInput> consume_input(
110       regexp_factory.CreateInput(input));
111   bool status =
112       cache->GetRegExp(new_pattern).Consume(consume_input.get(), group);
113   DCHECK(status);
114 }
115
116 PhoneMetadata CreateEmptyMetadata() {
117   PhoneMetadata metadata;
118   metadata.set_international_prefix("NA");
119   return metadata;
120 }
121
122 }  // namespace
123
124 AsYouTypeFormatter::AsYouTypeFormatter(const string& region_code)
125     : regexp_factory_(new RegExpFactory()),
126       regexp_cache_(*regexp_factory_.get(), 64),
127       current_output_(),
128       formatting_template_(),
129       current_formatting_pattern_(),
130       accrued_input_(),
131       accrued_input_without_formatting_(),
132       able_to_format_(true),
133       input_has_formatting_(false),
134       is_complete_number_(false),
135       is_expecting_country_code_(false),
136       phone_util_(*PhoneNumberUtil::GetInstance()),
137       default_country_(region_code),
138       empty_metadata_(CreateEmptyMetadata()),
139       default_metadata_(GetMetadataForRegion(region_code)),
140       current_metadata_(default_metadata_),
141       last_match_position_(0),
142       original_position_(0),
143       position_to_remember_(0),
144       prefix_before_national_number_(),
145       should_add_space_after_national_prefix_(false),
146       national_prefix_extracted_(),
147       national_number_(),
148       possible_formats_() {
149 }
150
151 // The metadata needed by this class is the same for all regions sharing the
152 // same country calling code. Therefore, we return the metadata for "main"
153 // region for this country calling code.
154 const PhoneMetadata* AsYouTypeFormatter::GetMetadataForRegion(
155     const string& region_code) const {
156   int country_calling_code = phone_util_.GetCountryCodeForRegion(region_code);
157   string main_country;
158   phone_util_.GetRegionCodeForCountryCode(country_calling_code, &main_country);
159   const PhoneMetadata* const metadata =
160       phone_util_.GetMetadataForRegion(main_country);
161   if (metadata) {
162     return metadata;
163   }
164   // Set to a default instance of the metadata. This allows us to function with
165   // an incorrect region code, even if formatting only works for numbers
166   // specified with "+".
167   return &empty_metadata_;
168 }
169
170 bool AsYouTypeFormatter::MaybeCreateNewTemplate() {
171   // When there are multiple available formats, the formatter uses the first
172   // format where a formatting template could be created.
173   for (list<const NumberFormat*>::const_iterator it = possible_formats_.begin();
174        it != possible_formats_.end(); ++it) {
175     DCHECK(*it);
176     const NumberFormat& number_format = **it;
177     const string& pattern = number_format.pattern();
178     if (current_formatting_pattern_ == pattern) {
179       return false;
180     }
181     if (CreateFormattingTemplate(number_format)) {
182       current_formatting_pattern_ = pattern;
183       SetShouldAddSpaceAfterNationalPrefix(number_format);
184       // With a new formatting template, the matched position using the old
185       // template needs to be reset.
186       last_match_position_ = 0;
187       return true;
188     }
189   }
190   able_to_format_ = false;
191   return false;
192 }
193
194 void AsYouTypeFormatter::GetAvailableFormats(
195     const string& leading_three_digits) {
196   const RepeatedPtrField<NumberFormat>& format_list =
197       (is_complete_number_ &&
198        current_metadata_->intl_number_format().size() > 0)
199           ? current_metadata_->intl_number_format()
200           : current_metadata_->number_format();
201   bool national_prefix_used_by_country =
202       current_metadata_->has_national_prefix();
203   for (RepeatedPtrField<NumberFormat>::const_iterator it = format_list.begin();
204        it != format_list.end(); ++it) {
205     if (!national_prefix_used_by_country || is_complete_number_ ||
206         it->national_prefix_optional_when_formatting() ||
207         phone_util_.FormattingRuleHasFirstGroupOnly(
208             it->national_prefix_formatting_rule())) {
209       if (phone_util_.IsFormatEligibleForAsYouTypeFormatter(it->format())) {
210         possible_formats_.push_back(&*it);
211       }
212     }
213   }
214   NarrowDownPossibleFormats(leading_three_digits);
215 }
216
217 void AsYouTypeFormatter::NarrowDownPossibleFormats(
218     const string& leading_digits) {
219   const int index_of_leading_digits_pattern =
220       leading_digits.length() - kMinLeadingDigitsLength;
221
222   for (list<const NumberFormat*>::iterator it = possible_formats_.begin();
223        it != possible_formats_.end(); ) {
224     DCHECK(*it);
225     const NumberFormat& format = **it;
226
227     if (format.leading_digits_pattern_size() >
228         index_of_leading_digits_pattern) {
229       const scoped_ptr<RegExpInput> input(
230           regexp_factory_->CreateInput(leading_digits));
231       if (!regexp_cache_.GetRegExp(format.leading_digits_pattern().Get(
232               index_of_leading_digits_pattern)).Consume(input.get())) {
233         it = possible_formats_.erase(it);
234         continue;
235       }
236     }  // else the particular format has no more specific leadingDigitsPattern,
237        // and it should be retained.
238     ++it;
239   }
240 }
241
242 void AsYouTypeFormatter::SetShouldAddSpaceAfterNationalPrefix(
243     const NumberFormat& format) {
244   static const scoped_ptr<const RegExp> national_prefix_separators_pattern(
245       regexp_factory_->CreateRegExp(kNationalPrefixSeparatorsPattern));
246   should_add_space_after_national_prefix_ =
247       national_prefix_separators_pattern->PartialMatch(
248           format.national_prefix_formatting_rule());
249 }
250
251 bool AsYouTypeFormatter::CreateFormattingTemplate(const NumberFormat& format) {
252   string number_pattern = format.pattern();
253
254   // The formatter doesn't format numbers when numberPattern contains "|", e.g.
255   // (20|3)\d{4}. In those cases we quickly return.
256   if (number_pattern.find('|') != string::npos) {
257     return false;
258   }
259   // Replace anything in the form of [..] with \d.
260   static const scoped_ptr<const RegExp> character_class_pattern(
261       regexp_factory_->CreateRegExp(kCharacterClassPattern));
262   character_class_pattern->GlobalReplace(&number_pattern, "\\\\d");
263
264   // Replace any standalone digit (not the one in d{}) with \d.
265   ReplacePatternDigits(&number_pattern);
266
267   string number_format = format.format();
268   formatting_template_.remove();
269   UnicodeString temp_template;
270   GetFormattingTemplate(number_pattern, number_format, &temp_template);
271
272   if (temp_template.length() > 0) {
273     formatting_template_.append(temp_template);
274     return true;
275   }
276   return false;
277 }
278
279 void AsYouTypeFormatter::GetFormattingTemplate(
280     const string& number_pattern,
281     const string& number_format,
282     UnicodeString* formatting_template) {
283   DCHECK(formatting_template);
284
285   // Creates a phone number consisting only of the digit 9 that matches the
286   // number_pattern by applying the pattern to the longest_phone_number string.
287   static const char longest_phone_number[] = "999999999999999";
288   string a_phone_number;
289
290   MatchAllGroups(number_pattern, longest_phone_number, *regexp_factory_,
291                  &regexp_cache_, &a_phone_number);
292   // No formatting template can be created if the number of digits entered so
293   // far is longer than the maximum the current formatting rule can accommodate.
294   if (a_phone_number.length() < national_number_.length()) {
295     formatting_template->remove();
296     return;
297   }
298   // Formats the number according to number_format.
299   regexp_cache_.GetRegExp(number_pattern).GlobalReplace(
300       &a_phone_number, number_format);
301   // Replaces each digit with character kDigitPlaceholder.
302   GlobalReplaceSubstring("9", kDigitPlaceholder, &a_phone_number);
303   formatting_template->setTo(a_phone_number.c_str(), a_phone_number.size());
304 }
305
306 void AsYouTypeFormatter::Clear() {
307   current_output_.clear();
308   accrued_input_.remove();
309   accrued_input_without_formatting_.remove();
310   formatting_template_.remove();
311   last_match_position_ = 0;
312   current_formatting_pattern_.clear();
313   prefix_before_national_number_.clear();
314   national_prefix_extracted_.clear();
315   national_number_.clear();
316   able_to_format_ = true;
317   input_has_formatting_ = false;
318   position_to_remember_ = 0;
319   original_position_ = 0;
320   is_complete_number_ = false;
321   is_expecting_country_code_ = false;
322   possible_formats_.clear();
323   should_add_space_after_national_prefix_ = false;
324
325   if (current_metadata_ != default_metadata_) {
326     current_metadata_ = GetMetadataForRegion(default_country_);
327   }
328 }
329
330 const string& AsYouTypeFormatter::InputDigit(char32 next_char, string* result) {
331   DCHECK(result);
332
333   InputDigitWithOptionToRememberPosition(next_char, false, &current_output_);
334   result->assign(current_output_);
335   return *result;
336 }
337
338 const string& AsYouTypeFormatter::InputDigitAndRememberPosition(
339     char32 next_char,
340     string* result) {
341   DCHECK(result);
342
343   InputDigitWithOptionToRememberPosition(next_char, true, &current_output_);
344   result->assign(current_output_);
345   return *result;
346 }
347
348 void AsYouTypeFormatter::InputDigitWithOptionToRememberPosition(
349     char32 next_char,
350     bool remember_position,
351     string* phone_number) {
352   DCHECK(phone_number);
353
354   accrued_input_.append(next_char);
355   if (remember_position) {
356     original_position_ = accrued_input_.length();
357   }
358   // We do formatting on-the-fly only when each character entered is either a
359   // plus sign (accepted at the start of the number only).
360   string next_char_string;
361   UnicodeString(next_char).toUTF8String(next_char_string);
362
363   char normalized_next_char = '\0';
364   if (!(phone_util_.ContainsOnlyValidDigits(next_char_string) ||
365       (accrued_input_.length() == 1 && next_char == kPlusSign))) {
366     able_to_format_ = false;
367     input_has_formatting_ = true;
368   } else {
369     normalized_next_char =
370         NormalizeAndAccrueDigitsAndPlusSign(next_char, remember_position);
371   }
372   if (!able_to_format_) {
373     // When we are unable to format because of reasons other than that
374     // formatting chars have been entered, it can be due to really long IDDs or
375     // NDDs. If that is the case, we might be able to do formatting again after
376     // extracting them.
377     if (input_has_formatting_) {
378       phone_number->clear();
379       accrued_input_.toUTF8String(*phone_number);
380     } else if (AttemptToExtractIdd()) {
381       if (AttemptToExtractCountryCode()) {
382         AttemptToChoosePatternWithPrefixExtracted(phone_number);
383         return;
384       }
385     } else if (AbleToExtractLongerNdd()) {
386       // Add an additional space to separate long NDD and national significant
387       // number for readability. We don't set
388       // should_add_space_after_national_prefix_ to true, since we don't want
389       // this to change later when we choose formatting templates.
390       prefix_before_national_number_.push_back(kSeparatorBeforeNationalNumber);
391       AttemptToChoosePatternWithPrefixExtracted(phone_number);
392       return;
393     }
394     phone_number->clear();
395     accrued_input_.toUTF8String(*phone_number);
396     return;
397   }
398
399   // We start to attempt to format only when at least kMinLeadingDigitsLength
400   // digits (the plus sign is counted as a digit as well for this purpose) have
401   // been entered.
402   switch (accrued_input_without_formatting_.length()) {
403     case 0:
404     case 1:
405     case 2:
406       phone_number->clear();
407       accrued_input_.toUTF8String(*phone_number);
408       return;
409     case 3:
410       if (AttemptToExtractIdd()) {
411         is_expecting_country_code_ = true;
412       } else {
413         // No IDD or plus sign is found, might be entering in national format.
414         RemoveNationalPrefixFromNationalNumber(&national_prefix_extracted_);
415         AttemptToChooseFormattingPattern(phone_number);
416         return;
417       }
418     default:
419       if (is_expecting_country_code_) {
420         if (AttemptToExtractCountryCode()) {
421           is_expecting_country_code_ = false;
422         }
423         phone_number->assign(prefix_before_national_number_);
424         phone_number->append(national_number_);
425         return;
426       }
427       if (possible_formats_.size() > 0) {
428         // The formatting pattern is already chosen.
429         string temp_national_number;
430         InputDigitHelper(normalized_next_char, &temp_national_number);
431         // See if accrued digits can be formatted properly already. If not, use
432         // the results from InputDigitHelper, which does formatting based on the
433         // formatting pattern chosen.
434         string formatted_number;
435         AttemptToFormatAccruedDigits(&formatted_number);
436         if (formatted_number.length() > 0) {
437           phone_number->assign(formatted_number);
438           return;
439         }
440         NarrowDownPossibleFormats(national_number_);
441         if (MaybeCreateNewTemplate()) {
442           InputAccruedNationalNumber(phone_number);
443           return;
444         }
445         if (able_to_format_) {
446           AppendNationalNumber(temp_national_number, phone_number);
447         } else {
448           phone_number->clear();
449           accrued_input_.toUTF8String(*phone_number);
450         }
451         return;
452       } else {
453         AttemptToChooseFormattingPattern(phone_number);
454       }
455   }
456 }
457
458 void AsYouTypeFormatter::AttemptToChoosePatternWithPrefixExtracted(
459     string* formatted_number) {
460   able_to_format_ = true;
461   is_expecting_country_code_ = false;
462   possible_formats_.clear();
463   AttemptToChooseFormattingPattern(formatted_number);
464 }
465
466 bool AsYouTypeFormatter::AbleToExtractLongerNdd() {
467   if (national_prefix_extracted_.length() > 0) {
468     // Put the extracted NDD back to the national number before attempting to
469     // extract a new NDD.
470     national_number_.insert(0, national_prefix_extracted_);
471     // Remove the previously extracted NDD from prefixBeforeNationalNumber. We
472     // cannot simply set it to empty string because people sometimes enter
473     // national prefix after country code, e.g +44 (0)20-1234-5678.
474     int index_of_previous_ndd =
475         prefix_before_national_number_.find_last_of(national_prefix_extracted_);
476     prefix_before_national_number_.resize(index_of_previous_ndd);
477   }
478   string new_national_prefix;
479   RemoveNationalPrefixFromNationalNumber(&new_national_prefix);
480   return national_prefix_extracted_ != new_national_prefix;
481 }
482
483 void AsYouTypeFormatter::AttemptToFormatAccruedDigits(
484     string* formatted_result) {
485   DCHECK(formatted_result);
486
487   for (list<const NumberFormat*>::const_iterator it = possible_formats_.begin();
488        it != possible_formats_.end(); ++it) {
489     DCHECK(*it);
490     const NumberFormat& number_format = **it;
491     const string& pattern = number_format.pattern();
492
493     if (regexp_cache_.GetRegExp(pattern).FullMatch(national_number_)) {
494       SetShouldAddSpaceAfterNationalPrefix(number_format);
495
496       string formatted_number(national_number_);
497       bool status = regexp_cache_.GetRegExp(pattern).GlobalReplace(
498           &formatted_number, number_format.format());
499       DCHECK(status);
500
501       AppendNationalNumber(formatted_number, formatted_result);
502       return;
503     }
504   }
505 }
506
507 int AsYouTypeFormatter::GetRememberedPosition() const {
508   UnicodeString current_output(current_output_.c_str());
509   if (!able_to_format_) {
510     return ConvertUnicodeStringPosition(current_output, original_position_);
511   }
512   int accrued_input_index = 0;
513   int current_output_index = 0;
514
515   while (accrued_input_index < position_to_remember_ &&
516          current_output_index < current_output.length()) {
517     if (accrued_input_without_formatting_[accrued_input_index] ==
518         current_output[current_output_index]) {
519       ++accrued_input_index;
520     }
521     ++current_output_index;
522   }
523   return ConvertUnicodeStringPosition(current_output, current_output_index);
524 }
525
526 void AsYouTypeFormatter::AppendNationalNumber(const string& national_number,
527                                               string* phone_number) const {
528   int prefix_before_national_number_length =
529       prefix_before_national_number_.size();
530   if (should_add_space_after_national_prefix_ &&
531       prefix_before_national_number_length > 0 &&
532       prefix_before_national_number_.at(
533           prefix_before_national_number_length - 1) !=
534       kSeparatorBeforeNationalNumber) {
535     // We want to add a space after the national prefix if the national prefix
536     // formatting rule indicates that this would normally be done, with the
537     // exception of the case where we already appended a space because the NDD
538     // was surprisingly long.
539     phone_number->assign(prefix_before_national_number_);
540     phone_number->push_back(kSeparatorBeforeNationalNumber);
541     StrAppend(phone_number, national_number);
542   } else {
543     phone_number->assign(
544         StrCat(prefix_before_national_number_, national_number));
545   }
546 }
547
548 void AsYouTypeFormatter::AttemptToChooseFormattingPattern(
549     string* formatted_number) {
550   DCHECK(formatted_number);
551
552   if (national_number_.length() >= kMinLeadingDigitsLength) {
553     const string leading_digits =
554         national_number_.substr(0, kMinLeadingDigitsLength);
555
556     GetAvailableFormats(leading_digits);
557     if (MaybeCreateNewTemplate()) {
558       InputAccruedNationalNumber(formatted_number);
559     } else {
560       formatted_number->clear();
561       accrued_input_.toUTF8String(*formatted_number);
562     }
563     return;
564   } else {
565     AppendNationalNumber(national_number_, formatted_number);
566   }
567 }
568
569 void AsYouTypeFormatter::InputAccruedNationalNumber(string* number) {
570   DCHECK(number);
571   int length_of_national_number = national_number_.length();
572
573   if (length_of_national_number > 0) {
574     string temp_national_number;
575
576     for (int i = 0; i < length_of_national_number; ++i) {
577       temp_national_number.clear();
578       InputDigitHelper(national_number_[i], &temp_national_number);
579     }
580     if (able_to_format_) {
581       AppendNationalNumber(temp_national_number, number);
582     } else {
583       number->clear();
584       accrued_input_.toUTF8String(*number);
585     }
586     return;
587   } else {
588     number->assign(prefix_before_national_number_);
589   }
590 }
591
592 bool AsYouTypeFormatter::IsNanpaNumberWithNationalPrefix() const {
593   // For NANPA numbers beginning with 1[2-9], treat the 1 as the national
594   // prefix. The reason is that national significant numbers in NANPA always
595   // start with [2-9] after the national prefix.  Numbers beginning with 1[01]
596   // can only be short/emergency numbers, which don't need the national
597   // prefix.
598   return (current_metadata_->country_code() == 1) &&
599          (national_number_[0] == '1') && (national_number_[1] != '0') &&
600          (national_number_[1] != '1');
601 }
602
603 void AsYouTypeFormatter::RemoveNationalPrefixFromNationalNumber(
604     string* national_prefix) {
605   int start_of_national_number = 0;
606
607   if (IsNanpaNumberWithNationalPrefix()) {
608     start_of_national_number = 1;
609     prefix_before_national_number_.append("1");
610     prefix_before_national_number_.push_back(kSeparatorBeforeNationalNumber);
611     is_complete_number_ = true;
612   } else if (current_metadata_->has_national_prefix_for_parsing()) {
613     const scoped_ptr<RegExpInput> consumed_input(
614         regexp_factory_->CreateInput(national_number_));
615     const RegExp& pattern = regexp_cache_.GetRegExp(
616         current_metadata_->national_prefix_for_parsing());
617
618     if (pattern.Consume(consumed_input.get())) {
619       // When the national prefix is detected, we use international formatting
620       // rules instead of national ones, because national formatting rules could
621       // countain local formatting rules for numbers entered without area code.
622       is_complete_number_ = true;
623       start_of_national_number =
624           national_number_.length() - consumed_input->ToString().length();
625       prefix_before_national_number_.append(
626           national_number_.substr(0, start_of_national_number));
627     }
628   }
629   national_prefix->assign(national_number_, 0, start_of_national_number);
630   national_number_.erase(0, start_of_national_number);
631 }
632
633 bool AsYouTypeFormatter::AttemptToExtractIdd() {
634   string accrued_input_without_formatting_stdstring;
635   accrued_input_without_formatting_
636       .toUTF8String(accrued_input_without_formatting_stdstring);
637   const scoped_ptr<RegExpInput> consumed_input(
638       regexp_factory_->CreateInput(accrued_input_without_formatting_stdstring));
639   const RegExp& international_prefix = regexp_cache_.GetRegExp(
640       StrCat("\\", string(&kPlusSign, 1), "|",
641              current_metadata_->international_prefix()));
642
643   if (international_prefix.Consume(consumed_input.get())) {
644     is_complete_number_ = true;
645     const int start_of_country_code =
646         accrued_input_without_formatting_.length() -
647         consumed_input->ToString().length();
648
649     national_number_.clear();
650     accrued_input_without_formatting_.tempSubString(start_of_country_code)
651         .toUTF8String(national_number_);
652
653     string before_country_code;
654     accrued_input_without_formatting_.tempSubString(0, start_of_country_code)
655         .toUTF8String(before_country_code);
656     prefix_before_national_number_.clear();
657     prefix_before_national_number_.append(before_country_code);
658
659     if (accrued_input_without_formatting_[0] != kPlusSign) {
660       prefix_before_national_number_.push_back(kSeparatorBeforeNationalNumber);
661     }
662     return true;
663   }
664   return false;
665 }
666
667 bool AsYouTypeFormatter::AttemptToExtractCountryCode() {
668   if (national_number_.length() == 0) {
669     return false;
670   }
671   string number_without_country_code(national_number_);
672   int country_code =
673     phone_util_.ExtractCountryCode(&number_without_country_code);
674   if (country_code == 0) {
675     return false;
676   }
677   national_number_.assign(number_without_country_code);
678   string new_region_code;
679   phone_util_.GetRegionCodeForCountryCode(country_code, &new_region_code);
680   if (PhoneNumberUtil::kRegionCodeForNonGeoEntity == new_region_code) {
681     current_metadata_ =
682         phone_util_.GetMetadataForNonGeographicalRegion(country_code);
683   } else if (new_region_code != default_country_) {
684     current_metadata_ = GetMetadataForRegion(new_region_code);
685   }
686   StrAppend(&prefix_before_national_number_, country_code);
687   prefix_before_national_number_.push_back(kSeparatorBeforeNationalNumber);
688
689   return true;
690 }
691
692 char AsYouTypeFormatter::NormalizeAndAccrueDigitsAndPlusSign(
693     char32 next_char,
694     bool remember_position) {
695   char normalized_char = next_char;
696
697   if (next_char == kPlusSign) {
698     accrued_input_without_formatting_.append(next_char);
699   } else {
700     string number;
701     UnicodeString(next_char).toUTF8String(number);
702     phone_util_.NormalizeDigitsOnly(&number);
703     accrued_input_without_formatting_.append(next_char);
704     national_number_.append(number);
705     normalized_char = number[0];
706   }
707   if (remember_position) {
708     position_to_remember_ = accrued_input_without_formatting_.length();
709   }
710   return normalized_char;
711 }
712
713 void AsYouTypeFormatter::InputDigitHelper(char next_char, string* number) {
714   DCHECK(number);
715   number->clear();
716   const char32 placeholder_codepoint = UnicodeString(kDigitPlaceholder)[0];
717   int placeholder_pos = formatting_template_
718       .tempSubString(last_match_position_).indexOf(placeholder_codepoint);
719   if (placeholder_pos != -1) {
720     UnicodeString temp_template = formatting_template_;
721     placeholder_pos = temp_template.indexOf(placeholder_codepoint);
722     temp_template.setCharAt(placeholder_pos, UnicodeString(next_char)[0]);
723     last_match_position_ = placeholder_pos;
724     formatting_template_.replace(0, temp_template.length(), temp_template);
725     formatting_template_.tempSubString(0, last_match_position_ + 1)
726         .toUTF8String(*number);
727   } else {
728     if (possible_formats_.size() == 1) {
729       // More digits are entered than we could handle, and there are no other
730       // valid patterns to try.
731       able_to_format_ = false;
732     }  // else, we just reset the formatting pattern.
733     current_formatting_pattern_.clear();
734     accrued_input_.toUTF8String(*number);
735   }
736 }
737
738 // Returns the number of bytes contained in the given UnicodeString up to the
739 // specified position.
740 // static
741 int AsYouTypeFormatter::ConvertUnicodeStringPosition(const UnicodeString& s,
742                                                      int pos) {
743   if (pos > s.length()) {
744     return -1;
745   }
746   string substring;
747   s.tempSubString(0, pos).toUTF8String(substring);
748   return substring.length();
749 }
750
751 }  // namespace phonenumbers
752 }  // namespace i18n