| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197 |
- import 'package:cardash_launcher/data/models/app_entry.dart';
- import 'package:cardash_launcher/data/models/slot_type.dart';
- import 'package:cardash_launcher/data/models/system_status.dart';
- import 'package:cardash_launcher/data/repositories/settings_repository.dart';
- import 'package:cardash_launcher/data/services/native_bridge.dart';
- import 'package:cardash_launcher/features/home/launcher_controller.dart';
- import 'package:flutter_test/flutter_test.dart';
- import 'package:shared_preferences/shared_preferences.dart';
- class FakeLauncherPlatform implements LauncherPlatform {
- FakeLauncherPlatform(this.apps);
- final List<AppEntry> apps;
- @override
- Future<List<AppEntry>> listApps() async => apps;
- @override
- Future<void> launchApp({
- required String packageName,
- required String activityName,
- }) async {}
- @override
- Future<bool> isDefaultHome() async => true;
- @override
- Future<bool> requestDefaultHome() async => true;
- @override
- Future<SystemStatus> getStatus() async => const SystemStatus();
- @override
- Future<VolumeInfo> getVolume() async => const VolumeInfo();
- @override
- Future<void> setVolume(int index) async {}
- @override
- Future<bool> isMusicPlaying() async => false;
- @override
- Future<bool> sendMediaKey(String action) async => true;
- }
- List<AppEntry> _apps(int count) {
- return List.generate(
- count,
- (index) => AppEntry(
- packageName: 'com.example.app$index',
- activityName: 'com.example.app$index.Main',
- label: 'App $index',
- ),
- );
- }
- Future<LauncherController> _controller({
- int appCount = 20,
- FakeLauncherPlatform? platform,
- }) async {
- SharedPreferences.setMockInitialValues({});
- final prefs = await SharedPreferences.getInstance();
- final controller = LauncherController(
- platform ?? FakeLauncherPlatform(_apps(appCount)),
- SettingsRepository(prefs),
- );
- controller.initialize();
- return controller;
- }
- void main() {
- TestWidgetsFlutterBinding.ensureInitialized();
- test('parses the native system-app flag', () {
- final system = AppEntry.fromMap({
- 'package': 'com.example.system',
- 'activity': 'com.example.system.Main',
- 'label': 'System',
- 'system': true,
- });
- final user = AppEntry.fromMap({
- 'package': 'com.example.user',
- 'activity': 'com.example.user.Main',
- 'label': 'User',
- 'system': false,
- });
- expect(system.isSystemApp, isTrue);
- expect(user.isSystemApp, isFalse);
- });
- test('home buttons default to enabled and count the fixed buttons', () async {
- final controller = await _controller();
- addTearDown(controller.dispose);
- expect(controller.isSlotEnabled(SlotType.navigation), isTrue);
- expect(controller.isSlotEnabled(SlotType.music), isTrue);
- expect(controller.isSlotEnabled(SlotType.radio), isTrue);
- expect(controller.homeButtonCount, 4);
- expect(controller.pinnedApps, isEmpty);
- });
- test('disabling a slot hides it and keeps the assignment', () async {
- final controller = await _controller();
- addTearDown(controller.dispose);
- final app = _apps(1).first;
- await controller.assign(SlotType.navigation, app);
- expect(await controller.setSlotEnabled(SlotType.navigation, false), isNull);
- expect(controller.isSlotEnabled(SlotType.navigation), isFalse);
- expect(controller.homeButtonCount, 3);
- expect(controller.assignmentFor(SlotType.navigation)?.label, 'App 0');
- expect(await controller.setSlotEnabled(SlotType.navigation, true), isNull);
- expect(controller.homeButtonCount, 4);
- });
- test('pinned apps can be added once and removed again', () async {
- final controller = await _controller();
- addTearDown(controller.dispose);
- final apps = _apps(3);
- expect(await controller.addPinnedApp(apps[0]), isNull);
- expect(controller.pinnedApps.length, 1);
- expect(controller.homeButtonCount, 5);
- expect(await controller.addPinnedApp(apps[0]), contains('already'));
- await controller.removePinnedApp(apps[0].toAssignment());
- expect(controller.pinnedApps, isEmpty);
- expect(controller.homeButtonCount, 4);
- });
- test('the home screen stops at 16 buttons', () async {
- final controller = await _controller();
- addTearDown(controller.dispose);
- final apps = _apps(20);
- for (var index = 0; index < 12; index++) {
- expect(await controller.addPinnedApp(apps[index]), isNull);
- }
- expect(controller.homeButtonCount, 16);
- expect(await controller.addPinnedApp(apps[12]), contains('full'));
- expect(controller.pinnedApps.length, 12);
- await controller.removePinnedApp(apps[0].toAssignment());
- expect(controller.homeButtonCount, 15);
- expect(await controller.addPinnedApp(apps[12]), isNull);
- expect(controller.homeButtonCount, 16);
- });
- test('pinned labels and custom icons persist', () async {
- SharedPreferences.setMockInitialValues({});
- final prefs = await SharedPreferences.getInstance();
- final apps = _apps(3);
- final platform = FakeLauncherPlatform(apps);
- final first = LauncherController(platform, SettingsRepository(prefs));
- first.initialize();
- addTearDown(first.dispose);
- expect(await first.addPinnedApp(apps[0]), isNull);
- final pinned = first.pinnedApps.first;
- await first.renamePinnedApp(pinned, 'My shortcut');
- await first.setPinnedIcon(pinned, 'assets/icons/star.svg');
- final second = LauncherController(platform, SettingsRepository(prefs));
- second.initialize();
- addTearDown(second.dispose);
- expect(second.pinnedApps.length, 1);
- expect(second.pinnedApps.first.label, 'My shortcut');
- expect(second.pinnedApps.first.iconAsset, 'assets/icons/star.svg');
- });
- test('pinned apps and slot visibility survive a new controller', () async {
- SharedPreferences.setMockInitialValues({});
- final prefs = await SharedPreferences.getInstance();
- final platform = FakeLauncherPlatform(_apps(3));
- final settings = SettingsRepository(prefs);
- final first = LauncherController(platform, settings);
- first.initialize();
- addTearDown(first.dispose);
- await first.setSlotEnabled(SlotType.radio, false);
- expect(await first.addPinnedApp(_apps(1).first), isNull);
- final second = LauncherController(platform, SettingsRepository(prefs));
- second.initialize();
- addTearDown(second.dispose);
- expect(second.isSlotEnabled(SlotType.radio), isFalse);
- expect(second.pinnedApps.length, 1);
- expect(second.pinnedApps.first.label, 'App 0');
- expect(second.homeButtonCount, 4);
- });
- }
|