feat: Add tests for Wolf3dGuiApp and refactor game data picker management

- Introduced unit tests for the Wolf3dGuiApp to ensure proper directory configuration and audio management.
- Refactored the GameDataPickerManager to streamline directory and file selection processes.
- Removed obsolete GameDataPickerManager and Wolf3dAppManager classes to simplify the architecture.
- Enhanced the Wolf3dFlutterEngine to improve game version handling during save loading.
- Updated existing tests to reflect changes in the game data management structure.
- Removed unnecessary dependencies and cleaned up the codebase for better maintainability.

Signed-off-by: Hans Kokx <hans.d.kokx@gmail.com>
This commit is contained in:
2026-03-24 14:35:20 +01:00
parent b980174905
commit ce4dd8d61d
18 changed files with 1919 additions and 810 deletions
@@ -2,7 +2,6 @@
library;
import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart';
import 'package:wolf_3d_dart/wolf_3d_data.dart';
import 'package:wolf_3d_dart/wolf_3d_data_types.dart';
import 'package:wolf_3d_dart/wolf_3d_engine.dart';
@@ -18,7 +17,6 @@ export 'audio/wolf3d_platform_audio.dart' show Wolf3dPlatformAudio;
export 'managers/game_app_lifecycle_manager.dart' show GameAppLifecycleManager;
export 'managers/game_data_directory_persistence.dart'
show DefaultGameDataDirectoryPersistence;
export 'managers/game_data_picker_manager.dart' show GameDataPickerManager;
export 'managers/game_display_manager.dart' show GameDisplayManager;
export 'managers/game_persistence_manager.dart' show GamePersistenceManager;
export 'managers/game_renderer_mode_manager.dart'
@@ -31,22 +29,19 @@ export 'managers/game_screen_input_manager.dart'
HostShortcutRegistry,
GameScreenInputManager,
isAltEnterShortcut;
export 'managers/wolf3d_app_manager.dart' show Wolf3dAppManager;
export 'screens/audio_gallery.dart' show AudioGallery;
export 'screens/debug_tools_screen.dart' show DebugToolsScreen;
export 'screens/game_screen.dart' show GameScreen;
export 'screens/no_game_data_screen.dart' show NoGameDataScreen;
export 'screens/sprite_gallery.dart' show SpriteGallery;
export 'screens/vga_gallery.dart' show VgaGallery;
export 'widgets/gallery_game_selector.dart'
show GalleryGameSelector, formatGalleryGameTitle;
export 'widgets/wolf3d_app.dart' show Wolf3dApp;
export 'widgets/wolf_menu_shell.dart' show WolfMenuShell;
/// Flutter-specific host facade built on top of [Wolf3dEngine].
///
/// This type keeps platform-neutral session/engine state in the Dart package
/// while owning Flutter-only concerns such as bundle loading and discovery.
/// while owning Flutter-only concerns such as platform discovery helpers.
class Wolf3dFlutterEngine extends Wolf3dEngine {
/// Creates an empty facade that must be initialized with [init].
Wolf3dFlutterEngine({
@@ -89,8 +84,9 @@ class Wolf3dFlutterEngine extends Wolf3dEngine {
/// used when available. [additionalDirectories] are scanned after the
/// primary directory and are not persisted.
///
/// This method merges bundled package data (when present) with discovered
/// external directories, deduplicating versions by [GameVersion].
/// This method scans only configured external directories, deduplicating
/// discovered versions by [GameVersion]. Shared package code does not bundle
/// or import game data on behalf of host applications.
Future<Wolf3dFlutterEngine> init({
String? directory,
Iterable<String>? additionalDirectories,
@@ -110,35 +106,6 @@ class Wolf3dFlutterEngine extends Wolf3dEngine {
await dataDirectoryPersistence.saveDataDirectory(requestedDirectory);
}
// Bundled assets let the GUI work out of the box on supported platforms.
final versionsToTry = [
(version: GameVersion.retail, path: 'retail'),
(version: GameVersion.shareware, path: 'shareware'),
];
for (final version in versionsToTry) {
try {
final ext = version.version.fileExtension;
final folder = 'packages/wolf_3d_assets/assets/${version.path}';
final data = WolfensteinLoader.loadFromBytes(
version: version.version,
vswap: await _tryLoad('$folder/VSWAP.$ext'),
mapHead: await _tryLoad('$folder/MAPHEAD.$ext'),
gameMaps: await _tryLoad('$folder/GAMEMAPS.$ext'),
vgaDict: await _tryLoad('$folder/VGADICT.$ext'),
vgaHead: await _tryLoad('$folder/VGAHEAD.$ext'),
vgaGraph: await _tryLoad('$folder/VGAGRAPH.$ext'),
audioHed: await _tryLoad('$folder/AUDIOHED.$ext'),
audioT: await _tryLoad('$folder/AUDIOT.$ext'),
);
availableGames.add(data);
} catch (e) {
debugPrint(e.toString());
}
}
// On non-web platforms, also scan local filesystem locations for
// user-supplied data folders so the host can pick up extra versions.
final Set<String> directoriesToScan = <String>{};
@@ -175,14 +142,4 @@ class Wolf3dFlutterEngine extends Wolf3dEngine {
return this;
}
/// Loads an asset from the Flutter bundle, returning `null` when absent.
Future<ByteData?> _tryLoad(String path) async {
try {
return await rootBundle.load(path);
} catch (e) {
debugPrint("Asset not found: $path");
return null;
}
}
}