Skip to content

Commit f5104eb

Browse files
committed
multiple file extensions wip
1 parent d788e9f commit f5104eb

6 files changed

Lines changed: 72 additions & 52 deletions

File tree

source/funkin/backend/assets/Paths.hx

Lines changed: 53 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import flixel.graphics.frames.FlxFramesCollection;
66
import funkin.backend.assets.ModsFolder;
77
import funkin.backend.scripting.Script;
88
import haxe.io.Path;
9+
import flixel.util.typeLimit.OneOfTwo;
910
import lime.utils.AssetLibrary;
1011
import openfl.utils.Assets as OpenFlAssets;
1112
import animate.FlxAnimateFrames;
@@ -24,8 +25,29 @@ class Paths
2425
});
2526
}
2627

27-
public static inline function getPath(file:String, ?library:String) {
28+
public static inline function getPath(file:String, ?library:String, ?exts:OneOfTwo<String, Array<String>>) {
2829
var returnedPath:String = library != null ? '$library:assets/$library/$file' : 'assets/$file';
30+
31+
// ext path search
32+
if (exts != null) {
33+
var sanitizedPath = Path.withoutExtension(returnedPath);
34+
if (Std.isOfType(exts, String))
35+
returnedPath = returnedPath + '.${cast(exts, String)}';
36+
else {
37+
var extArray:Array<String> = cast exts;
38+
for (extension in extArray) {
39+
var extPath:String = sanitizedPath + '.$extension';
40+
if (OpenFlAssets.exists(extPath)) {
41+
trace(extPath, OpenFlAssets.exists(extPath));
42+
returnedPath = extPath;
43+
break;
44+
}
45+
}
46+
if (returnedPath == sanitizedPath) returnedPath = returnedPath + extArray[0];
47+
}
48+
}
49+
50+
// unix path search
2951
#if (sys && !windows)
3052
returnedPath = Path.normalize(returnedPath);
3153
if (OpenFlAssets.exists(returnedPath)) return returnedPath;
@@ -45,11 +67,12 @@ class Paths
4567
}
4668
if (returnedPath.toLowerCase() == fixedPath.toLowerCase()) returnedPath = fixedPath;
4769
#end
70+
4871
return returnedPath;
4972
}
5073

51-
public static inline function video(key:String, ?ext:String)
52-
return getPath('videos/$key.${ext != null ? ext : Flags.VIDEO_EXT}');
74+
public static inline function video(key:String, ?ext:OneOfTwo<String, Array<String>>)
75+
return getPath('videos/$key', null, ext != null ? ext : Flags.VIDEO_EXT);
5376

5477
public static inline function ndll(key:String)
5578
return getPath('ndlls/$key.ndll');
@@ -81,38 +104,35 @@ class Paths
81104
public static inline function ps1(key:String, ?library:String)
82105
return getPath('data/$key.ps1', library);
83106

84-
static public function sound(key:String, ?library:String, ?ext:String)
85-
return getPath('sounds/$key.${ext != null ? ext : Flags.SOUND_EXT}', library);
107+
static public function sound(key:String, ?library:String, ?ext:OneOfTwo<String, Array<String>>)
108+
return getPath('sounds/$key', library, ext != null ? ext : Flags.SOUND_EXT);
86109

87110
public static inline function soundRandom(key:String, min:Int, max:Int, ?library:String)
88111
return sound(key + FlxG.random.int(min, max), library);
89112

90-
inline static public function music(key:String, ?library:String, ?ext:String)
91-
return getPath('music/$key.${ext != null ? ext : Flags.SOUND_EXT}', library);
113+
inline static public function music(key:String, ?library:String, ?ext:OneOfTwo<String, Array<String>>)
114+
return getPath('music/$key', library, ext != null ? ext : Flags.SOUND_EXT);
92115

