Show whether the app is using Impeller or Skia in the performance page (#6771)
diff --git a/packages/devtools_app/integration_test/test/offline/perfetto_test.dart b/packages/devtools_app/integration_test/test/offline/perfetto_test.dart index cce652b..5ded74e 100644 --- a/packages/devtools_app/integration_test/test/offline/perfetto_test.dart +++ b/packages/devtools_app/integration_test/test/offline/perfetto_test.dart
@@ -9,6 +9,9 @@ import 'package:flutter_test/flutter_test.dart'; import 'package:integration_test/integration_test.dart'; +// To run: +// dart run integration_test/run_tests.dart --target=integration_test/test/offline/perfetto_test.dart + void main() { final binding = IntegrationTestWidgetsFlutterBinding.ensureInitialized();
diff --git a/packages/devtools_app/lib/src/screens/performance/panes/flutter_frames/flutter_frames_chart.dart b/packages/devtools_app/lib/src/screens/performance/panes/flutter_frames/flutter_frames_chart.dart index f293f17..c801532 100644 --- a/packages/devtools_app/lib/src/screens/performance/panes/flutter_frames/flutter_frames_chart.dart +++ b/packages/devtools_app/lib/src/screens/performance/panes/flutter_frames/flutter_frames_chart.dart
@@ -33,12 +33,15 @@ this.framesController, { super.key, required this.offlineMode, + required this.impellerEnabled, }); final FlutterFramesController framesController; final bool offlineMode; + final bool impellerEnabled; + @override Widget build(BuildContext context) { return MultiValueListenableBuilder( @@ -57,6 +60,7 @@ displayRefreshRate: displayRefreshRate, isVisible: showChart, offlineMode: offlineMode, + impellerEnabled: impellerEnabled, ); }, ); @@ -70,6 +74,7 @@ required this.displayRefreshRate, required this.isVisible, required this.offlineMode, + required this.impellerEnabled, }); final FlutterFramesController framesController; @@ -82,6 +87,8 @@ final bool offlineMode; + final bool impellerEnabled; + static double get frameNumberSectionHeight => scaleByFontFactor(20.0); static double get frameChartScrollbarOffset => defaultScrollBarOffset; @@ -151,6 +158,7 @@ frames: widget.frames, displayRefreshRate: widget.displayRefreshRate, constraints: constraints, + impellerEnabled: widget.impellerEnabled, ); }, ), @@ -165,6 +173,7 @@ frames: widget.frames, displayRefreshRate: widget.displayRefreshRate, offlineMode: widget.offlineMode, + impellerEnabled: widget.impellerEnabled, ), ), ], @@ -181,6 +190,7 @@ required this.frames, required this.displayRefreshRate, required this.constraints, + required this.impellerEnabled, }); final FlutterFramesController framesController; @@ -191,6 +201,8 @@ final BoxConstraints constraints; + final bool impellerEnabled; + @override State<FramesChart> createState() => _FramesChartState(); } @@ -332,6 +344,14 @@ child: chart, ), fpsLinePainter, + Positioned( + right: denseSpacing, + top: densePadding, + child: Text( + 'Engine: ${widget.impellerEnabled ? 'Impeller' : 'Skia'}', + style: themeData.subtleChartTextStyle, + ), + ), ], ); } @@ -345,6 +365,7 @@ required this.frames, required this.displayRefreshRate, required this.offlineMode, + required this.impellerEnabled, }); static const _pauseTooltip = 'Pause Flutter frame recording'; @@ -359,6 +380,8 @@ final bool offlineMode; + final bool impellerEnabled; + @override Widget build(BuildContext context) { return Column( @@ -387,10 +410,11 @@ const LegendEntry('Frame Time (UI)', mainUiColor), const LegendEntry('Frame Time (Raster)', mainRasterColor), const LegendEntry('Jank (slow frame)', uiJankColor), - LegendEntry( - 'Shader Compilation', - shaderCompilationColor.background, - ), + if (!impellerEnabled) + LegendEntry( + 'Shader Compilation', + shaderCompilationColor.background, + ), ], ), AverageFPS(
diff --git a/packages/devtools_app/lib/src/screens/performance/performance_controller.dart b/packages/devtools_app/lib/src/screens/performance/performance_controller.dart index 5610586..cdd59de 100644 --- a/packages/devtools_app/lib/src/screens/performance/performance_controller.dart +++ b/packages/devtools_app/lib/src/screens/performance/performance_controller.dart
@@ -100,7 +100,7 @@ PerformanceData? offlinePerformanceData; bool get impellerEnabled => _impellerEnabled; - late final bool _impellerEnabled; + bool _impellerEnabled = false; final _initialized = Completer<void>();
diff --git a/packages/devtools_app/lib/src/screens/performance/performance_screen.dart b/packages/devtools_app/lib/src/screens/performance/performance_screen.dart index eed8a83..10a12c9 100644 --- a/packages/devtools_app/lib/src/screens/performance/performance_screen.dart +++ b/packages/devtools_app/lib/src/screens/performance/performance_screen.dart
@@ -126,6 +126,7 @@ FlutterFramesChart( controller.flutterFramesController, offlineMode: offlineMode, + impellerEnabled: controller.impellerEnabled, ), const Expanded(child: TabbedPerformanceView()), ],
diff --git a/packages/devtools_app/release_notes/NEXT_RELEASE_NOTES.md b/packages/devtools_app/release_notes/NEXT_RELEASE_NOTES.md index 7839d24..12cdc79 100644 --- a/packages/devtools_app/release_notes/NEXT_RELEASE_NOTES.md +++ b/packages/devtools_app/release_notes/NEXT_RELEASE_NOTES.md
@@ -21,6 +21,9 @@ ## Performance updates +* Add an indicator of the rendering engine to the Flutter Frames chart. - +[#6771](https://github.com/flutter/devtools/pull/6771) + * Improve messaging when we do not have analysis data available for a Flutter frame. - [#6768](https://github.com/flutter/devtools/pull/6768)
diff --git a/packages/devtools_app/release_notes/images/flutter_frames_engine_text.png b/packages/devtools_app/release_notes/images/flutter_frames_engine_text.png new file mode 100644 index 0000000..550a5ed --- /dev/null +++ b/packages/devtools_app/release_notes/images/flutter_frames_engine_text.png Binary files differ
diff --git a/packages/devtools_app/test/performance/flutter_frames/flutter_frames_chart_test.dart b/packages/devtools_app/test/performance/flutter_frames/flutter_frames_chart_test.dart index a47b835..6d81bd0 100644 --- a/packages/devtools_app/test/performance/flutter_frames/flutter_frames_chart_test.dart +++ b/packages/devtools_app/test/performance/flutter_frames/flutter_frames_chart_test.dart
@@ -20,12 +20,14 @@ Future<void> pumpChart( WidgetTester tester, { bool offlineMode = false, + bool impellerEnabled = false, }) async { await tester.pumpWidget( wrap( FlutterFramesChart( framesController, offlineMode: offlineMode, + impellerEnabled: impellerEnabled, ), ), ); @@ -70,6 +72,7 @@ expect(find.byType(Legend), findsOneWidget); expect(find.byType(AverageFPS), findsOneWidget); expect(find.byType(FlutterFramesChartItem), findsNothing); + expect(find.textContaining('Engine: Skia'), findsOneWidget); }); testWidgets( @@ -86,6 +89,7 @@ expect(find.byType(Legend), findsNothing); expect(find.byType(AverageFPS), findsNothing); expect(find.byType(FlutterFramesChartItem), findsNothing); + expect(find.textContaining('Engine:'), findsNothing); }, ); @@ -100,6 +104,7 @@ expect(find.byType(Legend), findsOneWidget); expect(find.byType(AverageFPS), findsOneWidget); expect(find.byType(FlutterFramesChartItem), findsNWidgets(2)); + expect(find.textContaining('Engine: Skia'), findsOneWidget); }); testWidgets('builds in offline mode', (WidgetTester tester) async { @@ -110,6 +115,18 @@ expect(find.byType(PauseResumeButtonGroup), findsNothing); expect(find.byType(Legend), findsOneWidget); expect(find.byType(AverageFPS), findsOneWidget); + expect(find.textContaining('Engine: Skia'), findsOneWidget); + }); + + testWidgets('builds with impeller enabled', (WidgetTester tester) async { + framesController.clearData(); + await pumpChart(tester, impellerEnabled: true); + expect(find.byType(FramesChart), findsOneWidget); + expect(find.byType(FramesChartControls), findsOneWidget); + expect(find.byType(PauseResumeButtonGroup), findsOneWidget); + expect(find.byType(Legend), findsOneWidget); + expect(find.byType(AverageFPS), findsOneWidget); + expect(find.textContaining('Engine: Impeller'), findsOneWidget); }); group('starting scroll position', () {