@@ -33,72 +33,86 @@ std::unordered_map<std::string, std::string> mGameList = {
3333 { " 9bef1128717f958171a4afac3ed78ee2bb4e86ce" , " Super Mario 64 (US)" },
3434};
3535
36- bool GameExtractor::SelectGameFromUI () {
37- std::vector<std::string> roms;
38- GetRoms (roms);
39-
40- bool foundGame = false ;
41-
36+ bool GameExtractor::RunStandalone (std::string rom) {
4237 // Store both path and already-read data
4338 std::string romPath;
4439 std::vector<uint8_t > romData;
4540
46- // Auto detect first baserom with valid hash
47- for (const auto & rom : roms) {
48- if (!std::filesystem::exists (rom))
49- continue ;
41+ if (!std::filesystem::exists (rom)) {
42+ return false ;
43+ }
5044
51- std::ifstream inFile (rom, std::ios::binary);
52- if (!inFile.is_open ()) {
53- SPDLOG_INFO (" Failed to open ROM at path: {}, continuing" , rom);
54- continue ;
55- }
45+ std::ifstream inFile (rom, std::ios::binary);
46+ if (!inFile.is_open ()) {
47+ SPDLOG_INFO (" Failed to open ROM at path: {}, continuing" , rom);
48+ return false ;
49+ }
5650
57- inFile.seekg (0 , std::ios::end);
58- size_t fileSize = inFile.tellg ();
59- inFile.seekg (0 , std::ios::beg);
51+ inFile.seekg (0 , std::ios::end);
52+ size_t fileSize = inFile.tellg ();
53+ inFile.seekg (0 , std::ios::beg);
6054
61- std::vector<uint8_t > data (fileSize);
62- if (!inFile.read (reinterpret_cast <char *>(data.data ()), fileSize)) {
63- SPDLOG_INFO (" Failed to read ROM at path: {}, continuing" , rom);
64- continue ;
65- }
55+ std::vector<uint8_t > data (fileSize);
56+ if (!inFile.read (reinterpret_cast <char *>(data.data ()), fileSize)) {
57+ SPDLOG_INFO (" Failed to read ROM at path: {}, continuing" , rom);
58+ return false ;
59+ }
6660
67- inFile.close ();
68- std::string hash = Companion::CalculateHash (data);
61+ inFile.close ();
62+ std::string hash = Companion::CalculateHash (data);
6963
70- if (mGameList .find (hash) != mGameList .end ()) {
71- romPath = rom;
72- romData = std::move (data);
73- foundGame = true ;
74- break ;
75- }
64+ if (mGameList .find (hash) != mGameList .end ()) {
65+ romPath = rom;
66+ romData = std::move (data);
7667 }
7768
78- #if !defined(__IOS__) && !defined(__ANDROID__) && !defined(__SWITCH__)
79- // Desktop: fallback to file dialogue if no baserom found
80- if (!foundGame) {
81- if (!pfd::settings::available ()) {
82- SPDLOG_ERROR (" portable-file-dialogs is not available on this system." );
69+ // Load file if it is not already open
70+ if (romData.empty ()) {
71+ std::ifstream inFile (romPath, std::ios::binary);
72+ if (!inFile.is_open ()) {
8373 return false ;
8474 }
8575
86- auto selection = pfd::open_file (" Select a file" , " ." , { " N64 Roms" , " *.z64" }).result ();
87- if (selection.empty ())
88- return false ;
76+ romData = std::vector<uint8_t >(std::istreambuf_iterator<char >(inFile), {});
77+ inFile.close ();
78+ }
79+
80+ this ->mGamePath = romPath;
81+ this ->mGameData = std::move (romData);
82+
83+ return true ;
84+ }
85+
86+ bool GameExtractor::SelectGameFromUI () {
87+ // // Store both path and already-read data
88+ std::string romPath;
89+ std::vector<uint8_t > romData;
8990
90- romPath = selection[0 ];
91+ #if !defined(__IOS__) && !defined(__ANDROID__) && !defined(__SWITCH__)
92+ // Desktop: fallback to file dialogue if no baserom found
93+ // if (!foundGame) {
94+ if (!pfd::settings::available ()) {
95+ SPDLOG_ERROR (" portable-file-dialogs is not available on this system." );
96+ return false ;
9197 }
98+
99+ auto selection = pfd::open_file (" Select a file" , " ." , { " N64 Roms" , " *.z64" }).result ();
100+ if (selection.empty ()) {
101+ return false ;
102+ }
103+
104+ romPath = selection[0 ];
105+ // }
92106#else
93107 // Mobile: fallback to baserom.us.z64
94- if (!foundGame && !std::filesystem::exists (Ship::Context::GetPathRelativeToAppDirectory (" baserom.us.z64" ))) {
108+ if (/* !foundGame && */ !std::filesystem::exists (Ship::Context::GetPathRelativeToAppDirectory (" baserom.us.z64" ))) {
95109 SPDLOG_ERROR (" baserom not found" );
96110 return false ;
97111 }
98112
99- if (!foundGame) {
100- romPath = Ship::Context::GetPathRelativeToAppDirectory (" baserom.us.z64" );
101- }
113+ // if (!foundGame) {
114+ romPath = Ship::Context::GetPathRelativeToAppDirectory (" baserom.us.z64" );
115+ // }
102116#endif
103117
104118 // Load file if it is not already open
@@ -109,8 +123,9 @@ bool GameExtractor::SelectGameFromUI() {
109123 }
110124
111125 std::ifstream inFile (romPath, std::ios::binary);
112- if (!inFile.is_open ())
126+ if (!inFile.is_open ()) {
113127 return false ;
128+ }
114129
115130 romData = std::vector<uint8_t >(std::istreambuf_iterator<char >(inFile), {});
116131 inFile.close ();
@@ -122,17 +137,23 @@ bool GameExtractor::SelectGameFromUI() {
122137 return true ;
123138}
124139
140+ void GameExtractor::SetSearchPath (const std::string& path) {
141+ mSearchPath = path;
142+ }
143+
125144void GameExtractor::GetRoms (std::vector<std::string>& roms) {
126145#ifdef _WIN32
127146 WIN32_FIND_DATAA ffd;
128- HANDLE h = FindFirstFileA (" .\\ *" , &ffd);
147+ std::string search = std::string (mSearchPath + " \\ *" );
148+ HANDLE h = FindFirstFileA (search.c_str (), &ffd);
129149
130150 do {
131151 if (!(ffd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY )) {
132152 char * ext = PathFindExtensionA (ffd.cFileName );
133153
134154 // Check for any standard N64 rom file extensions.
135- if ((strcmp (ext, " .z64" ) == 0 ))
155+ if (ext != NULL &&
156+ (strcmp (ext, " .z64" ) == 0 ) /* || (strcmp(ext, ".n64") == 0) || (strcmp(ext, ".v64") == 0)*/ )
136157 roms.push_back (ffd.cFileName );
137158 }
138159 } while (FindNextFileA (h, &ffd) != 0 );
@@ -141,37 +162,36 @@ void GameExtractor::GetRoms(std::vector<std::string>& roms) {
141162 // }
142163#elif unix
143164 // Open the directory of the app.
144- DIR * d = opendir (" . " );
165+ DIR * d = opendir (mSearchPath . c_str () );
145166 struct dirent * dir;
146167
147168 if (d != NULL ) {
148169 // Go through each file in the directory
149170 while ((dir = readdir (d)) != NULL ) {
150171 struct stat path;
151172
152- auto fullPath = std::filesystem::path (" ." ) / dir->d_name ;
153- auto fullPathString = fullPath.string ();
154- const char * fullPathCStr = fullPathString.c_str ();
155-
156173 // Check if current entry is not folder
157- stat (fullPathCStr , &path);
174+ stat (dir-> d_name , &path);
158175 if (S_ISREG (path.st_mode )) {
159176
160177 // Get the position of the extension character.
161178 char * ext = strrchr (dir->d_name , ' .' );
162- if (ext != NULL && (strcmp (ext, " .z64" ) == 0 )) {
163- roms.push_back (fullPathCStr);
179+ if (ext != NULL &&
180+ (strcmp (ext, " .z64" ) == 0 /* || strcmp(ext, ".n64") == 0 || strcmp(ext, ".v64") == 0*/ )) {
181+ roms.push_back (dir->d_name );
164182 }
165183 }
166184 }
167185 }
168186 closedir (d);
169187#else
170- for (const auto & file : std::filesystem::directory_iterator (" . " )) {
171- if (file.is_directory ())
188+ for (const auto & file : std::filesystem::directory_iterator (mSearchPath )) {
189+ if (file.is_directory ()) {
172190 continue ;
173- if (file.path ().extension () == " .z64" ) {
174- roms.push_back ((file.path ()));
191+ }
192+ if (/* (file.path().extension() == ".n64") || */ (file.path ().extension () == " .z64" )/* ||
193+ (file.path().extension() == ".v64")*/ ) {
194+ roms.push_back ((file.path ().generic_string ()));
175195 }
176196 }
177197#endif
@@ -200,14 +220,39 @@ void GameExtractor::WritePortVersion() {
200220 Companion::Instance->RegisterCompanionFile (" portVersion" , writer.ToVector ());
201221}
202222
203- bool GameExtractor::GenerateOTR () {
223+ std::string GameExtractor::GetRomPath () {
224+ return mGamePath .generic_string ();
225+ }
226+
227+ bool GameExtractor::Parse (std::atomic_ref<size_t > totalAssets, std::string appShortName) {
228+ const std::string assets_path = Ship::Context::GetAppBundlePath ();
229+ const std::string game_path = Ship::Context::GetAppDirectoryPath (appShortName);
230+
231+ Companion::Instance = new Companion (this ->mGameData , ArchiveType::O2R , false , assets_path, game_path);
232+ Companion::Instance->SetProcess (false );
233+ try {
234+ Companion::Instance->Init (ExportType::Binary, std::atomic_ref<size_t >(totalAssets));
235+ } catch (const std::exception& e) {
236+ SPDLOG_INFO (" Failed to process O2R {}" , e.what ());
237+ return false ;
238+ }
239+
240+ return true ;
241+ }
242+
243+ bool GameExtractor::GenerateOTR (std::string appShortName) {
244+ size_t assetCount = 0 ;
245+ return GenerateOTR (std::atomic_ref<size_t >(assetCount));
246+ }
247+
248+ bool GameExtractor::GenerateOTR (std::atomic_ref<size_t > assetCount, std::string appShortName) {
204249 const std::string assets_path = Ship::Context::GetAppBundlePath ();
205- const std::string game_path = Ship::Context::GetAppDirectoryPath ();
250+ const std::string game_path = Ship::Context::GetAppDirectoryPath (appShortName );
206251
207252 Companion::Instance = new Companion (this ->mGameData , ArchiveType::O2R , false , assets_path, game_path);
208253 this ->WritePortVersion ();
209254 try {
210- Companion::Instance->Init (ExportType::Binary);
255+ Companion::Instance->Init (ExportType::Binary, std::atomic_ref< size_t >(assetCount) );
211256 } catch (const std::exception& e) {
212257 SPDLOG_INFO (" Failed to process O2R {}" , e.what ());
213258 return false ;
0 commit comments