193 lines
6.7 KiB
Dart
193 lines
6.7 KiB
Dart
// Author: fruit.com.cn
|
|
|
|
import 'package:flutter/material.dart';
|
|
import 'package:flutter_test/flutter_test.dart';
|
|
import 'package:fruitshorts/core/data/models/category_ranking.dart';
|
|
import 'package:fruitshorts/core/data/models/content_category.dart';
|
|
import 'package:fruitshorts/core/data/models/drama.dart';
|
|
import 'package:fruitshorts/core/data/models/page_result.dart';
|
|
import 'package:fruitshorts/core/data/services/category_controller.dart';
|
|
import 'package:fruitshorts/l10n/app_localizations.dart';
|
|
import 'package:fruitshorts/pages/recommend/recommend_discover_page.dart';
|
|
import 'package:provider/provider.dart';
|
|
|
|
import '../support/fake_catalog.dart';
|
|
import '../support/fake_category.dart';
|
|
|
|
void main() {
|
|
testWidgets('should_keep_refresh_indicator_below_category_nav_when_pulling', (
|
|
tester,
|
|
) async {
|
|
tester.view.physicalSize = const Size(390, 844);
|
|
tester.view.devicePixelRatio = 1;
|
|
addTearDown(tester.view.resetPhysicalSize);
|
|
addTearDown(tester.view.resetDevicePixelRatio);
|
|
|
|
final controller = CategoryController(
|
|
FakeCategoryRepository(catalog: FakeCatalogRepository()),
|
|
);
|
|
final dramas = [for (var index = 1; index <= 12; index++) _drama('$index')];
|
|
controller.categories = const [ContentCategory(id: '7', name: 'Romance')];
|
|
controller.dramaPageLoader =
|
|
(categoryId, {pageIndex = 1, pageSize = 20}) async =>
|
|
PageResult(total: dramas.length, list: dramas);
|
|
addTearDown(controller.dispose);
|
|
|
|
await tester.pumpWidget(
|
|
MaterialApp(
|
|
locale: const Locale('en'),
|
|
localizationsDelegates: AppLocalizations.localizationsDelegates,
|
|
supportedLocales: AppLocalizations.supportedLocales,
|
|
home: Scaffold(
|
|
body: ChangeNotifierProvider<CategoryController>.value(
|
|
value: controller,
|
|
child: const RecommendDiscoverPage(active: true, onSearch: _noop),
|
|
),
|
|
),
|
|
),
|
|
);
|
|
await tester.pumpAndSettle();
|
|
|
|
final nav = tester.getRect(find.byKey(const Key('recommend-tab-7')));
|
|
final scroll = find.byKey(const PageStorageKey<String>('recommend-feed-7'));
|
|
final scrollable = tester.state<ScrollableState>(
|
|
find.descendant(of: scroll, matching: find.byType(Scrollable)).first,
|
|
);
|
|
expect(scrollable.position.pixels, 0);
|
|
final scrollRect = tester.getRect(scroll);
|
|
final gesture = await tester.startGesture(
|
|
Offset(scrollRect.center.dx, scrollRect.top + 120),
|
|
);
|
|
await gesture.moveBy(const Offset(0, 160));
|
|
await tester.pump();
|
|
|
|
final indicator = find.byKey(const Key('pull-refresh-indicator'));
|
|
expect(indicator, findsOneWidget);
|
|
expect(tester.getRect(indicator).top, greaterThanOrEqualTo(nav.bottom));
|
|
|
|
await gesture.up();
|
|
await tester.pumpAndSettle();
|
|
});
|
|
|
|
testWidgets('should_center_empty_state_when_category_has_no_dramas', (
|
|
tester,
|
|
) async {
|
|
tester.view.physicalSize = const Size(390, 844);
|
|
tester.view.devicePixelRatio = 1;
|
|
addTearDown(tester.view.resetPhysicalSize);
|
|
addTearDown(tester.view.resetDevicePixelRatio);
|
|
|
|
final controller = CategoryController(
|
|
FakeCategoryRepository(catalog: FakeCatalogRepository()),
|
|
);
|
|
controller.categories = const [ContentCategory(id: '7', name: 'Romance')];
|
|
controller.dramaPageLoader =
|
|
(categoryId, {pageIndex = 1, pageSize = 20}) async =>
|
|
const PageResult<Drama>();
|
|
addTearDown(controller.dispose);
|
|
|
|
await tester.pumpWidget(
|
|
MaterialApp(
|
|
locale: const Locale('zh'),
|
|
localizationsDelegates: AppLocalizations.localizationsDelegates,
|
|
supportedLocales: AppLocalizations.supportedLocales,
|
|
home: ChangeNotifierProvider<CategoryController>.value(
|
|
value: controller,
|
|
child: const RecommendDiscoverPage(active: true, onSearch: _noop),
|
|
),
|
|
),
|
|
);
|
|
await tester.pump();
|
|
await tester.pump();
|
|
await tester.pump(const Duration(milliseconds: 1));
|
|
|
|
expect(find.text('暂无剧目'), findsOneWidget);
|
|
expect(find.text('暂无剧目。'), findsNothing);
|
|
|
|
final content = tester.getRect(
|
|
find.byKey(const Key('empty-state-content')),
|
|
);
|
|
final icon = tester.getRect(find.byKey(const Key('empty-state-icon')));
|
|
final title = tester.getRect(find.byKey(const Key('empty-state-title')));
|
|
final viewport = tester.view.physicalSize / tester.view.devicePixelRatio;
|
|
expect(content.center.dx, closeTo(viewport.width / 2, 1.0));
|
|
expect(content.center.dy, closeTo(viewport.height / 2, 1.0));
|
|
expect(icon.center.dx, closeTo(title.center.dx, 0.1));
|
|
expect(title.top - icon.bottom, closeTo(12, 0.1));
|
|
});
|
|
|
|
testWidgets('should_render_ranking_layout_when_category_is_ranking', (
|
|
tester,
|
|
) async {
|
|
final controller = CategoryController(
|
|
FakeCategoryRepository(catalog: FakeCatalogRepository()),
|
|
);
|
|
controller.categories = const [
|
|
ContentCategory(
|
|
id: 'ranking',
|
|
name: '推荐榜',
|
|
layoutType: ContentCategory.rankingLayout,
|
|
),
|
|
];
|
|
var dramaLoads = 0;
|
|
var rankingLoads = 0;
|
|
controller.dramaPageLoader =
|
|
(categoryId, {pageIndex = 1, pageSize = 20}) async {
|
|
dramaLoads++;
|
|
return const PageResult<Drama>();
|
|
};
|
|
controller.rankingLoader = (categoryId) async {
|
|
rankingLoads++;
|
|
return CategoryRanking(
|
|
id: categoryId,
|
|
code: 'RECOMMEND_RANKING',
|
|
revision: '2',
|
|
entries: [
|
|
for (var rank = 1; rank <= 4; rank++)
|
|
CategoryRankingEntry(rank: rank, drama: _drama('$rank')),
|
|
],
|
|
);
|
|
};
|
|
addTearDown(controller.dispose);
|
|
|
|
await tester.pumpWidget(
|
|
MaterialApp(
|
|
locale: const Locale('zh'),
|
|
localizationsDelegates: AppLocalizations.localizationsDelegates,
|
|
supportedLocales: AppLocalizations.supportedLocales,
|
|
home: ChangeNotifierProvider<CategoryController>.value(
|
|
value: controller,
|
|
child: const RecommendDiscoverPage(active: true, onSearch: _noop),
|
|
),
|
|
),
|
|
);
|
|
await tester.pumpAndSettle();
|
|
|
|
expect(rankingLoads, 1);
|
|
expect(dramaLoads, 0);
|
|
expect(find.byKey(const Key('ranking-top-1')), findsOneWidget);
|
|
expect(find.byKey(const Key('ranking-row-3')), findsOneWidget);
|
|
final navUnderline = tester.getRect(
|
|
find.byKey(const Key('recommend-tab-ranking-underline')),
|
|
);
|
|
final firstRow = tester.getRect(find.byKey(const Key('ranking-row-0')));
|
|
final gap = firstRow.top - navUnderline.bottom;
|
|
expect(gap, greaterThan(10));
|
|
expect(gap, lessThan(26));
|
|
expect(
|
|
find.byKey(const Key('recommend-category-grid-ranking')),
|
|
findsNothing,
|
|
);
|
|
});
|
|
}
|
|
|
|
void _noop() {}
|
|
|
|
Drama _drama(String id) => Drama(
|
|
id: id,
|
|
title: 'Rank $id',
|
|
synopsis: '',
|
|
posterUrl: '',
|
|
viewCount: int.parse(id) * 10,
|
|
);
|