Skip to content

Commit

Permalink
Fix FontLoader does not remove the cache in web engine (flutter#14536)
Browse files Browse the repository at this point in the history
  • Loading branch information
chunhtai authored and fluttergithubbot committed Dec 18, 2019
1 parent 1e1f371 commit 988b8f1
Show file tree
Hide file tree
Showing 3 changed files with 33 additions and 5 deletions.
4 changes: 4 additions & 0 deletions lib/web_ui/lib/src/engine/text/font_collection.dart
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,10 @@ class FontManager {
final html.FontFace fontFace = html.FontFace(family, list);
return fontFace.load().then((_) {
html.document.fonts.add(fontFace);
// There might be paragraph measurements for this new font before it is
// loaded. They were measured using fallback font, so we should clear the
// cache.
TextMeasurementService.clearCache();
}, onError: (dynamic exception) {
// Failures here will throw an html.DomException which confusingly
// does not implement Exception or Error. Rethrow an Exception so it can
Expand Down
10 changes: 5 additions & 5 deletions lib/web_ui/lib/src/engine/text/measurement.dart
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,8 @@ abstract class TextMeasurementService {
/// Initializes the text measurement service with a specific
/// [rulerCacheCapacity] that gets passed to the [RulerManager].
static void initialize({@required int rulerCacheCapacity}) {
clearCache();
rulerManager?.dispose();
rulerManager = null;
rulerManager = RulerManager(rulerCacheCapacity: rulerCacheCapacity);
}

Expand Down Expand Up @@ -211,11 +212,10 @@ abstract class TextMeasurementService {
return domInstance;
}

/// Clears the cache of paragraph rulers.
@visibleForTesting
/// Clears the cache of paragraph rulers that are used for measuring paragraph
/// metrics.
static void clearCache() {
rulerManager?.dispose();
rulerManager = null;
rulerManager?._evictAllRulers();
}

static bool _canUseCanvasMeasurement(EngineParagraph paragraph) {
Expand Down
24 changes: 24 additions & 0 deletions lib/web_ui/test/text/font_loading_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import 'dart:typed_data';

import 'package:test/test.dart';
import 'package:ui/ui.dart' as ui;
import 'package:ui/src/engine.dart';

Future<void> main() async {
await ui.webOnlyInitializeTestDomRenderer();
Expand Down Expand Up @@ -34,6 +35,29 @@ Future<void> main() async {

expect(_containsFontFamily('Blehm'), true);
});

test('loads font should clear measurement caches', () async {
final ui.ParagraphStyle style = ui.ParagraphStyle();
final ui.ParagraphBuilder builder = ui.ParagraphBuilder(style);
final ui.ParagraphConstraints constraints = ui.ParagraphConstraints(width: 30.0);
builder.addText('test');
final ui.Paragraph paragraph = builder.build();
// Triggers the measuring and verifies the result has been cached.
paragraph.layout(constraints);
expect(TextMeasurementService.rulerManager.rulers.length, 1);

// Now, loads a new font using loadFontFromList. This should clear the
// cache
final html.HttpRequest response = await html.HttpRequest.request(
_testFontUrl,
responseType: 'arraybuffer');
await ui.loadFontFromList(Uint8List.view(response.response),
fontFamily: 'Blehm');

// Verifies the font is loaded, and the cache is cleaned.
expect(_containsFontFamily('Blehm'), true);
expect(TextMeasurementService.rulerManager.rulers.length, 0);
});
});
}

Expand Down

0 comments on commit 988b8f1

Please sign in to comment.