Skip to content

Commit d4cf2a1

Browse files
Add link to view release notes from About dialog (#4848)
1 parent 2413208 commit d4cf2a1

File tree

4 files changed

+51
-27
lines changed

4 files changed

+51
-27
lines changed

packages/devtools_app/lib/src/app.dart

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -330,10 +330,12 @@ class DevToolsAppState extends State<DevToolsApp> with AutoDisposeMixin {
330330
Provider<HoverCardController>.value(
331331
value: hoverCardController,
332332
),
333+
Provider<ReleaseNotesController>.value(
334+
value: releaseNotesController,
335+
),
333336
],
334337
child: NotificationsView(
335338
child: ReleaseNotesViewer(
336-
releaseNotesController: releaseNotesController,
337339
child: child,
338340
),
339341
),

packages/devtools_app/lib/src/framework/about_dialog.dart

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,15 +5,21 @@
55
import 'dart:async';
66

77
import 'package:flutter/material.dart';
8+
import 'package:provider/provider.dart';
89

910
import '../../devtools.dart' as devtools;
1011
import '../analytics/constants.dart' as analytics_constants;
1112
import '../shared/common_widgets.dart';
1213
import '../shared/dialogs.dart';
1314
import '../shared/globals.dart';
1415
import '../shared/theme.dart';
16+
import 'release_notes/release_notes.dart';
1517

1618
class DevToolsAboutDialog extends StatelessWidget {
19+
const DevToolsAboutDialog(this.releaseNotesController);
20+
21+
final ReleaseNotesController releaseNotesController;
22+
1723
@override
1824
Widget build(BuildContext context) {
1925
final theme = Theme.of(context);
@@ -23,7 +29,20 @@ class DevToolsAboutDialog extends StatelessWidget {
2329
mainAxisSize: MainAxisSize.min,
2430
crossAxisAlignment: CrossAxisAlignment.start,
2531
children: [
26-
const SelectableText('DevTools version ${devtools.version}'),
32+
Row(
33+
children: [
34+
const SelectableText('DevTools version ${devtools.version}'),
35+
const Text(' - '),
36+
InkWell(
37+
child: Text(
38+
'release notes',
39+
style: theme.linkTextStyle,
40+
),
41+
onTap: () =>
42+
releaseNotesController.toggleReleaseNotesVisible(true),
43+
),
44+
],
45+
),
2746
const SizedBox(height: defaultSpacing),
2847
...dialogSubHeader(theme, 'Feedback'),
2948
Wrap(
@@ -88,14 +107,15 @@ class _DiscordLink extends StatelessWidget {
88107
class OpenAboutAction extends StatelessWidget {
89108
@override
90109
Widget build(BuildContext context) {
110+
final releaseNotesController = Provider.of<ReleaseNotesController>(context);
91111
return DevToolsTooltip(
92112
message: 'About DevTools',
93113
child: InkWell(
94114
onTap: () async {
95115
unawaited(
96116
showDialog(
97117
context: context,
98-
builder: (context) => DevToolsAboutDialog(),
118+
builder: (context) => DevToolsAboutDialog(releaseNotesController),
99119
),
100120
);
101121
},

packages/devtools_app/lib/src/framework/release_notes/release_notes.dart

Lines changed: 23 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import 'package:flutter/foundation.dart';
1010
import 'package:flutter/material.dart';
1111
import 'package:flutter_markdown/flutter_markdown.dart';
1212
import 'package:http/http.dart' as http;
13+
import 'package:provider/provider.dart';
1314

1415
import '../../../devtools.dart' as devtools;
1516
import '../../config_specific/launch_url/launch_url.dart';
@@ -24,12 +25,9 @@ const debugTestReleaseNotes = false;
2425
class ReleaseNotesViewer extends StatefulWidget {
2526
const ReleaseNotesViewer({
2627
Key? key,
27-
required this.releaseNotesController,
2828
required this.child,
2929
}) : super(key: key);
3030

31-
final ReleaseNotesController releaseNotesController;
32-
3331
final Widget? child;
3432

3533
@override
@@ -50,20 +48,23 @@ class _ReleaseNotesViewerState extends State<ReleaseNotesViewer>
5048

5149
late bool isVisible;
5250

51+
late ReleaseNotesController releaseNotesController;
52+
5353
@override
54-
void initState() {
55-
super.initState();
56-
isVisible = widget.releaseNotesController.releaseNotesVisible.value;
57-
markdownData = widget.releaseNotesController.releaseNotesMarkdown.value;
54+
void didChangeDependencies() {
55+
super.didChangeDependencies();
56+
releaseNotesController = Provider.of<ReleaseNotesController>(context);
57+
58+
isVisible = releaseNotesController.releaseNotesVisible.value;
59+
markdownData = releaseNotesController.releaseNotesMarkdown.value;
5860

5961
visibilityController = longAnimationController(this);
6062
visibilityAnimation =
6163
Tween<double>(begin: 1.0, end: 0).animate(visibilityController);
6264

63-
addAutoDisposeListener(widget.releaseNotesController.releaseNotesVisible,
64-
() {
65+
addAutoDisposeListener(releaseNotesController.releaseNotesVisible, () {
6566
setState(() {
66-
isVisible = widget.releaseNotesController.releaseNotesVisible.value;
67+
isVisible = releaseNotesController.releaseNotesVisible.value;
6768
if (isVisible) {
6869
visibilityController.forward();
6970
} else {
@@ -72,11 +73,10 @@ class _ReleaseNotesViewerState extends State<ReleaseNotesViewer>
7273
});
7374
});
7475

75-
markdownData = widget.releaseNotesController.releaseNotesMarkdown.value;
76-
addAutoDisposeListener(widget.releaseNotesController.releaseNotesMarkdown,
77-
() {
76+
markdownData = releaseNotesController.releaseNotesMarkdown.value;
77+
addAutoDisposeListener(releaseNotesController.releaseNotesMarkdown, () {
7878
setState(() {
79-
markdownData = widget.releaseNotesController.releaseNotesMarkdown.value;
79+
markdownData = releaseNotesController.releaseNotesMarkdown.value;
8080
});
8181
});
8282
}
@@ -96,7 +96,7 @@ class _ReleaseNotesViewerState extends State<ReleaseNotesViewer>
9696
children: [
9797
if (child != null) child,
9898
ReleaseNotes(
99-
releaseNotesController: widget.releaseNotesController,
99+
releaseNotesController: releaseNotesController,
100100
visibilityAnimation: visibilityAnimation,
101101
markdownData: markdownData,
102102
width: width,
@@ -197,19 +197,19 @@ class ReleaseNotesController {
197197
final _releaseNotesVisible = ValueNotifier<bool>(false);
198198

199199
void _init() {
200-
if (server.isDevToolsServerAvailable) {
200+
if (debugTestReleaseNotes || server.isDevToolsServerAvailable) {
201201
_maybeFetchReleaseNotes();
202202
}
203203
}
204204

205205
void _maybeFetchReleaseNotes() async {
206-
final lastReleaseNotesShownVersion =
207-
await server.getLastShownReleaseNotesVersion();
208-
SemanticVersion previousVersion;
209-
if (debugTestReleaseNotes || lastReleaseNotesShownVersion.isEmpty) {
210-
previousVersion = SemanticVersion();
211-
} else {
212-
previousVersion = SemanticVersion.parse(lastReleaseNotesShownVersion);
206+
SemanticVersion previousVersion = SemanticVersion();
207+
if (server.isDevToolsServerAvailable) {
208+
final lastReleaseNotesShownVersion =
209+
await server.getLastShownReleaseNotesVersion();
210+
if (lastReleaseNotesShownVersion.isNotEmpty) {
211+
previousVersion = SemanticVersion.parse(lastReleaseNotesShownVersion);
212+
}
213213
}
214214
// Parse the current version instead of using [devtools.version] directly to
215215
// strip off any build metadata (any characters following a '+' character).

packages/devtools_app/test/shared/about_dialog_test.dart

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import 'package:devtools_app/src/config_specific/ide_theme/ide_theme.dart';
77
import 'package:devtools_app/src/extension_points/extensions_base.dart';
88
import 'package:devtools_app/src/extension_points/extensions_external.dart';
99
import 'package:devtools_app/src/framework/about_dialog.dart';
10+
import 'package:devtools_app/src/framework/release_notes/release_notes.dart';
1011
import 'package:devtools_app/src/service/service_manager.dart';
1112
import 'package:devtools_app/src/shared/globals.dart';
1213
import 'package:devtools_test/devtools_test.dart';
@@ -18,7 +19,7 @@ void main() {
1819

1920
group('About Dialog', () {
2021
setUp(() {
21-
aboutDialog = DevToolsAboutDialog();
22+
aboutDialog = DevToolsAboutDialog(ReleaseNotesController());
2223
final fakeServiceManager = FakeServiceManager();
2324
when(fakeServiceManager.vm.version).thenReturn('1.9.1');
2425
mockConnectedApp(
@@ -41,6 +42,7 @@ void main() {
4142
await tester.pumpWidget(wrap(aboutDialog));
4243
expect(find.text('About DevTools'), findsOneWidget);
4344
expect(findSubstring(aboutDialog, devtools.version), findsOneWidget);
45+
expect(find.text('release notes'), findsOneWidget);
4446
});
4547

4648
testWidgets('Feedback section', (WidgetTester tester) async {

0 commit comments

Comments
 (0)