99 lines
5.1 KiB
Dart
99 lines
5.1 KiB
Dart
import 'dart:io';
|
||
import 'dart:ui' as ui;
|
||
|
||
import 'package:flutter/material.dart';
|
||
import 'package:flutter/rendering.dart';
|
||
import 'package:flutter_test/flutter_test.dart';
|
||
import 'package:integration_test/integration_test.dart';
|
||
import 'package:jj_mkvmaker/app/app_controller.dart';
|
||
import 'package:jj_mkvmaker/app/i18n_controller.dart';
|
||
import 'package:jj_mkvmaker/l10n/tr.dart';
|
||
import 'package:jj_mkvmaker/platform/windows/desktop_storage_service.dart';
|
||
import 'package:jj_mkvmaker/platform/windows/process_media_tool.dart';
|
||
import 'package:jj_mkvmaker/services/platform_services.dart';
|
||
import 'package:jj_mkvmaker/ui/explorer_page.dart';
|
||
import 'package:jj_mkvmaker/ui/theme.dart';
|
||
import 'package:path/path.dart' as p;
|
||
|
||
import 'support/temp_dir.dart';
|
||
import '../test/support/test_explorer_device.dart';
|
||
|
||
/// 264 · 265 (관리자 지시 10/21): 폴더를 합쳐 옮긴 뒤 - 알림에 "n개는 원본에 남음 (건너뜀)" · 펼쳐 둔 원본 폴더를 다시 읽어
|
||
/// 옮겨진 파일은 보이지 않고 남은 것만 보인다. ko · en · ja × 960 · 1400 (두 창). 시험 폴더 안에서만 (실제 이동, 휴지통 쓰지 않음)
|
||
void main() {
|
||
late TestExplorerDevice device;
|
||
setUp(() => device = TestExplorerDevice());
|
||
IntegrationTestWidgetsFlutterBinding.ensureInitialized();
|
||
final out = Platform.environment['JJ_SHOT_DIR'] ?? '';
|
||
|
||
for (final lang in ['ko', 'en', 'ja']) {
|
||
for (final (w, h) in [(960, 600), (1400, 800)]) {
|
||
testWidgets('264 · 265 이동 뒤 $lang ${w}x$h', (t) async {
|
||
t.view.physicalSize = Size(w.toDouble(), h.toDouble());
|
||
t.view.devicePixelRatio = 1;
|
||
addTearDown(t.view.reset);
|
||
await t.runAsync(() => i18n.apply(lang, save: false));
|
||
addTearDown(() => i18n.apply('ko', save: false));
|
||
final tmp = testTempDir('jj_moveleft_');
|
||
final left = p.join(tmp.path, 'left'), right = p.join(tmp.path, 'right');
|
||
final d = p.join(left, 'D');
|
||
File(p.join(d, 'same.txt'))
|
||
..createSync(recursive: true)
|
||
..writeAsStringSync('old')
|
||
..setLastModifiedSync(DateTime(2026, 1, 1));
|
||
File(p.join(d, 'add.txt')).writeAsStringSync('a');
|
||
File(p.join(right, 'D', 'same.txt'))
|
||
..createSync(recursive: true)
|
||
..writeAsStringSync('NEWER');
|
||
final c = AppController(PlatformServices(mediaTool: ProcessMediaTool('x', 'y'), storage: DesktopStorageService()));
|
||
c.settings
|
||
..explorerPaths = [left, right]
|
||
..copyConflict = 'overwrite';
|
||
final root = p.rootPrefix(tmp.path);
|
||
device.volumes = () => [(root, root.replaceAll(RegExp(r'[\\/]+$'), ''))];
|
||
final shotKey = GlobalKey();
|
||
await t.pumpWidget(RepaintBoundary(
|
||
key: shotKey,
|
||
child: MaterialApp(theme: buildTheme(), debugShowCheckedModeBanner: false, home: ExplorerPage(device: device, c: c)),
|
||
));
|
||
Future<void> settle(bool Function() done, {int rounds = 150}) async {
|
||
for (var i = 0; i < rounds && !done(); i++) {
|
||
await t.runAsync(() => Future<void>.delayed(const Duration(milliseconds: 40)));
|
||
await t.pump();
|
||
}
|
||
await t.pump(const Duration(milliseconds: 300));
|
||
}
|
||
|
||
Future<void> shot(String name) async {
|
||
expect(t.takeException(), isNull, reason: '$name 넘침');
|
||
if (out.isEmpty) return;
|
||
final b = shotKey.currentContext!.findRenderObject()! as RenderRepaintBoundary;
|
||
final img = await t.runAsync(() => b.toImage());
|
||
final bytes = await t.runAsync(() => img!.toByteData(format: ui.ImageByteFormat.png));
|
||
Directory(out).createSync(recursive: true);
|
||
File(p.join(out, 'moveleft_${name}_${lang}_$w.png')).writeAsBytesSync(bytes!.buffer.asUint8List());
|
||
}
|
||
|
||
await settle(() => find.text('D').evaluate().length >= 2);
|
||
// 왼쪽 D 를 눌러 펼치고 (고른 것) 안의 add.txt 가 보이게
|
||
await t.tap(find.text('D').first);
|
||
await settle(() => find.text('add.txt').evaluate().isNotEmpty);
|
||
await shot('1_before');
|
||
await t.tap(find.text(tr('이동')).first);
|
||
await settle(() => find.widgetWithText(FilledButton, tr('이동')).evaluate().isNotEmpty);
|
||
await t.tap(find.widgetWithText(FilledButton, tr('이동')));
|
||
await settle(() => find.byType(LinearProgressIndicator).evaluate().isEmpty && find.byType(SnackBar).evaluate().isNotEmpty);
|
||
await settle(() => false, rounds: 10); // 알림이 다 올라오게
|
||
expect(File(p.join(right, 'D', 'add.txt')).existsSync(), isTrue);
|
||
expect(File(p.join(d, 'same.txt')).readAsStringSync(), 'old', reason: '받는 쪽이 더 새것이라 원본에 남음');
|
||
expect(find.textContaining(trf('{0}개는 원본에 남았습니다 (건너뜀).', [1])), findsOneWidget, reason: '264: 알림에');
|
||
expect(find.text('add.txt'), findsNothing, reason: '265: 원본 D 를 다시 읽음');
|
||
expect(find.text('same.txt'), findsOneWidget);
|
||
await shot('2_after');
|
||
ScaffoldMessenger.of(t.element(find.byType(ExplorerPage))).clearSnackBars();
|
||
await settle(() => false, rounds: 20);
|
||
});
|
||
}
|
||
}
|
||
}
|