93-
inline static public function voices(song:String, ?difficulty:String, ?suffix:String = "", ?ext:String) {
116+
inline static public function voices(song:String, ?difficulty:String, ?suffix:String = "", ?ext:OneOfTwo<String, Array<String>>) {
94117
if (difficulty == null) difficulty = Flags.DEFAULT_DIFFICULTY;
95-
if (ext == null) ext = Flags.SOUND_EXT;
96-
var diff = getPath('songs/$song/song/Voices$suffix-${difficulty}.${ext}', null);
97-
return OpenFlAssets.exists(diff) ? diff : getPath('songs/$song/song/Voices$suffix.${ext}', null);
118+
var diff = getPath('songs/$song/song/Voices$suffix-${difficulty}', null, ext != null ? ext : Flags.SOUND_EXT);
119+
return OpenFlAssets.exists(diff) ? diff : getPath('songs/$song/song/Voices$suffix', null, ext != null ? ext : Flags.SOUND_EXT);
98120
}
99121

100-
inline static public function inst(song:String, ?difficulty:String, ?suffix:String = "", ?ext:String) {
122+
inline static public function inst(song:String, ?difficulty:String, ?suffix:String = "", ?ext:OneOfTwo<String, Array<String>>) {
101123
if (difficulty == null) difficulty = Flags.DEFAULT_DIFFICULTY;
102-
if (ext == null) ext = Flags.SOUND_EXT;
103-
var diff = getPath('songs/$song/song/Inst$suffix-${difficulty}.${ext}', null);
104-
return OpenFlAssets.exists(diff) ? diff : getPath('songs/$song/song/Inst$suffix.${ext}', null);
124+
var diff = getPath('songs/$song/song/Inst$suffix-${difficulty}', null, ext != null ? ext : Flags.SOUND_EXT);
125+
return OpenFlAssets.exists(diff) ? diff : getPath('songs/$song/song/Inst$suffix', null, ext != null ? ext : Flags.SOUND_EXT);
105126
}
106127

107-
static public function image(key:String, ?library:String, checkForAtlas:Bool = false, ?ext:String) {
108-
if (ext == null) ext = Flags.IMAGE_EXT;
128+
static public function image(key:String, ?library:String, checkForAtlas:Bool = false, ?ext:OneOfTwo<String, Array<String>>) {
109129
if (checkForAtlas) {
110-
var atlasPath = getPath('images/$key/spritemap.$ext', library);
111-
var multiplePath = getPath('images/$key/1.$ext', library);
130+
var atlasPath = getPath('images/$key/spritemap', library, ext != null ? ext : Flags.IMAGE_EXT);
131+
var multiplePath = getPath('images/$key/1', library, ext != null ? ext : Flags.IMAGE_EXT);
112132
if (atlasPath != null && OpenFlAssets.exists(atlasPath)) return atlasPath.substr(0, atlasPath.length - 14);
113133
if (multiplePath != null && OpenFlAssets.exists(multiplePath)) return multiplePath.substr(0, multiplePath.length - 6);
114134
}
115-
return getPath('images/$key.$ext', library);
135+
return getPath('images/$key', library, ext != null ? ext : Flags.IMAGE_EXT);
116136
}
117137

118138
public static inline function script(key:String, ?library:String, isAssetsPath:Bool = false) {
@@ -172,25 +192,25 @@ class Paths
172192
return getPath('models/$key.awd');
173193
}
174194

175-
inline static public function getSparrowAtlas(key:String, ?library:String, ?ext:String)
195+
inline static public function getSparrowAtlas(key:String, ?library:String, ?ext:OneOfTwo<String, Array<String>>)
176196
return FlxAtlasFrames.fromSparrow(image(key, library, ext), file('images/$key.xml', library));
177197

178198
inline static public function getAnimateAtlasAlt(key:String, ?settings:FlxAnimateSettings)
179199
return FlxAnimateFrames.fromAnimate(key, null, null, null, false, settings);
180200

181-
inline static public function getSparrowAtlasAlt(key:String, ?ext:String)
201+
inline static public function getSparrowAtlasAlt(key:String, ?ext:OneOfTwo<String, Array<String>>)
182202
return FlxAtlasFrames.fromSparrow('$key.${ext != null ? ext : Flags.IMAGE_EXT}', '$key.xml');
183203

184-
inline static public function getPackerAtlas(key:String, ?library:String, ?ext:String)
204+
inline static public function getPackerAtlas(key:String, ?library:String, ?ext:OneOfTwo<String, Array<String>>)
185205
return FlxAtlasFrames.fromSpriteSheetPacker(image(key, library, ext), file('images/$key.txt', library));
186206

187-
inline static public function getPackerAtlasAlt(key:String, ?ext:String)
207+
inline static public function getPackerAtlasAlt(key:String, ?ext:OneOfTwo<String, Array<String>>)
188208
return FlxAtlasFrames.fromSpriteSheetPacker('$key.${ext != null ? ext : Flags.IMAGE_EXT}', '$key.txt');
189209

190-
inline static public function getAsepriteAtlas(key:String, ?library:String, ?ext:String)
210+
inline static public function getAsepriteAtlas(key:String, ?library:String, ?ext:OneOfTwo<String, Array<String>>)
191211
return FlxAtlasFrames.fromAseprite(image(key, library, ext), file('images/$key.json', library));
192212

193-
inline static public function getAsepriteAtlasAlt(key:String, ?ext:String)
213+
inline static public function getAsepriteAtlasAlt(key:String, ?ext:OneOfTwo<String, Array<String>>)
194214
return FlxAtlasFrames.fromAseprite('$key.${ext != null ? ext : Flags.IMAGE_EXT}', '$key.json');
195215

196216
static public function getAssetsRoot():String {
@@ -203,15 +223,15 @@ class Paths
203223
* @param key Path to the frames
204224
* @param library (Additional) library to load the frames from.
205225
*/
206-
public static function getFrames(key:String, assetsPath:Bool = false, ?library:String, ?ext:String = null, ?animateSettings:FlxAnimateSettings) {
226+
public static function getFrames(key:String, assetsPath:Bool = false, ?library:String, ?ext:OneOfTwo<String, Array<String>> = null, ?animateSettings:FlxAnimateSettings) {
207227
if (tempFramesCache.exists(key)) {
208228
var frames = tempFramesCache[key];
209229
if (frames != null && frames.parent != null && frames.parent.bitmap != null && frames.parent.bitmap.readable)
210230
return frames;
211231
else
212232
tempFramesCache.remove(key);
213233
}
214-
return tempFramesCache[key] = loadFrames(assetsPath ? key : Paths.image(key, library, true, ext), false, null, false, ext, animateSettings);
234+
return tempFramesCache[key] = loadFrames(assetsPath ? key : Paths.image(key, library, true, ext), false, null, false, animateSettings);
215235
}
216236

217237
/**
@@ -246,17 +266,17 @@ class Paths
246266
* @param ext (Additional) Extension of the images.
247267
* @return FlxFramesCollection Frames
248268
*/
249-
public static function getMultiFrames(sheets:Array<String>, ?unique:Bool = true, ?key:String = null, ?ext:String = null, ?animateSettings:FlxAnimateSettings):FlxFramesCollection {
269+
public static function getMultiFrames(sheets:Array<String>, ?unique:Bool = true, ?key:String = null, ?ext:OneOfTwo<String, Array<String>> = null, ?animateSettings:FlxAnimateSettings):FlxFramesCollection {
250270
// TODO: cache properly
251-
if (sheets.length == 1) return loadFrames(sheets[0], unique, key, false, false, ext, animateSettings);
271+
if (sheets.length == 1) return loadFrames(sheets[0], unique, key, false, false, animateSettings);
252272
if (key == null) key = 'combo/' + sheets.join(',');
253273
var graphic = FlxG.bitmap.add("flixel/images/logo/default.png", unique, key);
254274
var sprFrames:FlxAtlasFrames = new FlxAtlasFrames(graphic);
255275
try {
256276
for (x => path in sheets) {
257277
var noExt = haxe.io.Path.withoutExtension(Paths.image(path, null, true, ext));
258278
@:privateAccess
259-
var newFrames = cast Paths.loadFrames(noExt, true, key + '_$path', false, false, ext, animateSettings);
279+
var newFrames = cast Paths.loadFrames(noExt, true, key + '_$path', false, false, animateSettings);
260280
if (newFrames == null) {
261281
Logs.warn('There is no Bitmap asset for "$noExt". Skipping...');
262282
continue;
@@ -279,9 +299,9 @@ class Paths
279299
* @param Ext Extension of the image.
280300
* @return FlxFramesCollection Frames
281301
*/
282-
static function loadFrames(path:String, Unique:Bool = false, Key:String = null, SkipAtlasCheck:Bool = false, SkipMultiCheck:Bool = false, ?Ext:String = null, ?animateSettings:FlxAnimateSettings):FlxFramesCollection {
302+
static function loadFrames(path:String, Unique:Bool = false, Key:String = null, SkipAtlasCheck:Bool = false, SkipMultiCheck:Bool = false, ?animateSettings:FlxAnimateSettings):FlxFramesCollection {
283303
var noExt = Path.withoutExtension(path);
284-
var ext = Ext != null ? Ext : Flags.IMAGE_EXT;
304+
var ext = Path.extension(path);
285305

286306
if (!SkipMultiCheck && Assets.exists('$noExt/1.${ext}')) {
287307
// MULTIPLE SPRITESHEETS!!

source/funkin/backend/assets/ZipFolderLibrary.hx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ class ZipFolderLibrary extends AssetLibrary implements IModsAssetLibrary {
5555
}
5656

5757
public function precacheVideos() {
58-
_videoExtensions = [Flags.VIDEO_EXT];
58+
_videoExtensions = Flags.VIDEO_EXT;
5959

6060
videoCacheRemap = [];
6161
for (entry in zip.entries) {
@@ -70,7 +70,7 @@ class ZipFolderLibrary extends AssetLibrary implements IModsAssetLibrary {
7070
}
7171

7272
// Now we have supports for videos in ZIP!!
73-
public var _videoExtensions:Array<String> = [Flags.VIDEO_EXT];
73+
public var _videoExtensions:Array<String> = Flags.VIDEO_EXT;
7474
public var videoCacheRemap:Map<String, String> = [];
7575
public function getVideoRemap(originalPath:String):String {
7676
if (!_videoExtensions.contains(Path.extension(_parsedAsset))) return originalPath;

source/funkin/backend/system/Flags.hx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -65,9 +65,9 @@ class Flags {
6565
* Preferred sound extension for the game's audio files.
6666
* Currently is set to `mp3` for web targets, and `ogg` for other targets.
6767
*/
68-
public static var SOUND_EXT:String = #if web "mp3" #else "ogg" #end; // we also support wav
69-
public static var VIDEO_EXT:String = "mp4";
70-
public static var IMAGE_EXT:String = "png"; // we also support jpg
68+
public static var SOUND_EXT:Array<String> = ["ogg", "mp3", "flac", "wav"];
69+
public static var VIDEO_EXT:Array<String> = ["mp4", "webm"]; // is there any more?
70+
public static var IMAGE_EXT:Array<String> = ["png", "jpg", "jpeg"];
7171

7272
public static var DEFAULT_DISCORD_LOGO_KEY:String = "icon";
7373
public static var DEFAULT_DISCORD_CLIENT_ID:String = "1383853614589673472";

source/funkin/editors/charter/SongCreationScreen.hx

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -230,13 +230,13 @@ class SongCreationScreen extends UISubstateWindow {
230230
translate("songFileName"),
231231
[new FlxTextFormatMarkerPair(new FlxTextFormat(0xFFAD1212), "$")]);
232232

233-
importChartFile = new UIFileExplorer(importIdTextBox.x, importIdTextBox.y + importIdTextBox.height + 56, null, null, "fnfc", function (_, _) importIdTextBox.label.text = new haxe.io.Path(importChartFile.filePath).file);
233+
importChartFile = new UIFileExplorer(importIdTextBox.x, importIdTextBox.y + importIdTextBox.height + 56, null, null, ["fnfc"], function (_, _) importIdTextBox.label.text = new haxe.io.Path(importChartFile.filePath).file);
234234
importDataGroup.add(importChartFile);
235235
addLabelOn(importChartFile, "").applyMarkup(
236236
translate("songDataFile"),
237237
[new FlxTextFormatMarkerPair(new FlxTextFormat(0xFFAD1212), "$")]);
238238

239-
importMetaFile = new UIFileExplorer(importChartFile.x + 320 + 26, importChartFile.y, null, null, "json");
239+
importMetaFile = new UIFileExplorer(importChartFile.x + 320 + 26, importChartFile.y, null, null, ["json"]);
240240
importDataGroup.add(importMetaFile);
241241
addLabelOn(importMetaFile, "").applyMarkup(
242242
translate("songMetaFile"),
@@ -300,7 +300,7 @@ class SongCreationScreen extends UISubstateWindow {
300300
saveButton.selectable = #if TEST_BUILD true #else project ? true : (importInstExplorer.file != null) #end;
301301
} else if (curPage == 2) {
302302
importIdTextBox.selectable = !project;
303-
importChartFile.fileType = project ? "fnfc" : "json";
303+
importChartFile.fileType = project ? ["fnfc"] : ["json"];
304304
importMetaFile.selectable = name == translate("vslice");
305305
saveButton.selectable = importChartFile.file != null && (!importMetaFile.selectable || importMetaFile.file != null) && (!importIdTextBox.selectable || importIdTextBox.label.text.trim().length > 0);
306306
} else
@@ -452,7 +452,7 @@ class SongCreationScreen extends UISubstateWindow {
452452
var vslicechart:NewSwagSong = Json.parse(files.get('${songId}-chart.json'));
453453
var playData = vslicemeta.playData;
454454

455-
var meta:ChartMetaData = formatMeta({name: songId, needsVoices: files.get('Voices.${Flags.SOUND_EXT}') != null});
455+
var meta:ChartMetaData = formatMeta({name: songId, needsVoices: files.get('Voices.${Flags.SOUND_EXT[0]}') != null});
456456
var diffCharts:Array<ChartDataWithInfo> = [], events:Array<ChartEvent> = null;
457457
VSliceParser.parse(vslicemeta, vslicechart, meta, diffCharts, songId);
458458

@@ -461,10 +461,10 @@ class SongCreationScreen extends UISubstateWindow {
461461

462462
if (onSave != null) onSave({
463463
meta: meta,
464-
instBytes: files.get('Inst.${Flags.SOUND_EXT}'),
465-
voicesBytes: files.get('Voices.${Flags.SOUND_EXT}'), //it may exist
466-
playerVocals: files.get('Voices-${playData.characters.playerVocals != null ? playData.characters.playerVocals[0] : playData.characters.player}.${Flags.SOUND_EXT}'),
467-
oppVocals: files.get('Voices-${playData.characters.opponentVocals != null ? playData.characters.opponentVocals[0] : playData.characters.opponent}.${Flags.SOUND_EXT}'),
464+
instBytes: files.get('Inst.${Flags.SOUND_EXT[0]}'),
465+
voicesBytes: files.get('Voices.${Flags.SOUND_EXT[0]}'), //it may exist
466+
playerVocals: files.get('Voices-${playData.characters.playerVocals != null ? playData.characters.playerVocals[0] : playData.characters.player}.${Flags.SOUND_EXT[0]}'),
467+
oppVocals: files.get('Voices-${playData.characters.opponentVocals != null ? playData.characters.opponentVocals[0] : playData.characters.opponent}.${Flags.SOUND_EXT[0]}'),
468468
}, (songFolder:String) -> {
469469
#if sys
470470
for (diff in diffCharts) CoolUtil.safeSaveFile('$songFolder/${getChartSavePath(meta, diff.diffName)}', Json.stringify(diff.chart, Flags.JSON_PRETTY_PRINT));

source/funkin/editors/ui/UIFileExplorer.hx

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -19,23 +19,23 @@ class UIFileExplorer extends UISliceSprite {
1919

2020
public var uiElement:FlxSprite;
2121

22-
public var fileType:String = "txt";
22+
public var fileType:Array<String> = ["txt"];
2323

24-
public function new(x:Float, y:Float, ?w:Int, ?h:Int, fileType:String = "txt", ?onFile:(String, Bytes)->Void) {
24+
public function new(x:Float, y:Float, ?w:Int, ?h:Int, fileType:Array<String>, ?onFile:(String, Bytes)->Void) {
2525
super(x, y, (w != null ? w : 320), (h != null ? h : 58), 'editors/ui/inputbox');
26-
this.fileType = fileType;
26+
if (fileType != null) this.fileType = fileType;
2727

2828
if (onFile != null) this.onFile = onFile;
2929

3030
uploadButton = new UIButton(x + 8, y + 8, null, function () {
3131
#if lime_funkin
3232
FileDialog.openFile(FlxG.stage.window, "Open File", (fileNames:Array<String>, activeFilter:FileDialogFilter) -> {
3333
loadFile(fileNames[0]);
34-
}, this.fileType != null ? [new FileDialogFilter("Specified File Extension", this.fileType)] : null);
34+
}, this.fileType != null ? [new FileDialogFilter("Specified File Extension", this.fileType.join(";"))] : null);
3535
#else
3636
var fileDialog = new FileDialog();
3737
fileDialog.onSelect.add(loadFile);
38-
fileDialog.browse(OPEN, this.fileType);
38+
fileDialog.browse(OPEN, this.fileType[0]); // i dunno bro
3939
#end
4040
}, bWidth - 16, bHeight - 16);
4141
members.push(uploadButton);

source/funkin/editors/ui/UIImageExplorer.hx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ class UIImageExplorer extends UIFileExplorer {
3939
return TU.translate("uiImageExplorer." + id, args);
4040

4141
public function new(x:Float, y:Float, image:String, ?w:Int, ?h:Int, ?onFile:(String, Bytes)->Void, ?directory:String = "images") {
42-
super(x, y, w, h, "png;jpg", function (filePath, file) {
42+
super(x, y, w, h, Flags.IMAGE_EXT, function (filePath, file) {
4343
if (filePath != null && file != null) uploadImage(filePath, file);
4444
if (onFile != null) onFile(filePath, file);
4545
});

0 commit comments

Comments
 (0)