Files

61 lines
1.9 KiB
Dart

// Author: fruit.com.cn
// 为界面视觉复核加载项目字体并导出测试渲染图。
import 'dart:io';
import 'dart:ui' as ui;
import 'package:flutter/rendering.dart';
import 'package:flutter/services.dart';
import 'package:flutter_test/flutter_test.dart';
const double _capturePixelRatio = 3;
/// 为可选截图使用实际字体,不影响普通测试执行。
Future<void> loadCaptureFonts(WidgetTester tester) async {
await tester.runAsync(() async {
final fonts = {
'Outfit': [
'Outfit-Regular.ttf',
'Outfit-SemiBold.ttf',
'Outfit-Bold.ttf',
],
'PlusJakartaSans': [
'PlusJakartaSans-Regular.ttf',
'PlusJakartaSans-Medium.ttf',
'PlusJakartaSans-SemiBold.ttf',
'PlusJakartaSans-Bold.ttf',
],
// 测试默认字体仅作占位,截图使用项目正文字体替换。
'Ahem': ['PlusJakartaSans-Regular.ttf'],
};
for (final family in fonts.entries) {
final loader = FontLoader(family.key);
for (final asset in family.value) {
loader.addFont(rootBundle.load('assets/fonts/$asset'));
}
await loader.load();
}
final icons = FontLoader('MaterialIcons');
icons.addFont(rootBundle.load('fonts/MaterialIcons-Regular.otf'));
await icons.load();
});
}
/// 导出指定边界的渲染结果,图片为测试产物而非界面资源。
Future<void> saveWidgetCapture(
WidgetTester tester,
Key boundaryKey,
String path,
) async {
final boundary = tester.renderObject<RenderRepaintBoundary>(
find.byKey(boundaryKey),
);
await tester.runAsync(() async {
final image = await boundary.toImage(pixelRatio: _capturePixelRatio);
final bytes = await image.toByteData(format: ui.ImageByteFormat.png);
if (bytes == null) throw StateError('Screenshot encoding failed');
await File(path).writeAsBytes(bytes.buffer.asUint8List());
image.dispose();
});
}