mirror of
https://github.com/flutter/flutter.git
synced 2025-06-03 00:51:18 +00:00
Expose date symbols and patterns for en_US in framework (#67900)
* Expose date symbols and patterns for en_US in framework
This commit is contained in:
parent
8aee75f645
commit
244f5ab598
@ -75,6 +75,7 @@ Future<void> main(List<String> rawArgs) async {
|
||||
final Directory datePatternsDirectory = Directory(path.join(pathToIntl, 'src', 'data', 'dates', 'patterns'));
|
||||
final Map<String, File> patternFiles = _listIntlData(datePatternsDirectory);
|
||||
final StringBuffer buffer = StringBuffer();
|
||||
final Set<String> supportedLocales = _supportedLocales();
|
||||
|
||||
buffer.writeln(
|
||||
'''
|
||||
@ -94,7 +95,7 @@ Future<void> main(List<String> rawArgs) async {
|
||||
buffer.writeln('const Map<String, dynamic> dateSymbols = <String, dynamic> {');
|
||||
symbolFiles.forEach((String locale, File data) {
|
||||
currentLocale = locale;
|
||||
if (_supportedLocales().contains(locale))
|
||||
if (supportedLocales.contains(locale))
|
||||
buffer.writeln(_jsonToMapEntry(locale, json.decode(data.readAsStringSync())));
|
||||
});
|
||||
currentLocale = null;
|
||||
@ -107,7 +108,7 @@ Future<void> main(List<String> rawArgs) async {
|
||||
/// supported by flutter_localizations.''');
|
||||
buffer.writeln('const Map<String, Map<String, String>> datePatterns = <String, Map<String, String>> {');
|
||||
patternFiles.forEach((String locale, File data) {
|
||||
if (_supportedLocales().contains(locale)) {
|
||||
if (supportedLocales.contains(locale)) {
|
||||
final Map<String, dynamic> patterns = json.decode(data.readAsStringSync()) as Map<String, dynamic>;
|
||||
buffer.writeln("'$locale': <String, String>{");
|
||||
patterns.forEach((String key, dynamic value) {
|
||||
@ -164,13 +165,21 @@ String _jsonToMap(dynamic json) {
|
||||
}
|
||||
|
||||
Set<String> _supportedLocales() {
|
||||
final Set<String> supportedLocales = <String>{};
|
||||
// Assumes that en_US is a supported locale by default. Without this, usage
|
||||
// of the intl package APIs before Flutter populates its set of supported i18n
|
||||
// date patterns and symbols may cause problems.
|
||||
//
|
||||
// For more context, see https://github.com/flutter/flutter/issues/67644.
|
||||
final Set<String> supportedLocales = <String>{
|
||||
'en_US',
|
||||
};
|
||||
final RegExp filenameRE = RegExp(r'(?:material|cupertino)_(\w+)\.arb$');
|
||||
final Directory supportedLocalesDirectory = Directory(path.join('packages', 'flutter_localizations', 'lib', 'src', 'l10n'));
|
||||
for (final FileSystemEntity entity in supportedLocalesDirectory.listSync()) {
|
||||
final String filePath = entity.path;
|
||||
if (FileSystemEntity.isFileSync(filePath) && filenameRE.hasMatch(filePath))
|
||||
if (FileSystemEntity.isFileSync(filePath) && filenameRE.hasMatch(filePath)) {
|
||||
supportedLocales.add(filenameRE.firstMatch(filePath)[1]);
|
||||
}
|
||||
}
|
||||
|
||||
return supportedLocales;
|
||||
|
@ -4001,6 +4001,196 @@ const Map<String, dynamic> dateSymbols = <String, dynamic>{
|
||||
'{1}, {0}',
|
||||
],
|
||||
},
|
||||
'en_US': <String, dynamic>{
|
||||
'NAME': 'en_US',
|
||||
'ERAS': <dynamic>[
|
||||
'BC',
|
||||
'AD',
|
||||
],
|
||||
'ERANAMES': <dynamic>[
|
||||
'Before Christ',
|
||||
'Anno Domini',
|
||||
],
|
||||
'NARROWMONTHS': <dynamic>[
|
||||
'J',
|
||||
'F',
|
||||
'M',
|
||||
'A',
|
||||
'M',
|
||||
'J',
|
||||
'J',
|
||||
'A',
|
||||
'S',
|
||||
'O',
|
||||
'N',
|
||||
'D',
|
||||
],
|
||||
'STANDALONENARROWMONTHS': <dynamic>[
|
||||
'J',
|
||||
'F',
|
||||
'M',
|
||||
'A',
|
||||
'M',
|
||||
'J',
|
||||
'J',
|
||||
'A',
|
||||
'S',
|
||||
'O',
|
||||
'N',
|
||||
'D',
|
||||
],
|
||||
'MONTHS': <dynamic>[
|
||||
'January',
|
||||
'February',
|
||||
'March',
|
||||
'April',
|
||||
'May',
|
||||
'June',
|
||||
'July',
|
||||
'August',
|
||||
'September',
|
||||
'October',
|
||||
'November',
|
||||
'December',
|
||||
],
|
||||
'STANDALONEMONTHS': <dynamic>[
|
||||
'January',
|
||||
'February',
|
||||
'March',
|
||||
'April',
|
||||
'May',
|
||||
'June',
|
||||
'July',
|
||||
'August',
|
||||
'September',
|
||||
'October',
|
||||
'November',
|
||||
'December',
|
||||
],
|
||||
'SHORTMONTHS': <dynamic>[
|
||||
'Jan',
|
||||
'Feb',
|
||||
'Mar',
|
||||
'Apr',
|
||||
'May',
|
||||
'Jun',
|
||||
'Jul',
|
||||
'Aug',
|
||||
'Sep',
|
||||
'Oct',
|
||||
'Nov',
|
||||
'Dec',
|
||||
],
|
||||
'STANDALONESHORTMONTHS': <dynamic>[
|
||||
'Jan',
|
||||
'Feb',
|
||||
'Mar',
|
||||
'Apr',
|
||||
'May',
|
||||
'Jun',
|
||||
'Jul',
|
||||
'Aug',
|
||||
'Sep',
|
||||
'Oct',
|
||||
'Nov',
|
||||
'Dec',
|
||||
],
|
||||
'WEEKDAYS': <dynamic>[
|
||||
'Sunday',
|
||||
'Monday',
|
||||
'Tuesday',
|
||||
'Wednesday',
|
||||
'Thursday',
|
||||
'Friday',
|
||||
'Saturday',
|
||||
],
|
||||
'STANDALONEWEEKDAYS': <dynamic>[
|
||||
'Sunday',
|
||||
'Monday',
|
||||
'Tuesday',
|
||||
'Wednesday',
|
||||
'Thursday',
|
||||
'Friday',
|
||||
'Saturday',
|
||||
],
|
||||
'SHORTWEEKDAYS': <dynamic>[
|
||||
'Sun',
|
||||
'Mon',
|
||||
'Tue',
|
||||
'Wed',
|
||||
'Thu',
|
||||
'Fri',
|
||||
'Sat',
|
||||
],
|
||||
'STANDALONESHORTWEEKDAYS': <dynamic>[
|
||||
'Sun',
|
||||
'Mon',
|
||||
'Tue',
|
||||
'Wed',
|
||||
'Thu',
|
||||
'Fri',
|
||||
'Sat',
|
||||
],
|
||||
'NARROWWEEKDAYS': <dynamic>[
|
||||
'S',
|
||||
'M',
|
||||
'T',
|
||||
'W',
|
||||
'T',
|
||||
'F',
|
||||
'S',
|
||||
],
|
||||
'STANDALONENARROWWEEKDAYS': <dynamic>[
|
||||
'S',
|
||||
'M',
|
||||
'T',
|
||||
'W',
|
||||
'T',
|
||||
'F',
|
||||
'S',
|
||||
],
|
||||
'SHORTQUARTERS': <dynamic>[
|
||||
'Q1',
|
||||
'Q2',
|
||||
'Q3',
|
||||
'Q4',
|
||||
],
|
||||
'QUARTERS': <dynamic>[
|
||||
'1st quarter',
|
||||
'2nd quarter',
|
||||
'3rd quarter',
|
||||
'4th quarter',
|
||||
],
|
||||
'AMPMS': <dynamic>[
|
||||
'AM',
|
||||
'PM',
|
||||
],
|
||||
'DATEFORMATS': <dynamic>[
|
||||
'EEEE, MMMM d, y',
|
||||
'MMMM d, y',
|
||||
'MMM d, y',
|
||||
'M/d/yy',
|
||||
],
|
||||
'TIMEFORMATS': <dynamic>[
|
||||
'h:mm:ss a zzzz',
|
||||
'h:mm:ss a z',
|
||||
'h:mm:ss a',
|
||||
'h:mm a',
|
||||
],
|
||||
'AVAILABLEFORMATS': null,
|
||||
'FIRSTDAYOFWEEK': 6,
|
||||
'WEEKENDRANGE': <dynamic>[
|
||||
5,
|
||||
6,
|
||||
],
|
||||
'FIRSTWEEKCUTOFFDAY': 5,
|
||||
'DATETIMEFORMATS': <dynamic>[
|
||||
'{1} \'at\' {0}',
|
||||
'{1} \'at\' {0}',
|
||||
'{1}, {0}',
|
||||
'{1}, {0}',
|
||||
],
|
||||
},
|
||||
'en_ZA': <String, dynamic>{
|
||||
'NAME': 'en_ZA',
|
||||
'ERAS': <dynamic>[
|
||||
@ -18658,6 +18848,52 @@ const Map<String, Map<String, String>> datePatterns =
|
||||
'zzzz': 'zzzz',
|
||||
'ZZZZ': 'ZZZZ',
|
||||
},
|
||||
'en_US': <String, String>{
|
||||
'd': 'd',
|
||||
'E': 'ccc',
|
||||
'EEEE': 'cccc',
|
||||
'LLL': 'LLL',
|
||||
'LLLL': 'LLLL',
|
||||
'M': 'L',
|
||||
'Md': 'M/d',
|
||||
'MEd': 'EEE, M/d',
|
||||
'MMM': 'LLL',
|
||||
'MMMd': 'MMM d',
|
||||
'MMMEd': 'EEE, MMM d',
|
||||
'MMMM': 'LLLL',
|
||||
'MMMMd': 'MMMM d',
|
||||
'MMMMEEEEd': 'EEEE, MMMM d',
|
||||
'QQQ': 'QQQ',
|
||||
'QQQQ': 'QQQQ',
|
||||
'y': 'y',
|
||||
'yM': 'M/y',
|
||||
'yMd': 'M/d/y',
|
||||
'yMEd': 'EEE, M/d/y',
|
||||
'yMMM': 'MMM y',
|
||||
'yMMMd': 'MMM d, y',
|
||||
'yMMMEd': 'EEE, MMM d, y',
|
||||
'yMMMM': 'MMMM y',
|
||||
'yMMMMd': 'MMMM d, y',
|
||||
'yMMMMEEEEd': 'EEEE, MMMM d, y',
|
||||
'yQQQ': 'QQQ y',
|
||||
'yQQQQ': 'QQQQ y',
|
||||
'H': 'HH',
|
||||
'Hm': 'HH:mm',
|
||||
'Hms': 'HH:mm:ss',
|
||||
'j': 'h a',
|
||||
'jm': 'h:mm a',
|
||||
'jms': 'h:mm:ss a',
|
||||
'jmv': 'h:mm a v',
|
||||
'jmz': 'h:mm a z',
|
||||
'jz': 'h a z',
|
||||
'm': 'm',
|
||||
'ms': 'mm:ss',
|
||||
's': 's',
|
||||
'v': 'v',
|
||||
'z': 'z',
|
||||
'zzzz': 'zzzz',
|
||||
'ZZZZ': 'ZZZZ',
|
||||
},
|
||||
'en_ZA': <String, String>{
|
||||
'd': 'd',
|
||||
'E': 'ccc',
|
||||
|
@ -9,17 +9,18 @@ import '../l10n/generated_date_localizations.dart' as date_localizations;
|
||||
/// Tracks if date i18n data has been loaded.
|
||||
bool _dateIntlDataInitialized = false;
|
||||
|
||||
/// Loads i18n data for dates if it hasn't be loaded yet.
|
||||
/// Loads i18n data for dates if it hasn't been loaded yet.
|
||||
///
|
||||
/// Only the first invocation of this function has the effect of loading the
|
||||
/// data. Subsequent invocations have no effect.
|
||||
/// Only the first invocation of this function loads the data. Subsequent
|
||||
/// invocations have no effect.
|
||||
void loadDateIntlDataIfNotLoaded() {
|
||||
if (!_dateIntlDataInitialized) {
|
||||
// TODO(garyq): Add support for scriptCodes. Do not strip scriptCode from string.
|
||||
|
||||
// Keep track of initialzed locales, or will fail on attempted double init.
|
||||
// This can only happen if a locale with a stripped scriptCode has already
|
||||
// been initialzed. This should be removed when scriptCode stripping is removed.
|
||||
// Keeps track of initialized locales. This can only happen if a locale
|
||||
// with a stripped scriptCode has already been initialzed. The set of
|
||||
// initialized locales should be removed when scriptCode stripping is
|
||||
// removed.
|
||||
final Set<String> initializedLocales = <String>{};
|
||||
date_localizations.dateSymbols
|
||||
.cast<String, Map<String, dynamic>>()
|
||||
|
@ -7,6 +7,7 @@ import 'dart:async';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_localizations/flutter_localizations.dart';
|
||||
import 'package:flutter_test/flutter_test.dart';
|
||||
import 'package:intl/intl.dart';
|
||||
|
||||
void main() {
|
||||
group(GlobalMaterialLocalizations, () {
|
||||
@ -159,6 +160,28 @@ void main() {
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
// Regression test for https://github.com/flutter/flutter/issues/67644.
|
||||
testWidgets('en_US is initialized correctly by Flutter when DateFormat is used', (WidgetTester tester) async {
|
||||
DateFormat dateFormat;
|
||||
|
||||
await tester.pumpWidget(MaterialApp(
|
||||
supportedLocales: const <Locale>[
|
||||
Locale('en', 'US'),
|
||||
],
|
||||
locale: const Locale('en', 'US'),
|
||||
localizationsDelegates: const <LocalizationsDelegate<dynamic>>[
|
||||
GlobalMaterialLocalizations.delegate,
|
||||
],
|
||||
home: Builder(builder: (BuildContext context) {
|
||||
dateFormat = DateFormat('EEE, d MMM yyyy HH:mm:ss', 'en_US');
|
||||
|
||||
return Container();
|
||||
}),
|
||||
));
|
||||
|
||||
expect(dateFormat?.locale, 'en_US');
|
||||
});
|
||||
}
|
||||
|
||||
enum DateType { year, medium, full, monthYear }
|
||||
|
Loading…
Reference in New Issue
Block a user