Files
SpotiFLAC-Mobile/test/album_description_test.dart
T

146 lines
5.0 KiB
Dart

import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:spotiflac_android/l10n/l10n.dart';
import 'package:spotiflac_android/theme/mornye_theme.dart';
import 'package:spotiflac_android/utils/editorial_notes.dart';
import 'package:spotiflac_android/widgets/album_description.dart';
void main() {
test(
'editorial notes prefer full text and fall back to a usable summary',
() {
expect(
albumDescriptionFromMetadata({
'editorial_notes': {
'standard': '<p>Full notes.</p>',
'short': 'Short notes.',
},
}),
'<p>Full notes.</p>',
);
expect(
albumDescriptionFromMetadata({
'editorial_notes': {
'standard': '<p>&nbsp;</p>',
'short': 'Short notes.',
},
}),
'Short notes.',
);
expect(
albumDescriptionFromMetadata({'description': 'Plain notes.'}),
'Plain notes.',
);
expect(albumDescriptionFromMetadata({'editorial_notes': null}), isNull);
expect(albumDescriptionFromMetadata({'editorial_notes': 42}), isNull);
expect(
albumDescriptionFromMetadata({
'editorial_notes': {'standard': '<script>hidden</script>'},
}),
isNull,
);
},
);
for (final style in ['mornye-light', 'mornye-dark', 'material']) {
testWidgets('album description opens a formatted reading sheet ($style)', (
tester,
) async {
await tester.binding.setSurfaceSize(const Size(393, 700));
addTearDown(() => tester.binding.setSurfaceSize(null));
final mornye = style.startsWith('mornye');
await tester.pumpWidget(
ProviderScope(
child: MaterialApp(
theme: mornye
? MornyeTheme.build(
style.endsWith('light')
? Brightness.light
: Brightness.dark,
)
: ThemeData(),
localizationsDelegates: AppLocalizations.localizationsDelegates,
supportedLocales: AppLocalizations.supportedLocales,
home: Navigator(
onGenerateRoute: (_) => MaterialPageRoute<void>(
builder: (_) => Scaffold(
body: AlbumDescription(
title: 'Example Album',
description:
'A <i>new direction</i> &amp; a <b>bold sound</b>.\n\n'
'A second paragraph.\nOne line break remains.\n\n'
'${List.filled(12, '<p>The artists explore melodies and new ideas in these songs.</p>').join()}'
'<p>Final paragraph.</p><script>hidden script</script>',
),
),
),
),
),
),
);
await tester.pumpAndSettle();
final preview = tester.widget<Text>(
find.byWidgetPredicate(
(widget) => widget is Text && widget.textSpan != null,
),
);
expect(preview.maxLines, 2);
expect(
preview.textSpan!.toPlainText(),
contains('new direction & a bold sound.\n\n'),
);
expect(preview.textSpan!.toPlainText(), isNot(contains('hidden script')));
expect(
preview.textSpan!.toPlainText(),
contains('sound.\n\nA second paragraph.\nOne line break remains.\n\n'),
);
Iterable<TextSpan> spans(InlineSpan span) sync* {
if (span is TextSpan) {
yield span;
for (final child in span.children ?? <InlineSpan>[]) {
yield* spans(child);
}
}
}
expect(
spans(preview.textSpan!).any(
(span) =>
span.style?.fontStyle == FontStyle.italic &&
span.toPlainText() == 'new direction',
),
isTrue,
);
await tester.tap(find.text(mornye ? 'MORE' : 'More'));
await tester.pumpAndSettle();
expect(find.text('Example Album'), findsOneWidget);
expect(find.byType(SelectionArea), findsOneWidget);
expect(
ModalRoute.of(tester.element(find.byType(SelectionArea)))!.navigator,
tester.state<NavigatorState>(find.byType(Navigator).first),
);
expect(find.byTooltip('Close').hitTestable(), findsOneWidget);
await tester.drag(
find.byType(SingleChildScrollView),
const Offset(0, -600),
);
await tester.pumpAndSettle();
final scroll = tester.state<ScrollableState>(
find.descendant(
of: find.byType(SingleChildScrollView),
matching: find.byType(Scrollable),
),
);
expect(scroll.position.pixels, greaterThan(0));
expect(find.byTooltip('Close').hitTestable(), findsOneWidget);
await tester.tap(find.byTooltip('Close'));
await tester.pumpAndSettle();
expect(find.byType(SelectionArea), findsNothing);
expect(tester.takeException(), isNull);
});
}
}