Skip to content
This repository was archived by the owner on Feb 22, 2023. It is now read-only.

Commit 7855132

Browse files
authored
Generate a demo for new icons when updating icons (#101190)
* add code to generate new icon demo and make font family optional * remove trailing spaces * Update update_icons_test.dart * remove trailing space
1 parent bc0ec85 commit 7855132

File tree

2 files changed

+68
-6
lines changed

2 files changed

+68
-6
lines changed

dev/tools/test/update_icons_test.dart

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,4 +40,22 @@ void main() {
4040
test('no double underscores', () {
4141
expect(Icon.generateFlutterId('abc__123'), 'abc_123');
4242
});
43+
44+
test('usage string is correct', () {
45+
expect(
46+
Icon(const MapEntry<String, String>('abc', '')).usage,
47+
'Icon(Icons.abc),',
48+
);
49+
});
50+
51+
test('usage string is correct with replacement', () {
52+
expect(
53+
Icon(const MapEntry<String, String>('123', '')).usage,
54+
'Icon(Icons.onetwothree),',
55+
);
56+
expect(
57+
Icon(const MapEntry<String, String>('123_rounded', '')).usage,
58+
'Icon(Icons.onetwothree_rounded),',
59+
);
60+
});
4361
}

dev/tools/update_icons.dart

Lines changed: 50 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ const String _defaultIconsPath = 'packages/flutter/lib/src/material/icons.dart';
2525
const String _defaultNewCodepointsPath = 'codepoints';
2626
const String _defaultOldCodepointsPath = 'bin/cache/artifacts/material_fonts/codepoints';
2727
const String _defaultFontFamily = 'MaterialIcons';
28+
const String _defaultDemoFilePath = '/tmp/new_icons_demo.dart';
2829

2930
const String _beginGeneratedMark = '// BEGIN GENERATED ICONS';
3031
const String _endGeneratedMark = '// END GENERATED ICONS';
@@ -216,7 +217,12 @@ void main(List<String> args) {
216217
stdout.write(newIconsContents);
217218
} else {
218219
iconsFile.writeAsStringSync(newIconsContents);
219-
_regenerateCodepointsFile(oldCodepointsFile, newTokenPairMap);
220+
221+
final SplayTreeMap<String, String> sortedNewTokenPairMap = SplayTreeMap<String, String>.of(newTokenPairMap);
222+
_regenerateCodepointsFile(oldCodepointsFile, sortedNewTokenPairMap);
223+
224+
sortedNewTokenPairMap.removeWhere((String key, String value) => oldTokenPairMap.containsKey(key));
225+
_generateIconDemo(File(_defaultDemoFilePath), sortedNewTokenPairMap);
220226
}
221227
}
222228

@@ -276,7 +282,7 @@ String _regenerateIconsFile(
276282
bool enforceSafetyChecks,
277283
) {
278284
final List<Icon> newIcons = tokenPairMap.entries
279-
.map((MapEntry<String, String> entry) => Icon(entry, fontFamily))
285+
.map((MapEntry<String, String> entry) => Icon(entry, fontFamily: fontFamily))
280286
.toList();
281287
newIcons.sort((Icon a, Icon b) => a._compareTo(b));
282288

@@ -379,18 +385,54 @@ bool testIsStable(Map<String, String> newCodepoints, Map<String, String> oldCode
379385
}
380386
}
381387

382-
void _regenerateCodepointsFile(File oldCodepointsFile, Map<String, String> newTokenPairMap) {
388+
void _regenerateCodepointsFile(File oldCodepointsFile, Map<String, String> tokenPairMap) {
383389
stderr.writeln('Regenerating old codepoints file ${oldCodepointsFile.path}');
384390

385391
final StringBuffer buf = StringBuffer();
386-
final SplayTreeMap<String, String> sortedNewTokenPairMap = SplayTreeMap<String, String>.of(newTokenPairMap);
387-
sortedNewTokenPairMap.forEach((String key, String value) => buf.writeln('$key $value'));
392+
tokenPairMap.forEach((String key, String value) => buf.writeln('$key $value'));
388393
oldCodepointsFile.writeAsStringSync(buf.toString());
389394
}
390395

396+
void _generateIconDemo(File demoFilePath, Map<String, String> tokenPairMap) {
397+
if (tokenPairMap.isEmpty) {
398+
stderr.writeln('No new icons, skipping generating icon demo');
399+
return;
400+
}
401+
stderr.writeln('Generating icon demo at $_defaultDemoFilePath');
402+
403+
final StringBuffer newIconUsages = StringBuffer();
404+
for (final MapEntry<String, String> entry in tokenPairMap.entries) {
405+
newIconUsages.writeln(Icon(entry).usage);
406+
}
407+
final String demoFileContents = '''
408+
import 'package:flutter/material.dart';
409+
410+
void main() => runApp(const IconDemo());
411+
412+
class IconDemo extends StatelessWidget {
413+
const IconDemo({ Key? key }) : super(key: key);
414+
415+
@override
416+
Widget build(BuildContext context) {
417+
return MaterialApp(
418+
debugShowCheckedModeBanner: false,
419+
home: Scaffold(
420+
body: Wrap(
421+
children: const [
422+
${newIconUsages.toString()}
423+
],
424+
),
425+
),
426+
);
427+
}
428+
}
429+
''';
430+
demoFilePath.writeAsStringSync(demoFileContents);
431+
}
432+
391433
class Icon {
392434
// Parse tokenPair (e.g. {"6_ft_apart_outlined": "e004"}).
393-
Icon(MapEntry<String, String> tokenPair, this.fontFamily) {
435+
Icon(MapEntry<String, String> tokenPair, {this.fontFamily = _defaultFontFamily}) {
394436
id = tokenPair.key;
395437
hexCodepoint = tokenPair.value;
396438

@@ -450,6 +492,8 @@ class Icon {
450492
String get dartDoc =>
451493
'<i class="material-icons$htmlSuffix md-36">$shortId</i> &#x2014; $family icon named "$name"$style';
452494

495+
String get usage => 'Icon(Icons.$flutterId),';
496+
453497
String get mirroredInRTL => _iconsMirroredWhenRTL.contains(shortId)
454498
? ', matchTextDirection: true'
455499
: '';

0 commit comments

Comments
 (0)