style: refactored searching files into Simfile class

This commit is contained in:
Orangerot 2025-01-07 06:38:34 +01:00
parent 685323adea
commit 9c229b94d0
4 changed files with 36 additions and 37 deletions

View file

@ -50,8 +50,8 @@ class GameOverStats extends StatelessWidget {
]),
TextButton(
onPressed: () {
Route route = MaterialPageRoute(
builder: (context) => Level(stepmaniaFolderPath: simfile.directoryPath));
Route route =
MaterialPageRoute(builder: (context) => Level(simfile));
Navigator.pushReplacement(context, route);
},
child: Text('Retry'))

View file

@ -9,8 +9,8 @@ import 'package:sense_the_rhythm/game_over_stats.dart';
import 'package:sense_the_rhythm/simfile.dart';
class Level extends StatefulWidget {
const Level({super.key, required this.stepmaniaFolderPath});
final String stepmaniaFolderPath;
const Level(this.simfile, {super.key});
final Simfile simfile;
@override
State<Level> createState() => _LevelState();
@ -25,7 +25,6 @@ class InputDirection {
class _LevelState extends State<Level> {
final player = AudioPlayer();
Simfile? simfile;
bool _isPlaying = true;
Duration? _duration;
Duration? _position;
@ -77,7 +76,7 @@ class _LevelState extends State<Level> {
player.onPlayerComplete.listen((void _) {
Route route = MaterialPageRoute(
builder: (context) => GameOverStats(
simfile: simfile!,
simfile: widget.simfile,
notes: notes,
));
Navigator.pushReplacement(context, route);
@ -131,10 +130,7 @@ class _LevelState extends State<Level> {
}
});
simfile = Simfile(widget.stepmaniaFolderPath);
simfile!.load();
simfile!.chartSimplest!.beats.forEach((time, noteData) {
widget.simfile.chartSimplest!.beats.forEach((time, noteData) {
int arrowIndex = noteData.indexOf('1');
if (arrowIndex < 0 || arrowIndex > 3) {
return;
@ -142,7 +138,7 @@ class _LevelState extends State<Level> {
notes.add(Note(time: time, direction: ArrowDirection.values[arrowIndex]));
});
player.play(DeviceFileSource(simfile!.audioPath!));
player.play(DeviceFileSource(widget.simfile.audioPath!));
}
@override
@ -192,7 +188,7 @@ class _LevelState extends State<Level> {
}
},
),
title: Text(widget.stepmaniaFolderPath.split('/').last),
title: Text(widget.simfile.tags['TITLE']!),
actions: [
IconButton(
icon: Icon(Icons.close),

View file

@ -5,6 +5,7 @@ import 'package:file_picker/file_picker.dart';
import 'package:flutter/material.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:sense_the_rhythm/esense_connect_dialog.dart';
import 'package:sense_the_rhythm/simfile.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'level.dart';
@ -18,7 +19,7 @@ class LevelSelection extends StatefulWidget {
class _LevelSelectionState extends State<LevelSelection> {
String? stepmaniaCoursesPath;
List<FileSystemEntity> stepmaniaCoursesFolders = [];
List<Simfile> stepmaniaCoursesFolders = [];
String eSenseDeviceName = '';
ESenseManager? eSenseManager;
@ -109,7 +110,8 @@ class _LevelSelectionState extends State<LevelSelection> {
prefs.getString('stepmania_courses');
if (stepmaniaCoursesPathSetting == null) return;
List<FileSystemEntity> stepmaniaCoursesFoldersFuture = await listFilesAndFolders(stepmaniaCoursesPathSetting);
List<Simfile> stepmaniaCoursesFoldersFuture =
await listFilesAndFolders(stepmaniaCoursesPathSetting);
setState(() {
stepmaniaCoursesPath = stepmaniaCoursesPathSetting;
@ -129,15 +131,18 @@ class _LevelSelectionState extends State<LevelSelection> {
}
}
Future<List<FileSystemEntity>> listFilesAndFolders(
String directoryPath) async {
Future<List<Simfile>> listFilesAndFolders(String directoryPath) async {
final directory = Directory(directoryPath);
try {
// List all files and folders in the directory
return directory
.listSync()
.where((entity) => FileSystemEntity.isDirectorySync(entity.path))
.toList();
.map((entity) {
Simfile simfile = Simfile(entity.path);
simfile.load();
return simfile;
}).toList();
} catch (e) {
print("Error reading directory: $e");
return [];
@ -155,10 +160,10 @@ class _LevelSelectionState extends State<LevelSelection> {
context: context,
builder: (BuildContext context) {
return ESenseConnectDialog(
deviceStatus: _deviceStatus,
connect: (String name) {
_connectToESense(name);
});
deviceStatus: _deviceStatus,
connect: (String name) {
_connectToESense(name);
});
},
),
icon: const Icon(Icons.bluetooth))
@ -176,26 +181,17 @@ class _LevelSelectionState extends State<LevelSelection> {
separatorBuilder: (BuildContext context, int index) =>
const Divider(),
itemBuilder: (context, index) {
String thumbnailPath = Directory(
stepmaniaCoursesFolders[index].path)
.listSync()
.firstWhere(
(file) => file.path.toLowerCase().endsWith('banner.png'),
orElse: () => File(''))
.path;
return ListTile(
leading: Image.file(File(thumbnailPath)),
leading: Image.file(
File(stepmaniaCoursesFolders[index].bannerPath!)),
trailing: Icon(Icons.play_arrow),
title:
Text(stepmaniaCoursesFolders[index].path.split('/').last),
title: Text(stepmaniaCoursesFolders[index].tags["TITLE"]!),
subtitle: Text('3:45'),
onTap: () => Navigator.push(
context,
MaterialPageRoute(
builder: (BuildContext context) => Level(
stepmaniaFolderPath:
stepmaniaCoursesFolders[index].path,
))),
builder: (BuildContext context) =>
Level(stepmaniaCoursesFolders[index]))),
);
},
);

View file

@ -124,7 +124,8 @@ class Simfile {
simfilePath = Directory(directoryPath)
.listSync()
.firstWhere((entity) => entity.path.endsWith('.sm'),
orElse: () => File('')).path;
orElse: () => File(''))
.path;
audioPath = Directory(directoryPath)
.listSync()
@ -132,6 +133,12 @@ class Simfile {
orElse: () => File(''))
.path;
bannerPath = Directory(directoryPath)
.listSync()
.firstWhere((file) => file.path.toLowerCase().endsWith('banner.png'),
orElse: () => File(''))
.path;
lines = File(simfilePath!).readAsStringSync();
RegExp commentsRegExp = RegExp(r'//.*$');