| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 /** | 5 /** |
| 6 * DateFormat is for formatting and parsing dates in a locale-sensitive | 6 * DateFormat is for formatting and parsing dates in a locale-sensitive |
| 7 * manner. | 7 * manner. |
| 8 * It allows the user to choose from a set of standard date time formats as well | 8 * It allows the user to choose from a set of standard date time formats as well |
| 9 * as specify a customized pattern under certain locales. Date elements that | 9 * as specify a customized pattern under certain locales. Date elements that |
| 10 * vary across locales include month name, week name, field order, etc. | 10 * vary across locales include month name, week name, field order, etc. |
| (...skipping 408 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 419 * that are used to do the actual formatting and parsing. Do not use | 419 * that are used to do the actual formatting and parsing. Do not use |
| 420 * this variable directly, use the getter [_formatFields]. | 420 * this variable directly, use the getter [_formatFields]. |
| 421 */ | 421 */ |
| 422 List<_DateFormatField> _formatFieldsPrivate; | 422 List<_DateFormatField> _formatFieldsPrivate; |
| 423 | 423 |
| 424 /** | 424 /** |
| 425 * Getter for [_formatFieldsPrivate] that lazily initializes it. | 425 * Getter for [_formatFieldsPrivate] that lazily initializes it. |
| 426 */ | 426 */ |
| 427 get _formatFields { | 427 get _formatFields { |
| 428 if (_formatFieldsPrivate == null) { | 428 if (_formatFieldsPrivate == null) { |
| 429 if (_pattern == null) _useDefaultPattern(); |
| 429 _formatFieldsPrivate = parsePattern(_pattern); | 430 _formatFieldsPrivate = parsePattern(_pattern); |
| 430 } | 431 } |
| 431 return _formatFieldsPrivate; | 432 return _formatFieldsPrivate; |
| 432 } | 433 } |
| 433 | 434 |
| 434 /** | 435 /** |
| 436 * We are being asked to do formatting without having set any pattern. |
| 437 * Use a default. |
| 438 */ |
| 439 _useDefaultPattern() { |
| 440 add_yMMMMd(); |
| 441 add_jms(); |
| 442 } |
| 443 |
| 444 /** |
| 435 * A series of regular expressions used to parse a format string into its | 445 * A series of regular expressions used to parse a format string into its |
| 436 * component fields. | 446 * component fields. |
| 437 */ | 447 */ |
| 438 static var _matchers = const [ | 448 static var _matchers = const [ |
| 439 // Quoted String - anything between single quotes, with escaping | 449 // Quoted String - anything between single quotes, with escaping |
| 440 // of single quotes by doubling them. | 450 // of single quotes by doubling them. |
| 441 // e.g. in the pattern "hh 'o''clock'" will match 'o''clock' | 451 // e.g. in the pattern "hh 'o''clock'" will match 'o''clock' |
| 442 const RegExp("^\'(?:[^\']|\'\')*\'"), | 452 const RegExp("^\'(?:[^\']|\'\')*\'"), |
| 443 // Fields - any sequence of 1 or more of the same field characters. | 453 // Fields - any sequence of 1 or more of the same field characters. |
| 444 // e.g. in "hh:mm:ss" will match hh, mm, and ss. But in "hms" would | 454 // e.g. in "hh:mm:ss" will match hh, mm, and ss. But in "hms" would |
| 445 // match each letter individually. | 455 // match each letter individually. |
| 446 const RegExp( | 456 const RegExp( |
| 447 "^(?:G+|y+|M+|k+|S+|E+|a+|h+|K+|H+|c+|L+|Q+|d+|m+|s+|v+|z+|Z+)"), | 457 "^(?:G+|y+|M+|k+|S+|E+|a+|h+|K+|H+|c+|L+|Q+|d+|m+|s+|v+|z+|Z+)"), |
| 448 // Everything else - A sequence that is not quotes or field characters. | 458 // Everything else - A sequence that is not quotes or field characters. |
| 449 // e.g. in "hh:mm:ss" will match the colons. | 459 // e.g. in "hh:mm:ss" will match the colons. |
| 450 const RegExp("^[^\'GyMkSEahKHcLQdmsvzZ]+") | 460 const RegExp("^[^\'GyMkSEahKHcLQdmsvzZ]+") |
| 451 ]; | 461 ]; |
| 452 | 462 |
| 453 /** | 463 /** |
| 454 * Set our pattern, appending it to any existing patterns. Also adds a single | 464 * Set our pattern, appending it to any existing patterns. Also adds a single |
| 455 * space to separate the two. | 465 * space to separate the two. |
| 456 */ | 466 */ |
| 457 _setPattern(String inputPattern, [String separator = ' ']) { | 467 _appendPattern(String inputPattern, [String separator = ' ']) { |
| 458 if (_pattern == null) { | 468 if (_pattern == null) { |
| 459 _pattern = inputPattern; | 469 _pattern = inputPattern; |
| 460 } else { | 470 } else { |
| 461 _pattern = "$_pattern$separator$inputPattern"; | 471 _pattern = "$_pattern$separator$inputPattern"; |
| 462 } | 472 } |
| 463 } | 473 } |
| 464 | 474 |
| 465 /** | 475 /** |
| 466 * Add [inputPattern] to this instance as a pattern. If there was a previous | 476 * Add [inputPattern] to this instance as a pattern. If there was a previous |
| 467 * pattern, then this appends to it, separating the two by [separator]. | 477 * pattern, then this appends to it, separating the two by [separator]. |
| 468 * [inputPattern] is first looked up in our list of known skeletons. | 478 * [inputPattern] is first looked up in our list of known skeletons. |
| 469 * If it's found there, then use the corresponding pattern for this locale. | 479 * If it's found there, then use the corresponding pattern for this locale. |
| 470 * If it's not, then treat [inputPattern] as an explicit pattern. | 480 * If it's not, then treat [inputPattern] as an explicit pattern. |
| 471 */ | 481 */ |
| 472 DateFormat addPattern(String inputPattern, [String separator = ' ']) { | 482 DateFormat addPattern(String inputPattern, [String separator = ' ']) { |
| 473 // TODO(alanknight): This is an expensive operation. Caching recently used | 483 // TODO(alanknight): This is an expensive operation. Caching recently used |
| 474 // formats, or possibly introducing an entire "locale" object that would | 484 // formats, or possibly introducing an entire "locale" object that would |
| 475 // cache patterns for that locale could be a good optimization. | 485 // cache patterns for that locale could be a good optimization. |
| 476 if (!_availableSkeletons.containsKey(inputPattern)) { | |
| 477 _setPattern(inputPattern, separator); | |
| 478 } else { | |
| 479 _setPattern(_availableSkeletons[inputPattern], separator); | |
| 480 } | |
| 481 // If we have already parsed the format fields, reset them. | 486 // If we have already parsed the format fields, reset them. |
| 482 _formatFieldsPrivate = null; | 487 _formatFieldsPrivate = null; |
| 488 if (inputPattern == null) return this; |
| 489 if (!_availableSkeletons.containsKey(inputPattern)) { |
| 490 _appendPattern(inputPattern, separator); |
| 491 } else { |
| 492 _appendPattern(_availableSkeletons[inputPattern], separator); |
| 493 } |
| 483 return this; | 494 return this; |
| 484 } | 495 } |
| 485 | 496 |
| 486 /** Return the pattern that we use to format dates.*/ | 497 /** Return the pattern that we use to format dates.*/ |
| 487 get pattern => _pattern; | 498 get pattern => _pattern; |
| 488 | 499 |
| 489 /** Return the skeletons for our current locale. */ | 500 /** Return the skeletons for our current locale. */ |
| 490 Map get _availableSkeletons { | 501 Map get _availableSkeletons { |
| 491 return dateTimePatterns[locale]; | 502 return dateTimePatterns[locale]; |
| 492 } | 503 } |
| (...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 551 List _reverse(List list) { | 562 List _reverse(List list) { |
| 552 // TODO(alanknight): Use standardized list reverse when implemented. | 563 // TODO(alanknight): Use standardized list reverse when implemented. |
| 553 // See Issue 2804. | 564 // See Issue 2804. |
| 554 var result = new List(); | 565 var result = new List(); |
| 555 for (var i = list.length-1; i >= 0; i--) { | 566 for (var i = list.length-1; i >= 0; i--) { |
| 556 result.addLast(list[i]); | 567 result.addLast(list[i]); |
| 557 } | 568 } |
| 558 return result; | 569 return result; |
| 559 } | 570 } |
| 560 } | 571 } |
| OLD | NEW |